diff options
author | cinap_lenrek <cinap_lenrek@localhost> | 2011-05-16 22:09:39 +0000 |
---|---|---|
committer | cinap_lenrek <cinap_lenrek@localhost> | 2011-05-16 22:09:39 +0000 |
commit | 7b0e90b5d1019da77eaa5e7c390f45d6bf12eb40 (patch) | |
tree | 9ac93f845c8c5ca1b62b1753e27773694511b2c7 | |
parent | f148f75f096823ab6527d29ef8a4c8f57c2ba7c9 (diff) |
sb16: make it work in bochs
-rw-r--r-- | sys/src/9/pc/audiosb16.c | 131 | ||||
-rw-r--r-- | sys/src/9/port/master | 63 |
2 files changed, 62 insertions, 132 deletions
diff --git a/sys/src/9/pc/audiosb16.c b/sys/src/9/pc/audiosb16.c index d48a7e32b..1d042fe86 100644 --- a/sys/src/9/pc/audiosb16.c +++ b/sys/src/9/pc/audiosb16.c @@ -37,9 +37,7 @@ enum enum { Bufsize = 1024, /* 5.8 ms each, must be power of two */ - Nbuf = 128, /* .74 seconds total */ - Dma = 6, - IrqAUDIO = 7, + Nbuf = 128, /* .74 seconds total */ SBswab = 0, }; @@ -364,7 +362,6 @@ contindma(void) audio.current = b; if(b == 0) goto shutdown; - iprint("d"); if(dmasetup(blaster.dma, b->virt, Bufsize, 0) >= 0) return; print("#A%d: dmasetup fail\n", audio.ctlrno); @@ -400,12 +397,17 @@ sb16startdma(void) sbcmd(speed>>8); sbcmd(speed); - count = (Bufsize >> 1) - 1; if(0) sbcmd(0xbe); /* A/D, autoinit */ else sbcmd(0xb6); /* D/A, autoinit */ sbcmd(0x30); /* stereo, signed 16 bit */ + + /* + * not really sure if this is correct, but + * it works in bochs + */ + count = (Bufsize >> 2) - 1; sbcmd(count); sbcmd(count>>8); @@ -518,46 +520,40 @@ pokeaudio(void) static void sb16intr(void) { - int stat, dummy; + int stat; - stat = mxread(0x82) & 7; /* get irq status */ - iprint("i%d",stat); - if(stat) { - dummy = 0; - if(stat & 2) { - ilock(&blaster); - dummy = inb(blaster.clri16); + stat = mxread(0x82); /* get irq status */ + if(stat & 7) { + ilock(&blaster); + if(stat & 2) + inb(blaster.clri16); + else if(stat & 1) + inb(blaster.clri8); + if(stat & 3){ contindma(); iunlock(&blaster); + audio.intr = 1; wakeup(&audio.vous); } - if(stat & 1) { - dummy = inb(blaster.clri8); - } - if(stat & 4) { - dummy = inb(blaster.clri401); - } - USED(dummy); + if(stat & 4) + inb(blaster.clri401); } } static void ess1688intr(void) { - int dummy; - if(audio.active){ ilock(&blaster); contindma(); - dummy = inb(blaster.clri8); + inb(blaster.clri8); iunlock(&blaster); audio.intr = 1; wakeup(&audio.vous); - USED(dummy); + return; } - else - print("#A%d: unexpected ess1688 interrupt\n", audio.ctlrno); + print("#A%d: unexpected ess1688 interrupt\n", audio.ctlrno); } void @@ -596,6 +592,7 @@ waitaudio(void) pokeaudio(); tsleep(&audio.vous, anybuf, 0, 10000); if(audio.intr == 0) { + audio.active = 0; print("#A%d: audio timeout\n", audio.ctlrno); /**/ return -1; } @@ -709,10 +706,8 @@ audiowrite(Audio *, void *vp, long n, vlong) if(b == 0) { b = getbuf(&audio.empty); if(b == 0) { - if(waitaudio() < 0){ - audio.active = 0; + if(waitaudio()) pokeaudio(); - } continue; } audio.filling = b; @@ -840,13 +835,14 @@ audioprobe(Audio *adev) ISAConf sbconf; int i, x; static int irq[] = {2,5,7,10}; + static int dma16[] = {0,5,6,7}; if(audio.probed) return -1; sbconf.port = 0x220; - sbconf.dma = Dma; - sbconf.irq = IrqAUDIO; + sbconf.dma = 1; + sbconf.irq = 5; if(isaconfig("audio", adev->ctlrno, &sbconf) == 0) return -1; @@ -877,23 +873,6 @@ audioprobe(Audio *adev) return -1; } - switch(sbconf.irq){ - case 2: - case 5: - case 7: - case 9: - case 10: - break; - default: - print("#A%d: bad irq %d\n", audio.ctlrno, sbconf.irq); - iofree(sbconf.port); - iofree(sbconf.port+0x100); - return -1; - } - - print("#A%d: %s port 0x%04lux irq %d\n", audio.ctlrno, sbconf.type, - sbconf.port, sbconf.irq); - blaster.reset = sbconf.port + 0x6; blaster.read = sbconf.port + 0xa; blaster.write = sbconf.port + 0xc; @@ -954,42 +933,56 @@ audioprobe(Audio *adev) * but then use the contents in case the write is * disallowed. */ - mxcmd(0x80, /* irq */ - (sbconf.irq==2)? 1: - (sbconf.irq==5)? 2: - (sbconf.irq==7)? 4: - (sbconf.irq==9)? 1: - (sbconf.irq==10)? 8: - 0); - - mxcmd(0x81, 1<<blaster.dma); /* dma */ - - x = mxread(0x81); - for(i=5; i<=7; i++) - if(x & (1<<i)){ - blaster.dma = i; + for(i=0; i<nelem(irq); i++){ + if(irq[i] == sbconf.irq){ + mxcmd(0x80, 1<<i); break; } - + } x = mxread(0x80); - for(i=0; i<=3; i++) + for(i=0; i<nelem(irq); i++) if(x & (1<<i)){ sbconf.irq = irq[i]; break; } - adev->write = audiowrite; - adev->close = audioclose; - adev->status = audiostatus; - adev->buffered = audiobuffered; + if(blaster.dma < 4) + mxcmd(0x81, 1<<blaster.dma); + else { + for(i=0; i<nelem(dma16); i++){ + if(dma16[i] == blaster.dma){ + x = mxread(0x81); + mxcmd(0x81, 0x10<<i | (x & 0xf)); + break; + } + } + } + x = mxread(0x81); + for(i=0; i<4; i++) + if(x & (1<<i)) + blaster.dma = i; + for(i=0; i<nelem(dma16); i++) + if(x & (0x10<<i)){ + blaster.dma = dma16[i]; + break; + } + + print("#A%d: %s port 0x%04lux irq %d dma %d\n", audio.ctlrno, sbconf.type, + sbconf.port, sbconf.irq, blaster.dma); - dmainit(blaster.dma, Bufsize); + if(dmainit(blaster.dma, Bufsize)) + return -1; intrenable(sbconf.irq, pcaudiosbintr, 0, BUSUNKNOWN, "sb16"); sbbufinit(); setempty(); mxvolume(); + adev->write = audiowrite; + adev->close = audioclose; + adev->status = audiostatus; + adev->buffered = audiobuffered; + return 0; } diff --git a/sys/src/9/port/master b/sys/src/9/port/master deleted file mode 100644 index 0e627aaf8..000000000 --- a/sys/src/9/port/master +++ /dev/null @@ -1,63 +0,0 @@ -# do not edit; automatically generated - -$ pnp -/ root -A audio -A uda1341 -B bridge -C ce -D ssl -E sdp -F flash -G gs1 -I ip -K kprof -L lpt -M mnt -P arch -S sd -T lm78 -U usb -V lml -V tv -X loopback -Y pccard -a tls -b irq -c cons -d dup -e env -f floppy -g segment -i draw -k fs -l ether -m mouse -m penmouse -p proc -q qmux -r rtc -r µc -s srv -t uart -v vga -w wd -y i82365 -y pcmcia -| pipe -¤ cap -æ aoe -Ι kbin -κ kbmap -μ moipv6 -霞 kasumi - -α local use -β local use -γ local use -δ local use -ε local use -ζ local use -η local use -θ local use -ι local use |