Fix optimization for absolute addressing and two indices
This commit is contained in:
parent
48f97b6e60
commit
358def836d
|
@ -15,7 +15,7 @@ static struct SIDFXChannel
|
||||||
SIDFX * com;
|
SIDFX * com;
|
||||||
byte delay, cnt;
|
byte delay, cnt;
|
||||||
SIDFXState state;
|
SIDFXState state;
|
||||||
unsigned freq;
|
unsigned freq, pwm;
|
||||||
|
|
||||||
} channels[3];
|
} channels[3];
|
||||||
|
|
||||||
|
@ -46,86 +46,108 @@ void sidfx_stop(byte chn)
|
||||||
channels[chn].state = SIDFX_RESET_0;
|
channels[chn].state = SIDFX_RESET_0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline void sidfx_loop_ch(byte ch)
|
||||||
|
{
|
||||||
|
switch (channels[ch].state)
|
||||||
|
{
|
||||||
|
case SIDFX_IDLE:
|
||||||
|
break;
|
||||||
|
case SIDFX_RESET_0:
|
||||||
|
sid.voices[ch].ctrl = 0;
|
||||||
|
sid.voices[ch].attdec = 0;
|
||||||
|
sid.voices[ch].susrel = 0;
|
||||||
|
channels[ch].state = SIDFX_RESET_1;
|
||||||
|
break;
|
||||||
|
case SIDFX_RESET_1:
|
||||||
|
sid.voices[ch].ctrl = SID_CTRL_TEST;
|
||||||
|
channels[ch].state = SIDFX_READY;
|
||||||
|
break;
|
||||||
|
case SIDFX_READY:
|
||||||
|
if (channels[ch].com)
|
||||||
|
{
|
||||||
|
channels[ch].freq = channels[ch].com->freq;
|
||||||
|
channels[ch].pwm = channels[ch].com->pwm;
|
||||||
|
|
||||||
|
sid.voices[ch].freq = channels[ch].com->freq;
|
||||||
|
sid.voices[ch].pwm = channels[ch].com->pwm;
|
||||||
|
sid.voices[ch].attdec = channels[ch].com->attdec;
|
||||||
|
sid.voices[ch].susrel = channels[ch].com->susrel;
|
||||||
|
sid.voices[ch].ctrl = channels[ch].com->ctrl;
|
||||||
|
|
||||||
|
channels[ch].delay = channels[ch].com->time1;
|
||||||
|
channels[ch].state = SIDFX_PLAY;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
channels[ch].state = SIDFX_IDLE;
|
||||||
|
break;
|
||||||
|
case SIDFX_PLAY:
|
||||||
|
if (channels[ch].com->dfreq)
|
||||||
|
{
|
||||||
|
channels[ch].freq += channels[ch].com->dfreq;
|
||||||
|
sid.voices[ch].freq = channels[ch].freq;
|
||||||
|
}
|
||||||
|
if (channels[ch].com->dpwm)
|
||||||
|
{
|
||||||
|
channels[ch].pwm += channels[ch].com->dpwm;
|
||||||
|
sid.voices[ch].pwm = channels[ch].pwm;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (channels[ch].delay)
|
||||||
|
channels[ch].delay--;
|
||||||
|
else if (channels[ch].com->time0)
|
||||||
|
{
|
||||||
|
sid.voices[ch].ctrl = channels[ch].com->ctrl & ~SID_CTRL_GATE;
|
||||||
|
channels[ch].delay = channels[ch].com->time0;
|
||||||
|
channels[ch].state = SIDFX_WAIT;
|
||||||
|
}
|
||||||
|
else if (channels[ch].cnt)
|
||||||
|
{
|
||||||
|
channels[ch].cnt--;
|
||||||
|
channels[ch].com++;
|
||||||
|
channels[ch].state = SIDFX_READY;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
channels[ch].com = nullptr;
|
||||||
|
channels[ch].state = SIDFX_RESET_0;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
case SIDFX_WAIT:
|
||||||
|
if (channels[ch].com->dfreq)
|
||||||
|
{
|
||||||
|
channels[ch].freq += channels[ch].com->dfreq;
|
||||||
|
sid.voices[ch].freq = channels[ch].freq;
|
||||||
|
}
|
||||||
|
if (channels[ch].com->dpwm)
|
||||||
|
{
|
||||||
|
channels[ch].pwm += channels[ch].com->dpwm;
|
||||||
|
sid.voices[ch].pwm = channels[ch].pwm;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (channels[ch].delay)
|
||||||
|
channels[ch].delay--;
|
||||||
|
else if (channels[ch].cnt)
|
||||||
|
{
|
||||||
|
channels[ch].cnt--;
|
||||||
|
channels[ch].com++;
|
||||||
|
channels[ch].state = SIDFX_RESET_0;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
channels[ch].com = nullptr;
|
||||||
|
channels[ch].state = SIDFX_RESET_0;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void sidfx_loop_2(void)
|
||||||
|
{
|
||||||
|
sidfx_loop_ch(2);
|
||||||
|
}
|
||||||
|
|
||||||
void sidfx_loop(void)
|
void sidfx_loop(void)
|
||||||
{
|
{
|
||||||
for(byte ch=0; ch<3; ch++)
|
for(byte ch=0; ch<3; ch++)
|
||||||
{
|
sidfx_loop_ch(ch);
|
||||||
switch (channels[ch].state)
|
|
||||||
{
|
|
||||||
case SIDFX_IDLE:
|
|
||||||
break;
|
|
||||||
case SIDFX_RESET_0:
|
|
||||||
sid.voices[ch].ctrl = 0;
|
|
||||||
sid.voices[ch].attdec = 0;
|
|
||||||
sid.voices[ch].susrel = 0;
|
|
||||||
channels[ch].state = SIDFX_RESET_1;
|
|
||||||
break;
|
|
||||||
case SIDFX_RESET_1:
|
|
||||||
sid.voices[ch].ctrl = SID_CTRL_TEST;
|
|
||||||
channels[ch].state = SIDFX_READY;
|
|
||||||
break;
|
|
||||||
case SIDFX_READY:
|
|
||||||
if (channels[ch].com)
|
|
||||||
{
|
|
||||||
channels[ch].freq = channels[ch].com->freq;
|
|
||||||
sid.voices[ch].freq = channels[ch].com->freq;
|
|
||||||
sid.voices[ch].pwm = channels[ch].com->pwm;
|
|
||||||
sid.voices[ch].attdec = channels[ch].com->attdec;
|
|
||||||
sid.voices[ch].susrel = channels[ch].com->susrel;
|
|
||||||
sid.voices[ch].ctrl = channels[ch].com->ctrl;
|
|
||||||
channels[ch].delay = channels[ch].com->time1;
|
|
||||||
channels[ch].state = SIDFX_PLAY;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
channels[ch].state = SIDFX_IDLE;
|
|
||||||
break;
|
|
||||||
case SIDFX_PLAY:
|
|
||||||
if (channels[ch].com->dfreq)
|
|
||||||
{
|
|
||||||
channels[ch].freq += channels[ch].com->dfreq;
|
|
||||||
sid.voices[ch].freq = channels[ch].freq;
|
|
||||||
}
|
|
||||||
if (channels[ch].delay)
|
|
||||||
channels[ch].delay--;
|
|
||||||
else if (channels[ch].com->time0)
|
|
||||||
{
|
|
||||||
sid.voices[ch].ctrl = channels[ch].com->ctrl & ~SID_CTRL_GATE;
|
|
||||||
channels[ch].delay = channels[ch].com->time0;
|
|
||||||
channels[ch].state = SIDFX_WAIT;
|
|
||||||
}
|
|
||||||
else if (channels[ch].cnt)
|
|
||||||
{
|
|
||||||
channels[ch].cnt--;
|
|
||||||
channels[ch].com++;
|
|
||||||
channels[ch].state = SIDFX_READY;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
channels[ch].com = nullptr;
|
|
||||||
channels[ch].state = SIDFX_RESET_0;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case SIDFX_WAIT:
|
|
||||||
if (channels[ch].com->dfreq)
|
|
||||||
{
|
|
||||||
channels[ch].freq += channels[ch].com->dfreq;
|
|
||||||
sid.voices[ch].freq = channels[ch].freq;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (channels[ch].delay)
|
|
||||||
channels[ch].delay--;
|
|
||||||
else if (channels[ch].cnt)
|
|
||||||
{
|
|
||||||
channels[ch].cnt--;
|
|
||||||
channels[ch].com++;
|
|
||||||
channels[ch].state = SIDFX_RESET_0;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
channels[ch].com = nullptr;
|
|
||||||
channels[ch].state = SIDFX_RESET_0;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -13,12 +13,14 @@ struct SIDFX
|
||||||
|
|
||||||
void sidfx_init(void);
|
void sidfx_init(void);
|
||||||
|
|
||||||
void sidfx_play(byte chn, SIDFX * fx, byte cnt);
|
inline void sidfx_play(byte chn, SIDFX * fx, byte cnt);
|
||||||
|
|
||||||
void sidfx_stop(byte chn);
|
void sidfx_stop(byte chn);
|
||||||
|
|
||||||
void sidfx_loop(void);
|
void sidfx_loop(void);
|
||||||
|
|
||||||
|
void sidfx_loop_2(void);
|
||||||
|
|
||||||
#pragma compile("sidfx.c")
|
#pragma compile("sidfx.c")
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -16888,7 +16888,7 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(NativeCodeProcedure* proc, int pass
|
||||||
if (ains->mMode == ASMIM_IMMEDIATE)
|
if (ains->mMode == ASMIM_IMMEDIATE)
|
||||||
{
|
{
|
||||||
mIns[i + 1].mLinkerObject = 0;
|
mIns[i + 1].mLinkerObject = 0;
|
||||||
mIns[i + 1].mAddress = addr;
|
mIns[i + 1].mAddress = addr + mIns[i + 0].mAddress;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -18162,6 +18162,42 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(NativeCodeProcedure* proc, int pass
|
||||||
mIns[i + 3].mMode = ASMIM_IMPLIED;
|
mIns[i + 3].mMode = ASMIM_IMPLIED;
|
||||||
progress = true;
|
progress = true;
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
#if 1
|
||||||
|
else if (
|
||||||
|
mIns[i + 0].mType == ASMIT_CLC &&
|
||||||
|
mIns[i + 1].mType == ASMIT_LDA && mIns[i + 1].mMode == ASMIM_ZERO_PAGE &&
|
||||||
|
mIns[i + 2].mType == ASMIT_ADC && mIns[i + 2].mMode == ASMIM_IMMEDIATE && mIns[i + 2].mAddress <= 2 &&
|
||||||
|
mIns[i + 3].mType == ASMIT_TAX && !(mIns[i + 3].mLive & (LIVE_CPU_REG_A | LIVE_CPU_REG_Z | LIVE_CPU_REG_C)))
|
||||||
|
{
|
||||||
|
mIns[i + 0].mType = ASMIT_NOP; mIns[i + 0].mMode = ASMIM_IMPLIED;
|
||||||
|
mIns[i + 1].mType = ASMIT_LDX; mIns[i + 1].mLive |= LIVE_CPU_REG_X;
|
||||||
|
mIns[i + 2].mType = ASMIT_INX; mIns[i + 2].mMode = ASMIM_IMPLIED; mIns[i + 2].mLive |= LIVE_CPU_REG_X;
|
||||||
|
if (mIns[i + 2].mAddress == 2)
|
||||||
|
mIns[i + 3].mType = ASMIT_INX;
|
||||||
|
else
|
||||||
|
mIns[i + 3].mType = ASMIT_NOP;
|
||||||
|
mIns[i + 3].mMode = ASMIM_IMPLIED;
|
||||||
|
progress = true;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
#if 1
|
||||||
|
else if (
|
||||||
|
mIns[i + 0].mType == ASMIT_SEC &&
|
||||||
|
mIns[i + 1].mType == ASMIT_LDA && mIns[i + 1].mMode == ASMIM_ZERO_PAGE &&
|
||||||
|
mIns[i + 2].mType == ASMIT_SBC && mIns[i + 2].mMode == ASMIM_IMMEDIATE && mIns[i + 2].mAddress <= 2 &&
|
||||||
|
mIns[i + 3].mType == ASMIT_TAX && !(mIns[i + 3].mLive & (LIVE_CPU_REG_A | LIVE_CPU_REG_Z | LIVE_CPU_REG_C)))
|
||||||
|
{
|
||||||
|
mIns[i + 0].mType = ASMIT_NOP; mIns[i + 0].mMode = ASMIM_IMPLIED;
|
||||||
|
mIns[i + 1].mType = ASMIT_LDX; mIns[i + 1].mLive |= LIVE_CPU_REG_X;
|
||||||
|
mIns[i + 2].mType = ASMIT_DEX; mIns[i + 2].mMode = ASMIM_IMPLIED; mIns[i + 2].mLive |= LIVE_CPU_REG_X;
|
||||||
|
if (mIns[i + 2].mAddress == 2)
|
||||||
|
mIns[i + 3].mType = ASMIT_DEX;
|
||||||
|
else
|
||||||
|
mIns[i + 3].mType = ASMIT_NOP;
|
||||||
|
mIns[i + 3].mMode = ASMIM_IMPLIED;
|
||||||
|
progress = true;
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
else if (
|
else if (
|
||||||
mIns[i + 0].mType == ASMIT_TXA &&
|
mIns[i + 0].mType == ASMIT_TXA &&
|
||||||
|
|
Loading…
Reference in New Issue