2 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
3 ³ Programming the SoundBlaster DSP ³
4 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
6 Written for the PC-GPE by Mark Feldman
10 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
11 ³ THIS FILE MAY NOT BE DISTRIBUTED ³
12 ³ SEPARATE TO THE ENTIRE PC-GPE COLLECTION. ³
13 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
16 ÚÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
20 I assume no responsibility whatsoever for any effect that this file, the
21 information contained therein or the use thereof has on you, your sanity,
22 computer, spouse, children, pets or anything else related to you or your
23 existance. No warranty is provided nor implied with this information.
25 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
29 The SoundBlaster is capable of both FM and digitised sounds. The FM wave
30 is fully Adlib compatible, so check the ADLIB.TXT file for info
31 on how to program it. This file will concentrate on recording and playback
32 of digital samples through the SoundBlaster CT-DSP 1321 chip.
34 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
35 ³ The SoundBlaster DSP I/O Ports ³
36 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
38 The DSP (Digital Sound Processor) chip is programmed through 4 ports which
39 are determined by the SoundBlaster base address jumper setting:
45 WRITE COMMAND/DATA output
46 WRITE BUFFER STATUS input 2xCh
51 where x = 1 for base address jumper setting 210h
52 x = 2 for base address jumper setting 220h
55 x = 6 for base address jumper setting 260h
58 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
62 You have to reset the DSP before you program it. This is done with the
65 1) Write a 1 to the SoundBlaster RESET port (2x6h)
66 2) Wait for 3 micro-seconds
67 3) Write a 0 to the SoundBlaster RESET port (2x6h)
68 4) Read the byte from the DATA AVAILABLE (2xEh) port until bit 7 = 1
69 5) Poll for a ready byte (AAh) from the READ DATA port (2xAh). Before
70 reading the READ DATA port it is avdvisable.
72 The DSP usually takes somewhere around 100 micro-seconds to reset itself.
73 If it fails to do within a reasonable time (say 200 micro-seconds) then
74 an error has occurred, possibly an incorrect I/O address is being used.
76 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
77 ³ Writing to the DSP ³
78 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
80 A value can be written to the DSP with the following procedure :
82 1) Read the DSP's WRITE BUFFER STATUS port (2xCh) until bit 7 = 0
83 2) Write the value to the WRITE COMMAND/DATA port (2xCh)
85 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
89 A value can be read from the DSP with the following procedure :
91 1) Read the DSP's DATA AVAILABLE port (2xEh) until bit 7 = 1
92 2) Read the data from the READ DATA port (2xAh)
94 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
95 ³ Turning the speaker on and controlling DMA ³
96 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
98 Speaker and DMA control are handled by writing one of the following bytes
101 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
102 ³ Value Description ³
103 ÃÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ´
105 ³ D1h Turn speaker on ³
106 ³ D3h Turn speaker off ³
108 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
110 DMA is discussed below. The DMA commands shown here can be used to pause
111 the sample during DMA playback playback.
113 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
114 ³ Writing to the DAC ³
115 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
117 The DAC (Digital to Analog Converter) is the part of the card which converts
118 a sample number (ie 0 -> 255) to a sound level. To generate a square sound
119 wave at maximum volume (for example) you could alternate writing 0's and
122 Programming the DAC in direct mode involves the main program setting the
123 DAC to a desired value. Only 8 bit DAC is available in direct mode. To set
124 the DAC level you write the value 10h to the DSP followed by the sample
125 number (0 -> 255). Note that no sound will be heard unless the speaker has
126 been turned on. In direct mode the main program is responsible for the
127 timing between samples, the DAC can output sound samples as fast as the
128 calling program can change it. Typically the timer interrupt is reprogrammed
129 and used to generate the timing required for a sample playback. Info on
130 programming the PIT chip can be found in the PIT.TXT file.
132 The DAC can also be programmed to accept values sent to it via the DMA
133 chip. Draeden has written an excellent article on programming the DMA chip
134 (see DMA_VLA.TXT) so only a brief example of it's use will be given here.
135 The important thing to remember is that the DMA chip cannot transfer data
136 which crosses between page breaks. If the data does cross page breaks then
137 it will have to be split up into several transfers, with one page per
140 Setting the playback frequency for the DMA transfer is done by writing
141 the value 40h to the DSP followed by TIME_CONSTANT, where
142 TIME_CONSTANT = 256 - 1000000 / frequency
144 There are several types of DMA transfers available. The following table
147 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
148 ³DMA_TYPE_VALUE Description Frequency Range ³
149 ÃÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ´
150 ³ 14h 8 bit 4KHz -> 23 KHz ³
151 ³ 74h 4 bit ADPCM 4KHz -> 12 KHz ³
152 ³ 75h 4 bit ADPCM with 4KHz -> 12 KHz ³
154 ³ 76h 2.6 bit ADPCM 4KHz -> 13 KHz ³
155 ³ 77h 2.6 bit ADPCM with 4KHz -> 13 KHz ³
157 ³ 16h 2 bit ADPCM 4KHz -> 11 KHz ³
158 ³ 17h 2 bit ADPCM with 4KHz -> 11 KHz ³
160 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
162 ADPCM stands for Adaptive Pulse Code Modulation, a sound compression
163 technique where the difference between successive samples is stored rather
164 than their actual values. In the modes with reference bytes, the first
165 byte is the actual starting value. Having modes with and without reference
166 bytes means you can output successive blocks without the need for a
167 reference byte at the start of each one.
169 The procedure for doing a DMA transfer is as follows:
171 1) Load the sound data into memory
172 2) Set up the DMA chip for the tranfer
173 3) Set the DSP TIME_CONSTANT to the sampling rate
174 4) Write DMA_TYPE_VALUE value to the DSP
175 5) Write DATA_LENGTH to the DSP (2 bytes, LSB first) where
176 DATA_LENGTH = number of bytes to send - 1
178 Note that the DMA chip must be programmed before the BSP.
180 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
181 ³ Reading from the ADC ³
182 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
184 Reading samples from the ADC (Analog to Digital Converter) can also be
185 done in either direct or DMA mode.
187 To read a sample in direct mode write the value 20h to the DSP and then
188 read the value from the DSP. Simple as that!
190 To set up the DSP for a DMA transfer, follow this procedure :
192 1) Get a memory buffer ready to hold the sample
193 2) Set up the DMA chip for the transfer
194 3) Set the DSP TIME_CONSTANT to the sampling rate
195 4) Write the value 24h to the DSP
196 5) Write DATA_LENGTH to the DSP (2 bytes, LSB first) where
197 DATA_LENGTH = number of bytes to read - 1
199 Note that the DMA chip must be programmed before the BSP.
201 DMA reads only support 8 bit mode, compressed modes are done by software and
202 stored in the voc file. I haven't tried to figure out how the compression is
203 done. If someone does figure it out I'd like to know about it!
205 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
206 ³ Programming the DMA Chip ³
207 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
209 As mentioned before, Draeden has written a very good article on the dma
210 chip, but here is a brief run down on what you would need to do to program
211 the DMA channel 1 for the DSP in real mode:
213 1) Calculate the 20 bit address of the memory buffer you are using
214 where Base Address = Segment * 16 + Offset
215 eg 1234h:5678h = 179B8h
216 2) Send the value 05h to port 0Ah (mask off channel 1)
217 3) Send the value 00h to port 0Ch (clear the internal DMA flip/flop)
218 4) Send the value 49h to port 0Bh (for playback) or
219 45h to port 0Bh (for recording)
220 5) Write the LSB (bits 0 -> 7) of the 20 bit memory address to port 02h
221 6) Write the MSB (bits 8 -> 15) of the 20 bit memory address to ort 02h
222 7) Write the Page (bits 16 -> 19) of the 20 bit memory address to port 83h
223 8) Send the LSB of DATA_LENGTH to port 03h
224 9) Send the MSB of DATA_LENGTH to port 03h
225 10) Send the value 01h to port 0Ah (enable channel 1)
227 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
228 ³ End of DMA Interrupt ³
229 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
231 When a DMA transfer is complete an interrupt is generated. The actual
232 interrupt number depends on the SoundBlaster card's IRQ jumper setting:
234 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ¿
236 ³ Setting Interrupt ³
237 ÃÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ´
242 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
244 To service one of these interrupts you must perform these 3 tasks:
246 1) Acknowledge the DSP interrupt by reading the DATA AVAILABLE port (2xEh)
248 2) If there are more blocks to transfer then set them up
249 3) Output value 20h (EOI) to the interrupt controller port 20h
251 Of course, as with any hardware interrupt you must also leave the
252 state of the system (registers etc..) the way it was when the interrupt
255 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
256 ³ A Simple DSP Pascal Unit ³
257 ÀÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÙ
261 DSP.PAS - A demo SoundBlaster DSP unit for real mode
270 { ResetDSP returns true if reset was successful
271 base should be 1 for base address 210h, 2 for 220h etc... }
272 function ResetDSP(base : word) : boolean;
274 { Write DAC sets the speaker output level }
275 procedure WriteDAC(level : byte);
277 { ReadDAC reads the microphone input level }
278 function ReadDAC : byte;
280 { SpeakerOn connects the DAC to the speaker }
281 function SpeakerOn: byte;
283 { SpeakerOff disconnects the DAC from the speaker,
284 but does not affect the DAC operation }
285 function SpeakerOff: byte;
287 { Functions to pause DMA playback }
289 procedure DMAContinue;
291 { Playback plays a sample of a given size back at a given frequency using
292 DMA channel 1. The sample must not cross a page boundry }
293 procedure Playback(sound : Pointer; size : word; frequency : word);
299 var DSP_RESET : word;
300 DSP_READ_DATA : word;
301 DSP_WRITE_DATA : word;
302 DSP_WRITE_STATUS : word;
303 DSP_DATA_AVAIL : word;
305 function ResetDSP(base : word) : boolean;
310 { Calculate the port addresses }
311 DSP_RESET := base + $206;
312 DSP_READ_DATA := base + $20A;
313 DSP_WRITE_DATA := base + $20C;
314 DSP_WRITE_STATUS := base + $20C;
315 DSP_DATA_AVAIL := base + $20E;
317 { Reset the DSP, and give some nice long delays just to be safe }
318 Port[DSP_RESET] := 1;
320 Port[DSP_RESET] := 0;
322 if (Port[DSP_DATA_AVAIL] And $80 = $80) And
323 (Port[DSP_READ_DATA] = $AA) then
329 procedure WriteDSP(value : byte);
331 while Port[DSP_WRITE_STATUS] And $80 <> 0 do;
332 Port[DSP_WRITE_DATA] := value;
335 function ReadDSP : byte;
337 while Port[DSP_DATA_AVAIL] and $80 = 0 do;
338 ReadDSP := Port[DSP_READ_DATA];
341 procedure WriteDAC(level : byte);
347 function ReadDAC : byte;
353 function SpeakerOn: byte;
358 function SpeakerOff: byte;
363 procedure DMAContinue;
373 procedure Playback(sound : Pointer; size : word; frequency : word);
374 var time_constant : word;
382 { Set up the DMA chip }
383 offset := Seg(sound^) Shl 4 + Ofs(sound^);
384 page := (Seg(sound^) + Ofs(sound^) shr 4) shr 12;
388 Port[$02] := Lo(offset);
389 Port[$02] := Hi(offset);
391 Port[$03] := Lo(size);
392 Port[$03] := Hi(size);
395 { Set the playback frequency }
396 time_constant := 256 - 1000000 div frequency;
398 WriteDSP(time_constant);
400 { Set the playback type (8-bit) }
409 ÚÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
413 Title : The SoundBlaster Developpers Kit
414 Publishers : Creative Labs Inc
415 Creative Technology PTE LTD
417 Title : Sound Blaster - The Official Book
418 Authors : Richard Heimlich, David M. Golden, Ivan Luk, Peter M. Ridge
419 Publishers : Osborne/McGraw Hill
422 Some of the information in this file was either obtained from or verified
423 by the source code in a public domain library called SOUNDX by Peter
424 Sprenger. I haven't tried using his library yet (I don't have a C compiler
425 at the moment) but it looks very well done and contains numerous sound card
426 detection routines. Says Peter : "It would be nice, that when you make
427 something commercial with my routines, that you send me a copy of your
428 project or send me some bucks, just enough for pizza and coke to support my
429 night programming sessions. If you send me nothing, ok. But USE the stuff,
430 if you can need it!". Heh...a REAL programmer!
433 directory: /pub/msdos/demos/programming/game-dev/source
436 ÚÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÂÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄÄ
440 What the...why is there a faint glimmer of sunlight outside? HOLY $#!^!! It's
441 5:30am! I'm goin' to bed!