VOGONS


First post, by superfury

User metadata
Rank l33t++
Rank
l33t++

I'm trying to implement the Sound Blaster 1.0 DSP in UniPCemu, but so far the DMA 8-bit output doesn't work:

https://bitbucket.org/superfury/unipcemu/src/ … ter.c?at=master

I'm currently testing using Mike's 8088 version of Wolfenstein 3D. It detects the Sound Blaster without problems, but I don't hear the gun sound that I'm currently testing with.

I see it tries to write DMA samples while SOUNDBLASTER.DREQ is 3, which should mean that it's waiting for the sample to be rendered by updateSoundBlaster().

Seeing as DREQ is 3, but DMA is still transferring data(although DREQ bit 1 should cause the DMA DREQ to be lowered, effectively pausing Demand mode transfers), could this mean that rendering isn't done at the correct speed by toggling DREQ, but actually from an buffer in the Sound Blaster DSP? Anyone?

Last edited by superfury on 2016-08-09, 19:08. Edited 1 time in total.

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 1 of 11, by Jepael

User metadata
Rank Oldbie
Rank
Oldbie

Early Sound Blaster "DSP" is just a preprogrammed 8051 microcontroller. You load a time constant and the microcontroller triggers a DREQ every time the timer (or software counter) elapses and the byte transferred over DMA just gets sent to the DAC. For instance, to get 22050 rate, you load time constant 0xD3, because 1e6/(0x100-0xd3) is 22222 Hz. So each sample is transferred separately, I think.

Later Sound Blasters have some sort of FIFO buffer to keep few samples in a buffer.

Some other sound cards (some Covox ISA cards with DMA) just used a 8254 timer instead to trigger the DMA transfer periodically.

Reply 2 of 11, by superfury

User metadata
Rank l33t++
Rank
l33t++

Looking at my DMA code again, I think there might be a problem with the Single-cycle mode:
https://bitbucket.org/superfury/unipcemu/src/ … le-view-default

Currently both single cycle and burst/block mode start their transfers based on the DACK signal. The DACK signal doesn't automatically stop until terminal count is reached. Should I modify the Single-cycle mode to automatically clear the DACK signal after processing a byte? Thus transfers pause until DREQ is raised again, but Burst/Block mode keeps continuing? Is that better behaviour?

Edit: looking at the descriptions of the modes at https://docs.freebsd.org/doc/2.1.5-RELEASE/us … andbook248.html , it shows that, essentially, from the view of time position vs transfers, demand and single-cycle mode are essentially doing the exact same thing? The only difference being that single-cycle is seperated by CPU instructions, while demand mode moves more bytes at once(blocking the CPU longer periods of time while transferring chunks of data). So essentially demand mode is moving data like single-cycle mode, but in bigger chunks(provided DREQ is raised more than one byte/word transfer). Otherwise it's the same? Basically some kind of single-cycle splitting variable sized chunks instead of single bytes/words?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 3 of 11, by superfury

User metadata
Rank l33t++
Rank
l33t++

I've managed to get output pretty much working in 8-bit mode:
https://bitbucket.org/superfury/unipcemu/src/ … ter.c?at=master

Also modified the DMA to reset the DMA DACK 'signal' during Single-cycle to stop transfers when DREQ is lowered.
https://bitbucket.org/superfury/unipcemu/src/ … dma.c?at=master

I hear the gunsound at the game now, although there seems to be some kind of lag and residue samples?

I also still need to implement the ADPCM modes, as well as the MIDI commands(are these even present on the Sound Blaster? Aren't the MPU-401 ports used(330h/331h)?). Any suggestions how to do this?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 4 of 11, by jesolo

User metadata
Rank l33t
Rank
l33t

Unfortunately, my programming knowledge is zero, but the Sound Blaster 1.0, 2.0 and Pro cards did not have an MPU-401 UART mode MIDI interface.
They did have a combo MIDI/gameport, but unfortunately, I cannot provide you with any technical information.
There should be some documentation online.

Reply 5 of 11, by Jepael

User metadata
Rank Oldbie
Rank
Oldbie

Yes, early Sound Blasters have MIDI, but it is through DSP commands. They have no MPU-401 compatible anything at 0x330/0x331. I think SB16 onwards are MPU compatible, and I think they still work with DSP commands as well.

I don't know what software would even use this SB MIDI interface, perhaps some MIDI sequencing software but not many games I suppose. Not very important feature 😀

Reply 6 of 11, by superfury

User metadata
Rank l33t++
Rank
l33t++

Just tried the SB1.5 disks from https://www.vogonsdrivers.com/getfile.php?fil … =48&menustate=0 .
When I try to install, it installs, but when I run inst-drv.exe with port 220 hex(the emulated base port of the Sound Blaster DSP), it tells me "Error in Interrupt detection". Anyone knows what this is about?

Edit: I've improved interrupt detection, but the inst-drv.exe still gives the error. Anyone knows what's going wrong here?
https://bitbucket.org/superfury/unipcemu/src/ … ter.c?at=master

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 7 of 11, by peterferrie

User metadata
Rank Oldbie
Rank
Oldbie

after displaying "I/O Address: xxx", it hooks interrupts 0a (irq 2), 0b (irq 3), 0d (irq 5), 0f (irq 7);
reads port 0x21, ands with 0x53, writes port 0x21;
polls port+0x0c until bit 7 is clear, writes 0xf2;
waits for one of those interrupts to be triggered or timeout to expire;
restores port 0x21.

error message is displayed if timeout expires.

Reply 8 of 11, by superfury

User metadata
Rank l33t++
Rank
l33t++

After looking at my IRQ code, I noticed that I've changed the high nibble of the IRQ(since there's only 16 IRQs on a x86) to mean the subchannel of the IRQ(so multiple IRQs can have their own handlers for handling interrupt acnowledge and EOI), but this wasn't handled in the PIC. Thus it was resulting in a PIC being addressed that doesn't exist (PIC #(0x17>>3==2(0-based)) out of 2 PICs, thus silently overflowing).

Now that I've fixed this, the interrupt gets called correctly and the program continues without the error.

Edit: Now it only gives me the FM option(which terminates the program). Also all other software either gives messages explaining address conflicts or refuses to detect the Sound Blaster.

Edit: I've modified the Game Blaster to respond to ports as long as it doesn't conflict with the Sound Blaster (e.g. all OUT instructions to it's usual ports and only IN instructions to ports unused by the Sound Blaster(e.g. only disabling port 0x2?A reads for the Game Blaster)). Is that correct?

I see that the software gives an identification command(which gives the negated parameter in the input(from CPU perspective) buffer) to the DSP, but it doesn't detect the DSP it seems? I don't see anything else, besides a simple Speaker Off command followed by a reset? Does the ID command need to raise an IRQ?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 9 of 11, by Jepael

User metadata
Rank Oldbie
Rank
Oldbie
superfury wrote:

Edit: I've modified the Game Blaster to respond to ports as long as it doesn't conflict with the Sound Blaster (e.g. all OUT instructions to it's usual ports and only IN instructions to ports unused by the Sound Blaster(e.g. only disabling port 0x2?A reads for the Game Blaster)). Is that correct?

I see that the software gives an identification command(which gives the negated parameter in the input(from CPU perspective) buffer) to the DSP, but it doesn't detect the DSP it seems? I don't see anything else, besides a simple Speaker Off command followed by a reset? Does the ID command need to raise an IRQ?

Game Blaster and Sound Blaster cannot coexist at the same base address as they overlap. It's either SB or GB at some base port, so if you want GB and SB both at the same time then put them into different baseports, but then again most games search for 220h first and it may use the card it finds there and does not search for other addresses any more. This is the reason DosBox config file has entry to select if you want Game Blaster or Sound Blaster type emulation.

SB 1 and 2 support the same SAA1099P chips at 2X0h..2X3h just like Game Blaster, but the other ports don't work like Game Blaster.

SB Pro and later changed the 2X0h..2X3h for FM chip(s).

Reply 10 of 11, by superfury

User metadata
Rank l33t++
Rank
l33t++

OK. I'll leave the non-SB I/O Game Blaster ports enabled for the Game Blaster when Sound Blaster emulation is enabled. It just will ignore any reads to I/O ports that actually conflict with the Sound Blaster (the DSP Read Port is the only one as far as i can see that actually causes conflicts. Writes don't cause conflicts, since it's only the value that's stored and compared, no harm done for the Sound Blaster, as long as the values don't set anything weird in the Sound Blaster). That will ensure maximum possible compability with Sound Blaster and Game Blaster when Sound Blaster emulation is enabled combined with Game Blaster emulation(although not official Sound Blaster I/O results, this will keep Sound Blaster compatiblity with as much Game Blaster detectability as possible for software). Since output to a port won't affect the detection system and Sound Blaster that way. The only port that does cause problems (port 2XAh when read in this case) is now disabled in the Game Blaster(allowing the Sound Blaster to take priority for that port). Thus full Sound Blaster compatibiility with as much Game Blaster detectability as possible (as long as the data port 2XAh isn't relied on, detection should work, while being fully Sound Blaster compatible).

The only problem that's left now is: why doesn't the application give the other options? Doesn't it detect the Sound Blaster DSP correctly? Why does it simply terminate when selecting the FM option(and pressing enter)? The SB environmental variable points to the SB directory I've made on the virtual harddisk (D:\SB in this case, my games.sfdimg disk image, which contains games I'm using to test UniPCemu hardware)?
Anyone can answer that?

Game Blaster emulation: https://bitbucket.org/superfury/unipcemu/src/ … ter.c?at=master
Sound Blaster DSP emulation: https://bitbucket.org/superfury/unipcemu/src/ … ter.c?at=master
PIC emulation: https://bitbucket.org/superfury/unipcemu/src/ … pic.c?at=master
DMA emulation: https://bitbucket.org/superfury/unipcemu/src/ … dma.c?at=master

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io

Reply 11 of 11, by superfury

User metadata
Rank l33t++
Rank
l33t++

Just added ADPCM based on Dosbox's conversion:
https://bitbucket.org/superfury/unipcemu/src/ … ter.c?at=master

Although it still isn't detected correctly or fully working according to the SB1.5 disk(software hangs waiting for some result in the DSP input buffer)? Anyone knows what's going wrong here?

The inst-drv.exe's Install Menu only gives me 2 options:
- "Sound Blaster FM Driver"
- "Exit to DOS"

Why won't it give me the other options?

Choosing the Sound Blaster FM Driver terminates the application and returns to the MS-DOS prompt.

The attachment 1.jpg is no longer available

Looking at a CPU log shows that it's trying to execute 286+ commands(on the 186/8086 that's supported in UniPCemu so far). Any 8086-compatible test software exists?

Author of the UniPCemu emulator.
UniPCemu Git repository
UniPCemu for Android, Windows, PSP, Vita and Switch on itch.io