1/* 2 * BRIEF MODULE DESCRIPTION 3 * Driver for AMD Au1000 MIPS Processor, AC'97 Sound Port 4 * 5 * Copyright 2004 Cooper Street Innovations Inc. 6 * Author: Charles Eidsness <charles@cooper-street.com> 7 * 8 * This program is free software; you can redistribute it and/or modify it 9 * under the terms of the GNU General Public License as published by the 10 * Free Software Foundation; either version 2 of the License, or (at your 11 * option) any later version. 12 * 13 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED 14 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF 15 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN 16 * NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, 17 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT 18 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF 19 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON 20 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 21 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF 22 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 23 * 24 * You should have received a copy of the GNU General Public License along 25 * with this program; if not, write to the Free Software Foundation, Inc., 26 * 675 Mass Ave, Cambridge, MA 02139, USA. 27 * 28 * History: 29 * 30 * 2004-09-09 Charles Eidsness -- Original verion -- based on 31 * sa11xx-uda1341.c ALSA driver and the 32 * au1000.c OSS driver. 33 * 2004-09-09 Matt Porter -- Added support for ALSA 1.0.6 34 * 35 */ 36 37#include <linux/ioport.h> 38#include <linux/interrupt.h> 39#include <linux/init.h> 40#include <linux/platform_device.h> 41#include <linux/slab.h> 42#include <linux/module.h> 43#include <sound/core.h> 44#include <sound/initval.h> 45#include <sound/pcm.h> 46#include <sound/pcm_params.h> 47#include <sound/ac97_codec.h> 48#include <asm/mach-au1x00/au1000.h> 49#include <asm/mach-au1x00/au1000_dma.h> 50 51MODULE_AUTHOR("Charles Eidsness <charles@cooper-street.com>"); 52MODULE_DESCRIPTION("Au1000 AC'97 ALSA Driver"); 53MODULE_LICENSE("GPL"); 54MODULE_SUPPORTED_DEVICE("{{AMD,Au1000 AC'97}}"); 55 56#define PLAYBACK 0 57#define CAPTURE 1 58#define AC97_SLOT_3 0x01 59#define AC97_SLOT_4 0x02 60#define AC97_SLOT_6 0x08 61#define AC97_CMD_IRQ 31 62#define READ 0 63#define WRITE 1 64#define READ_WAIT 2 65#define RW_DONE 3 66 67struct au1000_period 68{ 69 u32 start; 70 u32 relative_end; /*realtive to start of buffer*/ 71 struct au1000_period * next; 72}; 73 74/*Au1000 AC97 Port Control Reisters*/ 75struct au1000_ac97_reg { 76 u32 volatile config; 77 u32 volatile status; 78 u32 volatile data; 79 u32 volatile cmd; 80 u32 volatile cntrl; 81}; 82 83struct audio_stream { 84 struct snd_pcm_substream *substream; 85 int dma; 86 spinlock_t dma_lock; 87 struct au1000_period * buffer; 88 unsigned int period_size; 89 unsigned int periods; 90}; 91 92struct snd_au1000 { 93 struct snd_card *card; 94 struct au1000_ac97_reg volatile *ac97_ioport; 95 96 struct resource *ac97_res_port; 97 spinlock_t ac97_lock; 98 struct snd_ac97 *ac97; 99 100 struct snd_pcm *pcm; 101 struct audio_stream *stream[2]; /* playback & capture */ 102 int dmaid[2]; /* tx(0)/rx(1) DMA ids */ 103}; 104 105/*--------------------------- Local Functions --------------------------------*/ 106static void 107au1000_set_ac97_xmit_slots(struct snd_au1000 *au1000, long xmit_slots) 108{ 109 u32 volatile ac97_config; 110 111 spin_lock(&au1000->ac97_lock); 112 ac97_config = au1000->ac97_ioport->config; 113 ac97_config = ac97_config & ~AC97C_XMIT_SLOTS_MASK; 114 ac97_config |= (xmit_slots << AC97C_XMIT_SLOTS_BIT); 115 au1000->ac97_ioport->config = ac97_config; 116 spin_unlock(&au1000->ac97_lock); 117} 118 119static void 120au1000_set_ac97_recv_slots(struct snd_au1000 *au1000, long recv_slots) 121{ 122 u32 volatile ac97_config; 123 124 spin_lock(&au1000->ac97_lock); 125 ac97_config = au1000->ac97_ioport->config; 126 ac97_config = ac97_config & ~AC97C_RECV_SLOTS_MASK; 127 ac97_config |= (recv_slots << AC97C_RECV_SLOTS_BIT); 128 au1000->ac97_ioport->config = ac97_config; 129 spin_unlock(&au1000->ac97_lock); 130} 131 132 133static void 134au1000_release_dma_link(struct audio_stream *stream) 135{ 136 struct au1000_period * pointer; 137 struct au1000_period * pointer_next; 138 139 stream->period_size = 0; 140 stream->periods = 0; 141 pointer = stream->buffer; 142 if (! pointer) 143 return; 144 do { 145 pointer_next = pointer->next; 146 kfree(pointer); 147 pointer = pointer_next; 148 } while (pointer != stream->buffer); 149 stream->buffer = NULL; 150} 151 152static int 153au1000_setup_dma_link(struct audio_stream *stream, unsigned int period_bytes, 154 unsigned int periods) 155{ 156 struct snd_pcm_substream *substream = stream->substream; 157 struct snd_pcm_runtime *runtime = substream->runtime; 158 struct au1000_period *pointer; 159 unsigned long dma_start; 160 int i; 161 162 dma_start = virt_to_phys(runtime->dma_area); 163 164 if (stream->period_size == period_bytes && 165 stream->periods == periods) 166 return 0; /* not changed */ 167 168 au1000_release_dma_link(stream); 169 170 stream->period_size = period_bytes; 171 stream->periods = periods; 172 173 stream->buffer = kmalloc(sizeof(struct au1000_period), GFP_KERNEL); 174 if (! stream->buffer) 175 return -ENOMEM; 176 pointer = stream->buffer; 177 for (i = 0; i < periods; i++) { 178 pointer->start = (u32)(dma_start + (i * period_bytes)); 179 pointer->relative_end = (u32) (((i+1) * period_bytes) - 0x1); 180 if (i < periods - 1) { 181 pointer->next = kmalloc(sizeof(struct au1000_period), GFP_KERNEL); 182 if (! pointer->next) { 183 au1000_release_dma_link(stream); 184 return -ENOMEM; 185 } 186 pointer = pointer->next; 187 } 188 } 189 pointer->next = stream->buffer; 190 return 0; 191} 192 193static void 194au1000_dma_stop(struct audio_stream *stream) 195{ 196 if (snd_BUG_ON(!stream->buffer)) 197 return; 198 disable_dma(stream->dma); 199} 200 201static void 202au1000_dma_start(struct audio_stream *stream) 203{ 204 if (snd_BUG_ON(!stream->buffer)) 205 return; 206 207 init_dma(stream->dma); 208 if (get_dma_active_buffer(stream->dma) == 0) { 209 clear_dma_done0(stream->dma); 210 set_dma_addr0(stream->dma, stream->buffer->start); 211 set_dma_count0(stream->dma, stream->period_size >> 1); 212 set_dma_addr1(stream->dma, stream->buffer->next->start); 213 set_dma_count1(stream->dma, stream->period_size >> 1); 214 } else { 215 clear_dma_done1(stream->dma); 216 set_dma_addr1(stream->dma, stream->buffer->start); 217 set_dma_count1(stream->dma, stream->period_size >> 1); 218 set_dma_addr0(stream->dma, stream->buffer->next->start); 219 set_dma_count0(stream->dma, stream->period_size >> 1); 220 } 221 enable_dma_buffers(stream->dma); 222 start_dma(stream->dma); 223} 224 225static irqreturn_t 226au1000_dma_interrupt(int irq, void *dev_id) 227{ 228 struct audio_stream *stream = (struct audio_stream *) dev_id; 229 struct snd_pcm_substream *substream = stream->substream; 230 231 spin_lock(&stream->dma_lock); 232 switch (get_dma_buffer_done(stream->dma)) { 233 case DMA_D0: 234 stream->buffer = stream->buffer->next; 235 clear_dma_done0(stream->dma); 236 set_dma_addr0(stream->dma, stream->buffer->next->start); 237 set_dma_count0(stream->dma, stream->period_size >> 1); 238 enable_dma_buffer0(stream->dma); 239 break; 240 case DMA_D1: 241 stream->buffer = stream->buffer->next; 242 clear_dma_done1(stream->dma); 243 set_dma_addr1(stream->dma, stream->buffer->next->start); 244 set_dma_count1(stream->dma, stream->period_size >> 1); 245 enable_dma_buffer1(stream->dma); 246 break; 247 case (DMA_D0 | DMA_D1): 248 printk(KERN_ERR "DMA %d missed interrupt.\n",stream->dma); 249 au1000_dma_stop(stream); 250 au1000_dma_start(stream); 251 break; 252 case (~DMA_D0 & ~DMA_D1): 253 printk(KERN_ERR "DMA %d empty irq.\n",stream->dma); 254 } 255 spin_unlock(&stream->dma_lock); 256 snd_pcm_period_elapsed(substream); 257 return IRQ_HANDLED; 258} 259 260/*-------------------------- PCM Audio Streams -------------------------------*/ 261 262static unsigned int rates[] = {8000, 11025, 16000, 22050}; 263static struct snd_pcm_hw_constraint_list hw_constraints_rates = { 264 .count = ARRAY_SIZE(rates), 265 .list = rates, 266 .mask = 0, 267}; 268 269static struct snd_pcm_hardware snd_au1000_hw = 270{ 271 .info = (SNDRV_PCM_INFO_INTERLEAVED | \ 272 SNDRV_PCM_INFO_MMAP | SNDRV_PCM_INFO_MMAP_VALID), 273 .formats = SNDRV_PCM_FMTBIT_S16_LE, 274 .rates = (SNDRV_PCM_RATE_8000 | SNDRV_PCM_RATE_11025 | 275 SNDRV_PCM_RATE_16000 | SNDRV_PCM_RATE_22050), 276 .rate_min = 8000, 277 .rate_max = 22050, 278 .channels_min = 1, 279 .channels_max = 2, 280 .buffer_bytes_max = 128*1024, 281 .period_bytes_min = 32, 282 .period_bytes_max = 16*1024, 283 .periods_min = 8, 284 .periods_max = 255, 285 .fifo_size = 16, 286}; 287 288static int 289snd_au1000_playback_open(struct snd_pcm_substream *substream) 290{ 291 struct snd_au1000 *au1000 = substream->pcm->private_data; 292 293 au1000->stream[PLAYBACK]->substream = substream; 294 au1000->stream[PLAYBACK]->buffer = NULL; 295 substream->private_data = au1000->stream[PLAYBACK]; 296 substream->runtime->hw = snd_au1000_hw; 297 return (snd_pcm_hw_constraint_list(substream->runtime, 0, 298 SNDRV_PCM_HW_PARAM_RATE, &hw_constraints_rates) < 0); 299} 300 301static int 302snd_au1000_capture_open(struct snd_pcm_substream *substream) 303{ 304 struct snd_au1000 *au1000 = substream->pcm->private_data; 305 306 au1000->stream[CAPTURE]->substream = substream; 307 au1000->stream[CAPTURE]->buffer = NULL; 308 substream->private_data = au1000->stream[CAPTURE]; 309 substream->runtime->hw = snd_au1000_hw; 310 return (snd_pcm_hw_constraint_list(substream->runtime, 0, 311 SNDRV_PCM_HW_PARAM_RATE, &hw_constraints_rates) < 0); 312} 313 314static int 315snd_au1000_playback_close(struct snd_pcm_substream *substream) 316{ 317 struct snd_au1000 *au1000 = substream->pcm->private_data; 318 319 au1000->stream[PLAYBACK]->substream = NULL; 320 return 0; 321} 322 323static int 324snd_au1000_capture_close(struct snd_pcm_substream *substream) 325{ 326 struct snd_au1000 *au1000 = substream->pcm->private_data; 327 328 au1000->stream[CAPTURE]->substream = NULL; 329 return 0; 330} 331 332static int 333snd_au1000_hw_params(struct snd_pcm_substream *substream, 334 struct snd_pcm_hw_params *hw_params) 335{ 336 struct audio_stream *stream = substream->private_data; 337 int err; 338 339 err = snd_pcm_lib_malloc_pages(substream, 340 params_buffer_bytes(hw_params)); 341 if (err < 0) 342 return err; 343 return au1000_setup_dma_link(stream, 344 params_period_bytes(hw_params), 345 params_periods(hw_params)); 346} 347 348static int 349snd_au1000_hw_free(struct snd_pcm_substream *substream) 350{ 351 struct audio_stream *stream = substream->private_data; 352 au1000_release_dma_link(stream); 353 return snd_pcm_lib_free_pages(substream); 354} 355 356static int 357snd_au1000_playback_prepare(struct snd_pcm_substream *substream) 358{ 359 struct snd_au1000 *au1000 = substream->pcm->private_data; 360 struct snd_pcm_runtime *runtime = substream->runtime; 361 362 if (runtime->channels == 1) 363 au1000_set_ac97_xmit_slots(au1000, AC97_SLOT_4); 364 else 365 au1000_set_ac97_xmit_slots(au1000, AC97_SLOT_3 | AC97_SLOT_4); 366 snd_ac97_set_rate(au1000->ac97, AC97_PCM_FRONT_DAC_RATE, runtime->rate); 367 return 0; 368} 369 370static int 371snd_au1000_capture_prepare(struct snd_pcm_substream *substream) 372{ 373 struct snd_au1000 *au1000 = substream->pcm->private_data; 374 struct snd_pcm_runtime *runtime = substream->runtime; 375 376 if (runtime->channels == 1) 377 au1000_set_ac97_recv_slots(au1000, AC97_SLOT_4); 378 else 379 au1000_set_ac97_recv_slots(au1000, AC97_SLOT_3 | AC97_SLOT_4); 380 snd_ac97_set_rate(au1000->ac97, AC97_PCM_LR_ADC_RATE, runtime->rate); 381 return 0; 382} 383 384static int 385snd_au1000_trigger(struct snd_pcm_substream *substream, int cmd) 386{ 387 struct audio_stream *stream = substream->private_data; 388 int err = 0; 389 390 spin_lock(&stream->dma_lock); 391 switch (cmd) { 392 case SNDRV_PCM_TRIGGER_START: 393 au1000_dma_start(stream); 394 break; 395 case SNDRV_PCM_TRIGGER_STOP: 396 au1000_dma_stop(stream); 397 break; 398 default: 399 err = -EINVAL; 400 break; 401 } 402 spin_unlock(&stream->dma_lock); 403 return err; 404} 405 406static snd_pcm_uframes_t 407snd_au1000_pointer(struct snd_pcm_substream *substream) 408{ 409 struct audio_stream *stream = substream->private_data; 410 struct snd_pcm_runtime *runtime = substream->runtime; 411 long location; 412 413 spin_lock(&stream->dma_lock); 414 location = get_dma_residue(stream->dma); 415 spin_unlock(&stream->dma_lock); 416 location = stream->buffer->relative_end - location; 417 if (location == -1) 418 location = 0; 419 return bytes_to_frames(runtime,location); 420} 421 422static struct snd_pcm_ops snd_card_au1000_playback_ops = { 423 .open = snd_au1000_playback_open, 424 .close = snd_au1000_playback_close, 425 .ioctl = snd_pcm_lib_ioctl, 426 .hw_params = snd_au1000_hw_params, 427 .hw_free = snd_au1000_hw_free, 428 .prepare = snd_au1000_playback_prepare, 429 .trigger = snd_au1000_trigger, 430 .pointer = snd_au1000_pointer, 431}; 432 433static struct snd_pcm_ops snd_card_au1000_capture_ops = { 434 .open = snd_au1000_capture_open, 435 .close = snd_au1000_capture_close, 436 .ioctl = snd_pcm_lib_ioctl, 437 .hw_params = snd_au1000_hw_params, 438 .hw_free = snd_au1000_hw_free, 439 .prepare = snd_au1000_capture_prepare, 440 .trigger = snd_au1000_trigger, 441 .pointer = snd_au1000_pointer, 442}; 443 444static int 445snd_au1000_pcm_new(struct snd_au1000 *au1000) 446{ 447 struct snd_pcm *pcm; 448 int err; 449 unsigned long flags; 450 451 if ((err = snd_pcm_new(au1000->card, "AU1000 AC97 PCM", 0, 1, 1, &pcm)) < 0) 452 return err; 453 454 snd_pcm_lib_preallocate_pages_for_all(pcm, SNDRV_DMA_TYPE_CONTINUOUS, 455 snd_dma_continuous_data(GFP_KERNEL), 128*1024, 128*1024); 456 457 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_PLAYBACK, 458 &snd_card_au1000_playback_ops); 459 snd_pcm_set_ops(pcm, SNDRV_PCM_STREAM_CAPTURE, 460 &snd_card_au1000_capture_ops); 461 462 pcm->private_data = au1000; 463 pcm->info_flags = 0; 464 strcpy(pcm->name, "Au1000 AC97 PCM"); 465 466 spin_lock_init(&au1000->stream[PLAYBACK]->dma_lock); 467 spin_lock_init(&au1000->stream[CAPTURE]->dma_lock); 468 469 flags = claim_dma_lock(); 470 au1000->stream[PLAYBACK]->dma = request_au1000_dma(au1000->dmaid[0], 471 "AC97 TX", au1000_dma_interrupt, 0, 472 au1000->stream[PLAYBACK]); 473 if (au1000->stream[PLAYBACK]->dma < 0) { 474 release_dma_lock(flags); 475 return -EBUSY; 476 } 477 au1000->stream[CAPTURE]->dma = request_au1000_dma(au1000->dmaid[1], 478 "AC97 RX", au1000_dma_interrupt, 0, 479 au1000->stream[CAPTURE]); 480 if (au1000->stream[CAPTURE]->dma < 0){ 481 release_dma_lock(flags); 482 return -EBUSY; 483 } 484 /* enable DMA coherency in read/write DMA channels */ 485 set_dma_mode(au1000->stream[PLAYBACK]->dma, 486 get_dma_mode(au1000->stream[PLAYBACK]->dma) & ~DMA_NC); 487 set_dma_mode(au1000->stream[CAPTURE]->dma, 488 get_dma_mode(au1000->stream[CAPTURE]->dma) & ~DMA_NC); 489 release_dma_lock(flags); 490 au1000->pcm = pcm; 491 return 0; 492} 493 494 495/*-------------------------- AC97 CODEC Control ------------------------------*/ 496 497static unsigned short 498snd_au1000_ac97_read(struct snd_ac97 *ac97, unsigned short reg) 499{ 500 struct snd_au1000 *au1000 = ac97->private_data; 501 u32 volatile cmd; 502 u16 volatile data; 503 int i; 504 505 spin_lock(&au1000->ac97_lock); 506/* would rather use the interrupt than this polling but it works and I can't 507get the interrupt driven case to work efficiently */ 508 for (i = 0; i < 0x5000; i++) 509 if (!(au1000->ac97_ioport->status & AC97C_CP)) 510 break; 511 if (i == 0x5000) 512 printk(KERN_ERR "au1000 AC97: AC97 command read timeout\n"); 513 514 cmd = (u32) reg & AC97C_INDEX_MASK; 515 cmd |= AC97C_READ; 516 au1000->ac97_ioport->cmd = cmd; 517 518 /* now wait for the data */ 519 for (i = 0; i < 0x5000; i++) 520 if (!(au1000->ac97_ioport->status & AC97C_CP)) 521 break; 522 if (i == 0x5000) { 523 printk(KERN_ERR "au1000 AC97: AC97 command read timeout\n"); 524 spin_unlock(&au1000->ac97_lock); 525 return 0; 526 } 527 528 data = au1000->ac97_ioport->cmd & 0xffff; 529 spin_unlock(&au1000->ac97_lock); 530 531 return data; 532 533} 534 535 536static void 537snd_au1000_ac97_write(struct snd_ac97 *ac97, unsigned short reg, unsigned short val) 538{ 539 struct snd_au1000 *au1000 = ac97->private_data; 540 u32 cmd; 541 int i; 542 543 spin_lock(&au1000->ac97_lock); 544/* would rather use the interrupt than this polling but it works and I can't 545get the interrupt driven case to work efficiently */ 546 for (i = 0; i < 0x5000; i++) 547 if (!(au1000->ac97_ioport->status & AC97C_CP)) 548 break; 549 if (i == 0x5000) 550 printk(KERN_ERR "au1000 AC97: AC97 command write timeout\n"); 551 552 cmd = (u32) reg & AC97C_INDEX_MASK; 553 cmd &= ~AC97C_READ; 554 cmd |= ((u32) val << AC97C_WD_BIT); 555 au1000->ac97_ioport->cmd = cmd; 556 spin_unlock(&au1000->ac97_lock); 557} 558 559/*------------------------------ Setup / Destroy ----------------------------*/ 560 561static void snd_au1000_free(struct snd_card *card) 562{ 563 struct snd_au1000 *au1000 = card->private_data; 564 565 if (au1000->stream[PLAYBACK]) { 566 if (au1000->stream[PLAYBACK]->dma >= 0) 567 free_au1000_dma(au1000->stream[PLAYBACK]->dma); 568 kfree(au1000->stream[PLAYBACK]); 569 } 570 571 if (au1000->stream[CAPTURE]) { 572 if (au1000->stream[CAPTURE]->dma >= 0) 573 free_au1000_dma(au1000->stream[CAPTURE]->dma); 574 kfree(au1000->stream[CAPTURE]); 575 } 576 577 if (au1000->ac97_res_port) { 578 /* put internal AC97 block into reset */ 579 if (au1000->ac97_ioport) { 580 au1000->ac97_ioport->cntrl = AC97C_RS; 581 iounmap(au1000->ac97_ioport); 582 au1000->ac97_ioport = NULL; 583 } 584 release_and_free_resource(au1000->ac97_res_port); 585 au1000->ac97_res_port = NULL; 586 } 587} 588 589static struct snd_ac97_bus_ops ops = { 590 .write = snd_au1000_ac97_write, 591 .read = snd_au1000_ac97_read, 592}; 593 594static int au1000_ac97_probe(struct platform_device *pdev) 595{ 596 int err; 597 void __iomem *io; 598 struct resource *r; 599 struct snd_card *card; 600 struct snd_au1000 *au1000; 601 struct snd_ac97_bus *pbus; 602 struct snd_ac97_template ac97; 603 604 err = snd_card_new(&pdev->dev, -1, "AC97", THIS_MODULE, 605 sizeof(struct snd_au1000), &card); 606 if (err < 0) 607 return err; 608 609 au1000 = card->private_data; 610 au1000->card = card; 611 spin_lock_init(&au1000->ac97_lock); 612 613 /* from here on let ALSA call the special freeing function */ 614 card->private_free = snd_au1000_free; 615 616 /* TX DMA ID */ 617 r = platform_get_resource(pdev, IORESOURCE_DMA, 0); 618 if (!r) { 619 err = -ENODEV; 620 snd_printk(KERN_INFO "no TX DMA platform resource!\n"); 621 goto out; 622 } 623 au1000->dmaid[0] = r->start; 624 625 /* RX DMA ID */ 626 r = platform_get_resource(pdev, IORESOURCE_DMA, 1); 627 if (!r) { 628 err = -ENODEV; 629 snd_printk(KERN_INFO "no RX DMA platform resource!\n"); 630 goto out; 631 } 632 au1000->dmaid[1] = r->start; 633 634 au1000->stream[PLAYBACK] = kmalloc(sizeof(struct audio_stream), 635 GFP_KERNEL); 636 if (!au1000->stream[PLAYBACK]) { 637 err = -ENOMEM; 638 goto out; 639 } 640 au1000->stream[PLAYBACK]->dma = -1; 641 642 au1000->stream[CAPTURE] = kmalloc(sizeof(struct audio_stream), 643 GFP_KERNEL); 644 if (!au1000->stream[CAPTURE]) { 645 err = -ENOMEM; 646 goto out; 647 } 648 au1000->stream[CAPTURE]->dma = -1; 649 650 r = platform_get_resource(pdev, IORESOURCE_MEM, 0); 651 if (!r) { 652 err = -ENODEV; 653 goto out; 654 } 655 656 err = -EBUSY; 657 au1000->ac97_res_port = request_mem_region(r->start, resource_size(r), 658 pdev->name); 659 if (!au1000->ac97_res_port) { 660 snd_printk(KERN_ERR "ALSA AC97: can't grab AC97 port\n"); 661 goto out; 662 } 663 664 io = ioremap(r->start, resource_size(r)); 665 if (!io) 666 goto out; 667 668 au1000->ac97_ioport = (struct au1000_ac97_reg *)io; 669 670 /* configure pins for AC'97 671 TODO: move to board_setup.c */ 672 au_writel(au_readl(SYS_PINFUNC) & ~0x02, SYS_PINFUNC); 673 674 /* Initialise Au1000's AC'97 Control Block */ 675 au1000->ac97_ioport->cntrl = AC97C_RS | AC97C_CE; 676 udelay(10); 677 au1000->ac97_ioport->cntrl = AC97C_CE; 678 udelay(10); 679 680 /* Initialise External CODEC -- cold reset */ 681 au1000->ac97_ioport->config = AC97C_RESET; 682 udelay(10); 683 au1000->ac97_ioport->config = 0x0; 684 mdelay(5); 685 686 /* Initialise AC97 middle-layer */ 687 err = snd_ac97_bus(au1000->card, 0, &ops, au1000, &pbus); 688 if (err < 0) 689 goto out; 690 691 memset(&ac97, 0, sizeof(ac97)); 692 ac97.private_data = au1000; 693 err = snd_ac97_mixer(pbus, &ac97, &au1000->ac97); 694 if (err < 0) 695 goto out; 696 697 err = snd_au1000_pcm_new(au1000); 698 if (err < 0) 699 goto out; 700 701 strcpy(card->driver, "Au1000-AC97"); 702 strcpy(card->shortname, "AMD Au1000-AC97"); 703 sprintf(card->longname, "AMD Au1000--AC97 ALSA Driver"); 704 705 err = snd_card_register(card); 706 if (err < 0) 707 goto out; 708 709 printk(KERN_INFO "ALSA AC97: Driver Initialized\n"); 710 711 platform_set_drvdata(pdev, card); 712 713 return 0; 714 715 out: 716 snd_card_free(card); 717 return err; 718} 719 720static int au1000_ac97_remove(struct platform_device *pdev) 721{ 722 return snd_card_free(platform_get_drvdata(pdev)); 723} 724 725struct platform_driver au1000_ac97c_driver = { 726 .driver = { 727 .name = "au1000-ac97c", 728 .owner = THIS_MODULE, 729 }, 730 .probe = au1000_ac97_probe, 731 .remove = au1000_ac97_remove, 732}; 733 734module_platform_driver(au1000_ac97c_driver); 735