Improve placement of "if" cascades

This commit is contained in:
drmortalwombat 2023-12-04 22:09:33 +01:00
parent 11f454390e
commit d48da32586
7 changed files with 311 additions and 47 deletions

View File

@ -328,6 +328,12 @@ void rirq_addr(RIRQCode * ic, byte n, void * addr)
ic->code[p + 1] = (unsigned)addr >> 8; ic->code[p + 1] = (unsigned)addr >> 8;
} }
void rirq_addrhi(RIRQCode * ic, byte n, byte hi)
{
byte p = irqai[n];
ic->code[p + 1] = hi;
}
void rirq_data(RIRQCode * ic, byte n, byte data) void rirq_data(RIRQCode * ic, byte n, byte data)
{ {
byte p = irqdi[n]; byte p = irqdi[n];

View File

@ -123,6 +123,9 @@ inline void rirq_call(RIRQCode * ic, byte n, void * addr);
// Change the address of a raster IRQ write command // Change the address of a raster IRQ write command
inline void rirq_addr(RIRQCode * ic, byte n, void * addr); inline void rirq_addr(RIRQCode * ic, byte n, void * addr);
// Change the high byte of the address of a raster IRQ write command
inline void rirq_addrhi(RIRQCode * ic, byte n, byte hi);
// Change the data of a raster IRQ write command // Change the data of a raster IRQ write command
inline void rirq_data(RIRQCode * ic, byte n, byte data); inline void rirq_data(RIRQCode * ic, byte n, byte data);

View File

@ -164,6 +164,15 @@ void vspr_init(char * screen)
} }
} }
void vspr_screen(char * screen)
{
vspriteScreen = screen + 0x3f8;
char hi = (unsigned)vspriteScreen >> 8;
#pragma unroll(8)
for(int i=0; i<VSPRITES_MAX - 8; i++)
rirq_addrhi(spirq + i, 3, hi);
}
#pragma native(vspr_init) #pragma native(vspr_init)
void vspr_set(char sp, int xpos, int ypos, char image, char color) void vspr_set(char sp, int xpos, int ypos, char image, char color)

View File

@ -68,6 +68,8 @@ inline void spr_expand(char sp, bool xexpand, bool yexpand);
void vspr_init(char * screen); void vspr_init(char * screen);
void vspr_screen(char * screen);
// set one sprite with the given attribute // set one sprite with the given attribute
void vspr_set(char sp, int xpos, int ypos, char image, char color); void vspr_set(char sp, int xpos, int ypos, char image, char color);

View File

@ -911,6 +911,20 @@ Expression* Expression::ConstantFold(Errors * errors, LinkerSection * dataSectio
ex->mDecType = mDecType; ex->mDecType = mDecType;
return ex; return ex;
} }
else if (mType == EX_INDEX && mLeft->mType == EX_VARIABLE && mLeft->mDecValue->mType == DT_VARIABLE && (mLeft->mDecValue->mFlags & DTF_GLOBAL) &&
mLeft->mDecType->mType == DT_TYPE_ARRAY && mLeft->mDecType->mStride == 0 &&
mRight->mType == EX_CONSTANT && mRight->mDecValue->mType == DT_CONST_INTEGER)
{
Expression* ex = new Expression(mLocation, EX_VARIABLE);
Declaration* dec = new Declaration(mLocation, DT_VARIABLE_REF);
dec->mFlags = mLeft->mDecValue->mFlags;
dec->mBase = mLeft->mDecValue;
dec->mOffset = mDecType->mSize * mRight->mDecValue->mInteger;
dec->mSize = mDecType->mSize;
ex->mDecValue = dec;
ex->mDecType = mDecType;
return ex;
}
else if (mType == EX_CALL && mLeft->mType == EX_CONSTANT && (mLeft->mDecValue->mFlags & DTF_INTRINSIC) && mRight->mType == EX_CONSTANT) else if (mType == EX_CALL && mLeft->mType == EX_CONSTANT && (mLeft->mDecValue->mFlags & DTF_INTRINSIC) && mRight->mType == EX_CONSTANT)
{ {
Declaration* decf = mLeft->mDecValue, * decp = mRight->mDecValue; Declaration* decf = mLeft->mDecValue, * decp = mRight->mDecValue;

View File

@ -6332,6 +6332,9 @@ bool NativeCodeBasicBlock::LoadLoadOpStoreIndirectValue(InterCodeProcedure* proc
{ {
if (rins1->mSrc[0].mMemory == IM_INDIRECT && rins0->mSrc[0].mMemory == IM_INDIRECT && wins->mSrc[1].mMemory == IM_INDIRECT) if (rins1->mSrc[0].mMemory == IM_INDIRECT && rins0->mSrc[0].mMemory == IM_INDIRECT && wins->mSrc[1].mMemory == IM_INDIRECT)
{ {
if (rins1->mSrc[0].mStride != 1 || rins0->mSrc[0].mStride != 1 || wins->mSrc[1].mStride != 1)
return false;
int size = InterTypeSize[oins->mDst.mType]; int size = InterTypeSize[oins->mDst.mType];
if (!wins->mSrc[0].mFinal) if (!wins->mSrc[0].mFinal)
@ -6643,7 +6646,7 @@ bool NativeCodeBasicBlock::LoadOpStoreIndirectValue(InterCodeProcedure* proc, co
return false; return false;
} }
if (rstride * size >= 256 || wstride * size >= 256) if (rstride * (size - 1) >= 256 || wstride * (size - 1) >= 256)
return false; return false;
uint32 rflags = NCIF_LOWER | NCIF_UPPER; uint32 rflags = NCIF_LOWER | NCIF_UPPER;
@ -9794,7 +9797,9 @@ NativeCodeBasicBlock* NativeCodeBasicBlock::BinaryOperator(InterCodeProcedure* p
{ {
if (sins1 && sins0) if (sins1 && sins0)
{ {
if (sins0->mSrc[0].mMemory == IM_INDIRECT && sins1->mSrc[0].mMemory == IM_INDIRECT && sins0->mSrc[0].mIntConst < 255 && sins1->mSrc[0].mIntConst < 255) if (sins0->mSrc[0].mMemory == IM_INDIRECT && sins1->mSrc[0].mMemory == IM_INDIRECT &&
sins0->mSrc[0].mIntConst + (InterTypeSize[ins->mDst.mType] - 1) * sins0->mSrc[0].mStride < 255 &&
sins1->mSrc[0].mIntConst + (InterTypeSize[ins->mDst.mType] - 1) * sins1->mSrc[0].mStride < 255)
{ {
if (ins->mOperator == IA_ADD) if (ins->mOperator == IA_ADD)
mIns.Push(NativeCodeInstruction(ins, ASMIT_CLC, ASMIM_IMPLIED)); mIns.Push(NativeCodeInstruction(ins, ASMIT_CLC, ASMIM_IMPLIED));
@ -9808,9 +9813,9 @@ NativeCodeBasicBlock* NativeCodeBasicBlock::BinaryOperator(InterCodeProcedure* p
mIns.Push(NativeCodeInstruction(ins, ASMIT_STA, ASMIM_ZERO_PAGE, BC_REG_WORK_Y)); mIns.Push(NativeCodeInstruction(ins, ASMIT_STA, ASMIM_ZERO_PAGE, BC_REG_WORK_Y));
else else
mIns.Push(NativeCodeInstruction(ins, ASMIT_STA, ASMIM_ZERO_PAGE, treg)); mIns.Push(NativeCodeInstruction(ins, ASMIT_STA, ASMIM_ZERO_PAGE, treg));
mIns.Push(NativeCodeInstruction(ins, ASMIT_LDY, ASMIM_IMMEDIATE, sins0->mSrc[0].mIntConst + 1)); mIns.Push(NativeCodeInstruction(ins, ASMIT_LDY, ASMIM_IMMEDIATE, sins0->mSrc[0].mIntConst + sins0->mSrc[0].mStride));
mIns.Push(NativeCodeInstruction(ins, ASMIT_LDA, ASMIM_INDIRECT_Y, BC_REG_TMP + proc->mTempOffset[sins0->mSrc[0].mTemp])); mIns.Push(NativeCodeInstruction(ins, ASMIT_LDA, ASMIM_INDIRECT_Y, BC_REG_TMP + proc->mTempOffset[sins0->mSrc[0].mTemp]));
mIns.Push(NativeCodeInstruction(ins, ASMIT_LDY, ASMIM_IMMEDIATE, sins1->mSrc[0].mIntConst + 1)); mIns.Push(NativeCodeInstruction(ins, ASMIT_LDY, ASMIM_IMMEDIATE, sins1->mSrc[0].mIntConst + sins1->mSrc[0].mStride));
mIns.Push(NativeCodeInstruction(ins, atype, ASMIM_INDIRECT_Y, BC_REG_TMP + proc->mTempOffset[sins1->mSrc[0].mTemp])); mIns.Push(NativeCodeInstruction(ins, atype, ASMIM_INDIRECT_Y, BC_REG_TMP + proc->mTempOffset[sins1->mSrc[0].mTemp]));
mIns.Push(NativeCodeInstruction(ins, ASMIT_STA, ASMIM_ZERO_PAGE, treg + 1)); mIns.Push(NativeCodeInstruction(ins, ASMIT_STA, ASMIM_ZERO_PAGE, treg + 1));
if (ins->mDst.mTemp == sins0->mSrc[0].mTemp || ins->mDst.mTemp == sins1->mSrc[0].mTemp) if (ins->mDst.mTemp == sins0->mSrc[0].mTemp || ins->mDst.mTemp == sins1->mSrc[0].mTemp)
@ -25032,7 +25037,7 @@ bool NativeCodeBasicBlock::CheckPatchFailLoop(const NativeCodeBasicBlock* block,
{ {
for (int i = 0; i < mIns.Size(); i++) for (int i = 0; i < mIns.Size(); i++)
{ {
if (mIns[i].ChangesZeroPage(reg)) if (mIns[i].ChangesZeroPage(reg) || mIns[i].ChangesZeroPage(reg + 1))
changed = true; changed = true;
} }
} }
@ -30767,6 +30772,11 @@ bool NativeCodeBasicBlock::ValueForwarding(NativeCodeProcedure* proc, const Nati
mFDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE; mFDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE;
mFDataSet.mRegs[CPU_REG_A].mValue = lins.mAddress; mFDataSet.mRegs[CPU_REG_A].mValue = lins.mAddress;
} }
else if (lins.mType == ASMIT_ORA || lins.mType == ASMIT_AND || lins.mType == ASMIT_EOR || lins.mType == ASMIT_ADC || lins.mType == ASMIT_SBC)
{
mFDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE;
mFDataSet.mRegs[CPU_REG_A].mValue = 0;
}
else if (lins.mType == ASMIT_TXA || lins.mType == ASMIT_TAX) else if (lins.mType == ASMIT_TXA || lins.mType == ASMIT_TAX)
{ {
mFDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE; mFDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE;
@ -30774,6 +30784,16 @@ bool NativeCodeBasicBlock::ValueForwarding(NativeCodeProcedure* proc, const Nati
mFDataSet.mRegs[CPU_REG_X].mMode = NRDM_IMMEDIATE; mFDataSet.mRegs[CPU_REG_X].mMode = NRDM_IMMEDIATE;
mFDataSet.mRegs[CPU_REG_X].mValue = 0; mFDataSet.mRegs[CPU_REG_X].mValue = 0;
} }
else if (lins.mType == ASMIT_INX || lins.mType == ASMIT_DEX)
{
mFDataSet.mRegs[CPU_REG_X].mMode = NRDM_IMMEDIATE;
mFDataSet.mRegs[CPU_REG_X].mValue = 0;
}
else if (lins.mType == ASMIT_INY || lins.mType == ASMIT_DEY)
{
mFDataSet.mRegs[CPU_REG_Y].mMode = NRDM_IMMEDIATE;
mFDataSet.mRegs[CPU_REG_Y].mValue = 0;
}
else if ((lins.mType == ASMIT_INC || lins.mType == ASMIT_DEC) && lins.mMode == ASMIM_ZERO_PAGE) else if ((lins.mType == ASMIT_INC || lins.mType == ASMIT_DEC) && lins.mMode == ASMIM_ZERO_PAGE)
{ {
mFDataSet.mRegs[lins.mAddress].mMode = NRDM_IMMEDIATE; mFDataSet.mRegs[lins.mAddress].mMode = NRDM_IMMEDIATE;
@ -30855,6 +30875,11 @@ bool NativeCodeBasicBlock::ValueForwarding(NativeCodeProcedure* proc, const Nati
mNDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE; mNDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE;
mNDataSet.mRegs[CPU_REG_A].mValue = lins.mAddress; mNDataSet.mRegs[CPU_REG_A].mValue = lins.mAddress;
} }
else if (lins.mType == ASMIT_ORA || lins.mType == ASMIT_AND || lins.mType == ASMIT_EOR || lins.mType == ASMIT_ADC || lins.mType == ASMIT_SBC)
{
mNDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE;
mNDataSet.mRegs[CPU_REG_A].mValue = 0;
}
else if (lins.mType == ASMIT_TXA || lins.mType == ASMIT_TAX) else if (lins.mType == ASMIT_TXA || lins.mType == ASMIT_TAX)
{ {
mNDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE; mNDataSet.mRegs[CPU_REG_A].mMode = NRDM_IMMEDIATE;
@ -30862,6 +30887,16 @@ bool NativeCodeBasicBlock::ValueForwarding(NativeCodeProcedure* proc, const Nati
mNDataSet.mRegs[CPU_REG_X].mMode = NRDM_IMMEDIATE; mNDataSet.mRegs[CPU_REG_X].mMode = NRDM_IMMEDIATE;
mNDataSet.mRegs[CPU_REG_X].mValue = 0; mNDataSet.mRegs[CPU_REG_X].mValue = 0;
} }
else if (lins.mType == ASMIT_INX || lins.mType == ASMIT_DEX)
{
mNDataSet.mRegs[CPU_REG_X].mMode = NRDM_IMMEDIATE;
mNDataSet.mRegs[CPU_REG_X].mValue = 0;
}
else if (lins.mType == ASMIT_INY || lins.mType == ASMIT_DEY)
{
mNDataSet.mRegs[CPU_REG_Y].mMode = NRDM_IMMEDIATE;
mNDataSet.mRegs[CPU_REG_Y].mValue = 0;
}
else if ((lins.mType == ASMIT_INC || lins.mType == ASMIT_DEC) && lins.mMode == ASMIM_ZERO_PAGE) else if ((lins.mType == ASMIT_INC || lins.mType == ASMIT_DEC) && lins.mMode == ASMIM_ZERO_PAGE)
{ {
mNDataSet.mRegs[lins.mAddress].mMode = NRDM_IMMEDIATE; mNDataSet.mRegs[lins.mAddress].mMode = NRDM_IMMEDIATE;
@ -34741,6 +34776,7 @@ bool NativeCodeBasicBlock::CollectSingleEntryGenericLoop(NativeCodeProcedure* pr
return false; return false;
} }
bool NativeCodeBasicBlock::OptimizeFindLoop(NativeCodeProcedure* proc) bool NativeCodeBasicBlock::OptimizeFindLoop(NativeCodeProcedure* proc)
{ {
bool changed = false; bool changed = false;
@ -34753,15 +34789,26 @@ bool NativeCodeBasicBlock::OptimizeFindLoop(NativeCodeProcedure* proc)
if (mLoopHead && mNumEntries == 2) if (mLoopHead && mNumEntries == 2)
{ {
if (mTrueJump && mFalseJump && if (mTrueJump && mFalseJump && mFalseJump->mNumEntries == 1 && mTrueJump->mNumEntries == 1)
mFalseJump->mNumEntries == 1 && !mFalseJump->mFalseJump && mFalseJump->mTrueJump == this && {
mTrueJump->mNumEntries == 1) NativeCodeBasicBlock* succ = nullptr, * body = nullptr;
if (!mFalseJump->mFalseJump && mFalseJump->mTrueJump == this)
{
succ = mTrueJump;
body = mFalseJump;
}
else if (!mTrueJump->mFalseJump && mTrueJump->mTrueJump == this)
{
succ = mFalseJump;
body = mTrueJump;
}
if (succ)
{ {
NativeCodeBasicBlock* pred = mEntryBlocks[0]; NativeCodeBasicBlock* pred = mEntryBlocks[0];
if (pred == mFalseJump) if (pred == mFalseJump)
pred = mEntryBlocks[0]; pred = mEntryBlocks[0];
NativeCodeBasicBlock * succ = mTrueJump;
NativeCodeBasicBlock * body = mFalseJump;
if (mIns.Size() > 0 && body->mIns.Size() > 0) if (mIns.Size() > 0 && body->mIns.Size() > 0)
{ {
@ -34802,6 +34849,141 @@ bool NativeCodeBasicBlock::OptimizeFindLoop(NativeCodeProcedure* proc)
} }
} }
} }
if (!ReferencesYReg() && body->mIns.Size() > 0 && body->mIns[0].mType == ASMIT_LDY && body->mIns[0].mMode == ASMIM_ZERO_PAGE && !mExitRequiredRegs[CPU_REG_Y])
{
int incdec = 0;
bool fail = false;
int addr = body->mIns[0].mAddress;
if (!ReferencesZeroPage(addr))
{
for (int i = 1; i < body->mIns.Size(); i++)
{
const NativeCodeInstruction& bins(body->mIns[i]);
if (bins.mMode == ASMIM_ZERO_PAGE && bins.mAddress == addr)
{
if (bins.mType == ASMIT_INC)
incdec++;
else if (bins.mType == ASMIT_DEC)
incdec--;
else
{
fail = true;
break;
}
}
else if (bins.ReferencesZeroPage(addr))
fail = true;
else if (bins.ChangesYReg())
fail = true;
}
if (!fail)
{
pred->mIns.Push(NativeCodeInstruction(body->mIns[0].mIns, ASMIT_LDY, ASMIM_ZERO_PAGE, addr));
body->mIns.Remove(0);
while (incdec > 0)
{
body->mIns.Push(NativeCodeInstruction(body->mIns[0].mIns, ASMIT_INY));
incdec--;
}
while (incdec < 0)
{
body->mIns.Push(NativeCodeInstruction(body->mIns[0].mIns, ASMIT_DEY));
incdec++;
}
for (int i = 0; i < body->mIns.Size(); i++)
{
if (body->mIns[i].mMode == ASMIM_ZERO_PAGE && body->mIns[i].mAddress == addr)
{
body->mIns[i].mType = ASMIT_NOP; body->mIns[i].mMode = ASMIM_IMPLIED;
}
}
succ->mIns.Insert(0, NativeCodeInstruction(body->mIns[0].mIns, ASMIT_STY, ASMIM_ZERO_PAGE, addr));
body->mEntryRequiredRegs += CPU_REG_Y;
body->mExitRequiredRegs += CPU_REG_Y;
mEntryRequiredRegs += CPU_REG_Y;
mExitRequiredRegs += CPU_REG_Y;
succ->mEntryRequiredRegs += CPU_REG_Y;
for (int i = 0; i < mIns.Size(); i++)
mIns[i].mLive |= LIVE_CPU_REG_Y;
for (int i = 0; i < body->mIns.Size(); i++)
body->mIns[i].mLive |= LIVE_CPU_REG_Y;
changed = true;
}
}
}
else if (!ReferencesXReg() && body->mIns.Size() > 0 && body->mIns[0].mType == ASMIT_LDX && body->mIns[0].mMode == ASMIM_ZERO_PAGE && !mExitRequiredRegs[CPU_REG_X])
{
int incdec = 0;
bool fail = false;
int addr = body->mIns[0].mAddress;
if (!ReferencesZeroPage(addr))
{
for (int i = 1; i < body->mIns.Size(); i++)
{
const NativeCodeInstruction& bins(body->mIns[i]);
if (bins.mMode == ASMIM_ZERO_PAGE && bins.mAddress == addr)
{
if (bins.mType == ASMIT_INC)
incdec++;
else if (bins.mType == ASMIT_DEC)
incdec--;
else
{
fail = true;
break;
}
}
else if (bins.ReferencesZeroPage(addr))
fail = true;
else if (bins.ChangesXReg())
fail = true;
}
if (!fail)
{
pred->mIns.Push(NativeCodeInstruction(body->mIns[0].mIns, ASMIT_LDX, ASMIM_ZERO_PAGE, addr));
body->mIns.Remove(0);
while (incdec > 0)
{
body->mIns.Push(NativeCodeInstruction(body->mIns[0].mIns, ASMIT_INX));
incdec--;
}
while (incdec < 0)
{
body->mIns.Push(NativeCodeInstruction(body->mIns[0].mIns, ASMIT_DEX));
incdec++;
}
for (int i = 0; i < body->mIns.Size(); i++)
{
if (body->mIns[i].mMode == ASMIM_ZERO_PAGE && body->mIns[i].mAddress == addr)
{
body->mIns[i].mType = ASMIT_NOP; body->mIns[i].mMode = ASMIM_IMPLIED;
}
}
succ->mIns.Insert(0, NativeCodeInstruction(body->mIns[0].mIns, ASMIT_STX, ASMIM_ZERO_PAGE, addr));
body->mEntryRequiredRegs += CPU_REG_X;
body->mExitRequiredRegs += CPU_REG_X;
mEntryRequiredRegs += CPU_REG_X;
mExitRequiredRegs += CPU_REG_X;
succ->mEntryRequiredRegs += CPU_REG_X;
for (int i = 0; i < mIns.Size(); i++)
mIns[i].mLive |= LIVE_CPU_REG_X;
for (int i = 0; i < body->mIns.Size(); i++)
body->mIns[i].mLive |= LIVE_CPU_REG_X;
changed = true;
}
}
}
}
} }
} }
@ -40397,6 +40579,18 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(NativeCodeProcedure* proc, int pass
mIns[i + 3].mType = ASMIT_NOP; mIns[i + 3].mMode = ASMIM_IMPLIED; mIns[i + 3].mType = ASMIT_NOP; mIns[i + 3].mMode = ASMIM_IMPLIED;
progress = true; progress = true;
} }
else if (
mIns[i + 0].mType == ASMIT_SEC &&
mIns[i + 1].mType == ASMIT_SBC && mIns[i + 1].mMode == ASMIM_IMMEDIATE &&
mIns[i + 2].mType == ASMIT_CLC &&
mIns[i + 3].mType == ASMIT_ADC && mIns[i + 3].mMode == ASMIM_IMMEDIATE && !(mIns[i + 3].mLive & LIVE_CPU_REG_C))
{
mIns[i + 0].mType = ASMIT_NOP; mIns[i + 0].mMode = ASMIM_IMPLIED;
mIns[i + 1].mType = ASMIT_NOP; mIns[i + 1].mMode = ASMIM_IMPLIED;
mIns[i + 3].mAddress = (mIns[i + 3].mAddress - mIns[i + 1].mAddress) & 0xff;
progress = true;
}
else if ( else if (
mIns[i + 0].mType == ASMIT_CLC && mIns[i + 0].mType == ASMIT_CLC &&
mIns[i + 1].mType == ASMIT_LDA && mIns[i + 1].mMode == ASMIM_ZERO_PAGE && mIns[i + 1].mType == ASMIT_LDA && mIns[i + 1].mMode == ASMIM_ZERO_PAGE &&
@ -40566,6 +40760,22 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(NativeCodeProcedure* proc, int pass
progress = true; progress = true;
} }
#endif #endif
#if 1
else if (
mIns[i + 0].mType == ASMIT_EOR && mIns[i + 0].mMode == ASMIM_IMMEDIATE && mIns[i + 0].mAddress == 0xff &&
mIns[i + 1].mType == ASMIT_CLC &&
mIns[i + 2].mType == ASMIT_ADC &&
mIns[i + 3].mType == ASMIT_EOR && mIns[i + 3].mMode == ASMIM_IMMEDIATE && mIns[i + 3].mAddress == 0xff && !(mIns[i + 3].mLive & LIVE_CPU_REG_C))
{
mIns[i + 1].mType = ASMIT_SEC;
mIns[i + 2].mType = ASMIT_SBC;
mIns[i + 0].mType = ASMIT_NOP; mIns[i + 0].mMode = ASMIM_IMPLIED;
mIns[i + 3].mType = ASMIT_NOP; mIns[i + 3].mMode = ASMIM_IMPLIED;
progress = true;
}
#endif
#if 1 #if 1
else if ( else if (
mIns[i + 0].mType == ASMIT_LDA && mIns[i + 0].mMode == ASMIM_IMMEDIATE && mIns[i + 0].mType == ASMIT_LDA && mIns[i + 0].mMode == ASMIM_IMMEDIATE &&
@ -43056,21 +43266,21 @@ NativeCodeBasicBlock* NativeCodeBasicBlock::BypassEmptyBlocks(void)
int NativeCodeBasicBlock::LeadsInto(NativeCodeBasicBlock* block, int dist) int NativeCodeBasicBlock::LeadsInto(NativeCodeBasicBlock* block, int dist)
{ {
if (mPlaced) if (mPlaced)
return 6; return 1000;
else if (mTrueJump == block || mFalseJump == block) else if (this == block)
return dist; return 0;
else if (dist < 5) else if (dist < 6)
{ {
int d0 = mTrueJump ? mTrueJump->LeadsInto(block, dist + 1) : 6; int d0 = mTrueJump ? mTrueJump->LeadsInto(block, dist + 1) : 1000;
int d1 = mFalseJump ? mFalseJump->LeadsInto(block, dist + 1) : 6; int d1 = mFalseJump ? mFalseJump->LeadsInto(block, dist + 1) : 1000;
if (d0 < d1) int d = (d0 < d1 ? d0 : d1) + mCode.Size();
return d0;
else if (d < 100)
return d1; return d;
} }
return 6; return 1000;
} }
void NativeCodeBasicBlock::BuildPlacement(ExpandingArray<NativeCodeBasicBlock*>& placement) void NativeCodeBasicBlock::BuildPlacement(ExpandingArray<NativeCodeBasicBlock*>& placement)
@ -43133,6 +43343,22 @@ void NativeCodeBasicBlock::BuildPlacement(ExpandingArray<NativeCodeBasicBlock*>&
mFalseJump->BuildPlacement(placement); mFalseJump->BuildPlacement(placement);
mTrueJump->BuildPlacement(placement); mTrueJump->BuildPlacement(placement);
} }
else if (!mTrueJump->mFalseJump && mTrueJump->mTrueJump && mTrueJump->mCode.Size() < 100 && mFalseJump->LeadsInto(mTrueJump->mTrueJump, 0) < 100)
{
mTrueJump->mPlaced = true;
mTrueJump->mPlace = placement.Size();
placement.Push(mTrueJump);
mFalseJump->BuildPlacement(placement);
}
else if (!mFalseJump->mFalseJump && mFalseJump->mTrueJump && mFalseJump->mCode.Size() < 100 && mTrueJump->LeadsInto(mFalseJump->mTrueJump, 0) < 100)
{
mFalseJump->mPlaced = true;
mFalseJump->mPlace = placement.Size();
placement.Push(mFalseJump);
mTrueJump->BuildPlacement(placement);
}
else if (mTrueJump->mIns.Size() == 0 && mTrueJump->mFalseJump == mFalseJump->mFalseJump && mTrueJump->mTrueJump == mFalseJump->mTrueJump) else if (mTrueJump->mIns.Size() == 0 && mTrueJump->mFalseJump == mFalseJump->mFalseJump && mTrueJump->mTrueJump == mFalseJump->mTrueJump)
{ {
mTrueJump->mPlaced = true; mTrueJump->mPlaced = true;
@ -43623,7 +43849,7 @@ void NativeCodeProcedure::Compile(InterCodeProcedure* proc)
{ {
mInterProc = proc; mInterProc = proc;
CheckFunc = !strcmp(mInterProc->mIdent->mString, "valinc"); CheckFunc = !strcmp(mInterProc->mIdent->mString, "vspr_update");
int nblocks = proc->mBlocks.Size(); int nblocks = proc->mBlocks.Size();
tblocks = new NativeCodeBasicBlock * [nblocks]; tblocks = new NativeCodeBasicBlock * [nblocks];
@ -44080,6 +44306,8 @@ void NativeCodeProcedure::Compile(InterCodeProcedure* proc)
void NativeCodeProcedure::Assemble(void) void NativeCodeProcedure::Assemble(void)
{ {
CheckFunc = !strcmp(mInterProc->mIdent->mString, "vspr_update");
if (mInterProc->mCompilerOptions & COPT_OPTIMIZE_MERGE_CALLS) if (mInterProc->mCompilerOptions & COPT_OPTIMIZE_MERGE_CALLS)
{ {
ResetVisited(); ResetVisited();
@ -44416,13 +44644,12 @@ void NativeCodeProcedure::Optimize(void)
mEntryBlock->CheckBlocks(); mEntryBlock->CheckBlocks();
#endif #endif
#if 1 #if 1
ResetVisited(); ResetVisited();
if (mEntryBlock->PeepHoleOptimizer(this, step)) if (mEntryBlock->PeepHoleOptimizer(this, step))
changed = true; changed = true;
#endif
#endif
if (step == 2) if (step == 2)
{ {
ResetVisited(); ResetVisited();
@ -45066,7 +45293,6 @@ void NativeCodeProcedure::Optimize(void)
else else
cnt++; cnt++;
} while (changed); } while (changed);
#if 1 #if 1

View File

@ -364,7 +364,7 @@ void SourceFile::ReadCharPad(SourceFileDecoder decoder)
fread(&ctmMarker, 2, 1, mFile); fread(&ctmMarker, 2, 1, mFile);
if (ctmHeader.mColorMethod == 2 && (decoder == SFD_CTM_CHAR_ATTRIB_1 || decoder == SFD_CTM_CHAR_ATTRIB_2)) if (decoder == SFD_CTM_CHAR_ATTRIB_1 || decoder == SFD_CTM_CHAR_ATTRIB_2)
{ {
mMemSize = numChars; mMemSize = numChars;
mLimit = mMemSize; mLimit = mMemSize;
@ -372,7 +372,7 @@ void SourceFile::ReadCharPad(SourceFileDecoder decoder)
mMemData = new uint8[mMemSize]; mMemData = new uint8[mMemSize];
} }
if (ctmHeader.mColorMethod == 2 && decoder == SFD_CTM_CHAR_ATTRIB_1) if (decoder == SFD_CTM_CHAR_ATTRIB_1)
{ {
for (int i = 0; i < mMemSize; i++) for (int i = 0; i < mMemSize; i++)
{ {
@ -429,6 +429,10 @@ void SourceFile::ReadCharPad(SourceFileDecoder decoder)
fseek(mFile, numChars, SEEK_CUR); fseek(mFile, numChars, SEEK_CUR);
} }
} }
else if (decoder == SFD_CTM_CHAR_ATTRIB_1)
{
return;
}
if (ctmHeader.mFlags & 1) if (ctmHeader.mFlags & 1)
{ {