[Back to SOUND SWAG index] [Back to Main SWAG index] [Original]
{
If anyone can fill me in on how to output in stereo, I'd be very
appreciative... I've heard that port $220/$221 is for left channel,
$222/$223 is for the right, but that doesn't make any sense...does it?
This code makes R2D2 noises on a SoundBlaster until you press ESC.
{adapted from SS4CH.PAS by Frank Hirsch}
USES Crt;
const sampleSize=4096;
var sampleData:array[0..sampleSize-1]of byte;
const samplePos:longint=0;
var sampleSpeed:longint;
var sampleDelta:longint;
const resetPort =$226;
const readPort =$22A;
const writePort =$22C;
const dataAvailPort=$22E;
function readByte:byte;begin
repeat until shortInt(port[dataAvailPort])<0;
readByte:=port[readPort];
end;
procedure initDSP;begin
port[resetPort]:=1;
delay(1);
port[resetPort]:=0;
repeat until readByte=$AA;
end;
var counter:longint;
procedure timerInt;assembler;asm
push ax
push bx
push dx
push di
push ds
push es
mov ax,seg @DATA
mov ds,ax
mov es,[segB800]
xor byte ptr es:[0],$21
mov bx,[word ptr samplePos+2]
mov ah,byte ptr sampleData[bx]
mov dx,[word ptr sampleSpeed] {next sample byte}
add [word ptr samplePos],dx
adc bx,[word ptr sampleSpeed+2]
and bx,[sampleSize-1]
mov [word ptr samplePos+2],bx
mov bx,[word ptr sampleDelta]
add [word ptr sampleSpeed],bx
mov bx,[word ptr sampleDelta+2]
adc [word ptr sampleSpeed+2],bx
mov dx,writePort
@P2: {ready for output byte?}
in al,dx
test al,$80
jnz @P2
mov al,ah
out dx,al
mov al,$20 {process interrupt}
out $20,al
{ sti}
{prep NEXT output}
@P1: {ready for command?}
in al,dx
test al,$80
jnz @P1
mov al,$10 {set up a DAC output}
out dx,al
db $66; inc word ptr [counter]
pop es
pop ds
pop di
pop dx
pop bx
pop ax
iret
end;
var
vec08:pointer absolute 0:8*4;
old08:pointer;
procedure setTimerTics(tics:word);begin
asm cli; end;
port[$43]:=$36;
port[$40]:=lo(tics);
port[$40]:=hi(tics);
asm sti end;
end;
procedure setTimerFreq(freq:word);begin
setTimerTics(succ(word($1234DC div freq)));
end;
procedure stopTimer;begin setTimerTics(0); end;
procedure writeByte(b:byte);begin
repeat until shortInt(port[writePort])>=0;
port[writePort]:=b;
end;
procedure speaker(onOff:boolean);begin
if onOff then writeByte($D1)
else writeByte($D3);
end;
var i,j,n:word;
const rate=16384;
procedure note(freq,dur,slide:longint);
begin
counter:=0;
sampleSpeed:=freq*sampleSize*(65536 div rate);
sampleDelta:=slide;
dur:=(dur*rate)div 1000;
repeat
if port[$60]=$81 then break;
until counter>=dur;
end;
begin
initDSP;
for i:=0 to sampleSize-1 do
sampleData[i]:=round(sin(i*pi/(sampleSize shr 1))*127.5+127.5);
old08:=vec08;
speaker(true);
writeByte($10); {prep sb for data}
asm cli end;
vec08:=@timerInt;
asm sti end;
setTimerFreq(rate);
repeat
case random(4) of
0:note(random(1900)+60,(random(2)*80)+40,integer(random(3))-1);
1:note(random(800)+450,(random(2)*80)+140,integer(random(2049))
-1024);
2:note(0,(random(2)+1)*40,0);
3:note(random(30)+15,(random(2)*80)+40,random(2));
end;
until port[$60]=$81;
stopTimer;
asm cli end;
vec08:=old08;
asm sti end;
speaker(false); {it's probably gonna eat this as data}
speaker(false);
end.
[Back to SOUND SWAG index] [Back to Main SWAG index] [Original]