…Show last 1390 lines
61
#define PI2 ((float)(2.0f * PI))
63
//Silence value?
65#define Silence 0x1FF
66
//Sign bit, disable mask and extension to 16-bit value! 3-bits exponent and 8-bits mantissa(which becomes 10-bits during lookup of Exponential data)
68//Sign bit itself!
69#define SIGNBIT 0x8000
70//Sign mask for preventing overflow
71#define SIGNMASK 0x7FFF
72
//Convert cents to samples to increase (instead of 1 sample/sample). Floating point number (between 0.0+ usually?) Use this as a counter for the current samples (1.1+1.1..., so keep the rest value (1,1,1,...,0,1,1,1,...))
74//The same applies to absolute and relative timecents (with absolute referring to 1 second intervals (framerate samples) and relative to the absolute value)
75#define cents2samplesfactor(cents) pow(2, ((cents) / 1200))
76//Convert to samples (not entire numbers, so keep them counted)!
77
//extern void set_port_write_redirector (uint16_t startport, uint16_t endport, void *callback);
79//extern void set_port_read_redirector (uint16_t startport, uint16_t endport, void *callback);
80
uint16_t baseport = 0x388; //Adlib address(w)/status(r) port, +1=Data port (write only)
82
//Sample based information!
84DOUBLE usesamplerate = 0.0; //The sample rate to use for output!
85DOUBLE adlib_soundtick = 0.0; //The length of a sample in ns!
86//The length of a sample step:
87#ifdef IS_LONGDOUBLE
88#define adlib_sampleLength (1.0L / (14318180.0L / 288.0L))
89#else
90#define adlib_sampleLength (1.0 / (14318180.0 / 288.0))
91#endif
92
//Counter info
94float counter80 = 0.0f, counter320 = 0.0f; //Counter ticks!
95byte timer80=0, timer320=0; //Timer variables for current timer ticks!
96
//Registers itself
98byte adlibregmem[0xFF], adlibaddr = 0;
99
word OPL2_ExpTable[0x100], OPL2_LogSinTable[0x100]; //The OPL2 Exponentional and Log-Sin tables!
101DOUBLE OPL2_ExponentialLookup[0x10000]; //Full exponential lookup table!
102float OPL2_ExponentialLookup2[0x10000]; //The full exponential lookup table, converted to -1 to +1 range!
103float OPL2_TremoloVibratoLookup[0x10000]; //The full tremolo/vibrato lookup table!
104word OPL2_TremoloVibratoLookupPhase[0x10000]; //The full tremolo/vibrato lookup table!
105
byte adliboperators[2][0x10] = { //Groupings of 22 registers! (20,40,60,80,E0)
107	{ 0x00, 0x01, 0x02, 0x08, 0x09, 0x0A, 0x10, 0x11, 0x12,255,255,255,255,255,255 },
108	{ 0x03, 0x04, 0x05, 0x0B, 0x0C, 0x0D, 0x13, 0x14, 0x15,255,255,255,255,255,255 }
109};
110
byte adliboperatorsreverse[0x20] = { 0, 1, 2, 0, 1, 2, 255, 255, 3, 4, 5, 3, 4, 5, 255, 255, 6, 7, 8, 6, 7, 8,255,255,255,255,255,255,255,255,255,255}; //Channel lookup of adlib operators!
112byte adliboperatorsreversekeyon[0x20] = { 1, 1, 1, 2, 2, 2, 255, 255, 1, 1, 1, 2, 2, 2, 255, 255, 1, 1, 1, 2, 2, 2,0,0,0,0,0,0,0,0,0,0}; //Modulator/carrier lookup of adlib operators in the keyon bits!
113
static const float feedbacklookup[8] = { 0, (float)(37.5), (float)(75), (float)(150), (float)(300), (float)600, (float)(1200), (float)(1200*2.0) }; //The feedback to use from opl3emu! Seems to be half a sinus wave per number!
115float feedbacklookup2[8]; //Actual feedback lookup value!
116
byte wavemask = 0; //Wave select mask!
118
byte NTS; //NTS bit!
120byte CSMMode; //CSM mode enabled?
121
SOUNDDOUBLEBUFFER adlib_soundbuffer; //Our sound buffer for rendering!
123
#ifdef WAV_ADLIB
125WAVEFILE *adlibout = NULL;
126#endif
127
typedef struct
129{
130	word m_fnum, m_block; //Our settings!
131	uint8_t keyon;
132	uint8_t synthmode; //What synthesizer mode (1=Additive synthesis, 0=Frequency modulation)
133	float feedback; //The feedback strength of the modulator signal.
134} ADLIBCHANNEL; //A channel!
135
typedef struct {
137	//Effects
138	word outputlevel; //(RAW) output level!
139	word volenv; //(RAW) volume level!
140	byte m_ar, m_dr, m_sl, m_rr; //Four rates and levels!
141	uint_32 m_counter; //Counter for the volume envelope!
142	word m_env;
143	word m_ksl, m_kslAdd, m_ksr; //Various key setttings regarding pitch&envelope!
144	byte ReleaseImmediately; //Release even when the note is still turned on?
145	word m_kslAdd2; //Translated value of m_ksl!
146
	//Volume envelope
148	uint8_t volenvstatus; //Envelope status and raw volume envelope value(0-64)
149	word gain; //The gain gotten from the volume envelopes!
150	word rawgain; //The gain without main volume control!
151
	byte vibrato, tremolo; //Vibrato/tremolo setting for this channel. 1=Enabled, 0=Disabled.
153
	//Signal generation
155	byte wavesel;
156	float ModulatorFrequencyMultiple; //What harmonic to sound?
157	float lastsignal[2]; //The last signal produced!
158	uint_32 phase; //Current phase calculated!
159	word increment; //Increment each sample!
160	ADLIBCHANNEL *channel;
161} ADLIBOP; //An adlib operator to process!
162
ADLIBOP adlibop[0x20];
164
ADLIBCHANNEL adlibch[0x10];
166
word outputtable[0x40]; //Build using software formulas!
168
uint8_t adlibpercussion = 0, adlibstatus = 0;
170
uint_32 OPL2_RNGREG = 0;
172uint_32 OPL2_RNG = 0; //The current random generated sample!
173
uint16_t adlibport = 0x388;
175
//Tremolo/vibrato support
178
typedef struct
180{
181	float time; //Current time(loops every second)!
182	float current; //Current value in absolute data!
183	word phase; //Raw phase!
184	float depth; //The depth to apply!
185	float active; //Active value, depending on tremolo/vibrato what this is: tremolo: volume to apply. vibrato: speedup to apply.
186} TREMOLOVIBRATOSIGNAL; //Tremolo&vibrato signals!
187
TREMOLOVIBRATOSIGNAL tremolovibrato[2]; //Tremolo&vibrato!
189
//RNG
191
OPTINLINE void OPL2_stepRNG() //Runs at the sampling rate!
193{
194	OPL2_RNG = ( (OPL2_RNGREG) ^ (OPL2_RNGREG>>14) ^ (OPL2_RNGREG>>15) ^ (OPL2_RNGREG>>22) ) & 1; //Get the current RNG!
195	OPL2_RNGREG = (OPL2_RNG<<22) | (OPL2_RNGREG>>1);
196}
197
OPTINLINE float calcModulatorFrequencyMultiple(byte data)
199{
200	switch (data)
201	{
202	case 0: return 0.5f;
203	case 11: return 10.0f;
204	case 13: return 12.0f;
205	case 14: return 15.0f;
206	default: return (float)data; //The same number!
207	}
208}
209
//Attenuation setting!
211void EnvelopeGenerator_setAttennuation(ADLIBOP *operator); //Prototype!
212void EnvelopeGenerator_setAttennuationCustom(ADLIBOP *op)
213{
214	op->m_kslAdd2 = (op->m_kslAdd<<3); //Multiply with 8!
215}
216
void writeadlibKeyON(byte channel, byte forcekeyon)
219{
220	byte isflipkeyon = 0; //Are we processing a low or high flipped key-on for High-hat/Cymbal? 1=Start modulator, 2=Start carrier!
221	byte ispercussionflipping = 0;
222	byte keyon;
223	byte oldkeyon;
224	keyon = ((adlibregmem[0xB0 + (channel&0xF)] >> 5) & 1)?3:0; //New key on for melodic channels? Affect both operators! This disturbs percussion mode!
225	if (adlibpercussion && (channel&0x80)) //Percussion enabled and percussion channel changed?
226	{
227		keyon = adlibregmem[0xBD]; //Total key status for percussion channels?
228		switch (channel&0xF) //What channel?
229		{
230			//Adjusted according to http://www.4front-tech.com/dmguide/dmfm.html
231			case 6: //Bass drum? Uses the channel normally!
232				keyon = (keyon&0x10)?3:0; //Bass drum on? Key on/off on both operators!
233				channel = 6; //Use channel 6!
234				break;
235			case 7: //Snare drum(Modulator)/Hi-hat(Carrier)? fmopl.c: High-hat uses modulator, Snare drum uses Carrier signals.
236				keyon = ((keyon>>3)&1)|((keyon<<1)&2); //Shift the information to modulator and carrier positions!
237				channel = 7; //Use channel 7!
238				ispercussionflipping = 1; //Enable flip key-on for modulator(High-hat)!
239				break;
240			case 8: //Tom-tom(Carrier)/Cymbal(Modulator)? fmopl.c:Tom-tom uses Modulator, Cymbal uses Carrier signals.
241				keyon = ((keyon>>2)&1)|(keyon&2); //Shift the information to modulator and carrier positions!
242				channel = 8; //Use channel 8!
243				ispercussionflipping = 2; //Enable flip key-on for carrier(Cymbal)!
244				break;
245			default: //Unknown channel?
246				//New key on for melodic channels? Don't change anything!
247				break;
248		}
249	}
250
	oldkeyon = adlibch[channel].keyon; //Current&old key on!
252
	nextkeyon:
254	adlibch[channel].m_block = (adlibregmem[0xB0 + channel] >> 2) & 7;
255	adlibch[channel].m_fnum = (adlibregmem[0xA0 + channel] | ((adlibregmem[0xB0 + channel] & 3) << 8)); //Frequency number!
256	if (adliboperators[0][channel] != 0xFF)
257	{
258		adlibop[adliboperators[0][channel]].increment = ((((uint_32)(adlibch[channel].m_fnum*(1.0/169.0)*(14318180.0 / 288.0))) >> (7 - adlibch[channel].m_block)) * adlibop[adliboperators[0][channel]].ModulatorFrequencyMultiple); //Calculate the effective frequency!
259	}
260	if (adliboperators[1][channel] != 0xFF)
261	{
262		adlibop[adliboperators[1][channel]].increment = ((((uint_32)(adlibch[channel].m_fnum*(1.0/169.0) * (14318180.0 / 288.0))) >> (7 - adlibch[channel].m_block)) * adlibop[adliboperators[1][channel]].ModulatorFrequencyMultiple); //Calculate the effective frequency!
263	}
264
	if ((adliboperators[0][channel]!=0xFF) && ((((keyon&1) && ((oldkeyon^keyon)&1)) || (forcekeyon&1)) || (isflipkeyon==1))) //Key ON on operator #1 or flip starting the modulator?
266	{
267		if (adlibop[adliboperators[0][channel]&0x1F].volenvstatus==0) //Not retriggering the volume envelope?
268		{
269			adlibop[adliboperators[0][channel]&0x1F].volenv = Silence; //No raw level: Start silence!
270			adlibop[adliboperators[0][channel]&0x1F].m_env = Silence; //No raw level: Start level!
271		}		
272		adlibop[adliboperators[0][channel]&0x1F].volenvstatus = 1; //Start attacking!
273		adlibop[adliboperators[0][channel]&0x1F].gain = ((adlibop[adliboperators[0][channel]].volenv)<<3); //Apply the start gain!
274		adlibop[adliboperators[0][channel]&0x1F].m_counter = 0; //No raw level: Start counter!
275		adlibop[adliboperators[0][channel]&0x1F].phase = 0; //Initialise operator signal!
276		adlibop[adliboperators[0][channel]&0x1F].lastsignal[0] = adlibop[adliboperators[1][channel]&0x1F].lastsignal[1] = 0.0f; //Reset the last signals!
277		EnvelopeGenerator_setAttennuation(&adlibop[adliboperators[0][channel]&0x1F]);
278		EnvelopeGenerator_setAttennuationCustom(&adlibop[adliboperators[0][channel]&0x1F]);
279		if (ispercussionflipping==1) //Are we flipping on this key-on?
280		{
281			ispercussionflipping = 3; //Start the other percussion flip after we're done!
282		}
283	}
284
	//Below block is a fix for stuck notes!
286	if ((adliboperators[0][channel] != 0xFF) && (((keyon & 1) == 0) && ((oldkeyon^keyon) & 1) && ((forcekeyon & 1) == 0))) //Key OFF on operator #1?
287	{
288		if (adlibop[adliboperators[0][channel] & 0x1F].volenvstatus == 0) //Not retriggering the volume envelope?
289		{
290			adlibop[adliboperators[0][channel] & 0x1F].volenv = Silence; //No raw level: Start silence!
291			adlibop[adliboperators[0][channel] & 0x1F].m_env = Silence; //No raw level: Start level!
292		}
293		adlibop[adliboperators[0][channel] & 0x1F].volenvstatus = 4; //Start attacking!
294		adlibop[adliboperators[0][channel] & 0x1F].gain = ((adlibop[adliboperators[0][channel]].volenv) << 3); //Apply the start gain!
295		EnvelopeGenerator_setAttennuation(&adlibop[adliboperators[0][channel] & 0x1F]);
296		EnvelopeGenerator_setAttennuationCustom(&adlibop[adliboperators[0][channel] & 0x1F]);
297	}
298
	if ((adliboperators[1][channel]!=0xFF) && ((((keyon&2) && ((oldkeyon^keyon)&2)) || (forcekeyon&2)) || (isflipkeyon==2))) //Key ON on operator #2 or flip starting the carrier?
300	{
301		if (adlibop[adliboperators[1][channel]&0x1F].volenvstatus==0) //Not retriggering the volume envelope?
302		{
303			adlibop[adliboperators[1][channel]&0x1F].volenv = Silence; //No raw level: silence!
304			adlibop[adliboperators[1][channel]&0x1F].m_env = Silence; //No raw level: Start level!
305		}
306		adlibop[adliboperators[1][channel]&0x1F].volenvstatus = 1; //Start attacking!
307		adlibop[adliboperators[1][channel]&0x1F].gain = ((adlibop[adliboperators[1][channel]].volenv)<<3); //Apply the start gain!
308		adlibop[adliboperators[1][channel]&0x1F].m_counter = 0; //No raw level: Start counter!
309		adlibop[adliboperators[1][channel]&0x1F].phase = 0; //Initialise operator signal!
310		adlibop[adliboperators[1][channel]&0x1F].lastsignal[0] = adlibop[adliboperators[1][channel]&0x1F].lastsignal[1] = 0.0f; //Reset the last signals!
311		EnvelopeGenerator_setAttennuation(&adlibop[adliboperators[1][channel]&0x1F]);
312		EnvelopeGenerator_setAttennuationCustom(&adlibop[adliboperators[1][channel]&0x1F]);
313		if (ispercussionflipping == 2) //Are we flipping on this key-on?
314		{
315			ispercussionflipping = 3; //Start the other percussion flip after we're done!
316		}
317	}
318
	//Below block is a fix for stuck notes!
320	if ((adliboperators[1][channel] != 0xFF) && (((keyon & 2) == 0) && ((oldkeyon^keyon) & 2) && ((forcekeyon & 2) == 0))) //Key OFF on operator #1?
321	{
322		if (adlibop[adliboperators[1][channel] & 0x1F].volenvstatus == 0) //Not retriggering the volume envelope?
323		{
324			adlibop[adliboperators[1][channel] & 0x1F].volenv = Silence; //No raw level: Start silence!
325			adlibop[adliboperators[1][channel] & 0x1F].m_env = Silence; //No raw level: Start level!
326		}
327		adlibop[adliboperators[1][channel] & 0x1F].volenvstatus = 4; //Start releasing!
328		adlibop[adliboperators[1][channel] & 0x1F].gain = ((adlibop[adliboperators[1][channel]].volenv) << 3); //Apply the start gain!
329		EnvelopeGenerator_setAttennuation(&adlibop[adliboperators[1][channel] & 0x1F]);
330		EnvelopeGenerator_setAttennuationCustom(&adlibop[adliboperators[1][channel] & 0x1F]);
331	}
332
	//Update keyon information!
334	adlibch[channel].keyon = keyon | forcekeyon; //Key is turned on?
335	if (ispercussionflipping == 3) //Flipping percussion halves?
336	{
337		forcekeyon = 0; //Don't force said key on, if so!
338		channel = (channel == 8) ? 7 : 8; //Flip the channel!
339		keyon = adlibch[channel].keyon; //The channel's actual key-on(so it doesn't detect any changes, so no strange effects)!
340		isflipkeyon = (channel == 7) ? 1 : 2; //Are we to start the modulator(0) or carrier(1) on said channel?
341		ispercussionflipping = 4; //Finish flipping afterwards!
342		goto nextkeyon;
343	}
344}
345
void writeadlibaddr(byte value)
347{
348	adlibaddr = value; //Set the address!
349}
350
void writeadlibdata(byte value)
352{
353	word portnum;
354	byte oldval;
355	portnum = adlibaddr;
356	oldval = adlibregmem[portnum]; //Save the old value for reference!
357	if (portnum != 4) adlibregmem[portnum] = value; //Timer control applies it itself, depending on the value!
358	switch (portnum & 0xF0) //What block to handle?
359	{
360	case 0x00:
361		switch (portnum) //What primary port?
362		{
363		case 1: //Waveform select enable
364			wavemask = (adlibregmem[1] & 0x20) ? 3 : 0; //Apply waveform mask!
365			break;
366		case 4: //timer control
367			if (value & 0x80) { //Special case: don't apply the value!
368				adlibstatus &= 0x1F; //Reset status flags needed!
369			}
370			else //Apply value to register?
371			{
372				adlibregmem[portnum] = value; //Apply the value set!
373				if (value & 1) //Timer1 enabled?
374				{
375					timer80 = adlibregmem[2]; //Reload timer!
376				}
377				if (value & 2) //Timer2 enabled?
378				{
379					timer320 = adlibregmem[3]; //Reload timer!					
380				}
381			}
382			break;
383		case 8: //CSW/Note-Sel?
384			CSMMode = (adlibregmem[8] & 0x80) ? 1 : 0; //Set CSM mode!
385			NTS = (adlibregmem[8] & 0x40) ? 1 : 0; //Set NTS mode!
386			break;
387		default: //Unknown?
388			break;
389		}
390	case 0x10: //Unused?
391		break;
392	case 0x20:
393	case 0x30:
394		if (portnum <= 0x35) //Various flags
395		{
396			portnum &= 0x1F;
397			adlibop[portnum].ModulatorFrequencyMultiple = calcModulatorFrequencyMultiple(value & 0xF); //Which harmonic to use?
398			adlibop[portnum].ReleaseImmediately = (value & 0x20) ? 0 : 1; //Release when not sustain until release!
399			adlibop[portnum].m_ksr = (value >> 4) & 1; //Keyboard scaling rate!
400			EnvelopeGenerator_setAttennuation(&adlibop[portnum]); //Apply attenuation settings!			
401			EnvelopeGenerator_setAttennuationCustom(&adlibop[portnum]); //Apply attenuation settings!			
402		}
403		break;
404	case 0x40:
405	case 0x50:
406		if (portnum <= 0x55) //KSL/Output level
407		{
408			portnum &= 0x1F;
409			adlibop[portnum].m_ksl = ((value >> 6) & 3); //Apply KSL!
410			adlibop[portnum].outputlevel = outputtable[value & 0x3F]; //Apply raw output level!
411			EnvelopeGenerator_setAttennuation(&adlibop[portnum]); //Apply attenuation settings!
412			EnvelopeGenerator_setAttennuationCustom(&adlibop[portnum]); //Apply attenuation settings!
413		}
414		break;
415	case 0x60:
416	case 0x70:
417		if (portnum <= 0x75) { //attack/decay
418			portnum &= 0x1F;
419			adlibop[portnum].m_ar = (value >> 4); //Attack rate
420			adlibop[portnum].m_dr = (value & 0xF); //Decay rate
421			EnvelopeGenerator_setAttennuation(&adlibop[portnum]); //Apply attenuation settings!			
422			EnvelopeGenerator_setAttennuationCustom(&adlibop[portnum]); //Apply attenuation settings!			
423		}
424		break;
425	case 0x80:
426	case 0x90:
427		if (portnum <= 0x95) //sustain/release
428		{
429			portnum &= 0x1F;
430			adlibop[portnum].m_sl = (value >> 4); //Sustain level
431			adlibop[portnum].m_rr = (value & 0xF); //Release rate
432			EnvelopeGenerator_setAttennuation(&adlibop[portnum]); //Apply attenuation settings!			
433			EnvelopeGenerator_setAttennuationCustom(&adlibop[portnum]); //Apply attenuation settings!			
434		}
435		break;
436	case 0xA0:
437	case 0xB0:
438		if (portnum <= 0xB8)
439		{ //octave, freq, key on
440			if ((portnum & 0xF) > 8) return; //Ignore A9-AF!
441			portnum &= 0xF; //Only take the lower nibble (the channel)!
442			writeadlibKeyON((byte)portnum, 0); //Write to this port! Don't force the key on!
443		}
444		else if (portnum == 0xBD) //Percussion settings etc.
445		{
446			adlibpercussion = (value & 0x20) ? 1 : 0; //Percussion enabled?
447			tremolovibrato[0].depth = (value & 0x80) ? 4.8f : 1.0f; //Default: 1dB AM depth, else 4.8dB!
448			tremolovibrato[1].depth = (value & 0x40) ? 14.0f : 7.0f; //Default: 7 cent vibrato depth, else 14 cents!
449			if (((oldval^value) & 0x1F) && adlibpercussion) //Percussion enabled and changed state?
450			{
451				writeadlibKeyON(0x86, 0); //Write to this port(Bass drum)! Don't force the key on!
452				writeadlibKeyON(0x87, 0); //Write to this port(Snare drum/Tom-tom)! Don't force the key on!
453				writeadlibKeyON(0x88, 0); //Write to this port(Cymbal/Hi-hat)! Don't force the key on!
454			}
455		}
456		break;
457	case 0xC0:
458		if (portnum <= 0xC8)
459		{
460			portnum &= 0xF;
461			adlibch[portnum].synthmode = (adlibregmem[0xC0 + portnum] & 1); //Save the synthesis mode!
462			byte feedback;
463			feedback = (adlibregmem[0xC0 + portnum] >> 1) & 7; //Get the feedback value used!
464			adlibch[portnum].feedback = (float)feedbacklookup2[feedback]; //Convert to a feedback of the modulator signal!
465		}
466		break;
467	case 0xE0:
468	case 0xF0:
469		if (portnum <= 0xF5) //waveform select
470		{
471			portnum &= 0x1F;
472			adlibop[portnum].wavesel = value & 3;
473		}
474		break;
475	default: //Unsupported port?
476		break;
477	}
478}
479
byte readadlibstatus()
481{
482	return adlibstatus; //Give the current status!
483}
484
byte outadlib (uint16_t portnum, uint8_t value) {
486	if (portnum==adlibport) {
487		writeadlibaddr(value); //Write to the address port!
488		return 1;
489		}
490	if (portnum != (adlibport+1)) return 0; //Don't handle what's not ours!
491	writeadlibdata(value); //Write to the data port!
492	return 1; //We're finished and handled, even non-used registers!
493}
494
uint8_t inadlib (uint16_t portnum, byte *result) {
496	if (portnum == adlibport) //Status port?
497	{
498		*result = readadlibstatus(); //Give the current status!
499		return 1; //We're handled!
500	}
501	return 0; //Not our port!
502}
503
//Native OPL2 Sinus Wave!
505OPTINLINE word OPL2SinWave(word r)
506{
507	INLINEREGISTER word index;
508	word entry; //The entry to convert!
509	INLINEREGISTER byte location; //The location in the table to use!
510	byte PIpart;
511	PIpart = 0; //Default: part 0!
512	index = r; //Default: take the index as specified!
513	index &= 0x3FF; //Loop the sinus infinitely!
514	if (index&0x200) //Second half?
515	{
516		PIpart = 2; //Second half!
517		index -= 0x200; //Convert to first half!
518	}
519	if (index&0x100) //Past quarter?
520	{
521		PIpart |= 1; //Second half!
522		index -= 0x100; //Convert to first quarter!
523	}
524	location = (byte)index; //Set the location to use!
525	if (PIpart&1) //Reversed quarter(second and fourth quarter)?
526	{
527		location = ~location; //Reverse us!
528	}
529
	entry = OPL2_LogSinTable[location]; //Take the full load!
531	if (PIpart&2) //Second half is negative?
532	{
533		entry |= SIGNBIT; //We're negative instead, so toggle the sign bit!
534	}
535	return entry; //Give the processed entry!
536}
537
OPTINLINE word OPL2SinWavePI(const float r)
539{
540	float index;
541	index = fmodf(r, PI2); //Loop the sinus infinitely!
542	return OPL2SinWave((word)(index*1024)); //Call the native OPL2 sinus wave function with the phase to generate!
543}
544
word MaximumExponential = 0; //Maximum exponential input!
546
OPTINLINE DOUBLE OPL2_Exponential_real(word v)
548{
549	//Exponential lookup also reverses the input, since it's a -logSin table!
550	//Exponent = x/256
551	//Significant = ExpTable[v%256]+1024
552	//Output = Significant * (2^Exponent)
553	DOUBLE sign;
554	#ifdef IS_LONGDOUBLE
555	sign = (v&SIGNBIT) ? -1.0L : 1.0L; //Get the sign first before removing it! Reverse the sign to create proper output!
556	#else
557	sign = (v&SIGNBIT) ? -1.0 : 1.0; //Get the sign first before removing it! Reverse the sign to create proper output!
558	#endif
559	v &= SIGNMASK; //Sign off!
560	//Reverse the range given! Input 0=Maximum volume, Input max=No output.
561	if (v>MaximumExponential) v = MaximumExponential; //Limit to the maximum value available!
562	v = MaximumExponential-v; //Reverse our range to get the correct value!
563	#ifdef IS_LONGDOUBLE
564	return sign*(DOUBLE)(OPL2_ExpTable[v & 0xFF] + 1024)*pow(2.0L, (DOUBLE)(v>>8)); //Lookup normally with the specified sign, mantissa(8 bits translated to 10 bits) and exponent(3 bits taken from the high part of the input)!
565	#else
566	return sign*(DOUBLE)(OPL2_ExpTable[v & 0xFF] + 1024)*pow(2.0, (DOUBLE)(v>>8)); //Lookup normally with the specified sign, mantissa(8 bits translated to 10 bits) and exponent(3 bits taken from the high part of the input)!
567	#endif
568}
569
OPTINLINE float OPL2_Exponential(word v)
571{
572	return OPL2_ExponentialLookup2[v]; //Give the precalculated lookup result!
573}
574
OPTINLINE float getOPL2TriangleWave(word v)
576{
577	return OPL2_TremoloVibratoLookup[v]; //Give the precalculated lookup result!
578}
579
OPTINLINE word getOPL2TriangleWavePhase(word v)
581{
582	return OPL2_TremoloVibratoLookupPhase[v]; //Give the precalculated lookup result!
583}
584
OPTINLINE void stepTremoloVibrato(TREMOLOVIBRATOSIGNAL *signal, float frequency)
586{
587	float temp, dummy;
588	word phasetemp;
589	signal->current = getOPL2TriangleWave(OPL2SinWave((float)1024*frequency*(float)signal->time)); //Apply the signal using the OPL2 Sine Wave, reverse the operation and convert to triangle wave!
590	signal->phase = getOPL2TriangleWavePhase(OPL2SinWave((float)1024 * frequency * (float)signal->time)); //Apply the signal using the OPL2 Sine Wave, reverse the operation and convert to triangle wave!
591
	signal->time += (float)adlib_sampleLength; //Add 1 sample to the time!
593
	temp = signal->time*frequency; //Calculate for overflow!
595	if (temp >= 1.0f) { //Overflow?
596		signal->time = modff(temp, &dummy) / frequency;
597	}
598}
599
OPTINLINE void OPL2_stepTremoloVibrato()
601{
602	//Step to the next value!
603	stepTremoloVibrato(&tremolovibrato[0], 3.7f); //Tremolo at 3.7Hz!
604	stepTremoloVibrato(&tremolovibrato[1], 6.4f); //Vibrato at 6.4Hz!
605
	//Now the current value of the signal is stored! Apply the active tremolo/vibrato!
607	#ifdef ADLIB_TREMOLOVIBRATO
608	tremolovibrato[0].active = (float)dB2factor(93.0f - (tremolovibrato[0].depth*tremolovibrato[0].current), 93.0f); //Calculate the current tremolo!
609	tremolovibrato[1].active = (100.0f + (tremolovibrato[1].depth*tremolovibrato[1].current))*0.01f*1024.0f; //Calculate the current vibrato!
610	#else
611	tremolovibrato[0].active = tremolovibrato[1].active = 1.0f; //No tremolo/vibrato!
612	#endif
613}
614
OPTINLINE float OPL2_Vibrato(word phase, byte operatornumber)
616{
617	if (adlibop[operatornumber].vibrato) //Vibrato enabled?
618	{
619		return phase + (tremolovibrato[1].phase * tremolovibrato[1].active); //Apply vibrato!
620	}
621	return phase; //Unchanged frequency!
622}
623
OPTINLINE float OPL2_Tremolo(byte operator, float f)
625{
626	if (adlibop[operator].tremolo) //Tremolo enabled?
627	{
628		return f*tremolovibrato[0].active; //Apply the current tremolo/vibrato!
629	}
630	return f; //Unchanged!
631}
632
OPTINLINE word OPL2_Sin(byte signal, word phase) {
634	#ifdef IS_FLOATDOUBLE
635	double dummy;
636	#else
637	DOUBLE dummy;
638	#endif
639	word t;
640	word result;
641	switch (signal) {
642	case 0: //SINE?
643		return OPL2SinWave(phase); //The sinus function!
644	default:
645		t = (phase&0x3FF); //Calculate rest for special signal information!
646		switch (signal) { //What special signal?
647		case 1: // Negative=0?
648			if (t >= 0x200) return OPL2_LogSinTable[0]; //Negative=0!
649			result = OPL2SinWave(phase); //The sinus function!
650			return result; //Positive!
651		case 3: // Absolute with second half=0?
652			if (phase&0x100) return OPL2_LogSinTable[0]; //Are we the second half of the half period? Clear the signal if so!
653		case 2: // Absolute?
654			result = OPL2SinWave(phase); //The sinus function!
655			result &= ~SIGNBIT; //Ignore negative values!
656			return result; //Simply absolute!
657		default: //Unknown signal?
658			return 0;
659		}
660	}
661}
662
OPTINLINE word calcOPL2Signal(byte wave, float phase, float operatorphase) //Calculates a signal for input to the adlib synth!
664{
665	word ftp;
666	ftp = (word)operatorphase; //Frequency!
667	ftp += (word)phase; //Apply raw phase, in raw units!
668	return OPL2_Sin(wave, ftp); //Give the generated sample!
669}
670
OPTINLINE void incop(byte operator)
672{
673	if (operator==0xFF) return; //Invalid operator or ignoring timing increase!
674	adlibop[operator].phase += adlibop[operator].increment; //Add 1 sample to the time!
675	adlibop[operator].phase = OPL2_Vibrato(adlibop[operator].phase, operator); //Apply vibrato!
676	adlibop[operator].phase &= 0xFFFFF; //20-bit number!
677}
678
OPTINLINE word calcModulator(float modulator)
680{
681	return (word)(modulator*1024*4); //Calculate current modulation! 4 full sinus periods range!
682}
683
OPTINLINE word calcFeedback(byte channel, ADLIBOP *operator)
685{
686	return (word)((operator->lastsignal[0]+operator->lastsignal[1])*0.5f*adlibch[channel].feedback); //Calculate current feedback
687}
688
//Calculate an operator signal!
690OPTINLINE float calcOperator(byte channel, byte operator, byte timingoperator, byte volenvoperator, float modulator, byte flags)
691{
692	if (operator==0xFF) return 0.0f; //Invalid operator!
693	INLINEREGISTER word result, gain; //The result to give!
694	float result2; //The translated result!
695	float activemodulation=0.0f;
696	//Generate the signal!
697	if ((flags & 0xC0)==0x80) //Apply channel feedback?
698	{
699		activemodulation = calcFeedback(channel, &adlibop[timingoperator]); //Apply this feedback signal!
700	}
701	else if ((flags&0x40)==0) //Apply normal modulation from a previous output?
702	{
703		activemodulation = calcModulator(modulator); //Use the normal modulator!
704	}
705
	//Generate the correct signal! Ignore time by setting frequency to 0.0f(effectively disables time, keeping it stuck at 0(frequencytime))!
707	if ((flags & 0x40) == 0) //Normal signal?
708	{
709		result = calcOPL2Signal(adlibop[operator].wavesel&wavemask, activemodulation, (adlibop[operator].phase>>10)); //Take the last frequency or current frequency!
710	}
711	else //Raw input/output(don't take a normal signal)!
712	{
713		result = calcOPL2Signal(adlibop[operator].wavesel&wavemask, activemodulation, (adlibop[operator].phase>>10)); //Take the last frequency or current frequency!
714	}
715
	//Calculate the gain!
717	gain = 0; //Init gain!
718	if (flags&2) //Special: ignore main volume control!
719	{
720		gain += outputtable[0]; //Always maximum volume, ignore the volume control!
721	}
722	else //Normal output level!
723	{
724		gain += adlibop[volenvoperator].outputlevel; //Current gain!
725	}
726	gain += adlibop[volenvoperator].gain; //Apply volume envelope and related calculations!
727	gain += adlibop[volenvoperator].m_kslAdd2; //Add KSL preprocessed!
728
	//Now apply the gain!
730	result += gain; //Simply add the gain!
731	if (flags&8) //Double the volume?
732	{
733		result = (result&SIGNBIT)|(MIN(((result&SIGNMASK)>>1),SIGNMASK)&SIGNMASK); //Double the volume!
734	}
735	result2 = OPL2_Exponential(result); //Translate to Exponential range!
736
	if (adlibop[timingoperator].increment && ((flags & 1) == 0)) //Running operator and allowed to update our signal?
738	{
739		adlibop[timingoperator].lastsignal[0] = adlibop[timingoperator].lastsignal[1]; //Previous last signal!
740		adlibop[timingoperator].lastsignal[1] = result2; //Set last signal #0 to #1(shift into the older one)!
741		incop(timingoperator); //Increase time for the operator when allowed to increase (frequency=0 during PCM output)!
742	}
743	result2 = OPL2_Tremolo(operator,result2); //Apply tremolo as well, after applying the new feedback signal(don't include tremolo in it)!
744	return result2; //Give the translated result!
745}
746
float adlib_scaleFactor = 0.0f; //We're running 9 channels in a 16-bit space, so 1/9 of SHRT_MAX
748
OPTINLINE float adlibsample(uint8_t curchan, word phase7_1, word phase8_2) {
750	byte op6_1, op6_2, op7_1, op7_2, op8_1, op8_2; //The four slots used during Drum samples!
751	word tempop_phase; //Current phase of an operator!
752	float result;
753	float immresult; //The operator result and the final result!
754	byte op1,op2; //The two operators to use!
755	curchan &= 0xF;
756	if (curchan >= NUMITEMS(adlibch)) return 0; //No sample with invalid channel!
757
	//Determine the modulator and carrier to use!
759	op1 = adliboperators[0][curchan]; //First operator number!
760	op2 = adliboperators[1][curchan]; //Second operator number!
761	if (adlibpercussion && (curchan >= 6) && (curchan <= 8)) //We're percussion?
762	{
763		#ifndef ADLIB_RHYTHM
764		return 0.0f; //Disable percussion!
765		#else
766		INLINEREGISTER word tempphase;
767		result = 0; //Initialise the result!
768		//Calculations based on http://bisqwit.iki.fi/source/opl3emu.html fmopl.c
769		//Load our four operators for processing!
770		op6_1 = adliboperators[0][6];
771		op6_2 = adliboperators[1][6];
772		op7_1 = adliboperators[0][7];
773		op7_2 = adliboperators[1][7];
774		op8_1 = adliboperators[0][8];
775		op8_2 = adliboperators[1][8];
776		switch (curchan) //What channel?
777		{
778			case 6: //Bass drum?
779				//Generate Bass drum samples!
780				//Special on Bass Drum: Additive synthesis(Operator 1) is ignored.
781
				//Calculate the frequency to use!
783				result = 0.0f;
784				if (adlibop[op6_2].volenvstatus) //Running?
785				{
786					result = calcOperator(6, op6_1, op6_1, op6_1, 0.0f, 0x00); //Calculate the modulator for feedback!
787
					if (adlibch[6].synthmode) //Additive synthesis?
789					{
790						result = calcOperator(6, op6_2, op6_2, op6_2, 0.0f, 0x08); //Calculate the carrier without applied modulator additive!
791					}
792					else //FM synthesis?
793					{
794						result = calcOperator(6, op6_2, op6_2, op6_2, result, 0x08); //Calculate the carrier with applied modulator!
795					}
796				}
797
				return result; //Apply the exponential! The volume is always doubled!
799				break;
800
				//Comments with information from fmopl.c:
802				/* Phase generation is based on: */
803				/* HH  (13) channel 7->slot 1 combined with channel 8->slot 2 (same combination as TOP CYMBAL but different output phases) */
804				/* SD  (16) channel 7->slot 1 */
805				/* TOM (14) channel 8->slot 1 */
806				/* TOP (17) channel 7->slot 1 combined with channel 8->slot 2 (same combination as HIGH HAT but different output phases) */
807
			
809				/* Envelope generation based on: */
810				/* HH  channel 7->slot1 */
811				/* SD  channel 7->slot2 */
812				/* TOM channel 8->slot1 */
813				/* TOP channel 8->slot2 */
814				//So phase modulation is based on the Modulator signal. The volume envelope is in the Carrier signal (Hi-hat/Tom-tom) or Carrier signal().
815			case 7: //Hi-hat(Carrier)/Snare drum(Modulator)? High-hat uses modulator, Snare drum uses Carrier signals.
816				immresult = 0.0f; //Initialize immediate result!
817				if (adlibop[op7_1].volenvstatus) //Hi-hat on Modulator?
818				{
819					//Derive frequency from channel 7(modulator) and 8(carrier).
820					tempop_phase = phase7_1; //Save the phase!
821					tempphase = (tempop_phase>>2);
822					tempphase ^= (tempop_phase>>7);
823					tempphase |= (tempop_phase>>3);
824					tempphase &= 1; //Only 1 bit is used!
825					tempphase = tempphase?(0x200|(0xD0>>2)):0xD0;
826					tempop_phase = phase8_2; //Calculate the phase of channel 8 carrier signal!
827					if (((tempop_phase>>3)^(tempop_phase>>5))&1) tempphase = 0x200|(0xD0>>2);
828					if (tempphase&0x200)
829					{
830						if (OPL2_RNG) tempphase = 0x2D0;
831					}
832					else if (OPL2_RNG) tempphase = (0xD0>>2);
833					result = calcOperator(8, op8_2,op8_2,op7_1,(float)(tempphase), 0x4B); //Calculate the modulator, but only use the current time(position in the sine wave)!
834					immresult += result; //Apply the tremolo!
835				}
836				if (adlibop[op7_2].volenvstatus) //Snare drum on Carrier volume?
837				{
838					//Derive frequency from channel 0.
839					tempphase = 0x100 << ((phase7_1 >> 8) & 1); //Bit8=0(Positive) then 0x100, else 0x200! Based on the phase to generate!
840					tempphase ^= (OPL2_RNG << 8); //Noise bits XOR'es phase by 0x100 when set!
841					result = calcOperator(7, op7_2,op7_2,op7_2,(float)tempphase, 0x40); //Calculate the carrier with applied modulator!
842					immresult += result; //Apply the tremolo!
843				}
844				result = immresult; //Load the resulting channel!
845				//result *= 0.5f; //We only have half(two channels combined)!
846				return result; //Give the result, converted to short!
847				break;
848			case 8: //Tom-tom(Carrier)/Cymbal(Modulator)? Tom-tom uses Modulator, Cymbal uses Carrier signals.
849				immresult = 0.0f; //Initialize immediate result!
850				if (adlibop[op8_1].volenvstatus) //Tom-tom(Modulator)?
851				{
852					result = calcOperator(8, op8_1, op8_1, op8_1, 0.0f, 0xA); //Calculate the carrier without applied modulator additive! Ignore volume!
853					immresult += result; //Apply the exponential!
854				}
855				if (adlibop[op8_2].volenvstatus) //Cymbal(Carrier)?
856				{
857					//Derive frequency from channel 7(modulator) and 8(carrier).
858					tempop_phase = phase7_1; //Save the phase!
859					tempphase = (tempop_phase>>2);
860					tempphase ^= (tempop_phase>>7);
861					tempphase |= (tempop_phase>>3);
862					tempphase &= 1; //Only 1 bit is used!
863					tempphase <<= 9; //0x200 when 1 makes it become 0x300
864					tempphase |= 0x100; //0x100 is always!
865					tempop_phase = phase8_2; //Calculate the phase of channel 8 carrier signal!
866					if (((tempop_phase>>3)^(tempop_phase>>5))&1) tempphase = 0x300;
867					
868					result = calcOperator(8, op8_2,op8_2,op8_2, (float)tempphase, 0x41); //Calculate the carrier with applied modulator! Use volume!
869					immresult += result; //Apply the exponential!
870				}
871
				//Advance the shared percussion channel by 7-1 and 8-2!
873				result = calcOperator(7, op7_1, op7_1, op7_1, 0.0f, 0); //Calculate the modulator, but only use the current time(position in the sine wave)!
874				result = calcOperator(8, op8_2, op8_2, op8_2, 0.0f, 0); //Calculate the carrier with applied modulator! Use volume!
875
				result = immresult; //Load the resulting channel!
877				//result *= 0.5f; //We only have half(two channels combined)!
878				return result; //Give the result, converted to short!
879				break;
880			default:
881				break;
882		}
883		#endif
884		//Not a percussion channel? Pass through!
885	}
886
	//Operator 1!
888	//Calculate the frequency to use!
889	result = calcOperator(curchan, op1,op1,op1, 0.0f,0x80); //Calculate the modulator for feedback!
890
	if (adlibch[curchan].synthmode) //Additive synthesis?
892	{
893		result += calcOperator(curchan, op2,op2,op2, 0.0f,0x00); //Calculate the carrier without applied modulator additive!
894	}
895	else //FM synthesis?
896	{
897		result = calcOperator(curchan, op2,op2,op2, result, 0x00); //Calculate the carrier with applied modulator!
898	}
899
	return result; //Give the result!
901}
902
//Timer ticks!
904
byte ticked80_320 = 0; //80/320 ticked?
906
OPTINLINE void tick_adlibtimer()
908{
909	if (CSMMode) //CSM enabled?
910	{
911		//Process CSM tick!
912		byte channel=0;
913		for (;;)
914		{
915			writeadlibKeyON(channel,3); //Force the key to turn on!
916			if (++channel==9) break; //Finished!
917		}
918	}
919}
920
OPTINLINE void adlib_timer320() //Second timer!
922{
923	if (adlibregmem[4] & 2) //Timer2 enabled?
924	{
925		if (++timer320 == 0) //Overflown?
926		{
927			if ((~adlibregmem[4]) & 0x20) //Update status register?
928			{
929				adlibstatus |= 0xA0; //Update status register and set the bits!
930			}
931			timer320 = adlibregmem[3]; //Reload timer!
932			ticked80_320 = 1; //We're ticked!
933		}
934	}
935}
936
byte ticks80 = 0; //How many timer 80 ticks have been done?
938
OPTINLINE void adlib_timer80() //First timer!
940{
941	ticked80_320 = 0; //Default: not ticked!
942	if (adlibregmem[4] & 1) //Timer1 enabled?
943	{
944		if (++timer80 == 0) //Overflown?
945		{
946			timer80 = adlibregmem[2]; //Reload timer!
947			if ((~adlibregmem[4]) & 0x40) //Update status?
948			{
949				adlibstatus |= 0xC0; //Update status register and set the bits!
950			}
951			ticked80_320 = 1; //Ticked 320 clock!
952		}
953	}
954	if (++ticks80 == 4) //Every 4 timer 80 ticks gets 1 timer 320 tick!
955	{
956		ticks80 = 0; //Reset counter to count 320us ticks!
957		adlib_timer320(); //Execute a timer 320 tick!
958	}
959	if (ticked80_320) tick_adlibtimer(); //Tick by either timer!
960}
961
float counter80step = 0.0f; //80us timer tick interval in samples!
963
OPTINLINE byte adlib_channelplaying(byte channel)
965{
966	if (channel==7) //Drum channels?
967	{
968		if (adlibpercussion) //Percussion mode? Split channels!
969		{
970			return 1; //Percussion channel is always on!
971		}
972		//Melodic?
973		return adlibop[adliboperators[1][7]].volenvstatus; //Melodic, so carrier!
974	}
975	else if (channel==8) //Drum channel?
976	{
977		if (adlibpercussion) //Percussion mode? Split channels!
978		{
979			return 1; //Percussion is always on?
980		}
981		//Melodic?
982		return adlibop[adliboperators[1][8]].volenvstatus; //Melodic, so carrier!
983	}
984	else //0 - 5=Melodic, 6=Melodic, Also drum channel, but no difference here.
985	{
986		return adlibop[adliboperators[1][channel]].volenvstatus; //Melodic, so carrier!
987	}
988	return 0; //Unknown channel!
989}
990
OPTINLINE float adlibgensample() {
993	float adlibaccum = 0.0f;
994	byte channel;
995	byte op7_1;
996	byte op8_2;
997	word phase7_1;
998	word phase8_2;
999	op7_1 = adliboperators[0][7];
1000	op8_2 = adliboperators[1][8];
1001	phase7_1 = (adlibop[op7_1].phase>>10); //Save the current 7_1 phase for usage in drum channels!
1002	phase8_2 = (adlibop[op8_2].phase>>10); //Save the current 8_2 phase for usage in drum channels!
1003
	for (channel=0;channel<9;++channel) //Process all channels!
1005	{
1006		if (adlib_channelplaying(channel)) adlibaccum += adlibsample(channel,phase7_1,phase8_2); //Sample when playing!
1007	}
1008	adlibaccum *= adlib_scaleFactor; //Scale according to volume!
1009	return adlibaccum;
1010}
1011
void EnvelopeGenerator_setAttennuation(ADLIBOP *operator)
1013{
1014	if( operator->m_ksl == 0 ) {
1015		operator->m_kslAdd = 0;
1016		return;
1017	}
1018
	if (!operator->channel) return; //Invalid channel?
1020	// 1.5 dB att. for base 2 of oct. 7
1021	// created by: round(8*log2( 10^(dbMax[msb]/10) ))+8;
1022	// verified from real chip ROM
1023	static const int kslRom[16] = {
1024		0, 32, 40, 45, 48, 51, 53, 55, 56, 58, 59, 60, 61, 62, 63, 64
1025	};
1026	// 7 negated is, by one's complement, effectively -8. To compensate this,
1027	// the ROM's values have an offset of 8.
1028	int tmp = kslRom[operator->channel->m_fnum >> 6] + 8 * ( operator->channel->m_block - 8 );
1029	if( tmp <= 0 ) {
1030	operator->m_kslAdd = 0;
1031	return;
1032	}
1033	operator->m_kslAdd = tmp;
1034	switch( operator->m_ksl ) {
1035		case 1:
1036		// 3 db
1037		operator->m_kslAdd <<= 1;
1038		break;
1039	case 2:
1040		// no change, 1.5 dB
1041		break;
1042        case 3:
1043		// 6 dB
1044		operator->m_kslAdd <<= 2;
1045		break;
1046	default:
1047		break;
1048	}
1049}
1050
OPTINLINE byte EnvelopeGenerator_nts(ADLIBOP *operator)
1052{
1053	return NTS; //Give the NTS bit!
1054}
1055
OPTINLINE uint8_t EnvelopeGenerator_calculateRate(ADLIBOP *operator, uint8_t rateValue )
1057{
1058	if (!operator->channel) return 0; //Invalid channel?
1059	if( rateValue == 0 ) {
1060		return 0;
1061	}
1062	// calculate key scale number (see NTS in the YMF262 manual)
1063	uint8_t rof = ( operator->channel->m_fnum >> ( EnvelopeGenerator_nts(operator) ? 8 : 9 ) ) & 0x1;
1064	// ...and KSR (see manual, again)
1065	rof |= operator->channel->m_block << 1;
1066	if( !operator->m_ksr ) {
1067		rof >>= 2;
1068	}
1069	// here, rof<=15
1070	// the limit of 60 results in rof=0 if rateValue=15 below
1071	return MIN( 60, rof + (rateValue << 2) );
1072}
1073
OPTINLINE uint8_t EnvelopeGenerator_advanceCounter(ADLIBOP *operator, uint8_t rate )
1075{
1076	if (rate >= 16 ) return 0;
1077	if( rate == 0 ) {
1078		return 0;
1079	}
1080	const uint8_t effectiveRate = EnvelopeGenerator_calculateRate(operator, rate );
1081	// rateValue <= 15
1082	const uint8_t rateValue = effectiveRate >> 2;
1083	// rof <= 3
1084	const uint8_t rof = effectiveRate & 3;
1085	// 4 <= Delta <= (7<<15)
1086	operator->m_counter += ((uint_32)(4 | rof )) << rateValue;
1087	// overflow <= 7
1088	uint8_t overflow = operator->m_counter >> 15;
1089	operator->m_counter &= ( 1 << 15 ) - 1;
1090	return overflow;
1091}
1092
OPTINLINE void EnvelopeGenerator_attenuate( ADLIBOP *operator,uint8_t rate )
1094{
1095	if( rate >= 64 ) return;
1096	operator->m_env += EnvelopeGenerator_advanceCounter(operator, rate );
1097	if( operator->m_env >= Silence ) {
1098		operator->m_env = Silence;
1099	}
1100}
1101
OPTINLINE void EnvelopeGenerator_release(ADLIBOP *operator)
1103{
1104	EnvelopeGenerator_attenuate(operator,operator->m_rr);
1105	if (operator->m_env>=Silence)
1106	{
1107		operator->m_env = Silence;
1108		operator->volenvstatus = 0; //Finished the volume envelope!
1109	}
1110}
1111
OPTINLINE void EnvelopeGenerator_decay(ADLIBOP *operator)
1113{
1114	if ((operator->m_env>>4)>=operator->m_sl)
1115	{
1116		operator->volenvstatus = 3; //Start sustaining!
1117		return;
1118	}
1119	EnvelopeGenerator_attenuate(operator,operator->m_dr);
1120}
1121
OPTINLINE void EnvelopeGenerator_attack(ADLIBOP *operator)
1123{
1124	if (operator->m_env<=0) //Nothin to attack anymore?
1125	{
1126		operator->volenvstatus = 2; //Start decaying!
1127	}
1128	else if (operator->m_ar==15)
1129	{
1130		operator->m_env = 0;
1131	}
1132	else //Attack!
1133	{
1134		if (operator->m_env<=0) return; //Abort if too high!
1135		byte overflow = EnvelopeGenerator_advanceCounter(operator,operator->m_ar); //Advance with attack rate!
1136		if (!overflow) return;
1137		operator->m_env -= ((operator->m_env*overflow)>>3)+1; //Affect envelope in a curve!
1138	}
1139}
1140
OPTINLINE void tickadlib()
1142{
1143	const byte maxop = NUMITEMS(adlibop); //Maximum OP count!
1144	uint8_t curop;
1145	for (curop = 0; curop < maxop; curop++)
1146	{
1147		if (!adlibop[curop].channel) continue; //Skip invalid operators!
1148		if (adlibop[curop].volenvstatus) //Are we a running envelope?
1149		{
1150			switch (adlibop[curop].volenvstatus)
1151			{
1152			case 1: //Attacking?
1153				EnvelopeGenerator_attack(&adlibop[curop]); //New method: Attack!
1154				adlibop[curop].volenv = LIMITRANGE(adlibop[curop].m_env,0,Silence); //Apply the linear curve
1155				adlibop[curop].gain = ((adlibop[curop].volenv)<<3); //Apply the start gain!
1156				break;
1157			case 2: //Decaying?
1158				EnvelopeGenerator_decay(&adlibop[curop]); //New method: Decay!
1159				if (adlibop[curop].volenvstatus==3)
1160				{
1161					goto startsustain; //Start sustaining if needed!
1162				}
1163				adlibop[curop].volenv = LIMITRANGE(adlibop[curop].m_env,0,Silence); //Apply the linear curve
1164				adlibop[curop].gain = ((adlibop[curop].volenv)<<3); //Apply the start gain!
1165				break;
1166			case 3: //Sustaining?
1167				startsustain:
1168				if (adlibop[curop].ReleaseImmediately) //Release entered?
1169				{
1170					++adlibop[curop].volenvstatus; //Enter next phase!
1171					goto startrelease; //Check again!
1172				}
1173				adlibop[curop].volenv = LIMITRANGE(adlibop[curop].m_env,0,Silence); //Apply the linear curve
1174				adlibop[curop].gain = ((adlibop[curop].volenv)<<3); //Apply the start gain!
1175				break;
1176			case 4: //Releasing?
1177				startrelease:
1178				EnvelopeGenerator_release(&adlibop[curop]); //Release: new method!
1179				adlibop[curop].volenv = LIMITRANGE(adlibop[curop].m_env,0,Silence); //Apply the linear curve
1180				adlibop[curop].gain = ((adlibop[curop].volenv)<<3); //Apply the start gain!
1181				break;
1182			default: //Unknown volume envelope status?
1183				adlibop[curop].volenvstatus = 0; //Disable this volume envelope!
1184				break;
1185			}
1186		}
1187	}
1188}
1189
//Check for timer occurrences.
1191void cleanAdlib()
1192{
1193	//Discard the amount of time passed!
1194}
1195
//Stuff for the low-pass filter!
1197HIGHLOWPASSFILTER adlibfilter; //Output filter of the OPL2 output!
1198float opl2_currentsample; //Current sample!
1199
byte adlib_ticktiming80 = 0; //80us divider!
1201uint_32 adlib_ticktiming=0; //Sound timing!
1202void updateAdlib(uint_32 MHZ14passed)
1203{
1204	//Adlib sound output and counters!
1205	adlib_ticktiming += MHZ14passed; //Get the amount of time passed!
1206	if (adlib_ticktiming>=MHZ14_TICK)
1207	{
1208		do
1209		{
1210			//Adlib timer!
1211			++adlib_ticktiming80; //Tick 80 divider!
1212			if (adlib_ticktiming80 >= TIMER80_TICK) //Enough time passed?
1213			{
1214				adlib_ticktiming80 -= TIMER80_TICK; //Tick once(never more than once!)
1215				adlib_timer80(); //Tick 80us timer!
1216			}
1217			//Now, process the samples required!
1218			OPL2_stepRNG(); //Tick the RNG!
1219			OPL2_stepTremoloVibrato(); //Step tremolo/vibrato!
1220			byte filled;
1221			float sample;
1222			filled = 0; //Default: not filled!
1223			filled |= adlib_channelplaying(0); //Channel 0?
1224			filled |= adlib_channelplaying(1); //Channel 1?
1225			filled |= adlib_channelplaying(2); //Channel 2?
1226			filled |= adlib_channelplaying(3); //Channel 3?
1227			filled |= adlib_channelplaying(4); //Channel 4?
1228			filled |= adlib_channelplaying(5); //Channel 5?
1229			filled |= adlib_channelplaying(6); //Channel 6?
1230			filled |= adlib_channelplaying(7); //Channel 7?
1231			filled |= adlib_channelplaying(8); //Channel 8?
1232			if (filled) sample = adlibgensample(); //Any sound to generate?
1233			else sample = 0.0f;
1234
			#ifdef ADLIB_LOWPASS
1236				opl2_currentsample = sample;
1237				//We're applying the low pass filter for the speaker!
1238				applySoundFilter(&adlibfilter, &opl2_currentsample);
1239				sample = opl2_currentsample; //Convert us back to our range!
1240			#endif
1241
			sample = LIMITRANGE(sample, (float)SHRT_MIN, (float)SHRT_MAX); //Clip our data to prevent overflow!
1243			#ifdef WAV_ADLIB
1244			writeWAVMonoSample(adlibout,sample); //Log the samples!
1245			#endif
1246			writeDoubleBufferedSound16(&adlib_soundbuffer,(word)sample); //Output the sample to the renderer!
1247			tickadlib(); //Tick us to the next timing if needed!
1248			adlib_ticktiming -= MHZ14_TICK; //Decrease timer to get time left!
1249		} while (adlib_ticktiming>=MHZ14_TICK);
1250	}
1251}
1252
byte adlib_soundGenerator(void* buf, uint_32 length, byte stereo, void *userdata) //Generate a sample!
1254{
1255	if (stereo) return 0; //We don't support stereo!
1256	
1257	uint_32 c;
1258	c = length; //Init c!
1259	
1260	static short last=0;
1261	
1262	short *data_mono;
1263	data_mono = (short *)buf; //The data in correct samples!
1264	for (;;) //Fill it!
1265	{
1266		//Left and right samples are the same: we're a mono signal!
1267		readDoubleBufferedSound16(&adlib_soundbuffer,(word *)&last); //Generate a mono sample if it's available!
1268		*data_mono++ = last; //Load the last generated sample!
1269		if (!--c) return SOUNDHANDLER_RESULT_FILLED; //Next item!
1270	}
1271}
1272
//Multicall speedup!
1274#define ADLIBMULTIPLIER 0
1275
void initAdlib()
1277{
1278	float current; //Current values for Tremolo/Vibrato lookup table!
1279	float dummy; //Dummy value for Tremolo/Vibrato lookup!
1280	if (__HW_DISABLED) return; //Abort!
1281
	//Initialize our timings!
1283	adlib_scaleFactor = SHRT_MAX / (3000.0f*9.0f); //We're running 9 channels in a 16-bit space, so 1/9 of SHRT_MAX
1284	#ifdef IS_LONGDOUBLE
1285	usesamplerate = 14318180.0L / 288.0L; //The sample rate to use for output!
1286	#else
1287	usesamplerate = 14318180.0 / 288.0; //The sample rate to use for output!
1288	#endif
1289
	int i;
1291	for (i = 0; i < 9; i++)
1292	{
1293		memset(&adlibch[i],0,sizeof(adlibch[i])); //Initialise all channels!
1294	}
1295
	//Build the needed tables!
1297	for (i = 0; i < (int)NUMITEMS(outputtable); ++i)
1298	{
1299		outputtable[i] = (((word)i)<<5); //Multiply the raw value by 5 to get the actual gain: the curve is applied by the register shifted left!
1300	}
1301
	for (i = 0; i < (int)NUMITEMS(adlibop); i++) //Process all channels!
1303	{
1304		memset(&adlibop[i],0,sizeof(adlibop[i])); //Initialise the channel!
1305
		//Apply default ADSR!
1307		adlibop[i].volenvstatus = 0; //Initialise to unused ADSR!
1308		adlibop[i].ReleaseImmediately = 1; //Release immediately by default!
1309
		adlibop[i].outputlevel = outputtable[0]; //Apply default output!
1311		adlibop[i].ModulatorFrequencyMultiple = calcModulatorFrequencyMultiple(0); //Which harmonic to use?
1312		adlibop[i].ReleaseImmediately = 1; //We're defaulting to value being 0=>Release immediately.
1313		adlibop[i].lastsignal[0] = adlibop[i].lastsignal[1] = 0.0f; //Reset the last signals!
1314		if (adliboperatorsreverse[i]!=0xFF) //Valid operator?
1315		{
1316			adlibop[i].channel = &adlibch[adliboperatorsreverse[i]&0x1F]; //The channel this operator belongs to!
1317		}
1318	}
1319
	//Source of the Exp and LogSin tables: https://docs.google.com/document/d/18IGx18NQY_Q1PJVZ-bHywao9bhsDoAqoIn1rIm42nwo/edit
1321	for (i = 0;i < 0x100;++i) //Initialise the exponentional and log-sin tables!
1322	{
1323		OPL2_ExpTable[i] = (word)round((pow(2, (float)i / 256.0f) - 1.0f) * 1024.0f);
1324		OPL2_LogSinTable[i] = (word)round(-log(sin((i + 0.5f)*PI / 256.0f / 2.0f)) / log(2.0f) * 256.0f);
1325	}
1326
	//Find the maximum volume archievable with exponential lookups!
1328	MaximumExponential = ((0x3F << 5) + (Silence << 3)) + OPL2_LogSinTable[0]; //Highest input to the LogSin input!
1329	DOUBLE maxresult=0.0,buffer=0.0;
1330	uint_32 n;
1331	n = 0;
1332	do
1333	{
1334		buffer = OPL2_Exponential_real((word)n); //Load the current value translated!
1335		OPL2_ExponentialLookup[n] = buffer; //Store the value for fast lookup!
1336	} while (++n<0x10000); //Loop while not finished processing all possibilities!
1337
	maxresult = OPL2_Exponential_real(0); //Zero is maximum output to give!
1339	DOUBLE generalmodulatorfactor = 0.0f; //Modulation factor!
1340	//Now, we know the biggest result given!
1341	#ifdef IS_LONGDOUBLE
1342	generalmodulatorfactor = (1.0L/(DOUBLE)maxresult); //General modulation factor, as applied to both modulation methods!
1343	#else
1344	generalmodulatorfactor = (1.0/(DOUBLE)maxresult); //General modulation factor, as applied to both modulation methods!
1345	#endif
1346
	n = 0; //Loop through again for te modified table!
1348	do
1349	{
1350		buffer = OPL2_ExponentialLookup[n]; //Load the current value translated!
1351		buffer *= generalmodulatorfactor; //Apply the general modulator factor to it to convert it to -1.0 to 1.0 range!
1352		OPL2_ExponentialLookup2[n] = (float)buffer; //Store the value for fast lookup!
1353	} while (++n<0x10000); //Loop while not finished processing all possibilities!
1354
	adlib_scaleFactor = (((float)(SHRT_MAX))/8.0f); //Highest volume conversion Exp table(resulting mix) to SHRT_MAX (8 channels before clipping)!
1356
	for (i = 0;i < (int)NUMITEMS(feedbacklookup2);++i) //Process all feedback values!
1358	{
1359		feedbacklookup2[i] = feedbacklookup[i]; //Don't convert for now!
1360	}
1361
	for (n=0;n<(int)NUMITEMS(OPL2_TremoloVibratoLookup);++n) //Process all Tremolo/Vibrato outputs!
1363	{
1364		current = modff(asinf(OPL2_Exponential((word)n)) / (float)PI2, &dummy); //Apply the signal using the OPL2 Sine Wave, reverse the operation and convert to triangle time!
1365		current = (current < 0.5f) ? ((current * 2.0f) - 0.5f) : (0.5f - ((current - 0.5f) * 2.0f));
1366		OPL2_TremoloVibratoLookupPhase[n] = ((current > 0.5f) ? 0x200 : 0) | ((fmodf(current, 0.5f) > 0.25f) ? 0x100 : 0) | ((byte)(fmodf(current, 0.25f) * 0x100)); //The raw OPL2 phase output!
1367		OPL2_TremoloVibratoLookup[n] = current; //Set the used Tremolo/Vibrato value!
1368	}
1369
	memset(&tremolovibrato,0,sizeof(tremolovibrato)); //Initialise tremolo/vibrato!
1371	tremolovibrato[0].depth = 1.0f; //Default: 1dB AM depth!
1372	tremolovibrato[1].depth = 7.0f; //Default: 7 cent vibrato depth!
1373	NTS = CSMMode = 0; //Reset the global flags!
1374
	//RNG support!
1376	OPL2_RNGREG = OPL2_RNG = 0; //Initialise the RNG!
1377	OPL2_RNGREG = 1; //Seed the noise register to a valid value(must be non-zero)!
1378
	adlib_ticktiming = 0; //Reset our output timing!
1380	adlib_ticktiming80 = 0; //80us tick timing!
1381
	if (__SOUND_ADLIB)
1383	{
1384		if (allocDoubleBufferedSound16(__ADLIB_SAMPLEBUFFERSIZE,&adlib_soundbuffer,0,usesamplerate)) //Valid buffer?
1385		{
1386			if (!addchannel(&adlib_soundGenerator,NULL,"Adlib",(float)usesamplerate,__ADLIB_SAMPLEBUFFERSIZE,0,SMPL16S,1)) //Start the sound emulation (mono) with automatic samples buffer?
1387			{
1388				dolog("adlib","Error registering sound channel for output!");
1389			}
1390			else
1391			{
1392				setVolume(&adlib_soundGenerator,NULL,ADLIB_VOLUME);
1393			}
1394		}
1395		else
1396		{
1397			dolog("adlib","Error registering double buffer for output!");
1398		}
1399	}
1400	//Ignore unregistered channel, we need to be used by software!
1401	register_PORTIN(&inadlib); //Status port (R)
1402	//All output!
1403	register_PORTOUT(&outadlib); //Address port (W)
1404
	#ifdef WAV_ADLIB
1406	adlibout = createWAV("captures/adlib.wav",1,usesamplerate); //Start logging!
1407	#endif
1408
	#ifdef WAVE_ADLIB
1410	WAVEFILE *w;
1411	float u,f,c,es,dummyfreq0=0.0f,dummytime=0.0f;
1412	uint_32 samples;
1413	samples = (uint_32)usesamplerate; //Load the current sample rate!
1414	word s,wave;
1415	uint_32 currenttime;
1416	c = (float)(SHRT_MAX); //Conversion for Exponential results!
1417	f = (1.0/(float)usesamplerate); //Time of a wave sample!
1418
	w = createWAV("captures/adlibwave.wav", 1, usesamplerate); //Start logging one wave! Wave exponential test!
1420	for (wave=0;wave<4;++wave) //Log all waves!
1421	{
1422		u = 0.0; //Reset the current time!
1423		for (currenttime = 0;currenttime<samples;++currenttime) //Process all samples!
1424		{
1425			s = calcOPL2Signal(wave,1.0f,(dummytime*1024.0f)); //Get the sample(1Hz sine wave)!
1426			es = OPL2_Exponential(s); //Get the raw sample at maximum volume!
1427			es *= c; //Apply the destination factor!
1428			writeWAVMonoSample(w,(word)(LIMITRANGE((sword)es,SHRT_MIN,SHRT_MAX))); //Log 1 wave, looked up through exponential input!
1429			dummytime += f; //Add one sample to the time!
1430		}
1431	}
1432	closeWAV(&w); //Close the wave file!
1433	#endif
1434
	initSoundFilter(&adlibfilter,0,ADLIB_LOWPASS, (float)usesamplerate); //Initialize our low-pass filter to use!
1436}
1437
void doneAdlib()
1439{
1440	if (__HW_DISABLED) return; //Abort!
1441	#ifdef WAV_ADLIB
1442	closeWAV(&adlibout); //Stop logging!
1443	#endif
1444	if (__SOUND_ADLIB)
1445	{
1446		removechannel(&adlib_soundGenerator,NULL,0); //Stop the sound emulation?
1447		freeDoubleBufferedSound(&adlib_soundbuffer); //Free out double buffered sound!
1448	}
1449}