Date: Mon, 09 Aug 1999 17:18:43 +0100 From: Francis Jordan <frankrj@netscape.net> To: Cameron Grant <gandalf@vilnya.demon.co.uk> Cc: multimedia@freebsd.org, current@freebsd.org Subject: Re: it's time... Message-ID: <37AEFF63.1354B1C8@netscape.net> References: <000901bee13c$b1831dc0$0304020a@rings>
next in thread | previous in thread | raw e-mail | index | archive | help
Cameron Grant wrote: > > to let newpcm out of the cage so you can all get your grubby little hands on > it. > > http://www.vilnya.demon.co.uk/newpcm+dfrpnp-19990807.diff.gz > > this is a patch against a recent -current. if you have a pci or isapnp > soundcard, you should have pnp0 and pcm0 in your kernel config as > appropriate. isapnp cards should not need any pnp lines in kernel.conf. > > the list of supported cards is as for luigi's driver, with the addition of a > couple more mss-clones, and trident 4dwave. there is a part done aureal > vortex driver which is as yet nonfunctional. mmap() is supported but not > well tested. format conversions are supported. the code seems to be > stable. > > please test it and email me success and failure reports. > > - cameron Hi, First, I'd like to thank Cameron for his great work on the pcm driver. It builds and installs cleanly, and generally looks very impressive. I apologize in advance if the following message is a bit on the long side, but the problem I'm going to describe is very odd. I must also make clear that the sound card works fine under Windoze, and it also worked fine with the old pcm driver, until something got broken around 20 April this year (_after_ the integration of new bus). The sound card settings are changeable in the BIOS; this is what I have (the card is a non-PnP Yamaha): Sound: Enabled (other options are: Disabled and Auto) SB I/O address: 220-22F WSS I/O address: 530-538 Adlib I/O address: 388-38F MPU I/O address: 300-301 CTRL I/O address: 100 (OPL3 chip control) DMA A: DMA 1 (other options: 0,7) DMA B: DMA 0 (other options: 1,7) IRQ: IRQ 5 In accordance with these settings, I used the following line in the kernel: device pcm0 at isa? port 0x530 irq 5 drq 1 flags 0x10 (Note the order of the DMA channels - 1, then 0) Now this is what happens: the driver successfully detects the card, but fails to register an interrupt: /kernel: mss_detect - chip revision 0x0a /kernel: mss_detect() - Detected CS4231 /kernel: pcm0: <CS4231> at port 0x530-0x53f,0x310-0x311 irq 5 drq 1 flags 0xa210 on isa0 /kernel: pcm: setmap 30000, ff00; 0xc7bdd000 -> 30000 /kernel: pcm: setmap 40000, ff00; 0xc7bed000 -> 40000 /kernel: device combination doesn't support shared irq3 /kernel: intr_connect(irq3) failed, result=-1 /kernel: device combination doesn't support shared irq4 /kernel: intr_connect(irq4) failed, result=-1 /kernel: device combination doesn't support shared irq5 /kernel: intr_connect(irq5) failed, result=-1 /kernel: device combination doesn't support shared irq7 /kernel: intr_connect(irq7) failed, result=-1 /kernel: device combination doesn't support shared irq9 /kernel: intr_connect(irq9) failed, result=-1 /kernel: device combination doesn't support shared irq12 /kernel: intr_connect(irq12) failed, result=-1 /kernel: device combination doesn't support shared irq14 /kernel: intr_connect(irq14) failed, result=-1 /kernel: device combination doesn't support shared irq15 /kernel: intr_connect(irq15) failed, result=-1 IRQ 5 is definitely unused, and exactly the same setup worked fine with the old pcm driver. Another strange thing is that cat /dev/sndstat shows: FreeBSD Audio Driver (newpcm) Aug 8 1999 21:55:41 Installed devices: pcm0: <CS4231> at io 0x530 irq 5 drq 1:0 (1/1 channels duplex) as if everything were ok. It also seems that although intr_connect fails, IRQ 5 is marked as being in use, because pcic then chooses the next one available (10): /kernel: PC-Card VLSI 82C146 (5 mem & 2 I/O windows) /kernel: pcic: controller irq 10 Now the VERY odd thing: if I use DMA channels 0 and 1 (as opposed to 1 and 0), change the BIOS settings accordingly, and compile the kernel with device pcm0 at isa? port 0x530 irq 5 drq 0 flags 0x11 I get the following error: /kernel: mss_detect - chip revision 0x0a /kernel: mss_detect() - Detected CS4231 /kernel: pcm0: <CS4231> at port 0x530-0x53f,0x310-0x311 irq 5 flags 0xa211 on isa0 + /kernel: device_probe_and_attach: pcm0 attach returned 6 /kernel: device combination doesn't support shared irq3 /kernel: intr_connect(irq3) failed, result=-1 /kernel: device combination doesn't support shared irq4 /kernel: intr_connect(irq4) failed, result=-1 /kernel: device combination doesn't support shared irq7 /kernel: intr_connect(irq7) failed, result=-1 /kernel: device combination doesn't support shared irq9 /kernel: intr_connect(irq9) failed, result=-1 /kernel: device combination doesn't support shared irq12 /kernel: intr_connect(irq12) failed, result=-1 /kernel: device combination doesn't support shared irq14 /kernel: intr_connect(irq14) failed, result=-1 /kernel: device combination doesn't support shared irq15 /kernel: intr_connect(irq15) failed, result=-1 /kernel: PC-Card VLSI 82C146 (5 mem & 2 I/O windows) + /kernel: pcic: controller irq 5 and cat: /dev/sndstat: Device not configured As you can see, this time attach really failed, and pcic reused IRQ 5. (By the way, the problem is not specific to IRQ 5; e.g. I can disable the parallel port and give the sound card IRQ 7 - the results are the same.) Now what difference can the order of DMA channels possibly make? The error message about "shared" interrupts also looks suspect - why is the interrupt marked as shared? I guess the answer is somewhere in /sys/i386/isa/intr_machdep.c. Here's the relevant part from add_intrdesc(): if ((idesc->flags & INTR_EXCL) != 0 || (head->flags & INTR_EXCL) != 0) { /* * can't append new handler, if either list head or * new handler do not allow interrupts to be shared */ if (bootverbose) printf("\tdevice combination doesn't support " "shared irq%d\n", irq); return (-1); } The function add_intrdesc() is called from inthand_add(): idesc->handler = handler; idesc->argument = arg; idesc->maskptr = maskptr; idesc->intr = irq; idesc->flags = flags; /* block this irq */ oldspl = splq(1 << irq); /* add irq to class selected by maskptr */ errcode = add_intrdesc(idesc); splx(oldspl); if (errcode != 0) { if (bootverbose) printf("\tintr_connect(irq%d) failed, result=%d\n", irq, errcode); free(idesc->name, M_DEVBUF); free(idesc, M_DEVBUF); idesc = NULL; } return (idesc); inthand_add() is called from register_intr() as follows: flags |= INTR_EXCL; idesc = inthand_add("old", intr, isa_intr_wrap, irec, maskptr, flags); if (idesc == NULL) { free(irec, M_DEVBUF); return -1; } isareclist[intr] = irec; return 0; } (inthand_add is called from isa_setup_intr called from bus_setup_intr) Since inthand_add returns NULL, free() should free the interrupt. In the first case (DMA channels 1,0) it doesn't happen; in the second case (0,1) it does. Why? But the most important question is: why didn't it register the interrupt in the first place? Hope you multimedia gurus can explain what's going down. Thanks, Frank. To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-current" in the body of the message
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?37AEFF63.1354B1C8>