1 /*- 2 * SPDX-License-Identifier: BSD-2-Clause 3 * 4 * Copyright (c) 2012-2021 Ruslan Bukin <br@bsdpad.com> 5 * Copyright (c) 2023-2024 Florian Walpen <dev@submerge.ch> 6 * All rights reserved. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 18 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 20 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 21 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 22 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 23 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 24 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 25 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 26 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 27 * SUCH DAMAGE. 28 */ 29 30 /* 31 * RME HDSPe driver for FreeBSD (pcm-part). 32 * Supported cards: AIO, RayDAT. 33 */ 34 35 #include <dev/sound/pcm/sound.h> 36 #include <dev/sound/pci/hdspe.h> 37 #include <dev/sound/chip.h> 38 39 #include <dev/pci/pcireg.h> 40 #include <dev/pci/pcivar.h> 41 42 #include <mixer_if.h> 43 44 struct hdspe_latency { 45 uint32_t n; 46 uint32_t period; 47 float ms; 48 }; 49 50 static struct hdspe_latency latency_map[] = { 51 { 7, 32, 0.7 }, 52 { 0, 64, 1.5 }, 53 { 1, 128, 3 }, 54 { 2, 256, 6 }, 55 { 3, 512, 12 }, 56 { 4, 1024, 23 }, 57 { 5, 2048, 46 }, 58 { 6, 4096, 93 }, 59 60 { 0, 0, 0 }, 61 }; 62 63 struct hdspe_rate { 64 uint32_t speed; 65 uint32_t reg; 66 }; 67 68 static struct hdspe_rate rate_map[] = { 69 { 32000, (HDSPE_FREQ_32000) }, 70 { 44100, (HDSPE_FREQ_44100) }, 71 { 48000, (HDSPE_FREQ_48000) }, 72 { 64000, (HDSPE_FREQ_32000 | HDSPE_FREQ_DOUBLE) }, 73 { 88200, (HDSPE_FREQ_44100 | HDSPE_FREQ_DOUBLE) }, 74 { 96000, (HDSPE_FREQ_48000 | HDSPE_FREQ_DOUBLE) }, 75 { 128000, (HDSPE_FREQ_32000 | HDSPE_FREQ_QUAD) }, 76 { 176400, (HDSPE_FREQ_44100 | HDSPE_FREQ_QUAD) }, 77 { 192000, (HDSPE_FREQ_48000 | HDSPE_FREQ_QUAD) }, 78 79 { 0, 0 }, 80 }; 81 82 static uint32_t 83 hdspe_channel_play_ports(struct hdspe_channel *hc) 84 { 85 return (hc->ports & (HDSPE_CHAN_AIO_ALL | HDSPE_CHAN_RAY_ALL)); 86 } 87 88 static uint32_t 89 hdspe_channel_rec_ports(struct hdspe_channel *hc) 90 { 91 return (hc->ports & (HDSPE_CHAN_AIO_ALL_REC | HDSPE_CHAN_RAY_ALL)); 92 } 93 94 static unsigned int 95 hdspe_adat_width(uint32_t speed) 96 { 97 if (speed > 96000) 98 return (2); 99 if (speed > 48000) 100 return (4); 101 return (8); 102 } 103 104 static uint32_t 105 hdspe_port_first(uint32_t ports) 106 { 107 return (ports & (~(ports - 1))); /* Extract first bit set. */ 108 } 109 110 static uint32_t 111 hdspe_port_first_row(uint32_t ports) 112 { 113 uint32_t ends; 114 115 /* Restrict ports to one set with contiguous slots. */ 116 if (ports & HDSPE_CHAN_AIO_LINE) 117 ports = HDSPE_CHAN_AIO_LINE; /* Gap in the AIO slots here. */ 118 else if (ports & HDSPE_CHAN_AIO_ALL) 119 ports &= HDSPE_CHAN_AIO_ALL; /* Rest of the AIO slots. */ 120 else if (ports & HDSPE_CHAN_RAY_ALL) 121 ports &= HDSPE_CHAN_RAY_ALL; /* All RayDAT slots. */ 122 123 /* Ends of port rows are followed by a port which is not in the set. */ 124 ends = ports & (~(ports >> 1)); 125 /* First row of contiguous ports ends in the first row end. */ 126 return (ports & (ends ^ (ends - 1))); 127 } 128 129 static unsigned int 130 hdspe_channel_count(uint32_t ports, uint32_t adat_width) 131 { 132 unsigned int count = 0; 133 134 if (ports & HDSPE_CHAN_AIO_ALL) { 135 /* AIO ports. */ 136 if (ports & HDSPE_CHAN_AIO_LINE) 137 count += 2; 138 if (ports & HDSPE_CHAN_AIO_PHONE) 139 count += 2; 140 if (ports & HDSPE_CHAN_AIO_AES) 141 count += 2; 142 if (ports & HDSPE_CHAN_AIO_SPDIF) 143 count += 2; 144 if (ports & HDSPE_CHAN_AIO_ADAT) 145 count += adat_width; 146 } else if (ports & HDSPE_CHAN_RAY_ALL) { 147 /* RayDAT ports. */ 148 if (ports & HDSPE_CHAN_RAY_AES) 149 count += 2; 150 if (ports & HDSPE_CHAN_RAY_SPDIF) 151 count += 2; 152 if (ports & HDSPE_CHAN_RAY_ADAT1) 153 count += adat_width; 154 if (ports & HDSPE_CHAN_RAY_ADAT2) 155 count += adat_width; 156 if (ports & HDSPE_CHAN_RAY_ADAT3) 157 count += adat_width; 158 if (ports & HDSPE_CHAN_RAY_ADAT4) 159 count += adat_width; 160 } 161 162 return (count); 163 } 164 165 static unsigned int 166 hdspe_channel_offset(uint32_t subset, uint32_t ports, unsigned int adat_width) 167 { 168 uint32_t preceding; 169 170 /* Make sure we have a subset of ports. */ 171 subset &= ports; 172 /* Include all ports preceding the first one of the subset. */ 173 preceding = ports & (~subset & (subset - 1)); 174 175 if (preceding & HDSPE_CHAN_AIO_ALL) 176 preceding &= HDSPE_CHAN_AIO_ALL; /* Contiguous AIO slots. */ 177 else if (preceding & HDSPE_CHAN_RAY_ALL) 178 preceding &= HDSPE_CHAN_RAY_ALL; /* Contiguous RayDAT slots. */ 179 180 return (hdspe_channel_count(preceding, adat_width)); 181 } 182 183 static unsigned int 184 hdspe_port_slot_offset(uint32_t port, unsigned int adat_width) 185 { 186 /* Exctract the first port (lowest bit) if set of ports. */ 187 switch (hdspe_port_first(port)) { 188 /* AIO ports */ 189 case HDSPE_CHAN_AIO_LINE: 190 return (0); 191 case HDSPE_CHAN_AIO_PHONE: 192 return (6); 193 case HDSPE_CHAN_AIO_AES: 194 return (8); 195 case HDSPE_CHAN_AIO_SPDIF: 196 return (10); 197 case HDSPE_CHAN_AIO_ADAT: 198 return (12); 199 200 /* RayDAT ports */ 201 case HDSPE_CHAN_RAY_AES: 202 return (0); 203 case HDSPE_CHAN_RAY_SPDIF: 204 return (2); 205 case HDSPE_CHAN_RAY_ADAT1: 206 return (4); 207 case HDSPE_CHAN_RAY_ADAT2: 208 return (4 + adat_width); 209 case HDSPE_CHAN_RAY_ADAT3: 210 return (4 + 2 * adat_width); 211 case HDSPE_CHAN_RAY_ADAT4: 212 return (4 + 3 * adat_width); 213 default: 214 return (0); 215 } 216 } 217 218 static unsigned int 219 hdspe_port_slot_width(uint32_t ports, unsigned int adat_width) 220 { 221 uint32_t row; 222 223 /* Count number of contiguous slots from the first physical port. */ 224 row = hdspe_port_first_row(ports); 225 return (hdspe_channel_count(row, adat_width)); 226 } 227 228 static int 229 hdspe_hw_mixer(struct sc_chinfo *ch, unsigned int dst, 230 unsigned int src, unsigned short data) 231 { 232 struct sc_pcminfo *scp; 233 struct sc_info *sc; 234 int offs; 235 236 scp = ch->parent; 237 sc = scp->sc; 238 239 offs = 0; 240 if (ch->dir == PCMDIR_PLAY) 241 offs = 64; 242 243 hdspe_write_4(sc, HDSPE_MIXER_BASE + 244 ((offs + src + 128 * dst) * sizeof(uint32_t)), 245 data & 0xFFFF); 246 247 return (0); 248 }; 249 250 static int 251 hdspechan_setgain(struct sc_chinfo *ch) 252 { 253 struct sc_info *sc; 254 uint32_t port, ports; 255 unsigned int slot, end_slot; 256 unsigned short volume; 257 258 sc = ch->parent->sc; 259 260 /* Iterate through all physical ports of the channel. */ 261 ports = ch->ports; 262 port = hdspe_port_first(ports); 263 while (port != 0) { 264 /* Get slot range of the physical port. */ 265 slot = 266 hdspe_port_slot_offset(port, hdspe_adat_width(sc->speed)); 267 end_slot = slot + 268 hdspe_port_slot_width(port, hdspe_adat_width(sc->speed)); 269 270 /* Treat first slot as left channel. */ 271 volume = ch->lvol * HDSPE_MAX_GAIN / 100; 272 for (; slot < end_slot; slot++) { 273 hdspe_hw_mixer(ch, slot, slot, volume); 274 /* Subsequent slots all get the right channel volume. */ 275 volume = ch->rvol * HDSPE_MAX_GAIN / 100; 276 } 277 278 ports &= ~port; 279 port = hdspe_port_first(ports); 280 } 281 282 return (0); 283 } 284 285 static int 286 hdspemixer_init(struct snd_mixer *m) 287 { 288 struct sc_pcminfo *scp; 289 struct sc_info *sc; 290 int mask; 291 292 scp = mix_getdevinfo(m); 293 sc = scp->sc; 294 if (sc == NULL) 295 return (-1); 296 297 mask = SOUND_MASK_PCM; 298 299 if (hdspe_channel_play_ports(scp->hc)) 300 mask |= SOUND_MASK_VOLUME; 301 302 if (hdspe_channel_rec_ports(scp->hc)) 303 mask |= SOUND_MASK_RECLEV; 304 305 snd_mtxlock(sc->lock); 306 pcm_setflags(scp->dev, pcm_getflags(scp->dev) | SD_F_SOFTPCMVOL); 307 mix_setdevs(m, mask); 308 snd_mtxunlock(sc->lock); 309 310 return (0); 311 } 312 313 static int 314 hdspemixer_set(struct snd_mixer *m, unsigned dev, 315 unsigned left, unsigned right) 316 { 317 struct sc_pcminfo *scp; 318 struct sc_chinfo *ch; 319 int i; 320 321 scp = mix_getdevinfo(m); 322 323 #if 0 324 device_printf(scp->dev, "hdspemixer_set() %d %d\n", 325 left, right); 326 #endif 327 328 for (i = 0; i < scp->chnum; i++) { 329 ch = &scp->chan[i]; 330 if ((dev == SOUND_MIXER_VOLUME && ch->dir == PCMDIR_PLAY) || 331 (dev == SOUND_MIXER_RECLEV && ch->dir == PCMDIR_REC)) { 332 ch->lvol = left; 333 ch->rvol = right; 334 if (ch->run) 335 hdspechan_setgain(ch); 336 } 337 } 338 339 return (0); 340 } 341 342 static kobj_method_t hdspemixer_methods[] = { 343 KOBJMETHOD(mixer_init, hdspemixer_init), 344 KOBJMETHOD(mixer_set, hdspemixer_set), 345 KOBJMETHOD_END 346 }; 347 MIXER_DECLARE(hdspemixer); 348 349 static void 350 hdspechan_enable(struct sc_chinfo *ch, int value) 351 { 352 struct sc_pcminfo *scp; 353 struct sc_info *sc; 354 uint32_t row, ports; 355 int reg; 356 unsigned int slot, end_slot; 357 358 scp = ch->parent; 359 sc = scp->sc; 360 361 if (ch->dir == PCMDIR_PLAY) 362 reg = HDSPE_OUT_ENABLE_BASE; 363 else 364 reg = HDSPE_IN_ENABLE_BASE; 365 366 ch->run = value; 367 368 /* Iterate through rows of ports with contiguous slots. */ 369 ports = ch->ports; 370 row = hdspe_port_first_row(ports); 371 while (row != 0) { 372 slot = 373 hdspe_port_slot_offset(row, hdspe_adat_width(sc->speed)); 374 end_slot = slot + 375 hdspe_port_slot_width(row, hdspe_adat_width(sc->speed)); 376 377 for (; slot < end_slot; slot++) { 378 hdspe_write_1(sc, reg + (4 * slot), value); 379 } 380 381 ports &= ~row; 382 row = hdspe_port_first_row(ports); 383 } 384 } 385 386 static int 387 hdspe_running(struct sc_info *sc) 388 { 389 struct sc_pcminfo *scp; 390 struct sc_chinfo *ch; 391 device_t *devlist; 392 int devcount; 393 int i, j; 394 int err; 395 396 if ((err = device_get_children(sc->dev, &devlist, &devcount)) != 0) 397 goto bad; 398 399 for (i = 0; i < devcount; i++) { 400 scp = device_get_ivars(devlist[i]); 401 for (j = 0; j < scp->chnum; j++) { 402 ch = &scp->chan[j]; 403 if (ch->run) 404 goto bad; 405 } 406 } 407 408 free(devlist, M_TEMP); 409 410 return (0); 411 bad: 412 413 #if 0 414 device_printf(sc->dev, "hdspe is running\n"); 415 #endif 416 417 free(devlist, M_TEMP); 418 419 return (1); 420 } 421 422 static void 423 hdspe_start_audio(struct sc_info *sc) 424 { 425 426 sc->ctrl_register |= (HDSPE_AUDIO_INT_ENABLE | HDSPE_ENABLE); 427 hdspe_write_4(sc, HDSPE_CONTROL_REG, sc->ctrl_register); 428 } 429 430 static void 431 hdspe_stop_audio(struct sc_info *sc) 432 { 433 434 if (hdspe_running(sc) == 1) 435 return; 436 437 sc->ctrl_register &= ~(HDSPE_AUDIO_INT_ENABLE | HDSPE_ENABLE); 438 hdspe_write_4(sc, HDSPE_CONTROL_REG, sc->ctrl_register); 439 } 440 441 static void 442 buffer_mux_write(uint32_t *dma, uint32_t *pcm, unsigned int pos, 443 unsigned int samples, unsigned int slots, unsigned int channels) 444 { 445 int slot; 446 447 for (; samples > 0; samples--) { 448 for (slot = 0; slot < slots; slot++) { 449 dma[slot * HDSPE_CHANBUF_SAMPLES + pos] = 450 pcm[pos * channels + slot]; 451 } 452 pos = (pos + 1) % HDSPE_CHANBUF_SAMPLES; 453 } 454 } 455 456 static void 457 buffer_mux_port(uint32_t *dma, uint32_t *pcm, uint32_t subset, uint32_t ports, 458 unsigned int pos, unsigned int samples, unsigned int adat_width, 459 unsigned int pcm_width) 460 { 461 unsigned int slot_offset, slots; 462 unsigned int channels, chan_pos; 463 464 /* Translate DMA slot offset to DMA buffer offset. */ 465 slot_offset = hdspe_port_slot_offset(subset, adat_width); 466 dma += slot_offset * HDSPE_CHANBUF_SAMPLES; 467 468 /* Channel position of the port subset and total number of channels. */ 469 chan_pos = hdspe_channel_offset(subset, ports, pcm_width); 470 pcm += chan_pos; 471 channels = hdspe_channel_count(ports, pcm_width); 472 473 /* Only copy as much as supported by both hardware and pcm channel. */ 474 slots = hdspe_port_slot_width(subset, MIN(adat_width, pcm_width)); 475 476 /* Let the compiler inline and loop unroll common cases. */ 477 if (slots == 2) 478 buffer_mux_write(dma, pcm, pos, samples, 2, channels); 479 else if (slots == 4) 480 buffer_mux_write(dma, pcm, pos, samples, 4, channels); 481 else if (slots == 8) 482 buffer_mux_write(dma, pcm, pos, samples, 8, channels); 483 else 484 buffer_mux_write(dma, pcm, pos, samples, slots, channels); 485 } 486 487 static void 488 buffer_demux_read(uint32_t *dma, uint32_t *pcm, unsigned int pos, 489 unsigned int samples, unsigned int slots, unsigned int channels) 490 { 491 int slot; 492 493 for (; samples > 0; samples--) { 494 for (slot = 0; slot < slots; slot++) { 495 pcm[pos * channels + slot] = 496 dma[slot * HDSPE_CHANBUF_SAMPLES + pos]; 497 } 498 pos = (pos + 1) % HDSPE_CHANBUF_SAMPLES; 499 } 500 } 501 502 static void 503 buffer_demux_port(uint32_t *dma, uint32_t *pcm, uint32_t subset, uint32_t ports, 504 unsigned int pos, unsigned int samples, unsigned int adat_width, 505 unsigned int pcm_width) 506 { 507 unsigned int slot_offset, slots; 508 unsigned int channels, chan_pos; 509 510 /* Translate port slot offset to DMA buffer offset. */ 511 slot_offset = hdspe_port_slot_offset(subset, adat_width); 512 dma += slot_offset * HDSPE_CHANBUF_SAMPLES; 513 514 /* Channel position of the port subset and total number of channels. */ 515 chan_pos = hdspe_channel_offset(subset, ports, pcm_width); 516 pcm += chan_pos; 517 channels = hdspe_channel_count(ports, pcm_width); 518 519 /* Only copy as much as supported by both hardware and pcm channel. */ 520 slots = hdspe_port_slot_width(subset, MIN(adat_width, pcm_width)); 521 522 /* Let the compiler inline and loop unroll common cases. */ 523 if (slots == 2) 524 buffer_demux_read(dma, pcm, pos, samples, 2, channels); 525 else if (slots == 4) 526 buffer_demux_read(dma, pcm, pos, samples, 4, channels); 527 else if (slots == 8) 528 buffer_demux_read(dma, pcm, pos, samples, 8, channels); 529 else 530 buffer_demux_read(dma, pcm, pos, samples, slots, channels); 531 } 532 533 534 /* Copy data between DMA and PCM buffers. */ 535 static void 536 buffer_copy(struct sc_chinfo *ch) 537 { 538 struct sc_pcminfo *scp; 539 struct sc_info *sc; 540 uint32_t row, ports; 541 unsigned int pos; 542 unsigned int n; 543 unsigned int adat_width, pcm_width; 544 545 scp = ch->parent; 546 sc = scp->sc; 547 548 n = AFMT_CHANNEL(ch->format); /* n channels */ 549 550 /* Let pcm formats differ from current hardware ADAT width. */ 551 adat_width = hdspe_adat_width(sc->speed); 552 if (n == hdspe_channel_count(ch->ports, 2)) 553 pcm_width = 2; 554 else if (n == hdspe_channel_count(ch->ports, 4)) 555 pcm_width = 4; 556 else 557 pcm_width = 8; 558 559 if (ch->dir == PCMDIR_PLAY) 560 pos = sndbuf_getreadyptr(ch->buffer); 561 else 562 pos = sndbuf_getfreeptr(ch->buffer); 563 564 pos /= 4; /* Bytes per sample. */ 565 pos /= n; /* Destination buffer n-times smaller. */ 566 567 /* Iterate through rows of ports with contiguous slots. */ 568 ports = ch->ports; 569 if (pcm_width == adat_width) 570 row = hdspe_port_first_row(ports); 571 else 572 row = hdspe_port_first(ports); 573 574 while (row != 0) { 575 if (ch->dir == PCMDIR_PLAY) 576 buffer_mux_port(sc->pbuf, ch->data, row, ch->ports, pos, 577 sc->period * 2, adat_width, pcm_width); 578 else 579 buffer_demux_port(sc->rbuf, ch->data, row, ch->ports, 580 pos, sc->period * 2, adat_width, pcm_width); 581 582 ports &= ~row; 583 if (pcm_width == adat_width) 584 row = hdspe_port_first_row(ports); 585 else 586 row = hdspe_port_first(ports); 587 } 588 } 589 590 static int 591 clean(struct sc_chinfo *ch) 592 { 593 struct sc_pcminfo *scp; 594 struct sc_info *sc; 595 uint32_t *buf; 596 uint32_t row, ports; 597 unsigned int offset, slots; 598 599 scp = ch->parent; 600 sc = scp->sc; 601 buf = sc->rbuf; 602 603 if (ch->dir == PCMDIR_PLAY) 604 buf = sc->pbuf; 605 606 /* Iterate through rows of ports with contiguous slots. */ 607 ports = ch->ports; 608 row = hdspe_port_first_row(ports); 609 while (row != 0) { 610 offset = hdspe_port_slot_offset(row, 611 hdspe_adat_width(sc->speed)); 612 slots = hdspe_port_slot_width(row, hdspe_adat_width(sc->speed)); 613 614 bzero(buf + offset * HDSPE_CHANBUF_SAMPLES, 615 slots * HDSPE_CHANBUF_SIZE); 616 617 ports &= ~row; 618 row = hdspe_port_first_row(ports); 619 } 620 621 return (0); 622 } 623 624 /* Channel interface. */ 625 static void * 626 hdspechan_init(kobj_t obj, void *devinfo, struct snd_dbuf *b, 627 struct pcm_channel *c, int dir) 628 { 629 struct sc_pcminfo *scp; 630 struct sc_chinfo *ch; 631 struct sc_info *sc; 632 int num; 633 634 scp = devinfo; 635 sc = scp->sc; 636 637 snd_mtxlock(sc->lock); 638 num = scp->chnum; 639 640 ch = &scp->chan[num]; 641 642 if (dir == PCMDIR_PLAY) 643 ch->ports = hdspe_channel_play_ports(scp->hc); 644 else 645 ch->ports = hdspe_channel_rec_ports(scp->hc); 646 647 ch->run = 0; 648 ch->lvol = 0; 649 ch->rvol = 0; 650 651 /* Support all possible ADAT widths as channel formats. */ 652 ch->cap_fmts[0] = 653 SND_FORMAT(AFMT_S32_LE, hdspe_channel_count(ch->ports, 2), 0); 654 ch->cap_fmts[1] = 655 SND_FORMAT(AFMT_S32_LE, hdspe_channel_count(ch->ports, 4), 0); 656 ch->cap_fmts[2] = 657 SND_FORMAT(AFMT_S32_LE, hdspe_channel_count(ch->ports, 8), 0); 658 ch->cap_fmts[3] = 0; 659 ch->caps = malloc(sizeof(struct pcmchan_caps), M_HDSPE, M_NOWAIT); 660 *(ch->caps) = (struct pcmchan_caps) {32000, 192000, ch->cap_fmts, 0}; 661 662 /* Allocate maximum buffer size. */ 663 ch->size = HDSPE_CHANBUF_SIZE * hdspe_channel_count(ch->ports, 8); 664 ch->data = malloc(ch->size, M_HDSPE, M_NOWAIT); 665 666 ch->buffer = b; 667 ch->channel = c; 668 ch->parent = scp; 669 670 ch->dir = dir; 671 672 snd_mtxunlock(sc->lock); 673 674 if (sndbuf_setup(ch->buffer, ch->data, ch->size) != 0) { 675 device_printf(scp->dev, "Can't setup sndbuf.\n"); 676 return (NULL); 677 } 678 679 return (ch); 680 } 681 682 static int 683 hdspechan_trigger(kobj_t obj, void *data, int go) 684 { 685 struct sc_pcminfo *scp; 686 struct sc_chinfo *ch; 687 struct sc_info *sc; 688 689 ch = data; 690 scp = ch->parent; 691 sc = scp->sc; 692 693 snd_mtxlock(sc->lock); 694 switch (go) { 695 case PCMTRIG_START: 696 #if 0 697 device_printf(scp->dev, "hdspechan_trigger(): start\n"); 698 #endif 699 hdspechan_enable(ch, 1); 700 hdspechan_setgain(ch); 701 hdspe_start_audio(sc); 702 break; 703 704 case PCMTRIG_STOP: 705 case PCMTRIG_ABORT: 706 #if 0 707 device_printf(scp->dev, "hdspechan_trigger(): stop or abort\n"); 708 #endif 709 clean(ch); 710 hdspechan_enable(ch, 0); 711 hdspe_stop_audio(sc); 712 break; 713 714 case PCMTRIG_EMLDMAWR: 715 case PCMTRIG_EMLDMARD: 716 if(ch->run) 717 buffer_copy(ch); 718 break; 719 } 720 721 snd_mtxunlock(sc->lock); 722 723 return (0); 724 } 725 726 static uint32_t 727 hdspechan_getptr(kobj_t obj, void *data) 728 { 729 struct sc_pcminfo *scp; 730 struct sc_chinfo *ch; 731 struct sc_info *sc; 732 uint32_t ret, pos; 733 734 ch = data; 735 scp = ch->parent; 736 sc = scp->sc; 737 738 snd_mtxlock(sc->lock); 739 ret = hdspe_read_2(sc, HDSPE_STATUS_REG); 740 snd_mtxunlock(sc->lock); 741 742 pos = ret & HDSPE_BUF_POSITION_MASK; 743 pos *= AFMT_CHANNEL(ch->format); /* Hardbuf with multiple channels. */ 744 745 return (pos); 746 } 747 748 static int 749 hdspechan_free(kobj_t obj, void *data) 750 { 751 struct sc_pcminfo *scp; 752 struct sc_chinfo *ch; 753 struct sc_info *sc; 754 755 ch = data; 756 scp = ch->parent; 757 sc = scp->sc; 758 759 #if 0 760 device_printf(scp->dev, "hdspechan_free()\n"); 761 #endif 762 763 snd_mtxlock(sc->lock); 764 if (ch->data != NULL) { 765 free(ch->data, M_HDSPE); 766 ch->data = NULL; 767 } 768 if (ch->caps != NULL) { 769 free(ch->caps, M_HDSPE); 770 ch->caps = NULL; 771 } 772 snd_mtxunlock(sc->lock); 773 774 return (0); 775 } 776 777 static int 778 hdspechan_setformat(kobj_t obj, void *data, uint32_t format) 779 { 780 struct sc_chinfo *ch; 781 782 ch = data; 783 784 #if 0 785 struct sc_pcminfo *scp = ch->parent; 786 device_printf(scp->dev, "hdspechan_setformat(%d)\n", format); 787 #endif 788 789 ch->format = format; 790 791 return (0); 792 } 793 794 static uint32_t 795 hdspechan_setspeed(kobj_t obj, void *data, uint32_t speed) 796 { 797 struct sc_pcminfo *scp; 798 struct hdspe_rate *hr; 799 struct sc_chinfo *ch; 800 struct sc_info *sc; 801 long long period; 802 int threshold; 803 int i; 804 805 ch = data; 806 scp = ch->parent; 807 sc = scp->sc; 808 hr = NULL; 809 810 #if 0 811 device_printf(scp->dev, "hdspechan_setspeed(%d)\n", speed); 812 #endif 813 814 if (hdspe_running(sc) == 1) 815 goto end; 816 817 if (sc->force_speed > 0) 818 speed = sc->force_speed; 819 820 /* First look for equal frequency. */ 821 for (i = 0; rate_map[i].speed != 0; i++) { 822 if (rate_map[i].speed == speed) 823 hr = &rate_map[i]; 824 } 825 826 /* If no match, just find nearest. */ 827 if (hr == NULL) { 828 for (i = 0; rate_map[i].speed != 0; i++) { 829 hr = &rate_map[i]; 830 threshold = hr->speed + ((rate_map[i + 1].speed != 0) ? 831 ((rate_map[i + 1].speed - hr->speed) >> 1) : 0); 832 if (speed < threshold) 833 break; 834 } 835 } 836 837 switch (sc->type) { 838 case HDSPE_RAYDAT: 839 case HDSPE_AIO: 840 period = HDSPE_FREQ_AIO; 841 break; 842 default: 843 /* Unsupported card. */ 844 goto end; 845 } 846 847 /* Write frequency on the device. */ 848 sc->ctrl_register &= ~HDSPE_FREQ_MASK; 849 sc->ctrl_register |= hr->reg; 850 hdspe_write_4(sc, HDSPE_CONTROL_REG, sc->ctrl_register); 851 852 speed = hr->speed; 853 if (speed > 96000) 854 speed /= 4; 855 else if (speed > 48000) 856 speed /= 2; 857 858 /* Set DDS value. */ 859 period /= speed; 860 hdspe_write_4(sc, HDSPE_FREQ_REG, period); 861 862 sc->speed = hr->speed; 863 end: 864 865 return (sc->speed); 866 } 867 868 static uint32_t 869 hdspechan_setblocksize(kobj_t obj, void *data, uint32_t blocksize) 870 { 871 struct hdspe_latency *hl; 872 struct sc_pcminfo *scp; 873 struct sc_chinfo *ch; 874 struct sc_info *sc; 875 int threshold; 876 int i; 877 878 ch = data; 879 scp = ch->parent; 880 sc = scp->sc; 881 hl = NULL; 882 883 #if 0 884 device_printf(scp->dev, "hdspechan_setblocksize(%d)\n", blocksize); 885 #endif 886 887 if (hdspe_running(sc) == 1) 888 goto end; 889 890 if (blocksize > HDSPE_LAT_BYTES_MAX) 891 blocksize = HDSPE_LAT_BYTES_MAX; 892 else if (blocksize < HDSPE_LAT_BYTES_MIN) 893 blocksize = HDSPE_LAT_BYTES_MIN; 894 895 blocksize /= 4 /* samples */; 896 897 if (sc->force_period > 0) 898 blocksize = sc->force_period; 899 900 /* First look for equal latency. */ 901 for (i = 0; latency_map[i].period != 0; i++) { 902 if (latency_map[i].period == blocksize) 903 hl = &latency_map[i]; 904 } 905 906 /* If no match, just find nearest. */ 907 if (hl == NULL) { 908 for (i = 0; latency_map[i].period != 0; i++) { 909 hl = &latency_map[i]; 910 threshold = hl->period + ((latency_map[i + 1].period != 0) ? 911 ((latency_map[i + 1].period - hl->period) >> 1) : 0); 912 if (blocksize < threshold) 913 break; 914 } 915 } 916 917 snd_mtxlock(sc->lock); 918 sc->ctrl_register &= ~HDSPE_LAT_MASK; 919 sc->ctrl_register |= hdspe_encode_latency(hl->n); 920 hdspe_write_4(sc, HDSPE_CONTROL_REG, sc->ctrl_register); 921 sc->period = hl->period; 922 snd_mtxunlock(sc->lock); 923 924 #if 0 925 device_printf(scp->dev, "New period=%d\n", sc->period); 926 #endif 927 928 sndbuf_resize(ch->buffer, 929 (HDSPE_CHANBUF_SIZE * AFMT_CHANNEL(ch->format)) / (sc->period * 4), 930 (sc->period * 4)); 931 end: 932 933 return (sndbuf_getblksz(ch->buffer)); 934 } 935 936 static uint32_t hdspe_bkp_fmt[] = { 937 SND_FORMAT(AFMT_S32_LE, 2, 0), 938 0 939 }; 940 941 static struct pcmchan_caps hdspe_bkp_caps = {32000, 192000, hdspe_bkp_fmt, 0}; 942 943 static struct pcmchan_caps * 944 hdspechan_getcaps(kobj_t obj, void *data) 945 { 946 struct sc_chinfo *ch; 947 948 ch = data; 949 950 #if 0 951 struct sc_pcminfo *scl = ch->parent; 952 device_printf(scp->dev, "hdspechan_getcaps()\n"); 953 #endif 954 955 if (ch->caps != NULL) 956 return (ch->caps); 957 958 return (&hdspe_bkp_caps); 959 } 960 961 static kobj_method_t hdspechan_methods[] = { 962 KOBJMETHOD(channel_init, hdspechan_init), 963 KOBJMETHOD(channel_free, hdspechan_free), 964 KOBJMETHOD(channel_setformat, hdspechan_setformat), 965 KOBJMETHOD(channel_setspeed, hdspechan_setspeed), 966 KOBJMETHOD(channel_setblocksize, hdspechan_setblocksize), 967 KOBJMETHOD(channel_trigger, hdspechan_trigger), 968 KOBJMETHOD(channel_getptr, hdspechan_getptr), 969 KOBJMETHOD(channel_getcaps, hdspechan_getcaps), 970 KOBJMETHOD_END 971 }; 972 CHANNEL_DECLARE(hdspechan); 973 974 static int 975 hdspe_pcm_probe(device_t dev) 976 { 977 978 #if 0 979 device_printf(dev,"hdspe_pcm_probe()\n"); 980 #endif 981 982 return (0); 983 } 984 985 static uint32_t 986 hdspe_pcm_intr(struct sc_pcminfo *scp) 987 { 988 struct sc_chinfo *ch; 989 struct sc_info *sc; 990 int i; 991 992 sc = scp->sc; 993 994 for (i = 0; i < scp->chnum; i++) { 995 ch = &scp->chan[i]; 996 snd_mtxunlock(sc->lock); 997 chn_intr(ch->channel); 998 snd_mtxlock(sc->lock); 999 } 1000 1001 return (0); 1002 } 1003 1004 static int 1005 hdspe_pcm_attach(device_t dev) 1006 { 1007 char status[SND_STATUSLEN]; 1008 struct sc_pcminfo *scp; 1009 const char *buf; 1010 int err; 1011 int play, rec; 1012 1013 scp = device_get_ivars(dev); 1014 scp->ih = &hdspe_pcm_intr; 1015 1016 if (scp->hc->ports & HDSPE_CHAN_AIO_ALL) 1017 buf = "AIO"; 1018 else if (scp->hc->ports & HDSPE_CHAN_RAY_ALL) 1019 buf = "RayDAT"; 1020 else 1021 buf = "?"; 1022 device_set_descf(dev, "HDSPe %s [%s]", buf, scp->hc->descr); 1023 1024 /* 1025 * We don't register interrupt handler with snd_setup_intr 1026 * in pcm device. Mark pcm device as MPSAFE manually. 1027 */ 1028 pcm_setflags(dev, pcm_getflags(dev) | SD_F_MPSAFE); 1029 1030 play = (hdspe_channel_play_ports(scp->hc)) ? 1 : 0; 1031 rec = (hdspe_channel_rec_ports(scp->hc)) ? 1 : 0; 1032 err = pcm_register(dev, scp, play, rec); 1033 if (err) { 1034 device_printf(dev, "Can't register pcm.\n"); 1035 return (ENXIO); 1036 } 1037 1038 scp->chnum = 0; 1039 if (play) { 1040 pcm_addchan(dev, PCMDIR_PLAY, &hdspechan_class, scp); 1041 scp->chnum++; 1042 } 1043 1044 if (rec) { 1045 pcm_addchan(dev, PCMDIR_REC, &hdspechan_class, scp); 1046 scp->chnum++; 1047 } 1048 1049 snprintf(status, SND_STATUSLEN, "port 0x%jx irq %jd on %s", 1050 rman_get_start(scp->sc->cs), 1051 rman_get_start(scp->sc->irq), 1052 device_get_nameunit(device_get_parent(dev))); 1053 pcm_setstatus(dev, status); 1054 1055 mixer_init(dev, &hdspemixer_class, scp); 1056 1057 return (0); 1058 } 1059 1060 static int 1061 hdspe_pcm_detach(device_t dev) 1062 { 1063 int err; 1064 1065 err = pcm_unregister(dev); 1066 if (err) { 1067 device_printf(dev, "Can't unregister device.\n"); 1068 return (err); 1069 } 1070 1071 return (0); 1072 } 1073 1074 static device_method_t hdspe_pcm_methods[] = { 1075 DEVMETHOD(device_probe, hdspe_pcm_probe), 1076 DEVMETHOD(device_attach, hdspe_pcm_attach), 1077 DEVMETHOD(device_detach, hdspe_pcm_detach), 1078 { 0, 0 } 1079 }; 1080 1081 static driver_t hdspe_pcm_driver = { 1082 "pcm", 1083 hdspe_pcm_methods, 1084 PCM_SOFTC_SIZE, 1085 }; 1086 1087 DRIVER_MODULE(snd_hdspe_pcm, hdspe, hdspe_pcm_driver, 0, 0); 1088 MODULE_DEPEND(snd_hdspe, sound, SOUND_MINVER, SOUND_PREFVER, SOUND_MAXVER); 1089 MODULE_VERSION(snd_hdspe, 1); 1090