Sidfx extend gate sprike condition
This commit is contained in:
parent
8175fae67a
commit
5b4e0c2b55
|
@ -112,6 +112,9 @@ inline void sidfx_loop_ch(byte ch)
|
||||||
break;
|
break;
|
||||||
case SIDFX_RESET_1:
|
case SIDFX_RESET_1:
|
||||||
sid.voices[ch].ctrl = SID_CTRL_TEST;
|
sid.voices[ch].ctrl = SID_CTRL_TEST;
|
||||||
|
sid.voices[ch].ctrl = 0;
|
||||||
|
sid.voices[ch].attdec = 0;
|
||||||
|
sid.voices[ch].susrel = 0;
|
||||||
channels[ch].state = SIDFX_READY;
|
channels[ch].state = SIDFX_READY;
|
||||||
break;
|
break;
|
||||||
case SIDFX_READY:
|
case SIDFX_READY:
|
||||||
|
@ -147,7 +150,7 @@ inline void sidfx_loop_ch(byte ch)
|
||||||
char sr = com->susrel & 0xf0;
|
char sr = com->susrel & 0xf0;
|
||||||
com++;
|
com++;
|
||||||
char ctrl = com->ctrl;
|
char ctrl = com->ctrl;
|
||||||
if (com->attdec == 0 && (ctrl & SID_CTRL_GATE) && (com->susrel & 0xf0) > sr)
|
if ((com->attdec & 0xef) == 0 && (ctrl & SID_CTRL_GATE) && (com->susrel & 0xf0) > sr)
|
||||||
{
|
{
|
||||||
sid.voices[ch].ctrl = ctrl & ~SID_CTRL_GATE;
|
sid.voices[ch].ctrl = ctrl & ~SID_CTRL_GATE;
|
||||||
sid.voices[ch].ctrl = ctrl | SID_CTRL_GATE;
|
sid.voices[ch].ctrl = ctrl | SID_CTRL_GATE;
|
||||||
|
|
|
@ -37080,6 +37080,201 @@ bool NativeCodeBasicBlock::OffsetValueForwarding(const ValueNumberingDataSet& da
|
||||||
return changed;
|
return changed;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool NativeCodeBasicBlock::CheckLoopIndexXRegisters(NativeCodeBasicBlock* head, int xreg)
|
||||||
|
{
|
||||||
|
for (int i = mIns.Size() - 1; i >= 0; i--)
|
||||||
|
{
|
||||||
|
if (mIns[i].ChangesXReg())
|
||||||
|
{
|
||||||
|
if ((mIns[i].mType == ASMIT_LDX || mIns[i].mType == ASMIT_STX) && mIns[i].mMode == ASMIM_ZERO_PAGE && mIns[i].mAddress == xreg)
|
||||||
|
return true;
|
||||||
|
else if (mIns[i].ChangesXReg() || mIns[i].ChangesZeroPage(xreg))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this == head)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (mLoopHead)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
for (int i = 0; i < mEntryBlocks.Size(); i++)
|
||||||
|
{
|
||||||
|
if (!mEntryBlocks[i]->CheckLoopIndexXRegisters(head, xreg))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool NativeCodeBasicBlock::CheckLoopIndexYRegisters(NativeCodeBasicBlock* head, int yreg)
|
||||||
|
{
|
||||||
|
for (int i = mIns.Size() - 1; i >= 0; i--)
|
||||||
|
{
|
||||||
|
if (mIns[i].ChangesYReg())
|
||||||
|
{
|
||||||
|
if ((mIns[i].mType == ASMIT_LDY || mIns[i].mType == ASMIT_STY) && mIns[i].mMode == ASMIM_ZERO_PAGE && mIns[i].mAddress == yreg)
|
||||||
|
return true;
|
||||||
|
else if (mIns[i].ChangesYReg() || mIns[i].ChangesZeroPage(yreg))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (this == head)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (mLoopHead)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
for (int i = 0; i < mEntryBlocks.Size(); i++)
|
||||||
|
{
|
||||||
|
if (!mEntryBlocks[i]->CheckLoopIndexYRegisters(head, yreg))
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool NativeCodeBasicBlock::ReduceIndexXYZeroShuffle(NativeCodeBasicBlock* from, int xreg, int yreg)
|
||||||
|
{
|
||||||
|
bool changed = false;
|
||||||
|
|
||||||
|
if (!mVisited)
|
||||||
|
{
|
||||||
|
if (mLoopHead)
|
||||||
|
{
|
||||||
|
if (xreg >= 0)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < mEntryBlocks.Size(); i++)
|
||||||
|
{
|
||||||
|
if (mEntryBlocks[i] != from && !mEntryBlocks[i]->CheckLoopIndexXRegisters(this, xreg))
|
||||||
|
{
|
||||||
|
xreg = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (yreg >= 0)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < mEntryBlocks.Size(); i++)
|
||||||
|
{
|
||||||
|
if (mEntryBlocks[i] != from && !mEntryBlocks[i]->CheckLoopIndexYRegisters(this, yreg))
|
||||||
|
{
|
||||||
|
yreg = -1;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else if (mNumEntries > 0)
|
||||||
|
{
|
||||||
|
if (mNumEntered > 0)
|
||||||
|
{
|
||||||
|
if (xreg != mXReg)
|
||||||
|
xreg = -1;
|
||||||
|
if (yreg != mYReg)
|
||||||
|
yreg = -1;
|
||||||
|
}
|
||||||
|
|
||||||
|
mXReg = xreg;
|
||||||
|
mYReg = yreg;
|
||||||
|
|
||||||
|
mNumEntered++;
|
||||||
|
|
||||||
|
if (mNumEntered < mNumEntries)
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
mVisited = true;
|
||||||
|
|
||||||
|
if (yreg >= 0)
|
||||||
|
{
|
||||||
|
int ix = 0, iy = 0;
|
||||||
|
while (ix < mIns.Size() && !mIns[ix].ReferencesXReg())
|
||||||
|
ix++;
|
||||||
|
while (iy < mIns.Size() && !mIns[iy].ChangesYReg() && mIns[iy].mMode != ASMIM_INDIRECT_Y)
|
||||||
|
iy++;
|
||||||
|
|
||||||
|
if (ix < mIns.Size() && mIns[ix].mType == ASMIT_LDX && mIns[ix].mMode == ASMIM_ZERO_PAGE && mIns[ix].mAddress == yreg && ((iy > ix) || mIns[iy].mType == ASMIT_LDY))
|
||||||
|
{
|
||||||
|
for (int i = 0; i < iy; i++)
|
||||||
|
{
|
||||||
|
if (mIns[i].mMode == ASMIM_ABSOLUTE_Y)
|
||||||
|
{
|
||||||
|
mIns[i].mMode = ASMIM_ABSOLUTE_X;
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (changed)
|
||||||
|
{
|
||||||
|
mIns.Insert(0, NativeCodeInstruction(mIns[ix].mIns, ASMIT_LDX, ASMIM_ZERO_PAGE, yreg));
|
||||||
|
mIns.Remove(ix + 1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i = 0; i < mIns.Size(); i++)
|
||||||
|
{
|
||||||
|
if (i + 1 < mIns.Size() &&
|
||||||
|
mIns[i].mType == ASMIT_LDX && xreg >= 0 &&
|
||||||
|
HasAsmInstructionMode(ASMIT_LDY, mIns[i].mMode) &&
|
||||||
|
!(mIns[i].mLive & LIVE_CPU_REG_Y) &&
|
||||||
|
mIns[i + 1].mMode == ASMIM_ABSOLUTE_X &&
|
||||||
|
HasAsmInstructionMode(mIns[i + 1].mType, ASMIM_ABSOLUTE_Y) &&
|
||||||
|
!(mIns[i].mLive & (LIVE_CPU_REG_X | LIVE_CPU_REG_Y)))
|
||||||
|
{
|
||||||
|
int j = i + 2;
|
||||||
|
while (j < mIns.Size() && !mIns[j].ReferencesXReg())
|
||||||
|
j++;
|
||||||
|
if (j < mIns.Size() && mIns[j].mType == ASMIT_LDX && mIns[j].mMode == ASMIM_ZERO_PAGE && mIns[j].mAddress == xreg)
|
||||||
|
{
|
||||||
|
mIns[i].mType = ASMIT_LDY;
|
||||||
|
mIns[i + 1].mMode = ASMIM_ABSOLUTE_Y;
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mIns[i].mType == ASMIT_LDX && mIns[i].mMode == ASMIM_ZERO_PAGE)
|
||||||
|
xreg = mIns[i].mAddress;
|
||||||
|
else if (mIns[i].mType == ASMIT_LDY && mIns[i].mMode == ASMIM_ZERO_PAGE)
|
||||||
|
yreg = mIns[i].mAddress;
|
||||||
|
else if (mIns[i].mType == ASMIT_STX && mIns[i].mMode == ASMIM_ZERO_PAGE && xreg == -1)
|
||||||
|
{
|
||||||
|
xreg = mIns[i].mAddress;
|
||||||
|
if (yreg == mIns[i].mAddress)
|
||||||
|
yreg = -1;
|
||||||
|
}
|
||||||
|
else if (mIns[i].mType == ASMIT_STY && mIns[i].mMode == ASMIM_ZERO_PAGE && yreg == -1)
|
||||||
|
{
|
||||||
|
yreg = mIns[i].mAddress;
|
||||||
|
if (xreg == mIns[i].mAddress)
|
||||||
|
xreg = -1;
|
||||||
|
}
|
||||||
|
else if (xreg >=0 && xreg == yreg && mIns[i].mMode == ASMIM_ABSOLUTE_Y && HasAsmInstructionMode(mIns[i].mType, ASMIM_ABSOLUTE_X))
|
||||||
|
mIns[i].mMode = ASMIM_ABSOLUTE_X;
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (mIns[i].ChangesXReg())
|
||||||
|
xreg = -1;
|
||||||
|
if (mIns[i].ChangesYReg())
|
||||||
|
yreg = -1;
|
||||||
|
if (xreg >= 0 && mIns[i].ChangesZeroPage(xreg))
|
||||||
|
xreg = -1;
|
||||||
|
if (yreg >= 0 && mIns[i].ChangesZeroPage(yreg))
|
||||||
|
yreg = -1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mTrueJump && mTrueJump->ReduceIndexXYZeroShuffle(this, xreg, yreg))
|
||||||
|
changed = true;
|
||||||
|
if (mFalseJump && mFalseJump->ReduceIndexXYZeroShuffle(this, xreg, yreg))
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return changed;
|
||||||
|
}
|
||||||
|
|
||||||
bool NativeCodeBasicBlock::IndexXYValueForwarding(int xreg, int xoffset, int xvalue, int yreg, int yoffset, int yvalue)
|
bool NativeCodeBasicBlock::IndexXYValueForwarding(int xreg, int xoffset, int xvalue, int yreg, int yoffset, int yvalue)
|
||||||
{
|
{
|
||||||
bool changed = false;
|
bool changed = false;
|
||||||
|
@ -37960,7 +38155,15 @@ bool NativeCodeBasicBlock::ValueForwarding(NativeCodeProcedure* proc, const Nati
|
||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
#if 0
|
||||||
|
if (i + 1 < mIns.Size() && mIns[i].mType == ASMIT_LDY && mIns[i].mMode == ASMIM_ZERO_PAGE &&
|
||||||
|
mNDataSet.mRegs[CPU_REG_X].mMode == NRDM_ZERO_PAGE && mNDataSet.mRegs[CPU_REG_X].mValue == mIns[i].mAddress &&
|
||||||
|
mIns[i + 1].mMode == ASMIM_ABSOLUTE_Y && HasAsmInstructionMode(mIns[i + 1].mType, ASMIM_ABSOLUTE_X))
|
||||||
|
{
|
||||||
|
mIns[i + 1].mMode = ASMIM_ABSOLUTE_X;
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
if (mIns[i].ValueForwarding(mNDataSet, carryop, !global, final, proc->mFastCallBase))
|
if (mIns[i].ValueForwarding(mNDataSet, carryop, !global, final, proc->mFastCallBase))
|
||||||
changed = true;
|
changed = true;
|
||||||
if (carryop != ASMIT_NOP)
|
if (carryop != ASMIT_NOP)
|
||||||
|
@ -55645,7 +55848,7 @@ void NativeCodeProcedure::Compile(InterCodeProcedure* proc)
|
||||||
|
|
||||||
mInterProc->mLinkerObject->mNativeProc = this;
|
mInterProc->mLinkerObject->mNativeProc = this;
|
||||||
|
|
||||||
CheckFunc = !strcmp(mIdent->mString, "main");
|
CheckFunc = !strcmp(mIdent->mString, "sidfx_loop");
|
||||||
|
|
||||||
int nblocks = proc->mBlocks.Size();
|
int nblocks = proc->mBlocks.Size();
|
||||||
tblocks = new NativeCodeBasicBlock * [nblocks];
|
tblocks = new NativeCodeBasicBlock * [nblocks];
|
||||||
|
@ -57518,6 +57721,13 @@ void NativeCodeProcedure::Optimize(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (step == 20)
|
if (step == 20)
|
||||||
|
{
|
||||||
|
ResetVisited();
|
||||||
|
if (mEntryBlock->ReduceIndexXYZeroShuffle(nullptr, -1, -1))
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (step == 21)
|
||||||
{
|
{
|
||||||
ResetVisited();
|
ResetVisited();
|
||||||
if (mEntryBlock->OptimizeLoopRegisterWrapAround())
|
if (mEntryBlock->OptimizeLoopRegisterWrapAround())
|
||||||
|
@ -57532,7 +57742,7 @@ void NativeCodeProcedure::Optimize(void)
|
||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (step == 21 && (mCompilerOptions & COPT_OPTIMIZE_BASIC))
|
if (step == 22 && (mCompilerOptions & COPT_OPTIMIZE_BASIC))
|
||||||
{
|
{
|
||||||
ResetVisited();
|
ResetVisited();
|
||||||
if (mEntryBlock->EliminateNonAliasedLocalStores())
|
if (mEntryBlock->EliminateNonAliasedLocalStores())
|
||||||
|
@ -57564,7 +57774,7 @@ void NativeCodeProcedure::Optimize(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
#if 1
|
#if 1
|
||||||
if (!changed && step < 22)
|
if (!changed && step < 23)
|
||||||
{
|
{
|
||||||
ResetIndexFlipped();
|
ResetIndexFlipped();
|
||||||
|
|
||||||
|
|
|
@ -609,6 +609,9 @@ public:
|
||||||
bool OffsetValueForwarding(const ValueNumberingDataSet & data);
|
bool OffsetValueForwarding(const ValueNumberingDataSet & data);
|
||||||
bool AbsoluteValueForwarding(const ExpandingArray<NativeCodeLoadStorePair>& npairs);
|
bool AbsoluteValueForwarding(const ExpandingArray<NativeCodeLoadStorePair>& npairs);
|
||||||
bool IndexXYValueForwarding(int xreg, int xoffset, int xvalue, int yreg, int yoffset, int yvalue);
|
bool IndexXYValueForwarding(int xreg, int xoffset, int xvalue, int yreg, int yoffset, int yvalue);
|
||||||
|
bool ReduceIndexXYZeroShuffle(NativeCodeBasicBlock* from, int xreg, int yreg);
|
||||||
|
bool CheckLoopIndexXRegisters(NativeCodeBasicBlock* head, int xreg);
|
||||||
|
bool CheckLoopIndexYRegisters(NativeCodeBasicBlock* head, int yreg);
|
||||||
|
|
||||||
void MarkLocalUsedLinkerObjects(void);
|
void MarkLocalUsedLinkerObjects(void);
|
||||||
bool RemoveLocalUnusedLinkerObjects(void);
|
bool RemoveLocalUnusedLinkerObjects(void);
|
||||||
|
|
Loading…
Reference in New Issue