Change runtime assembler generator use value and return instead of reference

This commit is contained in:
drmortalwombat 2021-11-29 18:37:15 +01:00
parent a6fa114a5b
commit 15c65f69aa
3 changed files with 124 additions and 60 deletions

View File

@ -82,91 +82,91 @@ enum AsmIns
ASM_JSR = 0x2c
};
inline void asm_np(byte ** ip, AsmIns ins)
inline byte asm_np(byte * ip, AsmIns ins)
{
(*ip)[0] = ins & 0xff;
(*ip)++;
ip[0] = ins & 0xff;
return 1;
}
inline void asm_zp(byte ** ip, AsmIns ins, byte addr)
inline byte asm_zp(byte * ip, AsmIns ins, byte addr)
{
(*ip)[0] = (ins & 0xff) | 0x04;
(*ip)[1] = addr;
(*ip) += 2;
ip[0] = (ins & 0xff) | 0x04;
ip[1] = addr;
return 2;
}
inline void asm_rl(byte ** ip, AsmIns ins, byte addr)
inline byte asm_rl(byte * ip, AsmIns ins, byte addr)
{
(*ip)[0] = ins & 0xff;
(*ip)[1] = addr;
(*ip) += 2;
ip[0] = ins & 0xff;
ip[1] = addr;
return 2;
}
inline void asm_im(byte ** ip, AsmIns ins, byte value)
inline byte asm_im(byte * ip, AsmIns ins, byte value)
{
(*ip)[0] = (ins & 0xff) | ((ins & 0x01) << 3);
(*ip)[1] = value;
(*ip) += 2;
ip[0] = (ins & 0xff) | ((ins & 0x01) << 3);
ip[1] = value;
return 2;
}
inline void asm_zx(byte ** ip, AsmIns ins, byte addr)
inline byte asm_zx(byte * ip, AsmIns ins, byte addr)
{
(*ip)[0] = (ins & 0xff) | 0x05;
(*ip)[1] = addr;
(*ip) += 2;
ip[0] = (ins & 0xff) | 0x05;
ip[1] = addr;
return 2;
}
inline void asm_zy(byte ** ip, AsmIns ins, byte addr)
inline byte asm_zy(byte * ip, AsmIns ins, byte addr)
{
(*ip)[0] = (ins & 0xff) | 0x05;
(*ip)[1] = addr;
(*ip) += 2;
ip[0] = (ins & 0xff) | 0x05;
ip[1] = addr;
return 2;
}
inline void asm_ab(byte ** ip, AsmIns ins, unsigned addr)
inline byte asm_ab(byte * ip, AsmIns ins, unsigned addr)
{
(*ip)[0] = (ins & 0xff) ^ 0x0c;
(*ip)[1] = addr & 0xff;
(*ip)[2] = addr >> 8;
(*ip) += 3;
ip[0] = (ins & 0xff) ^ 0x0c;
ip[1] = addr & 0xff;
ip[2] = addr >> 8;
return 3;
}
inline void asm_in(byte ** ip, AsmIns ins, unsigned addr)
inline byte asm_in(byte * ip, AsmIns ins, unsigned addr)
{
(*ip)[0] = (ins & 0xff) ^ 0x2c;
(*ip)[1] = addr & 0xff;
(*ip)[2] = addr >> 8;
(*ip) += 3;
ip[0] = (ins & 0xff) ^ 0x2c;
ip[1] = addr & 0xff;
ip[2] = addr >> 8;
return 3;
}
inline void asm_ax(byte ** ip, AsmIns ins, unsigned addr)
inline byte asm_ax(byte * ip, AsmIns ins, unsigned addr)
{
(*ip)[0] = (ins & 0xff) | 0x1c;
(*ip)[1] = addr & 0xff;
(*ip)[2] = addr >> 8;
(*ip) += 3;
ip[0] = (ins & 0xff) | 0x1c;
ip[1] = addr & 0xff;
ip[2] = addr >> 8;
return 3;
}
inline void asm_ay(byte ** ip, AsmIns ins, unsigned addr)
inline byte asm_ay(byte * ip, AsmIns ins, unsigned addr)
{
(*ip)[0] = (ins & 0xff) | 0x18;
(*ip)[1] = addr & 0xff;
(*ip)[2] = addr >> 8;
(*ip) += 3;
ip[0] = (ins & 0xff) | 0x18;
ip[1] = addr & 0xff;
ip[2] = addr >> 8;
return 3;
}
inline void asm_ix(byte ** ip, AsmIns ins, byte addr)
inline byte asm_ix(byte * ip, AsmIns ins, byte addr)
{
(*ip)[0] = (ins & 0xff) | 0x00;
(*ip)[1] = addr;
(*ip) += 2;
ip[0] = (ins & 0xff) | 0x00;
ip[1] = addr;
return 2;
}
inline void asm_iy(byte ** ip, AsmIns ins, byte addr)
inline byte * asm_iy(byte * ip, AsmIns ins, byte addr)
{
(*ip)[0] = (ins & 0xff) | 0x01;
(*ip)[1] = addr;
(*ip) += 2;
ip[0] = (ins & 0xff) | 0x01;
ip[1] = addr;
return 2;
}
#endif

View File

@ -2,6 +2,7 @@
#include <c64/vic.h>
#include <c64/cia.h>
#include <c64/asm6502.h>
volatile char npos = 1, tpos = 0;
@ -164,6 +165,12 @@ void rirq_build(RIRQCode * ic, byte size)
{
ic->size = size;
asm_im(ic->code + 0, ASM_LDY, 0);
asm_im(ic->code + 2, ASM_LDA, 0);
asm_ab(ic->code + 4, ASM_CPX, 0xd012);
asm_rl(ic->code + 7, ASM_BCS, -5);
asm_ab(ic->code + 9, ASM_STY, 0x0000);
/*
ic->code[0] = 0xa0; // ldy #
ic->code[2] = 0xa9; // lda #
ic->code[4] = 0xec; // cpx
@ -172,23 +179,28 @@ void rirq_build(RIRQCode * ic, byte size)
ic->code[7] = 0xb0; // bcs
ic->code[8] = -5;
ic->code[9] = 0x8c; // sty
*/
if (size == 1)
{
ic->code[12] = 0x60; // rts
asm_np(ic->code + 12, ASM_RTS);
//ic->code[12] = 0x60; // rts
}
else
{
ic->code[12] = 0x8d; // sty
asm_ab(ic->code + 12, ASM_STA, 0x0000);
// ic->code[12] = 0x8d; // sty
byte p = 15;
for(byte i=2; i<size; i++)
{
ic->code[p] = 0xa9; // lda #
ic->code[p + 2] = 0x8d; // sta
p += 5;
p += asm_im(ic->code + p, ASM_LDA, 0x00);
p += asm_ab(ic->code + p, ASM_STA, 0x0000);
//ic->code[p] = 0xa9; // lda #
//ic->code[p + 2] = 0x8d; // sta
//p += 5;
}
ic->code[p] = 0x60;
asm_np(ic->code + p, ASM_RTS);
//ic->code[p] = 0x60;
}
}

View File

@ -10272,7 +10272,47 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(int pass)
}
}
#endif
#if 1
if (
mIns[i + 0].mType == ASMIT_LDY && mIns[i + 0].mMode == ASMIM_IMMEDIATE && mIns[i + 0].mAddress <= 3 &&
mIns[i + 1].mType == ASMIT_STA && mIns[i + 1].mMode == ASMIM_INDIRECT_Y)
{
int apos, breg, ireg;
if (FindAddressSumY(i, mIns[i + 1].mAddress, apos, breg, ireg))
{
if (breg != mIns[i + 1].mAddress && ireg != mIns[i + 1].mAddress)// || !(mIns[i + 1].mLive & LIVE_MEM))
{
int yoffset = mIns[i + 0].mAddress;
if (breg == mIns[i + 1].mAddress)
{
mIns[apos + 3].mType = ASMIT_NOP;
mIns[apos + 3].mMode = ASMIM_IMPLIED;
mIns[apos + 6].mType = ASMIT_NOP;
mIns[apos + 6].mMode = ASMIM_IMPLIED;
}
if (mIns[i + 1].mLive & LIVE_CPU_REG_Y)
{
mIns.Insert(i + 2, NativeCodeInstruction(ASMIT_LDY, ASMIM_IMMEDIATE, yoffset));
mIns[i + 2].mLive |= LIVE_CPU_REG_Y;
}
mIns[i + 0].mMode = ASMIM_ZERO_PAGE;
mIns[i + 0].mAddress = ireg;
mIns[i + 1].mAddress = breg;
for(int j=0; j<yoffset; j++)
{
mIns.Insert(i + 1, NativeCodeInstruction(ASMIT_INY, ASMIM_IMPLIED));
mIns[i + 1].mLive = mIns[i + 0].mLive;
}
progress = true;
}
}
}
#endif
}
@ -10540,13 +10580,15 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(int pass)
#endif
#if 1
if (
mIns[i + 0].mType == ASMIT_LDY && mIns[i + 0].mMode == ASMIM_IMMEDIATE && mIns[i + 0].mAddress == 0 &&
mIns[i + 0].mType == ASMIT_LDY && mIns[i + 0].mMode == ASMIM_IMMEDIATE && mIns[i + 0].mAddress <= 1 &&
mIns[i + 1].mType == ASMIT_LDA &&
mIns[i + 2].mType == ASMIT_STA && mIns[i + 2].mMode == ASMIM_INDIRECT_Y && !(mIns[i + 2].mLive & LIVE_MEM))
{
int apos, breg, ireg;
if (FindAddressSumY(i, mIns[i + 2].mAddress, apos, breg, ireg))
{
int yoffset = mIns[i + 0].mAddress;
if (breg == mIns[i + 2].mAddress)
{
mIns[apos + 3].mType = ASMIT_NOP;
@ -10556,9 +10598,11 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(int pass)
}
if (mIns[i + 2].mLive & LIVE_CPU_REG_Y)
{
mIns.Insert(i + 3, NativeCodeInstruction(ASMIT_LDY, ASMIM_IMMEDIATE, 0));
mIns.Insert(i + 3, NativeCodeInstruction(ASMIT_LDY, ASMIM_IMMEDIATE, yoffset));
mIns[i + 3].mLive |= LIVE_CPU_REG_Y;
}
int ypos = i;
if (mIns[i + 1].mMode != ASMIM_INDIRECT_Y && mIns[i + 1].mMode != ASMIM_ABSOLUTE_Y)
{
mIns[i + 0].mMode = ASMIM_ZERO_PAGE;
@ -10569,8 +10613,16 @@ bool NativeCodeBasicBlock::PeepHoleOptimizer(int pass)
{
mIns.Insert(i + 2, NativeCodeInstruction(ASMIT_LDY, ASMIM_ZERO_PAGE, ireg));
mIns[i + 2].mLive = mIns[i + 3].mLive | LIVE_CPU_REG_Y | LIVE_MEM;
ypos = i + 2;
mIns[i + 3].mAddress = breg;
}
if (yoffset == 1)
{
mIns.Insert(ypos + 1, NativeCodeInstruction(ASMIT_INY, ASMIM_IMPLIED));
mIns[ypos + 1].mLive = mIns[ypos].mLive;
}
progress = true;
}
}