new version
[Chiptunes.git] / foo.c
1 #include <stdio.h>
2 #include "fakeasm.h"
3 typedef unsigned char u8;
4
5 u8 data[] = {
6 0x84, 0x9d, 0xb0, 0x69, 0x9d, 0x84, 0x69, 0x58,
7 0x75, 0x8c, 0xb0, 0x69, 0x8c, 0x75, 0x69, 0x58
8 };
9 u8 zero; //r16
10 u8 acc; //r17
11 u8 i0; //r18
12 u8 i1; //r19
13 u8 i2; //r20
14 u8 i3; //r21
15 u8 n; //r22
16 u8 s; //r23
17 u8 _; //r24
18 u8 loop; //r25
19 u8 t;/*==Ml*/ //r26 (Xlo)
20 u8 x;/*==Mh*/ //r27 (Xhi)
21 //r28
22 //r29
23 /*fakestack_l*/ //r30 (Zlo)
24 /*fakestack_h*/ //r31 (Zhi)
25 #define Mh x //mod3 vars
26 #define Ml t // -"-
27 //http://homepage.divms.uiowa.edu/~jones/bcd/mod.shtml
28 void mod3(void) {
29 // mod3(Mh.Ml) -> t
30 #define tmp _
31 ADD (Ml, Mh)
32 CLR (Mh)
33 ADC (Mh, zero, carry) //Mh only holds the carry bit
34 MOV (tmp, Ml)
35 SWAP (tmp)
36 ANDI (tmp, 0x0f)
37 SWAP (Mh)
38 OR (tmp, Mh)
39 ANDI (Ml, 0x0f)
40 ADD (Ml, tmp)
41 MOV (tmp, Ml)
42 LSR (tmp)
43 LSR (tmp)
44 ANDI (Ml, 0x03)
45 ADD (Ml, tmp)
46 MOV (tmp, Ml)
47 LSR (tmp)
48 LSR (tmp)
49 ANDI (Ml, 0x03)
50 ADD (Ml, tmp)
51 CPI (Ml, 3)
52 BRPL (skip)
53 SUBI (Ml, 3)
54 skip:;
55 RET
56 #undef tmp
57 }
58 void mul(void) { //don't need overhead of function (inline it)
59 // i1.i0 * t -> _.x.t
60 #define a1 x
61 #define a2 _
62 #define a0 t
63 // start MUL -- 92 cycles :( (unrolled and skipping second bit: 76)
64 CLR (a2)
65 CLR (a1)
66
67 switch(t) {
68 case 0x58: // 0101 1000
69 LSR (a2)
70 ROR (a1)
71 LSR (a2)
72 ROR (a1)
73 LSR (a2)
74 ROR (a1)
75 ADD (a1, i0)
76 ADC (a2, i1, carry)
77 LSR (a2)
78 ROR (a1)
79
80 ADD (a1, i0)
81 ADC (a2, i1, carry)
82 LSR (a2)
83 ROR (a1)
84 LSR (a2)
85 ROR (a1)
86 ADD (a1, i0)
87 ADC (a2, i1, carry)
88 LSR (a2)
89 ROR (a1)
90 LSR (a2)
91 ROR (a1)
92 break;
93 case 0x69: // 0110 1001
94 ADD (a1, i0)
95 ADC (a2, i1, carry)
96 LSR (a2)
97 ROR (a1)
98 LSR (a2)
99 ROR (a1)
100 LSR (a2)
101 ROR (a1)
102 ADD (a1, i0)
103 ADC (a2, i1, carry)
104 LSR (a2)
105 ROR (a1)
106
107 LSR (a2)
108 ROR (a1)
109 ADD (a1, i0)
110 ADC (a2, i1, carry)
111 LSR (a2)
112 ROR (a1)
113 ADD (a1, i0)
114 ADC (a2, i1, carry)
115 LSR (a2)
116 ROR (a1)
117 LSR (a2)
118 ROR (a1)
119 break;
120 case 0x75: // 0111 0101
121 ADD (a1, i0)
122 ADC (a2, i1, carry)
123 LSR (a2)
124 ROR (a1)
125 LSR (a2)
126 ROR (a1)
127 ADD (a1, i0)
128 ADC (a2, i1, carry)
129 LSR (a2)
130 ROR (a1)
131 LSR (a2)
132 ROR (a1)
133
134 ADD (a1, i0)
135 ADC (a2, i1, carry)
136 LSR (a2)
137 ROR (a1)
138 ADD (a1, i0)
139 ADC (a2, i1, carry)
140 LSR (a2)
141 ROR (a1)
142 ADD (a1, i0)
143 ADC (a2, i1, carry)
144 LSR (a2)
145 ROR (a1)
146 LSR (a2)
147 ROR (a1)
148 break;
149 case 0x84: // 1000 0100
150 LSR (a2)
151 ROR (a1)
152 LSR (a2)
153 ROR (a1)
154 ADD (a1, i0)
155 ADC (a2, i1, carry)
156 LSR (a2)
157 ROR (a1)
158 LSR (a2)
159 ROR (a1)
160
161 LSR (a2)
162 ROR (a1)
163 LSR (a2)
164 ROR (a1)
165 LSR (a2)
166 ROR (a1)
167 ADD (a1, i0)
168 ADC (a2, i1, carry)
169 LSR (a2)
170 ROR (a1)
171 break;
172 case 0x8c: // 1000 1100
173 LSR (a2)
174 ROR (a1)
175 LSR (a2)
176 ROR (a1)
177 ADD (a1, i0)
178 ADC (a2, i1, carry)
179 LSR (a2)
180 ROR (a1)
181 ADD (a1, i0)
182 ADC (a2, i1, carry)
183 LSR (a2)
184 ROR (a1)
185
186 LSR (a2)
187 ROR (a1)
188 LSR (a2)
189 ROR (a1)
190 LSR (a2)
191 ROR (a1)
192 ADD (a1, i0)
193 ADC (a2, i1, carry)
194 LSR (a2)
195 ROR (a1)
196 break;
197 case 0x9d: // 1001 1101
198 ADD (a1, i0)
199 ADC (a2, i1, carry)
200 LSR (a2)
201 ROR (a1)
202 LSR (a2)
203 ROR (a1)
204 ADD (a1, i0)
205 ADC (a2, i1, carry)
206 LSR (a2)
207 ROR (a1)
208 ADD (a1, i0)
209 ADC (a2, i1, carry)
210 LSR (a2)
211 ROR (a1)
212
213 ADD (a1, i0)
214 ADC (a2, i1, carry)
215 LSR (a2)
216 ROR (a1)
217 LSR (a2)
218 ROR (a1)
219 LSR (a2)
220 ROR (a1)
221 ADD (a1, i0)
222 ADC (a2, i1, carry)
223 LSR (a2)
224 ROR (a1)
225 break;
226 case 0xb0: // 1011 0000
227 LSR (a2)
228 ROR (a1)
229 LSR (a2)
230 ROR (a1)
231 LSR (a2)
232 ROR (a1)
233 LSR (a2)
234 ROR (a1)
235
236 ADD (a1, i0)
237 ADC (a2, i1, carry)
238 LSR (a2)
239 ROR (a1)
240 ADD (a1, i0)
241 ADC (a2, i1, carry)
242 LSR (a2)
243 ROR (a1)
244 LSR (a2)
245 ROR (a1)
246 ADD (a1, i0)
247 ADC (a2, i1, carry)
248 LSR (a2)
249 ROR (a1)
250 }
251
252 // end MUL
253 #undef a0
254 #undef a1
255 #undef a2
256 RET
257 }
258 void g(void) {
259 // g(i, t) -> t
260 // tempvars: `x` and `_`
261 #define tmp _
262 ANDI (t, 0x07)
263 MOV (tmp, i2)
264 ANDI (tmp, 3)
265 TST (tmp)
266 #undef tmp
267 BREQ (skip)
268 SUBI (t, -8)
269 skip:
270 t = data[t];
271 /*MOV X_hi==x, data_hi
272 MOV X_lo==t, data_lo
273 ADD X_lo, t
274 ADC X_hi, zero
275 LD t, X */
276 RCALL mul(); //stores used value in in x
277 MOV (t, x)
278 RET //TODO: replace CALL/RET with IJMP?
279 };
280
281 int main(void) {
282 CLR (zero)
283 CLR (i0)
284 CLR (i1)
285 CLR (i2)
286 CLR (i3)
287 for (;;) {
288 MOV (n, i2)
289 LSL (n)
290 LSL (n)
291 #define tmp _
292 MOV (tmp, i1)
293 SWAP (tmp)
294 ANDI (tmp, 0x0f)
295 LSR (tmp)
296 LSR (tmp)
297 OR (n, tmp)
298 #undef tmp
299 MOV (s, i3)
300 LSR (s)
301 ROR (s)
302 ANDI (s, 0x80)
303 #define tmp _
304 MOV (tmp, i2)
305 LSR (tmp)
306 OR (s, tmp)
307 #undef tmp
308
309 //voice 1:
310 MOV (t, n)
311 RCALL g();
312 SWAP (t)
313 ANDI (t, 1)
314 MOV (acc, t)
315
316 //voice 2:
317 #define tmp _
318 MOV (tmp, i2)
319 LSL (tmp)
320 LSL (tmp)
321 LSL (tmp)
322 MOV (t, i1)
323 SWAP (t)
324 ANDI (t, 0xf)
325 LSR (t)
326 OR (t, tmp)
327 #undef tmp
328 EOR (t, n)
329 RCALL g();
330 LSR (t)
331 LSR (t)
332 ANDI (t, 3)
333 AND (t, s)
334 ADD (acc, t)
335
336 //voice 3:
337 MOV (Ml, i2)
338 SWAP (Ml)
339 ANDI (Ml, 0xf0)
340 LSL (Ml)
341 #define tmp _
342 MOV (tmp, i1)
343 LSR (tmp)
344 LSR (tmp)
345 LSR (tmp)
346 OR (Ml, tmp)
347 #undef tmp
348 MOV (Mh, i3)
349 SWAP (Mh)
350 ANDI (Mh, 0xf0)
351 LSL (Mh)
352 #define tmp _
353 MOV (tmp, i2)
354 LSR (tmp)
355 LSR (tmp)
356 LSR (tmp)
357 OR (Mh, tmp)
358 #undef tmp
359 RCALL mod3();
360 ADD (t, n)
361 RCALL g();
362 LSR (t)
363 LSR (t)
364 ANDI (t, 3)
365 MOV (x, s)
366 INC (x)
367 #define tmp _
368 MOV (tmp, x)
369 LSR (tmp)
370 LSR (tmp)
371 ADD (tmp, x)
372 ROR (tmp)
373 LSR (tmp)
374 ADD (tmp, x)
375 ROR (tmp)
376 LSR (tmp)
377 ADD (tmp, x)
378 ROR (tmp)
379 LSR (tmp)
380 AND (t, tmp)
381 #undef tmp
382 ADD (acc, t)
383
384 //voice 4:
385 MOV (Ml, i2)
386 SWAP (Ml)
387 ANDI (Ml, 0xf0)
388 LSL (Ml)
389 LSL (Ml)
390 #define tmp _
391 MOV (tmp, i1)
392 LSR (tmp)
393 LSR (tmp)
394 OR (Ml, tmp)
395 #undef tmp
396 MOV (Mh, i3)
397 SWAP (Mh)
398 ANDI (Mh, 0xf0)
399 LSL (Mh)
400 LSL (Mh)
401 #define tmp _
402 MOV (tmp, i2)
403 LSR (tmp)
404 LSR (tmp)
405 OR (Mh, tmp)
406 #undef tmp
407 RCALL mod3();
408 SUB (t, n)
409 NEG (t)
410 SUBI (t, -8)
411 RCALL g();
412 LSR (t)
413 ANDI (t, 3)
414 INC (s)
415 #define tmp _
416 MOV (tmp, s)
417 LSR (tmp)
418 ADD (tmp, s)
419 ROR (tmp)
420 LSR (tmp)
421 LSR (tmp)
422 ADD (tmp, s)
423 ROR (tmp)
424 ADD (tmp, s)
425 ROR (tmp)
426 LSR (tmp)
427 LSR (tmp)
428 AND (t, tmp)
429 #undef tmp
430 ADD (acc, t)
431
432 putchar(acc<<4); //TODO
433 SUBI (i0, -1)
434 ADC (i1, zero, !i0)
435 ADC (i2, zero, !i0&&!i1)
436 ADC (i3, zero, !i0&&!i1&&!i2)
437 }
438 }
Imprint / Impressum