-
Notifications
You must be signed in to change notification settings - Fork 2
/
Copy pathnsfDriver.cm
189 lines (172 loc) · 3.71 KB
/
nsfDriver.cm
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
//@9900
extern const1 w64notelo[64]; //w64
extern const1 w64notehi[64];//data|0x40
extern const1 sawnotelo[64]; //saw
extern const1 sawnotehi[64];
//@9A00
extern const1 sqrnotelo[64]; //sqr1~3
extern const1 sqrnotehi[64];
extern const1 divnotelo[64]; //REC1~6,tri
extern const1 divnotehi[64];
//@9B00
extern const1 fmnote[128]; //fm1~6
extern const1 fmoct[128];
//@9C00
extern const1 fx16notelo[128]; //fx1~8
extern const1 fx16notemid[128];
//@9D00
extern const1 fx16notehi[128];//data|0xF0
extern const1 fx32notelo[128];
//@9E00
extern const1 fx32notemid[128];
extern const1 fx32notehi[128];//data|0xE0
//@9F00
extern const1 startbank[256]=<weak>{};
//@F0
var1 apu,songnum,state,count,tempomul,tempodiv,ralo,rahi,bank,loopbank,loopralo,looprahi;
//@9004
const1 fdsinitreg[8]={ //4080~4087
0x80,0x00,0x00,0xC0,
0x80,0x00,0x00,0x80,
};
//@9014
const1 cpuinitreg[20]={ //4000~4013
0x30,0x00,0x00,0x07,
0x30,0x00,0x00,0x07,
0x00,0x00,0x00,0x00,
0x30,0x00,0x00,0x00,
0x0F,0x40,0x40,0x00,
};
const1 mmc5initreg[8]={ //5000~5007
0x30,0x00,0x00,0x00,
0x30,0x00,0x00,0x00,
};
//@9031
#include "./nsfDriver/CPU.ah"
#include "./nsfDriver/MMC5.ah"
#include "./nsfDriver/VRC6.ah"
#include "./nsfDriver/FDS.ah"
#include "./nsfDriver/S5B.ah"
#include "./nsfDriver/VRC7.ah"
#include "./nsfDriver/N163.ah"
\nsf_:init(A){
apu=X;
songnum=A;
//stop sound generators
apustatus=Y=0x00; //2A03 kill sound
mmc5status=0x00; //MMC5 kill sound
rec6hiperiod=rec5hiperiod=0x00; //VRC6 kill sound
sawhiperiod=0x00;
fdsstatus=0x03;
w64hifreq=0xC0; //FDS kill sound
s5b.s5bstate=0x3F; //S5B kill sound
n163.fx8vol=0x00; //N163 kill sound
for (X=fm9oct;X>=fm1oct;--X){ //VRC7 kill sound
vrc7.X=0x00;
}
//init CPU
for (X=0x13;X>=0;--X){
rec1vol[X]=cpuinitreg[X];
}
apustatus=0x0F;
apuirq=0xC0;
noiselen=0x00;
//init MMC5
for (X=0x07;X>=0;--X){
rec3vol[X]=mmc5initreg[X];
}
mmc5status=0x03;
//init VRC6
vrc6test=0x00;
rec6loperiod=rec5loperiod=0x00;
rec6vol=rec5vol=0x00;
sawloperiod=0x00;
sawvol=0x00;
//init FDS
w64envspd=0x00;
for (X=0x07;X>=0;--X){
w64vol[X]=fdsinitreg[X];//last([0]) is 0x80
}
w64en=0x80;//A
A=Y;
for (X=0x3F;X>=0;--X){
w64wave[X]=0x00;//A
}
w64en=0x00;
for (X=0x1F;X>=0;--X){
wmodwave=0x00;
}
//init S5B
for (X=senvwave;X>=sqr1vol;--X){
s5b.X=0x00;
}
for (--X;X>=0;--X){
s5b.X=0x00;
}
//init VRC7
for (X=fm9freq;X>=0;--X){
vrc7.X=0x00;
}
A=0x0F;
for (X=fm9vol;X>=fm1vol;--X){
vrc7.X=0x0F;//A
}
//init N163
n163addr=fxwavei;
for (X=0x7E;X>=0;--X){
n163data=0x00;
}
//init system
count=4; //init delay count
state=-1; //play delay mode
tempodiv=tempomul=1; //init tempo to 450*mul/div (dummy)
A=startbank[songnum];
if (!A){
state=0; //refuse to execute null songs
}
nsfbank8=bank=A
ralo=0xFF;
rahi=0x7F;
}
\nsf_:play(){
if (!(A=state)) return; //stop playing when state=0
if (A<0){
if (count){
--count; //frame delay
return;
}
state=1; //ready to play
}
ifcs (count=A=count-tempomul) return; //tempo adapter
count=A+tempodiv;
PUSH(rahi); //push return address for jump
PUSH(ralo);
} //this "return" does jump
setloop(){ //set loop stamp, call this on the beginning of looping row
loopbank=bank;
loopralo=POP();
looprahi=A=POP();
PUSH(A);
PUSH(loopralo);
}
nextloop(){ //terminate current row, the next row will be the row which called setloop()
nsfbank8=bank=loopbank
ralo=loopralo;
rahi=looprahi;
POP();
POP();
}
nextpage(){ //terminate current row, the next row will be the start of next page
nsfbank8=++bank;
ralo=0xFF;
rahi=0x7F;
POP();
POP();
}
endsong(){ //terminate current row, and terminate the song
state=0;
}//#no return
endrow(){ //terminate current row, the next row is right after this call
ralo=POP();
rahi=POP();
}