³ Gravis Ultrasound Tech Specs ³ ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ The Unofficial Dox Written December, 1992 By Tran of Renaissance and Joshua Jensen OK, folks, here it is. This is the programming information that Gravis didn't and won't give you any time soon. These dox have been obtained through long hours of debug sessions and experimentation. Let's clear up some things that have been debated in comp.sys.ibm.pc.soundcard for quit sometime now: þ The GUS can play 32 mono samples at once, fully pannable through 16 different positions. þ This is still a bit unclear. The SDK says that samples have to be 32-byte aligned in memory. I've been following this. Maybe that is not the case, though, and I haven't tested it. Credits: Tran came up with the initial information about programming the card. Josh documented it and included actual assembly language information in this archive on how it works. It's relatively simple, but some things are unclear and are explained here in the dox and in the code. ÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Methods ³ ÄÄÄÄÄÄÄÄÙ @DELAY = (in byte 300h)*7 Description: All this function does is give a short idle wait for the card to do whatever processing it needs to. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Probe Ultra Sound ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+103h, 4Ch out BASE+105h, 0 @DELAY @DELAY out BASE+103h, 4Ch out BASE+105h, 1 Poke Data Byte Loc: 0h, Byte: AA ; Don't think this HAS to be an AA. Poke Data Byte Loc: 100h, Byte: 55 ; Don't think this is needed. Peek Data Byte Loc: 0h Store Byte out BASE+103h, 4Ch out BASE+105h, 0 Restore Byte Is it AA? If so, then we have found a GUS. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Test for amount of memory installed on UltraSound ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ Poke Data Byte Loc: 40000h, Byte: AA Peek Data Byte Loc: 40000h Is it an AA? If not, then there is 256k of DRAM. Exit. Poke Data Byte Loc: 80000h, Byte: AA Peek Data Byte Loc: 80000h Is it an AA? If not, then there is 512k of DRAM. Exit. Poke Data Byte Loc: C0000h, Byte: AA Peek Data Byte Loc: C0000h Is it an AA? If not, then there is 768k of DRAM. Exit. Poke Data Byte Loc: 0FFFFFh, Byte: AA Peek Data Byte Loc: 0FFFFFh Is it an AA? If not, then there is 1024k of DRAM. Exit. Description: Poke these bytes on the boundaries of 256k, 512k, 768k, and 1024k. If the memory isn't there, then it won't return what is poked. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Peek Data Byte ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+103h, 43h out BASE+104h, low word address out BASE+103h, 44h out BASE+105h, high byte address in BASE+107h, INBYTE Description: The card's memory can be from 00000h to fffffh. INBYTE is the byte value returned from the card that was at that memory location. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Poke Data Byte ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+103h, 43h out BASE+104h, low word address out BASE+103h, 44h out BASE+105h, high byte address out BASE+107h, OUTBYTE ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Set Voice Frequency ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+102h, voice number out BASE+103h, 1 out BASE+104h, word frequency number (actual frequency / 19.0579083837) Description: Tran thought he'd give you the exact value :) Dividing by 19 will give enough accuracy for the task, though. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Set Voice Balance ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+102h, voice number out BASE+103h, 0ch out BASE+105h, byte balance (0-0fh) Description: The Balance byte can range from 0 to 15. 0 is far left, 15 is far right, and 7 is right in the middle. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Set Voice Volume ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+102h, voice number out BASE+103h, 9 out BASE+104h, word volume value (0-0ffffh, log ... not linear) ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Set Loop Mode ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+102h, voice number out BASE+103h, 80h in BASE+105h, TEMP out BASE+103h, 0 out BASE+105h, (TEMP & 0e7h) or MODE Description: This is not really necessary. Actually, the Set Loop Mode and Stop Voice Immediately could be one function. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Stop Voice Immediately ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+102h, voice number out BASE+103h, 80h in BASE+105h, TEMP out BASE+103h, 0 out BASE+105h, (TEMP & 0dfh) | 3 @DELAY out BASE+103h, 0 out BASE+105h, (TEMP & 0dfh) | 3 Description: Dunno why the extra delay and duplicated code is there. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Start Voice Playing ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+102h, voice number out BASE+103h, 0ah out BASE+104h, word BEGIN >> 7 out BASE+103h, 0bh out BASE+104h, word BEGIN << 9 out BASE+103h, 2 out BASE+104h, word START >> 7 out BASE+103h, 3 out BASE+104h, word START << 9 out BASE+103h, 4 out BASE+104h, word END >> 7 out BASE+103h, 5 out BASE+104h, word END << 9 out BASE+103h, 0 out BASE+105h, MODE & 0fch ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Read Voice Location ³ ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ out BASE+102h, voice number out BASE+103h, 8ah ; in BASE+104h, low byte TEMP0 ; in BASE+105h, high byte TEMP0 in BASE+104h, word TEMP0 out BASE+103h, 8bh ; in BASE+104h, low byte TEMP1 ; in BASE+105h, high byte TEMP1 in BASE+104h, word TEMP1 LOC = ((TEMP0 << 7) | (TEMP1 >> 9)) & 0xfffff Note: Word read at BASE+104h seems to work same as sequential byte reads from BASE+104h then BASE+105h. ÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ ÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Ports ³ As you can see, there are a lot of blanks to be filled. Hope Gravis ÄÄÄÄÄÄÙ will take a hint soon. BASE - write only, mix control ÚÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄ¿ ³ 7 ³ 6 ³ 5 ³ 4 ³ 3 ³ 2 ³ 1 ³ 0 ³ ÀÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÙ ? ? ? ? ? ³ ³ ³ ³ ³ À 0 = Line in on. 1 = Line in off. ³ ÀÄÄÄÄ 0 = Output on. 1 = Output off. ÀÄÄÄÄÄÄÄÄ 0 = Mic in off. 1 = Mic in on. ??? BASE+102h - Active voice select (byte port) BASE+103h - command port (byte port) Bitmap so far: ÚÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄ¿ ³ 7 ³ 6 ³ 5 ³ 4 ³ 3 ³ 2 ³ 1 ³ 0 ³ ÀÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÙ ³ ³ ? ? ³ ³ ³ ³ ³ ³ ³ ³ ³ ³ ³ ³ ³ ³ ÀÄÄÄ´ ³ ³ ³ ÀÄÄÄÄÄÄÄÅ Command for voice ³ ³ ÀÄÄÄÄÄÄÄÄÄÄÄÙ ³ ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Command for card. ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Read from voice. 0h - write voice mode (loop and data type) - byte on 105h ÚÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄÂÄÄÄ¿ ³ 7 ³ 6 ³ 5 ³ 4 ³ 3 ³ 2 ³ 1 ³ 0 ³ Designated as MODE through dox ÀÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÁÄÂÄÙ ? ? ? ³ ³ ³ ³ ³ ³ ³ ³ ³ À Voice On/Off (If both set to 0, voice on.) ³ ³ ³ ÀÄÄÄÄ Voice On/Off (If both set to 1, voice off.) ³ ³ ÀÄÄÄÄÄÄÄÄ 0 = 8 bit data. 1 = 16 bit data. ³ ÀÄÄÄÄÄÄÄÄÄÄÄÄ 0 = No loop. 1 = Loop Sample. ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ 0 = Go forward. 1 = Go backward. 1h - voice frequency - word on 104h 2h - loop start location / 80h - word on 104h 3h - loop start location << 9 - word on 104h 4h - loop end location / 80h - word on 104h 5h - loop end location << 9 - word on 104h 9h - voice volume - word on 104h 0ah - voice location / 80h - word on 104h 0bh - voice location << 9 - word on 104h 0ch - voice balance - byte on 105h 0eh - Unsure. Has something to do with turning - byte on 105h stereo on and off. See U_Reset for an example of usage. 43h - low word of DRAM address - word on 104h 44h - high byte of DRAM address - byte on 105h 4Ch - Unsure exactly of what this does - byte on 105h However, a 1 must be output to BASE+105h for the card to do memory writes. At least, that's the only way I could get it to work. 80h - read voice mode - byte on 105h 8ah - read voice location - bytes on 104h, 105h 8bh - read voice location - bytes on 104h, 105h Notes: Any >= 80h plus a number might be the read mode of the value - 80h. In other words, to read the voice volume (this is untested), you'd output an 89h through BASE+103h and then read BASE+105h. BASE+104h - word writes/reads BASE+105h - byte writes/reads ÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ Notes ³ ÄÄÄÄÄÄÙ To stop an instrument when the sample ends (not immediately), change its loop type to 'no loop'. If you are making a lot of changes to just ONE voice, the OUT BASE+102h, Channel needs only to be done once.