Fix emulator cycle count
This commit is contained in:
parent
94181326ca
commit
1c0db235a8
|
@ -115,7 +115,7 @@ void Emulator::DumpCycles(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, int & cycles)
|
bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, int & cycles, bool cross, bool indexed)
|
||||||
{
|
{
|
||||||
int t;
|
int t;
|
||||||
|
|
||||||
|
@ -134,12 +134,14 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
|
|
||||||
mRegA = (t & 255);
|
mRegA = (t & 255);
|
||||||
UpdateStatusCarry(mRegA, t >= 256);
|
UpdateStatusCarry(mRegA, t >= 256);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_AND:
|
case ASMIT_AND:
|
||||||
if (mode != ASMIM_IMMEDIATE)
|
if (mode != ASMIM_IMMEDIATE)
|
||||||
addr = mMemory[addr];
|
addr = mMemory[addr];
|
||||||
mRegA &= addr;
|
mRegA &= addr;
|
||||||
UpdateStatus(mRegA);
|
UpdateStatus(mRegA);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_ASL:
|
case ASMIT_ASL:
|
||||||
if (mode == ASMIM_IMPLIED)
|
if (mode == ASMIM_IMPLIED)
|
||||||
|
@ -154,19 +156,29 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
mMemory[addr] = t & 255;
|
mMemory[addr] = t & 255;
|
||||||
UpdateStatusCarry(t & 255, t >= 256);
|
UpdateStatusCarry(t & 255, t >= 256);
|
||||||
cycles += 2;
|
cycles += 2;
|
||||||
|
if (indexed) cycles++;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_BCC:
|
case ASMIT_BCC:
|
||||||
if (!(mRegP & STATUS_CARRY))
|
if (!(mRegP & STATUS_CARRY))
|
||||||
|
{
|
||||||
mIP = addr;
|
mIP = addr;
|
||||||
|
cycles++;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_BCS:
|
case ASMIT_BCS:
|
||||||
if ((mRegP & STATUS_CARRY))
|
if ((mRegP & STATUS_CARRY))
|
||||||
|
{
|
||||||
mIP = addr;
|
mIP = addr;
|
||||||
|
cycles++;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_BEQ:
|
case ASMIT_BEQ:
|
||||||
if ((mRegP & STATUS_ZERO))
|
if ((mRegP & STATUS_ZERO))
|
||||||
|
{
|
||||||
mIP = addr;
|
mIP = addr;
|
||||||
|
cycles++;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_BIT:
|
case ASMIT_BIT:
|
||||||
t = mMemory[addr];
|
t = mMemory[addr];
|
||||||
|
@ -235,6 +247,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
mRegP |= STATUS_OVERFLOW;
|
mRegP |= STATUS_OVERFLOW;
|
||||||
|
|
||||||
UpdateStatusCarry(t & 255, t >= 256);
|
UpdateStatusCarry(t & 255, t >= 256);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_CPX:
|
case ASMIT_CPX:
|
||||||
if (mode != ASMIM_IMMEDIATE)
|
if (mode != ASMIM_IMMEDIATE)
|
||||||
|
@ -275,6 +288,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
mMemory[addr] = t & 255;
|
mMemory[addr] = t & 255;
|
||||||
UpdateStatus(t & 255);
|
UpdateStatus(t & 255);
|
||||||
cycles += 2;
|
cycles += 2;
|
||||||
|
if (indexed) cycles++;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_DEX:
|
case ASMIT_DEX:
|
||||||
|
@ -292,6 +306,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
addr = mMemory[addr];
|
addr = mMemory[addr];
|
||||||
mRegA ^= addr;
|
mRegA ^= addr;
|
||||||
UpdateStatus(mRegA);
|
UpdateStatus(mRegA);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_INC:
|
case ASMIT_INC:
|
||||||
if (mode == ASMIM_IMPLIED)
|
if (mode == ASMIM_IMPLIED)
|
||||||
|
@ -306,6 +321,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
mMemory[addr] = t & 255;
|
mMemory[addr] = t & 255;
|
||||||
UpdateStatus(t & 255);
|
UpdateStatus(t & 255);
|
||||||
cycles += 2;
|
cycles += 2;
|
||||||
|
if (indexed) cycles++;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_INX:
|
case ASMIT_INX:
|
||||||
|
@ -334,18 +350,21 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
addr = mMemory[addr];
|
addr = mMemory[addr];
|
||||||
mRegA = addr;
|
mRegA = addr;
|
||||||
UpdateStatus(mRegA);
|
UpdateStatus(mRegA);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_LDX:
|
case ASMIT_LDX:
|
||||||
if (mode != ASMIM_IMMEDIATE)
|
if (mode != ASMIM_IMMEDIATE)
|
||||||
addr = mMemory[addr];
|
addr = mMemory[addr];
|
||||||
mRegX = addr;
|
mRegX = addr;
|
||||||
UpdateStatus(mRegX);
|
UpdateStatus(mRegX);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_LDY:
|
case ASMIT_LDY:
|
||||||
if (mode != ASMIM_IMMEDIATE)
|
if (mode != ASMIM_IMMEDIATE)
|
||||||
addr = mMemory[addr];
|
addr = mMemory[addr];
|
||||||
mRegY = addr;
|
mRegY = addr;
|
||||||
UpdateStatus(mRegY);
|
UpdateStatus(mRegY);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_LSR:
|
case ASMIT_LSR:
|
||||||
if (mode == ASMIM_IMPLIED)
|
if (mode == ASMIM_IMPLIED)
|
||||||
|
@ -362,6 +381,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
mMemory[addr] = t & 255;
|
mMemory[addr] = t & 255;
|
||||||
UpdateStatusCarry(t & 255, c != 0);
|
UpdateStatusCarry(t & 255, c != 0);
|
||||||
cycles += 2;
|
cycles += 2;
|
||||||
|
if (indexed) cycles++;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_NOP:
|
case ASMIT_NOP:
|
||||||
|
@ -371,6 +391,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
addr = mMemory[addr];
|
addr = mMemory[addr];
|
||||||
mRegA |= addr;
|
mRegA |= addr;
|
||||||
UpdateStatus(mRegA);
|
UpdateStatus(mRegA);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_PHA:
|
case ASMIT_PHA:
|
||||||
mMemory[0x100 + mRegS] = mRegA;
|
mMemory[0x100 + mRegS] = mRegA;
|
||||||
|
@ -405,6 +426,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
mMemory[addr] = t & 255;
|
mMemory[addr] = t & 255;
|
||||||
UpdateStatusCarry(t & 255, t >= 256);
|
UpdateStatusCarry(t & 255, t >= 256);
|
||||||
cycles+=2;
|
cycles+=2;
|
||||||
|
if (indexed) cycles++;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_ROR:
|
case ASMIT_ROR:
|
||||||
|
@ -422,6 +444,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
mMemory[addr] = t & 255;
|
mMemory[addr] = t & 255;
|
||||||
UpdateStatusCarry(t & 255, c != 0);
|
UpdateStatusCarry(t & 255, c != 0);
|
||||||
cycles += 2;
|
cycles += 2;
|
||||||
|
if (indexed) cycles++;
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case ASMIT_RTI:
|
case ASMIT_RTI:
|
||||||
|
@ -444,6 +467,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
|
|
||||||
mRegA = (t & 255);
|
mRegA = (t & 255);
|
||||||
UpdateStatusCarry(t & 255, t >= 256);
|
UpdateStatusCarry(t & 255, t >= 256);
|
||||||
|
if (cross) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_SEC:
|
case ASMIT_SEC:
|
||||||
mRegP |= STATUS_CARRY;
|
mRegP |= STATUS_CARRY;
|
||||||
|
@ -454,6 +478,7 @@ bool Emulator::EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, in
|
||||||
break;
|
break;
|
||||||
case ASMIT_STA:
|
case ASMIT_STA:
|
||||||
mMemory[addr] = mRegA;
|
mMemory[addr] = mRegA;
|
||||||
|
if (indexed) cycles++;
|
||||||
break;
|
break;
|
||||||
case ASMIT_STX:
|
case ASMIT_STX:
|
||||||
mMemory[addr] = mRegX;
|
mMemory[addr] = mRegX;
|
||||||
|
@ -512,13 +537,12 @@ int Emulator::Emulate(int startIP, int trace)
|
||||||
mMemory[0x1fe] = 0xff;
|
mMemory[0x1fe] = 0xff;
|
||||||
mMemory[0x1ff] = 0xff;
|
mMemory[0x1ff] = 0xff;
|
||||||
|
|
||||||
int ticks = 0;
|
int tcycles = 0, cycles = 0;
|
||||||
while (mIP != 0)
|
while (mIP != 0)
|
||||||
{
|
{
|
||||||
if (mJiffies)
|
if (mJiffies)
|
||||||
{
|
{
|
||||||
ticks++;
|
if (cycles >= tcycles + 16667)
|
||||||
if (ticks > 4500)
|
|
||||||
{
|
{
|
||||||
mMemory[0xa2]++;
|
mMemory[0xa2]++;
|
||||||
if (!mMemory[0xa2])
|
if (!mMemory[0xa2])
|
||||||
|
@ -529,7 +553,7 @@ int Emulator::Emulate(int startIP, int trace)
|
||||||
mMemory[0xa0]++;
|
mMemory[0xa0]++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
ticks = 0;
|
tcycles += 16667;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -561,6 +585,8 @@ int Emulator::Emulate(int startIP, int trace)
|
||||||
int addr = 0, taddr;
|
int addr = 0, taddr;
|
||||||
int ip = mIP;
|
int ip = mIP;
|
||||||
int iip = mMemory[BC_REG_IP] + 256 * mMemory[BC_REG_IP + 1];
|
int iip = mMemory[BC_REG_IP] + 256 * mMemory[BC_REG_IP + 1];
|
||||||
|
bool cross = false, indexed = false;
|
||||||
|
int icycles = 0;
|
||||||
|
|
||||||
mIP++;
|
mIP++;
|
||||||
switch (d.mMode)
|
switch (d.mMode)
|
||||||
|
@ -568,56 +594,60 @@ int Emulator::Emulate(int startIP, int trace)
|
||||||
case ASMIM_IMPLIED:
|
case ASMIM_IMPLIED:
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x __ __ %s (A:%02x X:%02x Y:%02x P:%02x S:%02x)\n", iip, ip, mMemory[ip], AsmInstructionNames[d.mType], mRegA, mRegX, mRegY, mRegP, mRegS);
|
printf("%04x : %04x %02x __ __ %s (A:%02x X:%02x Y:%02x P:%02x S:%02x)\n", iip, ip, mMemory[ip], AsmInstructionNames[d.mType], mRegA, mRegX, mRegY, mRegP, mRegS);
|
||||||
mCycles[ip] += 2;
|
icycles = 2;
|
||||||
break;
|
break;
|
||||||
case ASMIM_IMMEDIATE:
|
case ASMIM_IMMEDIATE:
|
||||||
addr = mMemory[mIP++];
|
addr = mMemory[mIP++];
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x __ %s #$%02x (A:%02x X:%02x Y:%02x P:%02x S:%02x)\n", iip, ip, mMemory[ip], mMemory[ip+1], AsmInstructionNames[d.mType], addr, mRegA, mRegX, mRegY, mRegP, mRegS);
|
printf("%04x : %04x %02x %02x __ %s #$%02x (A:%02x X:%02x Y:%02x P:%02x S:%02x)\n", iip, ip, mMemory[ip], mMemory[ip+1], AsmInstructionNames[d.mType], addr, mRegA, mRegX, mRegY, mRegP, mRegS);
|
||||||
mCycles[ip] += 2;
|
icycles = 2;
|
||||||
break;
|
break;
|
||||||
case ASMIM_ZERO_PAGE:
|
case ASMIM_ZERO_PAGE:
|
||||||
addr = mMemory[mIP++];
|
addr = mMemory[mIP++];
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x __ %s $%02x (A:%02x X:%02x Y:%02x P:%02x S:%02x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], addr, mRegA, mRegX, mRegY, mRegP, mRegS, mMemory[addr]);
|
printf("%04x : %04x %02x %02x __ %s $%02x (A:%02x X:%02x Y:%02x P:%02x S:%02x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], addr, mRegA, mRegX, mRegY, mRegP, mRegS, mMemory[addr]);
|
||||||
mCycles[ip] += 3;
|
icycles = 3;
|
||||||
break;
|
break;
|
||||||
case ASMIM_ZERO_PAGE_X:
|
case ASMIM_ZERO_PAGE_X:
|
||||||
taddr = mMemory[mIP++];
|
taddr = mMemory[mIP++];
|
||||||
addr = (taddr + mRegX) & 0xff;
|
addr = (taddr + mRegX) & 0xff;
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x __ %s $%02x,x (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
printf("%04x : %04x %02x %02x __ %s $%02x,x (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
||||||
mCycles[ip] += 3;
|
icycles = 4;
|
||||||
break;
|
break;
|
||||||
case ASMIM_ZERO_PAGE_Y:
|
case ASMIM_ZERO_PAGE_Y:
|
||||||
taddr = mMemory[mIP++];
|
taddr = mMemory[mIP++];
|
||||||
addr = (taddr + mRegY) & 0xff;
|
addr = (taddr + mRegY) & 0xff;
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x __ %s $%02x,y (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
printf("%04x : %04x %02x %02x __ %s $%02x,y (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
||||||
mCycles[ip] += 3;
|
icycles = 4;
|
||||||
break;
|
break;
|
||||||
case ASMIM_ABSOLUTE:
|
case ASMIM_ABSOLUTE:
|
||||||
addr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
addr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x %02x %s $%04x (A:%02x X:%02x Y:%02x P:%02x S:%02x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], addr, mRegA, mRegX, mRegY, mRegP, mRegS, mMemory[addr]);
|
printf("%04x : %04x %02x %02x %02x %s $%04x (A:%02x X:%02x Y:%02x P:%02x S:%02x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], addr, mRegA, mRegX, mRegY, mRegP, mRegS, mMemory[addr]);
|
||||||
mIP += 2;
|
mIP += 2;
|
||||||
mCycles[ip] += 4;
|
icycles = 4;
|
||||||
break;
|
break;
|
||||||
case ASMIM_ABSOLUTE_X:
|
case ASMIM_ABSOLUTE_X:
|
||||||
taddr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
taddr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
||||||
addr = (taddr + mRegX) & 0xffff;
|
addr = (taddr + mRegX) & 0xffff;
|
||||||
|
cross = mMemory[mIP] + mRegX >= 256;
|
||||||
|
indexed = true;
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x %02x %s $%04x,x (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
printf("%04x : %04x %02x %02x %02x %s $%04x,x (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
||||||
mIP += 2;
|
mIP += 2;
|
||||||
mCycles[ip] += 5;
|
icycles = 4;
|
||||||
break;
|
break;
|
||||||
case ASMIM_ABSOLUTE_Y:
|
case ASMIM_ABSOLUTE_Y:
|
||||||
taddr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
taddr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
||||||
addr = (taddr + mRegY) & 0xffff;
|
addr = (taddr + mRegY) & 0xffff;
|
||||||
|
cross = mMemory[mIP] + mRegY >= 256;
|
||||||
|
indexed = true;
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x %02x %s $%04x,y (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
printf("%04x : %04x %02x %02x %02x %s $%04x,y (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
||||||
mIP += 2;
|
mIP += 2;
|
||||||
mCycles[ip] += 5;
|
icycles = 4;
|
||||||
break;
|
break;
|
||||||
case ASMIM_INDIRECT:
|
case ASMIM_INDIRECT:
|
||||||
taddr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
taddr = mMemory[mIP] + 256 * mMemory[mIP + 1];
|
||||||
|
@ -625,21 +655,23 @@ int Emulator::Emulate(int startIP, int trace)
|
||||||
addr = mMemory[taddr] + 256 * mMemory[taddr + 1];
|
addr = mMemory[taddr] + 256 * mMemory[taddr + 1];
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x %02x %s ($%04x) (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr);
|
printf("%04x : %04x %02x %02x %02x %s ($%04x) (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], mMemory[ip + 2], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr);
|
||||||
mCycles[ip] += 6;
|
icycles = 6;
|
||||||
break;
|
break;
|
||||||
case ASMIM_INDIRECT_X:
|
case ASMIM_INDIRECT_X:
|
||||||
taddr = (mMemory[mIP++] + mRegX) & 0xff;
|
taddr = (mMemory[mIP++] + mRegX) & 0xff;
|
||||||
addr = mMemory[taddr] + 256 * mMemory[taddr + 1];
|
addr = mMemory[taddr] + 256 * mMemory[taddr + 1];
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x __ %s ($%02x,x) (A:%02x X:%02x Y:%02x P:%02x S:%02x %02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], mMemory[ip + 1], mRegA, mRegX, mRegY, mRegP, mRegS, taddr, addr, mMemory[addr]);
|
printf("%04x : %04x %02x %02x __ %s ($%02x,x) (A:%02x X:%02x Y:%02x P:%02x S:%02x %02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], mMemory[ip + 1], mRegA, mRegX, mRegY, mRegP, mRegS, taddr, addr, mMemory[addr]);
|
||||||
mCycles[ip] += 6;
|
icycles = 6;
|
||||||
break;
|
break;
|
||||||
case ASMIM_INDIRECT_Y:
|
case ASMIM_INDIRECT_Y:
|
||||||
taddr = mMemory[mIP++];
|
taddr = mMemory[mIP++];
|
||||||
addr = (mMemory[taddr] + 256 * mMemory[taddr + 1] + mRegY) & 0xffff;
|
addr = (mMemory[taddr] + 256 * mMemory[taddr + 1] + mRegY) & 0xffff;
|
||||||
|
cross = mMemory[taddr] + mRegY >= 256;
|
||||||
|
indexed = true;
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x __ %s ($%02x),y (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
printf("%04x : %04x %02x %02x __ %s ($%02x),y (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x M:%02x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr, mMemory[addr]);
|
||||||
mCycles[ip] += 6;
|
icycles = 5;
|
||||||
break;
|
break;
|
||||||
case ASMIM_RELATIVE:
|
case ASMIM_RELATIVE:
|
||||||
taddr = mMemory[mIP++];
|
taddr = mMemory[mIP++];
|
||||||
|
@ -649,7 +681,7 @@ int Emulator::Emulate(int startIP, int trace)
|
||||||
addr = taddr + mIP;
|
addr = taddr + mIP;
|
||||||
if (trace & 2)
|
if (trace & 2)
|
||||||
printf("%04x : %04x %02x %02x __ %s $%02x (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr);
|
printf("%04x : %04x %02x %02x __ %s $%02x (A:%02x X:%02x Y:%02x P:%02x S:%02x %04x)\n", iip, ip, mMemory[ip], mMemory[ip + 1], AsmInstructionNames[d.mType], taddr, mRegA, mRegX, mRegY, mRegP, mRegS, addr);
|
||||||
mCycles[ip] += 2;
|
icycles = 2;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -685,8 +717,11 @@ int Emulator::Emulate(int startIP, int trace)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!EmulateInstruction(d.mType, d.mMode, addr, mCycles[ip]))
|
if (!EmulateInstruction(d.mType, d.mMode, addr, icycles, cross, indexed))
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
|
mCycles[ip] += icycles;
|
||||||
|
cycles += icycles;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (mRegS == 0xff)
|
if (mRegS == 0xff)
|
||||||
|
|
|
@ -22,7 +22,7 @@ public:
|
||||||
|
|
||||||
int Emulate(int startIP, int trace);
|
int Emulate(int startIP, int trace);
|
||||||
void DumpProfile(void);
|
void DumpProfile(void);
|
||||||
bool EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, int & cycles);
|
bool EmulateInstruction(AsmInsType type, AsmInsMode mode, int addr, int & cycles, bool cross, bool indexed);
|
||||||
protected:
|
protected:
|
||||||
void UpdateStatus(uint8 result);
|
void UpdateStatus(uint8 result);
|
||||||
void UpdateStatusCarry(uint8 result, bool carry);
|
void UpdateStatusCarry(uint8 result, bool carry);
|
||||||
|
|
|
@ -8333,9 +8333,9 @@ void InterCodeBasicBlock::UpdateLocalIntegerRangeSetsBackward(const GrowingVaria
|
||||||
{
|
{
|
||||||
InterInstruction* ins(mInstructions[i]);
|
InterInstruction* ins(mInstructions[i]);
|
||||||
if (ins->mCode == IC_LOAD && ins->mSrc[0].mMemory == IM_INDIRECT && ins->mSrc[0].mTemp >= 0)
|
if (ins->mCode == IC_LOAD && ins->mSrc[0].mMemory == IM_INDIRECT && ins->mSrc[0].mTemp >= 0)
|
||||||
mMemoryValueSize[ins->mSrc[0].mTemp] = int64max(mMemoryValueSize[ins->mSrc[0].mTemp], ins->mSrc[0].mIntConst + InterTypeSize[ins->mDst.mType]);
|
mMemoryValueSize[ins->mSrc[0].mTemp] = int64max(mMemoryValueSize[ins->mSrc[0].mTemp], ins->mSrc[0].mIntConst + (InterTypeSize[ins->mDst.mType] - 1) * ins->mSrc[0].mStride + 1);
|
||||||
else if (ins->mCode == IC_STORE && ins->mSrc[1].mMemory == IM_INDIRECT && ins->mSrc[1].mTemp >= 0)
|
else if (ins->mCode == IC_STORE && ins->mSrc[1].mMemory == IM_INDIRECT && ins->mSrc[1].mTemp >= 0)
|
||||||
mMemoryValueSize[ins->mSrc[1].mTemp] = int64max(mMemoryValueSize[ins->mSrc[1].mTemp], ins->mSrc[1].mIntConst + InterTypeSize[ins->mSrc[0].mType]);
|
mMemoryValueSize[ins->mSrc[1].mTemp] = int64max(mMemoryValueSize[ins->mSrc[1].mTemp], ins->mSrc[1].mIntConst + (InterTypeSize[ins->mSrc[0].mType] - 1) * ins->mSrc[1].mStride + 1);
|
||||||
else if (ins->mCode == IC_FILL)
|
else if (ins->mCode == IC_FILL)
|
||||||
{
|
{
|
||||||
if (ins->mSrc[1].mMemory == IM_INDIRECT && ins->mSrc[1].mTemp >= 0)
|
if (ins->mSrc[1].mMemory == IM_INDIRECT && ins->mSrc[1].mTemp >= 0)
|
||||||
|
@ -8711,6 +8711,7 @@ void InterCodeBasicBlock::UpdateLocalIntegerRangeSets(const GrowingVariableArray
|
||||||
break;
|
break;
|
||||||
#endif
|
#endif
|
||||||
case IA_CMPLS:
|
case IA_CMPLS:
|
||||||
|
// Why limit weak, makes no sense
|
||||||
if (s0 < 0)
|
if (s0 < 0)
|
||||||
{
|
{
|
||||||
mTrueValueRange[s1].LimitMax(mInstructions[sz - 2]->mSrc[0].mIntConst - 1);
|
mTrueValueRange[s1].LimitMax(mInstructions[sz - 2]->mSrc[0].mIntConst - 1);
|
||||||
|
@ -8825,6 +8826,10 @@ void InterCodeBasicBlock::UpdateLocalIntegerRangeSets(const GrowingVariableArray
|
||||||
if (s0 < 0)
|
if (s0 < 0)
|
||||||
{
|
{
|
||||||
mTrueValueRange[s1].LimitMax(mInstructions[sz - 2]->mSrc[0].mIntConst - 1);
|
mTrueValueRange[s1].LimitMax(mInstructions[sz - 2]->mSrc[0].mIntConst - 1);
|
||||||
|
|
||||||
|
if (mInstructions[sz - 2]->mSrc[0].mIntConst > 0 && mInstructions[sz - 2]->mSrc[0].mIntConst < SignedTypeMax(mInstructions[sz - 2]->mSrc[1].mType))
|
||||||
|
mTrueValueRange[s1].LimitMin(0);
|
||||||
|
else
|
||||||
mTrueValueRange[s1].LimitMinWeak(0);
|
mTrueValueRange[s1].LimitMinWeak(0);
|
||||||
|
|
||||||
if (mFalseValueRange[s1].mMinState == IntegerValueRange::S_BOUND && mFalseValueRange[s1].mMinValue >= 0)
|
if (mFalseValueRange[s1].mMinState == IntegerValueRange::S_BOUND && mFalseValueRange[s1].mMinValue >= 0)
|
||||||
|
@ -12240,8 +12245,11 @@ InterInstruction* InterCodeBasicBlock::FindTempOrigin(int temp) const
|
||||||
for (int i = mInstructions.Size() - 1; i >= 0; i--)
|
for (int i = mInstructions.Size() - 1; i >= 0; i--)
|
||||||
{
|
{
|
||||||
if (mInstructions[i]->mDst.mTemp == temp)
|
if (mInstructions[i]->mDst.mTemp == temp)
|
||||||
|
{
|
||||||
|
mMark = i;
|
||||||
return mInstructions[i];
|
return mInstructions[i];
|
||||||
}
|
}
|
||||||
|
}
|
||||||
return nullptr;
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -17554,6 +17562,133 @@ void InterCodeBasicBlock::SingleBlockLoopOptimisation(const NumberSet& aliasedPa
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static bool IsSimilarLea(InterInstruction* ins0, InterInstruction* ins1)
|
||||||
|
{
|
||||||
|
if (ins0->mCode == IC_LEA && ins1->mCode == IC_LEA &&
|
||||||
|
ins0->mSrc[0].mTemp == ins1->mSrc[0].mTemp &&
|
||||||
|
ins0->mSrc[1].mTemp == ins1->mSrc[1].mTemp &&
|
||||||
|
ins0->mSrc[0].IsUByte() && ins1->mSrc[0].IsUByte())
|
||||||
|
{
|
||||||
|
if (ins0->mSrc[1].mTemp >= 0 && ins0->mSrc[1].mFinal && ins1->mSrc[1].mFinal ||
|
||||||
|
ins0->mSrc[1].mMemory == ins1->mSrc[1].mMemory &&
|
||||||
|
ins0->mSrc[1].mVarIndex == ins1->mSrc[1].mVarIndex &&
|
||||||
|
ins0->mSrc[1].mLinkerObject == ins1->mSrc[1].mLinkerObject)
|
||||||
|
{
|
||||||
|
if (ins0->mSrc[1].mIntConst < ins1->mSrc[1].mIntConst)
|
||||||
|
{
|
||||||
|
if (ins1->mSrc[0].mRange.mMaxValue + ins1->mSrc[1].mIntConst - ins0->mSrc[1].mIntConst < 128)
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else if (ins0->mSrc[1].mIntConst > ins1->mSrc[1].mIntConst)
|
||||||
|
{
|
||||||
|
if (ins0->mSrc[0].mRange.mMaxValue + ins0->mSrc[1].mIntConst - ins1->mSrc[1].mIntConst < 128)
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool InterCodeBasicBlock::ShortLeaMerge(void)
|
||||||
|
{
|
||||||
|
bool changed = false;
|
||||||
|
|
||||||
|
if (!mVisited)
|
||||||
|
{
|
||||||
|
mVisited = true;
|
||||||
|
|
||||||
|
if (!mLoopHead && mEntryBlocks.Size() > 1)
|
||||||
|
{
|
||||||
|
int k = 0;
|
||||||
|
while (k < mEntryBlocks.Size() && !mEntryBlocks[k]->mFalseJump)
|
||||||
|
k++;
|
||||||
|
|
||||||
|
if (k == mEntryBlocks.Size())
|
||||||
|
{
|
||||||
|
GrowingInstructionArray iins(nullptr);
|
||||||
|
|
||||||
|
for (int i = 0; i < mInstructions.Size(); i++)
|
||||||
|
{
|
||||||
|
InterInstruction* ins = mInstructions[i];
|
||||||
|
|
||||||
|
int ttemp = -1;
|
||||||
|
if (ins->mCode == IC_STORE && ins->mSrc[1].mTemp >= 0)
|
||||||
|
ttemp = ins->mSrc[1].mTemp;
|
||||||
|
else if (ins->mCode == IC_LOAD && ins->mSrc[0].mTemp >= 0)
|
||||||
|
ttemp = ins->mSrc[0].mTemp;
|
||||||
|
|
||||||
|
if (ttemp >= 0 && !IsTempModifiedInRange(0, i, ttemp))
|
||||||
|
{
|
||||||
|
bool found = true;
|
||||||
|
|
||||||
|
iins.SetSize(0);
|
||||||
|
for (int k = 0; k < mEntryBlocks.Size(); k++)
|
||||||
|
{
|
||||||
|
InterInstruction* sins = mEntryBlocks[k]->FindTempOrigin(ttemp);
|
||||||
|
if (sins && sins->mCode == IC_LEA && mEntryBlocks[k]->CanMoveInstructionBehindBlock(mEntryBlocks[k]->mMark))
|
||||||
|
iins.Push(sins);
|
||||||
|
else
|
||||||
|
{
|
||||||
|
found = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (found)
|
||||||
|
{
|
||||||
|
int64 minint = iins[0]->mSrc[1].mIntConst;
|
||||||
|
|
||||||
|
for (int k = 1; k < mEntryBlocks.Size(); k++)
|
||||||
|
{
|
||||||
|
if (IsSimilarLea(iins[0], iins[k]))
|
||||||
|
{
|
||||||
|
if (iins[k]->mSrc[1].mIntConst < minint)
|
||||||
|
minint = iins[k]->mSrc[1].mIntConst;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
found = false;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (found)
|
||||||
|
{
|
||||||
|
mInstructions.Insert(0, iins[0]->Clone());
|
||||||
|
iins[0]->mSrc[1].mIntConst = minint;
|
||||||
|
|
||||||
|
for (int k = 0; k < mEntryBlocks.Size(); k++)
|
||||||
|
{
|
||||||
|
InterInstruction* sins = iins[k];
|
||||||
|
sins->mCode = IC_BINARY_OPERATOR;
|
||||||
|
sins->mOperator = IA_ADD;
|
||||||
|
sins->mDst = sins->mSrc[0];
|
||||||
|
sins->mSrc[1].mTemp = -1;
|
||||||
|
sins->mSrc[1].mType = sins->mSrc[0].mType;
|
||||||
|
sins->mSrc[1].mIntConst -= minint;
|
||||||
|
sins->mDst.mRange.mMaxValue += sins->mSrc[1].mIntConst;
|
||||||
|
mEntryBlocks[k]->mExitRequiredTemps += sins->mDst.mTemp;
|
||||||
|
}
|
||||||
|
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (mTrueJump && mTrueJump->ShortLeaMerge()) changed = true;
|
||||||
|
if (mFalseJump && mFalseJump->ShortLeaMerge()) changed = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return changed;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void InterCodeBasicBlock::CompactInstructions(void)
|
void InterCodeBasicBlock::CompactInstructions(void)
|
||||||
{
|
{
|
||||||
if (!mVisited)
|
if (!mVisited)
|
||||||
|
@ -17735,6 +17870,28 @@ bool InterCodeBasicBlock::PeepholeReplaceOptimization(const GrowingVariableArray
|
||||||
mInstructions[i + 2]->mSrc[1].mFinal = false;
|
mInstructions[i + 2]->mSrc[1].mFinal = false;
|
||||||
changed = true;
|
changed = true;
|
||||||
}
|
}
|
||||||
|
else if (
|
||||||
|
mInstructions[i + 0]->mCode == IC_BINARY_OPERATOR && mInstructions[i + 0]->mOperator == IA_ADD &&
|
||||||
|
mInstructions[i + 0]->mSrc[0].mTemp < 0 && mInstructions[i + 0]->mSrc[0].mIntConst >= 0 &&
|
||||||
|
mInstructions[i + 1]->mCode == IC_TYPECAST && mInstructions[i + 1]->mSrc[0].mTemp == mInstructions[i + 0]->mDst.mTemp && mInstructions[i + 1]->mSrc[0].mFinal &&
|
||||||
|
mInstructions[i + 1]->mDst.mType == IT_POINTER && mInstructions[i + 1]->mSrc[0].mType == IT_INT16)
|
||||||
|
{
|
||||||
|
int64 addr = mInstructions[i + 0]->mSrc[0].mIntConst;
|
||||||
|
|
||||||
|
mInstructions[i + 0]->mCode = IC_LEA;
|
||||||
|
mInstructions[i + 0]->mSrc[0] = mInstructions[i + 0]->mSrc[1];
|
||||||
|
mInstructions[i + 0]->mSrc[1].mTemp = -1;
|
||||||
|
mInstructions[i + 0]->mSrc[1].mType = IT_POINTER;
|
||||||
|
mInstructions[i + 0]->mSrc[1].mMemory = IM_ABSOLUTE;
|
||||||
|
mInstructions[i + 0]->mSrc[1].mIntConst = addr;
|
||||||
|
mInstructions[i + 0]->mSrc[1].mLinkerObject = nullptr;
|
||||||
|
mInstructions[i + 0]->mSrc[1].mVarIndex = -1;
|
||||||
|
mInstructions[i + 0]->mDst = mInstructions[i + 1]->mDst;
|
||||||
|
|
||||||
|
mInstructions[i + 1]->mCode = IC_NONE;
|
||||||
|
mInstructions[i + 1]->mNumOperands = 0;
|
||||||
|
changed = true;
|
||||||
|
}
|
||||||
else if (
|
else if (
|
||||||
mInstructions[i + 0]->mCode == IC_BINARY_OPERATOR && mInstructions[i + 0]->mOperator == IA_SAR && mInstructions[i + 0]->mSrc[0].mTemp < 0 &&
|
mInstructions[i + 0]->mCode == IC_BINARY_OPERATOR && mInstructions[i + 0]->mOperator == IA_SAR && mInstructions[i + 0]->mSrc[0].mTemp < 0 &&
|
||||||
mInstructions[i + 1]->mCode == IC_BINARY_OPERATOR && mInstructions[i + 1]->mOperator == IA_MUL && mInstructions[i + 1]->mSrc[0].mTemp < 0 &&
|
mInstructions[i + 1]->mCode == IC_BINARY_OPERATOR && mInstructions[i + 1]->mOperator == IA_MUL && mInstructions[i + 1]->mSrc[0].mTemp < 0 &&
|
||||||
|
@ -21034,7 +21191,7 @@ void InterCodeProcedure::Close(void)
|
||||||
{
|
{
|
||||||
GrowingTypeArray tstack(IT_NONE);
|
GrowingTypeArray tstack(IT_NONE);
|
||||||
|
|
||||||
CheckFunc = !strcmp(mIdent->mString, "main");
|
CheckFunc = !strcmp(mIdent->mString, "getch");
|
||||||
CheckCase = false;
|
CheckCase = false;
|
||||||
|
|
||||||
mEntryBlock = mBlocks[0];
|
mEntryBlock = mBlocks[0];
|
||||||
|
@ -22223,12 +22380,14 @@ bool InterCodeBasicBlock::SameExitCode(const InterCodeBasicBlock* block) const
|
||||||
{
|
{
|
||||||
if (!(mInstructions[j0]->IsEqual(block->mInstructions[j1])))
|
if (!(mInstructions[j0]->IsEqual(block->mInstructions[j1])))
|
||||||
{
|
{
|
||||||
if (mInstructions[j0]->mCode == IC_LEA && mInstructions[j0]->mSrc[1].mTemp < 0)
|
if (mInstructions[j0]->mCode == IC_LEA && mInstructions[j0]->mSrc[1].mTemp < 0 ||
|
||||||
return false;
|
block->mInstructions[j1]->mCode == IC_LEA && block->mInstructions[j1]->mSrc[1].mTemp < 0)
|
||||||
if (block->mInstructions[j1]->mCode == IC_LEA && block->mInstructions[j1]->mSrc[1].mTemp < 0)
|
{
|
||||||
|
if (!IsSimilarLea(mInstructions[j0], block->mInstructions[j1]))
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (InterTypeSize[ins0->mSrc[0].mType] == 4)
|
if (InterTypeSize[ins0->mSrc[0].mType] == 4)
|
||||||
{
|
{
|
||||||
|
@ -22257,13 +22416,15 @@ bool InterCodeBasicBlock::SameExitCode(const InterCodeBasicBlock* block) const
|
||||||
{
|
{
|
||||||
if (!(mInstructions[j0]->IsEqual(block->mInstructions[j1])))
|
if (!(mInstructions[j0]->IsEqual(block->mInstructions[j1])))
|
||||||
{
|
{
|
||||||
if (mInstructions[j0]->mCode == IC_LEA && mInstructions[j0]->mSrc[1].mTemp < 0)
|
if (mInstructions[j0]->mCode == IC_LEA && mInstructions[j0]->mSrc[1].mTemp < 0 ||
|
||||||
return false;
|
block->mInstructions[j1]->mCode == IC_LEA && block->mInstructions[j1]->mSrc[1].mTemp < 0)
|
||||||
if (block->mInstructions[j1]->mCode == IC_LEA && mInstructions[j1]->mSrc[1].mTemp < 0)
|
{
|
||||||
|
if (!IsSimilarLea(mInstructions[j0], block->mInstructions[j1]))
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
@ -22305,6 +22466,14 @@ bool PartitionSameExitCode(GrowingArray<InterCodeBasicBlock* > & eblocks, Growin
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void InterCodeProcedure::ShortLeaMerge(void)
|
||||||
|
{
|
||||||
|
ResetVisited();
|
||||||
|
mEntryBlock->ShortLeaMerge();
|
||||||
|
|
||||||
|
DisassembleDebug("ShortLeaMerge");
|
||||||
|
}
|
||||||
|
|
||||||
void InterCodeProcedure::MergeBasicBlocks(void)
|
void InterCodeProcedure::MergeBasicBlocks(void)
|
||||||
{
|
{
|
||||||
ResetVisited();
|
ResetVisited();
|
||||||
|
@ -22461,6 +22630,12 @@ void InterCodeProcedure::MergeBasicBlocks(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!changed)
|
||||||
|
{
|
||||||
|
ResetVisited();
|
||||||
|
changed = mEntryBlock->ShortLeaMerge();
|
||||||
|
}
|
||||||
|
|
||||||
} while (changed);
|
} while (changed);
|
||||||
|
|
||||||
ResetVisited();
|
ResetVisited();
|
||||||
|
|
|
@ -367,6 +367,7 @@ public:
|
||||||
GrowingInstructionArray mInstructions;
|
GrowingInstructionArray mInstructions;
|
||||||
|
|
||||||
bool mVisited, mInPath, mLoopHead, mChecked, mConditionBlockTrue, mUnreachable, mLoopPath, mValueRangeValid;
|
bool mVisited, mInPath, mLoopHead, mChecked, mConditionBlockTrue, mUnreachable, mLoopPath, mValueRangeValid;
|
||||||
|
mutable int mMark;
|
||||||
|
|
||||||
NumberSet mLocalUsedTemps, mLocalModifiedTemps;
|
NumberSet mLocalUsedTemps, mLocalModifiedTemps;
|
||||||
NumberSet mLocalRequiredTemps, mLocalProvidedTemps;
|
NumberSet mLocalRequiredTemps, mLocalProvidedTemps;
|
||||||
|
@ -616,6 +617,8 @@ public:
|
||||||
void SplitBranches(void);
|
void SplitBranches(void);
|
||||||
void FollowJumps(void);
|
void FollowJumps(void);
|
||||||
|
|
||||||
|
bool ShortLeaMerge(void);
|
||||||
|
|
||||||
bool IsEqual(const InterCodeBasicBlock* block) const;
|
bool IsEqual(const InterCodeBasicBlock* block) const;
|
||||||
|
|
||||||
void CompactInstructions(void);
|
void CompactInstructions(void);
|
||||||
|
@ -742,6 +745,8 @@ protected:
|
||||||
void RecheckLocalAliased(void);
|
void RecheckLocalAliased(void);
|
||||||
void ConstLoopOptimization(void);
|
void ConstLoopOptimization(void);
|
||||||
|
|
||||||
|
void ShortLeaMerge(void);
|
||||||
|
|
||||||
void MergeBasicBlocks(void);
|
void MergeBasicBlocks(void);
|
||||||
void CheckUsedDefinedTemps(void);
|
void CheckUsedDefinedTemps(void);
|
||||||
void WarnUsedUndefinedVariables(void);
|
void WarnUsedUndefinedVariables(void);
|
||||||
|
|
|
@ -50355,8 +50355,13 @@ void NativeCodeProcedure::Optimize(void)
|
||||||
if (step == 12)
|
if (step == 12)
|
||||||
{
|
{
|
||||||
ResetVisited();
|
ResetVisited();
|
||||||
if (mEntryBlock->GlobalLoadStoreForwarding(false, NativeCodeInstruction(), NativeCodeInstruction(), NativeCodeInstruction()) ||
|
bool cc = mEntryBlock->GlobalLoadStoreForwarding(false, NativeCodeInstruction(), NativeCodeInstruction(), NativeCodeInstruction());
|
||||||
mEntryBlock->GlobalLoadStoreForwarding(true, NativeCodeInstruction(), NativeCodeInstruction(), NativeCodeInstruction()))
|
if (!cc)
|
||||||
|
{
|
||||||
|
ResetVisited();
|
||||||
|
cc = mEntryBlock->GlobalLoadStoreForwarding(true, NativeCodeInstruction(), NativeCodeInstruction(), NativeCodeInstruction());
|
||||||
|
}
|
||||||
|
if (cc)
|
||||||
{
|
{
|
||||||
ResetVisited();
|
ResetVisited();
|
||||||
NativeRegisterDataSet data;
|
NativeRegisterDataSet data;
|
||||||
|
|
Loading…
Reference in New Issue