initial import
[picodrive.git] / Pico / sound / ym2612.s
CommitLineData
cc68a136 1@ this is a rewrite of MAME's ym2612 code, in particular this is only the main sample-generatin loop.
2@ it does not seem to give much performance increase (if any at all), so don't use it if it causes trouble.
3@ - notaz, 2006
4
5.equiv SLOT1, 0
6.equiv SLOT2, 2
7.equiv SLOT3, 1
8.equiv SLOT4, 3
9.equiv SLOT_STRUCT_SIZE, 0x30
10
11.equiv TL_TAB_LEN, 0x1A00
12
13.equiv EG_ATT, 4
14.equiv EG_DEC, 3
15.equiv EG_SUS, 2
16.equiv EG_REL, 1
17.equiv EG_OFF, 0
18
19.equiv EG_SH, 16 @ 16.16 fixed point (envelope generator timing)
20.equiv EG_TIMER_OVERFLOW, (3*(1<<EG_SH)) @ envelope generator timer overflows every 3 samples (on real chip)
21.equiv LFO_SH, 25 /* 7.25 fixed point (LFO calculations) */
22
23.equiv ENV_QUIET, (2*13*256/8)/2
24
25
26@ r5=slot, r1=eg_cnt, trashes: r0,r2,r3
27@ writes output to routp, but only if vol_out changes
28.macro update_eg_phase_slot slot
29 ldrb r2, [r5,#0x17] @ state
30 mov r3, #1 @ 1ci
31 cmp r2, #1
32 blt 5f @ EG_OFF
33 beq 3f @ EG_REL
34 cmp r2, #3
35 blt 2f @ EG_SUS
36 beq 1f @ EG_DEC
37
380: @ EG_ATT
39 ldr r2, [r5,#0x20] @ eg_pack_ar (1ci)
40 mov r0, r2, lsr #24
41 mov r3, r3, lsl r0
42 sub r3, r3, #1
43 tst r1, r3
44 bne 5f @ do smth for tl problem (set on init?)
45 mov r3, r1, lsr r0
46 ldrh r0, [r5,#0x1a] @ volume, unsigned (0-1023)
47 and r3, r3, #7
48 add r3, r3, r3, lsl #1
49 mov r3, r2, lsr r3
50 and r3, r3, #7 @ shift for eg_inc calculation
51 mvn r2, r0
52 mov r2, r2, lsl r3
53 add r0, r0, r2, asr #5
54 cmp r0, #0 @ if (volume <= MIN_ATT_INDEX)
55 movle r3, #EG_DEC
56 strleb r3, [r5,#0x17] @ state
57 movle r0, #0
58 b 4f
59
601: @ EG_DEC
61 ldr r2, [r5,#0x24] @ eg_pack_d1r (1ci)
62 mov r0, r2, lsr #24
63 mov r3, r3, lsl r0
64 sub r3, r3, #1
65 tst r1, r3
66 bne 5f @ do smth for tl problem (set on init?)
67 mov r3, r1, lsr r0
68 ldrh r0, [r5,#0x1a] @ volume
69 and r3, r3, #7
70 add r3, r3, r3, lsl #1
71 mov r3, r2, lsr r3
72 and r3, r3, #7 @ shift for eg_inc calculation
73 mov r2, #1
74 mov r3, r2, lsl r3
75 ldr r2, [r5,#0x1c] @ sl (can be 16bit?)
76 add r0, r0, r3, asr #1
77 cmp r0, r2 @ if ( volume >= (INT32) SLOT->sl )
78 movge r3, #EG_SUS
79 strgeb r3, [r5,#0x17] @ state
80 b 4f
81
822: @ EG_SUS
83 ldr r2, [r5,#0x28] @ eg_pack_d2r (1ci)
84 mov r0, r2, lsr #24
85 mov r3, r3, lsl r0
86 sub r3, r3, #1
87 tst r1, r3
88 bne 5f @ do smth for tl problem (set on init?)
89 mov r3, r1, lsr r0
90 ldrh r0, [r5,#0x1a] @ volume
91 and r3, r3, #7
92 add r3, r3, r3, lsl #1
93 mov r3, r2, lsr r3
94 and r3, r3, #7 @ shift for eg_inc calculation
95 mov r2, #1
96 mov r3, r2, lsl r3
97 add r0, r0, r3, asr #1
98 mov r2, #1024
99 sub r2, r2, #1 @ r2 = MAX_ATT_INDEX
100 cmp r0, r2 @ if ( volume >= MAX_ATT_INDEX )
101 movge r0, r2
102 b 4f
103
1043: @ EG_REL
105 ldr r2, [r5,#0x2c] @ eg_pack_rr (1ci)
106 mov r0, r2, lsr #24
107 mov r3, r3, lsl r0
108 sub r3, r3, #1
109 tst r1, r3
110 bne 5f @ do smth for tl problem (set on init?)
111 mov r3, r1, lsr r0
112 ldrh r0, [r5,#0x1a] @ volume
113 and r3, r3, #7
114 add r3, r3, r3, lsl #1
115 mov r3, r2, lsr r3
116 and r3, r3, #7 @ shift for eg_inc calculation
117 mov r2, #1
118 mov r3, r2, lsl r3
119 add r0, r0, r3, asr #1
120 mov r2, #1024
121 sub r2, r2, #1 @ r2 = MAX_ATT_INDEX
122 cmp r0, r2 @ if ( volume >= MAX_ATT_INDEX )
123 movge r0, r2
124 movge r3, #EG_OFF
125 strgeb r3, [r5,#0x17] @ state
126
1274:
128 ldrh r3, [r5,#0x18] @ tl
129 strh r0, [r5,#0x1a] @ volume
130.if \slot == SLOT1
131 mov r6, r6, lsr #16
132 add r0, r0, r3
133 orr r6, r0, r6, lsl #16
134.elseif \slot == SLOT2
135 mov r6, r6, lsl #16
136 add r0, r0, r3
137 mov r0, r0, lsl #16
138 orr r6, r0, r6, lsr #16
139.elseif \slot == SLOT3
140 mov r7, r7, lsr #16
141 add r0, r0, r3
142 orr r7, r0, r7, lsl #16
143.elseif \slot == SLOT4
144 mov r7, r7, lsl #16
145 add r0, r0, r3
146 mov r0, r0, lsl #16
147 orr r7, r0, r7, lsr #16
148.endif
149
1505:
151.endm
152
153
154@ r12=lfo_ampm[31:16], r1=lfo_cnt_old, r2=lfo_cnt, r3=scratch
155.macro advance_lfo_m
156 mov r2, r2, lsr #LFO_SH
157 cmp r2, r1, lsr #LFO_SH
158 beq 0f
159 and r3, r2, #0x3f
160 cmp r2, #0x40
161 rsbge r3, r3, #0x3f
162 bic r12,r12, #0xff000000 @ lfo_ampm &= 0xff
163 orr r12,r12, r3, lsl #1+24
164
165 mov r2, r2, lsr #2
166 cmp r2, r1, lsr #LFO_SH+2
167 bicne r12,r12, #0xff0000
168 orrne r12,r12, r2, lsl #16
169
1700:
171.endm
172
173
174@ result goes to r1, trashes r2
175.macro make_eg_out slot
176 tst r12, #8
177 tstne r12, #(1<<(\slot+8))
178.if \slot == SLOT1
179 mov r1, r6, lsl #16
180 mov r1, r1, lsr #17
181.elseif \slot == SLOT2
182 mov r1, r6, lsr #17
183.elseif \slot == SLOT3
184 mov r1, r7, lsl #16
185 mov r1, r1, lsr #17
186.elseif \slot == SLOT4
187 mov r1, r7, lsr #17
188.endif
189 andne r2, r12, #0xc0
190 movne r2, r2, lsr #6
191 addne r2, r2, #24
192 addne r1, r1, r12, lsr r2
193.endm
194
195
196.macro lookup_tl r
197 tst \r, #0x100
198 eorne \r, \r, #0xff @ if (sin & 0x100) sin = 0xff - (sin&0xff);
199 tst \r, #0x200
200 and \r, \r, #0xff
201 orr \r, \r, r1, lsl #8
202 mov \r, \r, lsl #1
203 ldrh \r, [r3, \r] @ 2ci if ne
204 rsbne \r, \r, #0
205.endm
206
207
208@ lr=context, r12=pack (stereo, lastchan, disabled, lfo_enabled | pan_r, pan_l, ams[2] | AMmasks[4] | FB[4] | lfo_ampm[16])
209@ r0-r2=scratch, r3=sin_tab, r5=scratch, r6-r7=vol_out[4], r10=op1_out
210.macro upd_algo0_m
211
212 @ SLOT3
213 make_eg_out SLOT3
214 cmp r1, #ENV_QUIET
215 movcs r0, #0
216 bcs 0f
217 ldr r2, [lr, #0x18]
218 ldr r0, [lr, #0x38] @ mem (signed)
219 mov r2, r2, lsr #16
220 add r0, r2, r0, lsr #1
221 lookup_tl r0 @ r0=c2
222
2230:
224
225 @ SLOT4
226 make_eg_out SLOT4
227 cmp r1, #ENV_QUIET
228 movcs r0, #0
229 bcs 1f
230 ldr r2, [lr, #0x1c]
231 mov r0, r0, lsr #1
232 add r0, r0, r2, lsr #16
233 lookup_tl r0 @ r0=output smp
234
2351:
236 @ SLOT2
237 make_eg_out SLOT2
238 cmp r1, #ENV_QUIET
239 movcs r2, #0
240 bcs 2f
241 ldr r2, [lr, #0x14] @ 1ci
242 mov r5, r10, lsr #17
243 add r2, r5, r2, lsr #16
244 lookup_tl r2 @ r2=mem
245
2462:
247 str r2, [lr, #0x38] @ mem
248.endm
249
250
251.macro upd_algo1_m
252
253 @ SLOT3
254 make_eg_out SLOT3
255 cmp r1, #ENV_QUIET
256 movcs r0, #0
257 bcs 0f
258 ldr r2, [lr, #0x18]
259 ldr r0, [lr, #0x38] @ mem (signed)
260 mov r2, r2, lsr #16
261 add r0, r2, r0, lsr #1
262 lookup_tl r0 @ r0=c2
263
2640:
265 @ SLOT4
266 make_eg_out SLOT4
267 cmp r1, #ENV_QUIET
268 movcs r0, #0
269 bcs 1f
270 ldr r2, [lr, #0x1c]
271 mov r0, r0, lsr #1
272 add r0, r0, r2, lsr #16
273 lookup_tl r0 @ r0=output smp
274
2751:
276 @ SLOT2
277 make_eg_out SLOT2
278 cmp r1, #ENV_QUIET
279 movcs r2, #0
280 bcs 2f
281 ldr r2, [lr, #0x14] @ 1ci
282 mov r2, r2, lsr #16
283 lookup_tl r2 @ r2=mem
284
2852:
286 add r2, r2, r10, asr #16
287 str r2, [lr, #0x38]
288.endm
289
290
291.macro upd_algo2_m
292
293 @ SLOT3
294 make_eg_out SLOT3
295 cmp r1, #ENV_QUIET
296 movcs r0, #0
297 bcs 0f
298 ldr r2, [lr, #0x18]
299 ldr r0, [lr, #0x38] @ mem (signed)
300 mov r2, r2, lsr #16
301 add r0, r2, r0, lsr #1
302 lookup_tl r0 @ r0=c2
303
3040:
305 add r0, r0, r10, asr #16
306
307 @ SLOT4
308 make_eg_out SLOT4
309 cmp r1, #ENV_QUIET
310 movcs r0, #0
311 bcs 1f
312 ldr r2, [lr, #0x1c]
313 mov r0, r0, lsr #1
314 add r0, r0, r2, lsr #16
315 lookup_tl r0 @ r0=output smp
316
3171:
318 @ SLOT2
319 make_eg_out SLOT2
320 cmp r1, #ENV_QUIET
321 movcs r2, #0
322 bcs 2f
323 ldr r2, [lr, #0x14]
324 mov r2, r2, lsr #16 @ 1ci
325 lookup_tl r2 @ r2=mem
326
3272:
328 str r2, [lr, #0x38] @ mem
329.endm
330
331
332.macro upd_algo3_m
333
334 @ SLOT3
335 make_eg_out SLOT3
336 cmp r1, #ENV_QUIET
337 ldr r2, [lr, #0x38] @ mem (for future)
338 movcs r0, r2
339 bcs 0f
340 ldr r0, [lr, #0x18] @ 1ci
341 mov r0, r0, lsr #16
342 lookup_tl r0 @ r0=c2
343
3440:
345 add r0, r0, r2
346
347 @ SLOT4
348 make_eg_out SLOT4
349 cmp r1, #ENV_QUIET
350 movcs r0, #0
351 bcs 1f
352 ldr r2, [lr, #0x1c]
353 mov r0, r0, lsr #1
354 add r0, r0, r2, lsr #16
355 lookup_tl r0 @ r0=output smp
356
3571:
358 @ SLOT2
359 make_eg_out SLOT2
360 cmp r1, #ENV_QUIET
361 movcs r2, #0
362 bcs 2f
363 ldr r2, [lr, #0x14]
364 mov r5, r10, lsr #17
365 add r2, r5, r2, lsr #16
366 lookup_tl r2 @ r2=mem
367
3682:
369 str r2, [lr, #0x38] @ mem
370.endm
371
372
373.macro upd_algo4_m
374
375 @ SLOT3
376 make_eg_out SLOT3
377 cmp r1, #ENV_QUIET
378 movcs r0, #0
379 bcs 0f
380 ldr r0, [lr, #0x18]
381 mov r0, r0, lsr #16 @ 1ci
382 lookup_tl r0 @ r0=c2
383
3840:
385 @ SLOT4
386 make_eg_out SLOT4
387 cmp r1, #ENV_QUIET
388 movcs r0, #0
389 bcs 1f
390 ldr r2, [lr, #0x1c]
391 mov r0, r0, lsr #1
392 add r0, r0, r2, lsr #16
393 lookup_tl r0 @ r0=output smp
394
3951:
396 @ SLOT2
397 make_eg_out SLOT2
398 cmp r1, #ENV_QUIET
399 bcs 2f
400 ldr r2, [lr, #0x14]
401 mov r5, r10, lsr #17
402 add r2, r5, r2, lsr #16
403 lookup_tl r2
404 add r0, r0, r2 @ add to smp
405
4062:
407.endm
408
409
410.macro upd_algo5_m
411
412 @ SLOT3
413 make_eg_out SLOT3
414 cmp r1, #ENV_QUIET
415 movcs r0, #0
416 bcs 0f
417 ldr r2, [lr, #0x18]
418 ldr r0, [lr, #0x38] @ mem (signed)
419 mov r2, r2, lsr #16
420 add r0, r2, r0, lsr #1
421 lookup_tl r0 @ r0=output smp
422
4230:
424 @ SLOT4
425 make_eg_out SLOT4
426 cmp r1, #ENV_QUIET
427 bcs 1f
428 ldr r2, [lr, #0x1c]
429 mov r5, r10, lsr #17
430 add r2, r5, r2, lsr #16
431 lookup_tl r2
432 add r0, r0, r2 @ add to smp
433
4341: @ SLOT2
435 make_eg_out SLOT2
436 cmp r1, #ENV_QUIET
437 bcs 2f
438 ldr r2, [lr, #0x14]
439 mov r5, r10, lsr #17
440 add r2, r5, r2, lsr #16
441 lookup_tl r2
442 add r0, r0, r2 @ add to smp
443
4442:
445 mov r1, r10, asr #16
446 str r1, [lr, #0x38] @ mem
447.endm
448
449
450.macro upd_algo6_m
451
452 @ SLOT3
453 make_eg_out SLOT3
454 cmp r1, #ENV_QUIET
455 movcs r0, #0
456 bcs 0f
457 ldr r0, [lr, #0x18]
458 mov r0, r0, lsr #16 @ 1ci
459 lookup_tl r0 @ r0=output smp
460
4610:
462 @ SLOT4
463 make_eg_out SLOT4
464 cmp r1, #ENV_QUIET
465 bcs 1f
466 ldr r2, [lr, #0x1c]
467 mov r2, r2, lsr #16 @ 1ci
468 lookup_tl r2
469 add r0, r0, r2 @ add to smp
470
4711: @ SLOT2
472 make_eg_out SLOT2
473 cmp r1, #ENV_QUIET
474 bcs 2f
475 ldr r2, [lr, #0x14]
476 mov r5, r10, lsr #17
477 add r2, r5, r2, lsr #16
478 lookup_tl r2
479 add r0, r0, r2 @ add to smp
480
4812:
482.endm
483
484
485.macro upd_algo7_m
486
487 @ SLOT3
488 make_eg_out SLOT3
489 cmp r1, #ENV_QUIET
490 movcs r0, #0
491 bcs 0f
492 ldr r0, [lr, #0x18]
493 mov r0, r0, lsr #16 @ 1ci
494 lookup_tl r0 @ r0=output smp
495
4960:
497 add r0, r0, r10, asr #16
498
499 @ SLOT4
500 make_eg_out SLOT4
501 cmp r1, #ENV_QUIET
502 bcs 1f
503 ldr r2, [lr, #0x1c]
504 mov r2, r2, lsr #16 @ 1ci
505 lookup_tl r2
506 add r0, r0, r2 @ add to smp
507
5081: @ SLOT2
509 make_eg_out SLOT2
510 cmp r1, #ENV_QUIET
511 bcs 2f
512 ldr r2, [lr, #0x14]
513 mov r2, r2, lsr #16 @ 1ci
514 lookup_tl r2
515 add r0, r0, r2 @ add to smp
516
5172:
518.endm
519
520
521.macro upd_slot1_m
522
523 make_eg_out SLOT1
524 cmp r1, #ENV_QUIET
525 movcs r10, r10, lsl #16 @ ct->op1_out <<= 16; // op1_out0 = op1_out1; op1_out1 = 0;
526 bcs 0f
527 ands r2, r12, #0xf000
528 moveq r0, #0
529 movne r2, r2, lsr #12
530 addne r0, r10, r10, lsl #16
531 movne r0, r0, asr #16
532 movne r0, r0, lsl r2
533
534 ldr r2, [lr, #0x10]
535 mov r0, r0, lsr #16
536 add r0, r0, r2, lsr #16
537 lookup_tl r0
538 mov r10,r10,lsl #16 @ ct->op1_out <<= 16;
539 mov r0, r0, lsl #16
540 orr r10,r10, r0, lsr #16
541
5420:
543.endm
544
545
546/*
547.global update_eg_phase @ FM_SLOT *SLOT, UINT32 eg_cnt
548
549update_eg_phase:
550 stmfd sp!, {r5,r6}
551 mov r5, r0 @ slot
552 ldrh r3, [r5,#0x18] @ tl
553 ldrh r6, [r5,#0x1a] @ volume
554 add r6, r6, r3
555 update_eg_phase_slot SLOT1
556 mov r0, r6
557 ldmfd sp!, {r5,r6}
558 bx lr
559.pool
560
561
562.global advance_lfo @ int lfo_ampm, UINT32 lfo_cnt_old, UINT32 lfo_cnt
563
564advance_lfo:
565 mov r12, r0, lsl #16
566 advance_lfo_m
567 mov r0, r12, lsr #16
568 bx lr
569.pool
570
571
572.global upd_algo0 @ chan_rend_context *c
573upd_algo0:
574 stmfd sp!, {r4-r10,lr}
575 mov lr, r0
576
577 ldr r3, =ym_sin_tab
578 ldr r5, =ym_tl_tab
579 ldmia lr, {r6-r7}
580 ldr r10, [lr, #0x54]
581 ldr r12, [lr, #0x4c]
582
583 upd_algo0_m
584
585 ldmfd sp!, {r4-r10,pc}
586.pool
587
588
589.global upd_algo1 @ chan_rend_context *c
590upd_algo1:
591 stmfd sp!, {r4-r10,lr}
592 mov lr, r0
593
594 ldr r3, =ym_sin_tab
595 ldr r5, =ym_tl_tab
596 ldmia lr, {r6-r7}
597 ldr r10, [lr, #0x54]
598 ldr r12, [lr, #0x4c]
599
600 upd_algo1_m
601
602 ldmfd sp!, {r4-r10,pc}
603.pool
604
605
606.global upd_algo2 @ chan_rend_context *c
607upd_algo2:
608 stmfd sp!, {r4-r10,lr}
609 mov lr, r0
610
611 ldr r3, =ym_sin_tab
612 ldr r5, =ym_tl_tab
613 ldmia lr, {r6-r7}
614 ldr r10, [lr, #0x54]
615 ldr r12, [lr, #0x4c]
616
617 upd_algo2_m
618
619 ldmfd sp!, {r4-r10,pc}
620.pool
621
622
623.global upd_algo3 @ chan_rend_context *c
624upd_algo3:
625 stmfd sp!, {r4-r10,lr}
626 mov lr, r0
627
628 ldr r3, =ym_sin_tab
629 ldr r5, =ym_tl_tab
630 ldmia lr, {r6-r7}
631 ldr r10, [lr, #0x54]
632 ldr r12, [lr, #0x4c]
633
634 upd_algo3_m
635
636 ldmfd sp!, {r4-r10,pc}
637.pool
638
639
640.global upd_algo4 @ chan_rend_context *c
641upd_algo4:
642 stmfd sp!, {r4-r10,lr}
643 mov lr, r0
644
645 ldr r3, =ym_sin_tab
646 ldr r5, =ym_tl_tab
647 ldmia lr, {r6-r7}
648 ldr r10, [lr, #0x54]
649 ldr r12, [lr, #0x4c]
650
651 upd_algo4_m
652
653 ldmfd sp!, {r4-r10,pc}
654.pool
655
656
657.global upd_algo5 @ chan_rend_context *c
658upd_algo5:
659 stmfd sp!, {r4-r10,lr}
660 mov lr, r0
661
662 ldr r3, =ym_sin_tab
663 ldr r5, =ym_tl_tab
664 ldmia lr, {r6-r7}
665 ldr r10, [lr, #0x54]
666 ldr r12, [lr, #0x4c]
667
668 upd_algo5_m
669
670 ldmfd sp!, {r4-r10,pc}
671.pool
672
673
674.global upd_algo6 @ chan_rend_context *c
675upd_algo6:
676 stmfd sp!, {r4-r10,lr}
677 mov lr, r0
678
679 ldr r3, =ym_sin_tab
680 ldr r5, =ym_tl_tab
681 ldmia lr, {r6-r7}
682 ldr r10, [lr, #0x54]
683 ldr r12, [lr, #0x4c]
684
685 upd_algo6_m
686
687 ldmfd sp!, {r4-r10,pc}
688.pool
689
690
691.global upd_algo7 @ chan_rend_context *c
692upd_algo7:
693 stmfd sp!, {r4-r10,lr}
694 mov lr, r0
695
696 ldr r3, =ym_sin_tab
697 ldr r5, =ym_tl_tab
698 ldmia lr, {r6-r7}
699 ldr r10, [lr, #0x54]
700 ldr r12, [lr, #0x4c]
701
702 upd_algo7_m
703
704 ldmfd sp!, {r4-r10,pc}
705.pool
706
707
708.global upd_slot1 @ chan_rend_context *c
709upd_slot1:
710 stmfd sp!, {r4-r10,lr}
711 mov lr, r0
712
713 ldr r3, =ym_sin_tab
714 ldr r5, =ym_tl_tab
715 ldmia lr, {r6-r7}
716 ldr r10, [lr, #0x54]
717 ldr r12, [lr, #0x4c]
718
719 upd_slot1_m
720 str r10, [lr, #0x38]
721
722 ldmfd sp!, {r4-r10,pc}
723.pool
724*/
725
726
727@ lr=context, r12=pack (stereo, lastchan, disabled, lfo_enabled | pan_r, pan_l, ams[2] | AMmasks[4] | FB[4] | lfo_ampm[16])
728@ r0-r2=scratch, r3=sin_tab/scratch, r4=(length<<8)|algo, r5=tl_tab/slot,
729@ r6-r7=vol_out[4], r8=eg_timer, r9=eg_timer_add[31:16], r10=op1_out, r11=buffer
730.global chan_render_loop @ chan_rend_context *ct, int *buffer, int length
731
732chan_render_loop:
733 stmfd sp!, {r4-r11,lr}
734 mov lr, r0
735 mov r4, r2, lsl #8 @ no more 24 bits here
736 ldr r12, [lr, #0x4c]
737 ldr r0, [lr, #0x50]
738 mov r11, r1
739 and r0, r0, #7
740 orr r4, r4, r0 @ (length<<8)|algo
741 add r0, lr, #0x44
742 ldmia r0, {r8,r9} @ eg_timer, eg_timer_add
743 ldr r10, [lr, #0x54] @ op1_out
744 ldmia lr, {r6,r7} @ load volumes
745
746 tst r12, #8 @ lfo?
747 beq crl_loop
748
749crl_loop_lfo:
750 add r0, lr, #0x30
751 ldmia r0, {r1,r2}
752 add r2, r2, r1
753 str r2, [lr, #0x30]
754 @ r12=lfo_ampm[31:16], r1=lfo_cnt_old, r2=lfo_cnt
755 advance_lfo_m
756
757crl_loop:
758 subs r4, r4, #0x100
759 bmi crl_loop_end
760
761 @ -- EG --
762 add r8, r8, r9
763 cmp r8, #EG_TIMER_OVERFLOW
764 bcc eg_done
765 add r0, lr, #0x3c
766 ldmia r0, {r1,r5} @ eg_cnt, CH
767eg_loop:
768 sub r8, r8, #EG_TIMER_OVERFLOW
769 add r1, r1, #1
770 @ SLOT1 (0)
771 @ r5=slot, r1=eg_cnt, trashes: r0,r2,r3
772 update_eg_phase_slot SLOT1
773 add r5, r5, #SLOT_STRUCT_SIZE*2 @ SLOT2 (2)
774 update_eg_phase_slot SLOT2
775 sub r5, r5, #SLOT_STRUCT_SIZE @ SLOT3 (1)
776 update_eg_phase_slot SLOT3
777 add r5, r5, #SLOT_STRUCT_SIZE*2 @ SLOT4 (3)
778 update_eg_phase_slot SLOT4
779
780 cmp r8, #EG_TIMER_OVERFLOW
781 subcs r5, r5, #SLOT_STRUCT_SIZE*3
782 bcs eg_loop
783 str r1, [lr, #0x3c]
784
785eg_done:
786
787 @ -- disabled? --
788 and r0, r12, #0xC
789 cmp r0, #0xC
790 beq crl_loop_lfo
791 cmp r0, #0x4
792 beq crl_loop
793
794 @ -- SLOT1 --
795 ldr r3, =ym_tl_tab
796
797 @ lr=context, r12=pack (stereo, lastchan, disabled, lfo_enabled | pan_r, pan_l, ams[2] | AMmasks[4] | FB[4] | lfo_ampm[16])
798 @ r0-r2=scratch, r3=tl_tab, r5=scratch, r6-r7=vol_out[4], r10=op1_out
799 upd_slot1_m
800
801 @ -- SLOT2+ --
802 and r0, r4, #7
803 ldr pc, [pc, r0, lsl #2]
804 nop
805 .word crl_algo0
806 .word crl_algo1
807 .word crl_algo2
808 .word crl_algo3
809 .word crl_algo4
810 .word crl_algo5
811 .word crl_algo6
812 .word crl_algo7
813 .pool
814
815crl_algo0:
816 upd_algo0_m
817 b crl_algo_done
818 .pool
819
820crl_algo1:
821 upd_algo1_m
822 b crl_algo_done
823 .pool
824
825crl_algo2:
826 upd_algo2_m
827 b crl_algo_done
828 .pool
829
830crl_algo3:
831 upd_algo3_m
832 b crl_algo_done
833 .pool
834
835crl_algo4:
836 upd_algo4_m
837 b crl_algo_done
838 .pool
839
840crl_algo5:
841 upd_algo5_m
842 b crl_algo_done
843 .pool
844
845crl_algo6:
846 upd_algo6_m
847 b crl_algo_done
848 .pool
849
850crl_algo7:
851 upd_algo7_m
852 .pool
853
854
855crl_algo_done:
856 @ -- WRITE SAMPLE --
857 tst r0, r0
858 beq ctl_sample_skip
859 tst r12, #1
860 beq ctl_sample_mono
861
862 tst r12, #0x20 @ L
863 ldrne r1, [r11]
864 addeq r11, r11, #4
865 addne r1, r0, r1
866 strne r1, [r11], #4
867 tst r12, #0x10 @ R
868 ldrne r1, [r11]
869 addeq r11, r11, #4
870 addne r1, r0, r1
871 strne r1, [r11], #4
872 b crl_do_phase
873
874ctl_sample_skip:
875 and r1, r12, #1
876 add r1, r1, #1
877 add r11,r11, r1, lsl #2
878 b crl_do_phase
879
880ctl_sample_mono:
881 ldr r1, [r11]
882 add r1, r0, r1
883 str r1, [r11], #4
884
885crl_do_phase:
886 @ -- PHASE UPDATE --
887 add r5, lr, #0x10
888 ldmia r5, {r0-r1}
889 add r5, lr, #0x20
890 ldmia r5, {r2-r3}
891 add r5, lr, #0x10
892 add r0, r0, r2
893 add r1, r1, r3
894 stmia r5!,{r0-r1}
895 ldmia r5, {r0-r1}
896 add r5, lr, #0x28
897 ldmia r5, {r2-r3}
898 add r5, lr, #0x18
899 add r0, r0, r2
900 add r1, r1, r3
901 stmia r5, {r0-r1}
902
903 tst r12, #8
904 bne crl_loop_lfo
905 b crl_loop
906
907
908crl_loop_end:
909 str r8, [lr, #0x44] @ eg_timer
910 str r12, [lr, #0x4c] @ pack (for lfo_ampm)
911 str r10, [lr, #0x54] @ op1_out
912 ldmfd sp!, {r4-r11,pc}
913
914.pool
915