1//
2// snd_mixa.s
3// x86 assembly-language sound code
4//
5
6#include "qasm.h"
7
8#if	id386
9
10	.text
11
12//----------------------------------------------------------------------
13// 8-bit sound-mixing code
14//----------------------------------------------------------------------
15
16#define ch		4+16
17#define sc		8+16
18#define count	12+16
19
20.globl C(S_PaintChannelFrom8)
21C(S_PaintChannelFrom8):
22	pushl	%esi				// preserve register variables
23	pushl	%edi
24	pushl	%ebx
25	pushl	%ebp
26
27//	int 	data;
28//	short	*lscale, *rscale;
29//	unsigned char *sfx;
30//	int		i;
31
32	movl	ch(%esp),%ebx
33	movl	sc(%esp),%esi
34
35//	if (ch->leftvol > 255)
36//		ch->leftvol = 255;
37//	if (ch->rightvol > 255)
38//		ch->rightvol = 255;
39	movl	ch_leftvol(%ebx),%eax
40	movl	ch_rightvol(%ebx),%edx
41	cmpl	$255,%eax
42	jna		LLeftSet
43	movl	$255,%eax
44LLeftSet:
45	cmpl	$255,%edx
46	jna		LRightSet
47	movl	$255,%edx
48LRightSet:
49
50//	lscale = snd_scaletable[ch->leftvol >> 3];
51//	rscale = snd_scaletable[ch->rightvol >> 3];
52//	sfx = (signed char *)sc->data + ch->pos;
53//	ch->pos += count;
54	andl	$0xF8,%eax
55	addl	$(sfxc_data),%esi
56	andl	$0xF8,%edx
57	movl	ch_pos(%ebx),%edi
58	movl	count(%esp),%ecx
59	addl	%edi,%esi
60	shll	$7,%eax
61	addl	%ecx,%edi
62	shll	$7,%edx
63	movl	%edi,ch_pos(%ebx)
64	addl	$(C(snd_scaletable)),%eax
65	addl	$(C(snd_scaletable)),%edx
66	subl	%ebx,%ebx
67	movb	-1(%esi,%ecx,1),%bl
68
69	testl	$1,%ecx
70	jz		LMix8Loop
71
72	movl	(%eax,%ebx,4),%edi
73	movl	(%edx,%ebx,4),%ebp
74	addl	C(paintbuffer)+psp_left-psp_size(,%ecx,psp_size),%edi
75	addl	C(paintbuffer)+psp_right-psp_size(,%ecx,psp_size),%ebp
76	movl	%edi,C(paintbuffer)+psp_left-psp_size(,%ecx,psp_size)
77	movl	%ebp,C(paintbuffer)+psp_right-psp_size(,%ecx,psp_size)
78	movb	-2(%esi,%ecx,1),%bl
79
80	decl	%ecx
81	jz		LDone
82
83//	for (i=0 ; i<count ; i++)
84//	{
85LMix8Loop:
86
87//		data = sfx[i];
88//		paintbuffer[i].left += lscale[data];
89//		paintbuffer[i].right += rscale[data];
90	movl	(%eax,%ebx,4),%edi
91	movl	(%edx,%ebx,4),%ebp
92	addl	C(paintbuffer)+psp_left-psp_size(,%ecx,psp_size),%edi
93	addl	C(paintbuffer)+psp_right-psp_size(,%ecx,psp_size),%ebp
94	movb	-2(%esi,%ecx,1),%bl
95	movl	%edi,C(paintbuffer)+psp_left-psp_size(,%ecx,psp_size)
96	movl	%ebp,C(paintbuffer)+psp_right-psp_size(,%ecx,psp_size)
97
98	movl	(%eax,%ebx,4),%edi
99	movl	(%edx,%ebx,4),%ebp
100	movb	-3(%esi,%ecx,1),%bl
101	addl	C(paintbuffer)+psp_left-psp_size*2(,%ecx,psp_size),%edi
102	addl	C(paintbuffer)+psp_right-psp_size*2(,%ecx,psp_size),%ebp
103	movl	%edi,C(paintbuffer)+psp_left-psp_size*2(,%ecx,psp_size)
104	movl	%ebp,C(paintbuffer)+psp_right-psp_size*2(,%ecx,psp_size)
105
106//	}
107	subl	$2,%ecx
108	jnz		LMix8Loop
109
110LDone:
111	popl	%ebp
112	popl	%ebx
113	popl	%edi
114	popl	%esi
115
116	ret
117
118
119//----------------------------------------------------------------------
120// Transfer of stereo buffer to 16-bit DMA buffer code
121//----------------------------------------------------------------------
122
123.globl C(S_WriteLinearBlastStereo16)
124C(S_WriteLinearBlastStereo16):
125	pushl	%edi
126	pushl	%ebx
127
128//	int		i;
129//	int		val;
130	movl	C(snd_linear_count),%ecx
131	movl	C(snd_p),%ebx
132	movl	C(snd_out),%edi
133
134//	for (i=0 ; i<snd_linear_count ; i+=2)
135//	{
136LWLBLoopTop:
137
138//		val = (snd_p[i]*snd_vol)>>8;
139//		if (val > 0x7fff)
140//			snd_out[i] = 0x7fff;
141//		else if (val < (short)0x8000)
142//			snd_out[i] = (short)0x8000;
143//		else
144//			snd_out[i] = val;
145	movl	-8(%ebx,%ecx,4),%eax
146	sarl	$8,%eax
147	cmpl	$0x7FFF,%eax
148	jg		LClampHigh
149	cmpl	$0xFFFF8000,%eax
150	jnl		LClampDone
151	movl	$0xFFFF8000,%eax
152	jmp		LClampDone
153LClampHigh:
154	movl	$0x7FFF,%eax
155LClampDone:
156
157//		val = (snd_p[i+1]*snd_vol)>>8;
158//		if (val > 0x7fff)
159//			snd_out[i+1] = 0x7fff;
160//		else if (val < (short)0x8000)
161//			snd_out[i+1] = (short)0x8000;
162//		else
163//			snd_out[i+1] = val;
164	movl	-4(%ebx,%ecx,4),%edx
165	sarl	$8,%edx
166	cmpl	$0x7FFF,%edx
167	jg		LClampHigh2
168	cmpl	$0xFFFF8000,%edx
169	jnl		LClampDone2
170	movl	$0xFFFF8000,%edx
171	jmp		LClampDone2
172LClampHigh2:
173	movl	$0x7FFF,%edx
174LClampDone2:
175	shll	$16,%edx
176	andl	$0xFFFF,%eax
177	orl		%eax,%edx
178	movl	%edx,-4(%edi,%ecx,2)
179
180//	}
181	subl	$2,%ecx
182	jnz		LWLBLoopTop
183
184//	snd_p += snd_linear_count;
185
186	popl	%ebx
187	popl	%edi
188
189	ret
190
191
192#endif	// id386
193
194