More native code compiler additions
This commit is contained in:
parent
056df56eef
commit
fcedf69aff
|
@ -36,6 +36,9 @@ if %errorlevel% neq 0 goto :error
|
||||||
..\release\oscar64 -i=../include -rt=../include/crt.c -e array2stringinittest.c
|
..\release\oscar64 -i=../include -rt=../include/crt.c -e array2stringinittest.c
|
||||||
if %errorlevel% neq 0 goto :error
|
if %errorlevel% neq 0 goto :error
|
||||||
|
|
||||||
|
..\release\oscar64 -i=../include -rt=../include/crt.c -e testint16cmp.c
|
||||||
|
if %errorlevel% neq 0 goto :error
|
||||||
|
|
||||||
exit /b 0
|
exit /b 0
|
||||||
:error
|
:error
|
||||||
echo Failed with error #%errorlevel%.
|
echo Failed with error #%errorlevel%.
|
||||||
|
|
|
@ -0,0 +1,147 @@
|
||||||
|
#include <stdio.h>
|
||||||
|
#include <assert.h>
|
||||||
|
|
||||||
|
bool beq(int a, int b)
|
||||||
|
{
|
||||||
|
return a == b;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool blt(int a, int b)
|
||||||
|
{
|
||||||
|
return a < b;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool bgt(int a, int b)
|
||||||
|
{
|
||||||
|
return a > b;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool ble(int a, int b)
|
||||||
|
{
|
||||||
|
return a <= b;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool bge(int a, int b)
|
||||||
|
{
|
||||||
|
return a >= b;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool neq(int a, int b)
|
||||||
|
{
|
||||||
|
return a == b;
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma native(neq)
|
||||||
|
|
||||||
|
bool nlt(int a, int b)
|
||||||
|
{
|
||||||
|
return a < b;
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma native(nlt)
|
||||||
|
|
||||||
|
bool ngt(int a, int b)
|
||||||
|
{
|
||||||
|
return a > b;
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma native(ngt)
|
||||||
|
|
||||||
|
bool nle(int a, int b)
|
||||||
|
{
|
||||||
|
return a <= b;
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma native(nlt)
|
||||||
|
|
||||||
|
bool nge(int a, int b)
|
||||||
|
{
|
||||||
|
return a >= b;
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma native(ngt)
|
||||||
|
|
||||||
|
void cmp(int a, int b)
|
||||||
|
{
|
||||||
|
bool beqf = beq(a, b), bltf = blt(a, b), bgtf = bgt(a, b), blef = blt(a, b), bgef = bgt(a, b);
|
||||||
|
bool neqf = neq(a, b), nltf = nlt(a, b), ngtf = ngt(a, b), nlef = nlt(a, b), ngef = ngt(a, b);
|
||||||
|
|
||||||
|
// printf("BYTE %d, %d : EQ %d LT %d GT %d\r", a, b, beqf, bltf, bgtf);
|
||||||
|
// printf("NATIVE %d, %d : EQ %d LT %d GT %d\r", a, b, neqf, nltf, ngtf);
|
||||||
|
|
||||||
|
assert(beqf == neqf);
|
||||||
|
assert(bltf == nltf);
|
||||||
|
assert(bgtf == ngtf);
|
||||||
|
assert(blef == nlef);
|
||||||
|
assert(bgef == ngef);
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(void)
|
||||||
|
{
|
||||||
|
cmp( 0, 1);
|
||||||
|
cmp( 0, -1);
|
||||||
|
cmp( 1, 0);
|
||||||
|
cmp(-1, 0);
|
||||||
|
|
||||||
|
cmp(1, 1);
|
||||||
|
cmp(1, 2);
|
||||||
|
cmp(2, 1);
|
||||||
|
|
||||||
|
cmp(-1, -1);
|
||||||
|
cmp(-1, -2);
|
||||||
|
cmp(-2, -1);
|
||||||
|
|
||||||
|
cmp( 1, -1);
|
||||||
|
cmp( 1, -2);
|
||||||
|
cmp( 2, -1);
|
||||||
|
|
||||||
|
cmp(-1, 1);
|
||||||
|
cmp(-1, 2);
|
||||||
|
cmp(-2, 1);
|
||||||
|
|
||||||
|
|
||||||
|
cmp( 0, 10000);
|
||||||
|
cmp( 0, -10000);
|
||||||
|
cmp( 10000, 0);
|
||||||
|
cmp(-10000, 0);
|
||||||
|
|
||||||
|
cmp(10000, 10000);
|
||||||
|
cmp(10000, 20000);
|
||||||
|
cmp(20000, 10000);
|
||||||
|
|
||||||
|
cmp(-10000, -10000);
|
||||||
|
cmp(-10000, -20000);
|
||||||
|
cmp(-20000, -10000);
|
||||||
|
|
||||||
|
cmp( 10000, -10000);
|
||||||
|
cmp( 10000, -20000);
|
||||||
|
cmp( 20000, -10000);
|
||||||
|
|
||||||
|
cmp(-10000, 10000);
|
||||||
|
cmp(-10000, 20000);
|
||||||
|
cmp(-20000, 10000);
|
||||||
|
|
||||||
|
cmp( 0, 1024);
|
||||||
|
cmp( 0, -1024);
|
||||||
|
cmp( 1024, 0);
|
||||||
|
cmp(-1024, 0);
|
||||||
|
|
||||||
|
cmp(1024, 1024);
|
||||||
|
cmp(1024, 1025);
|
||||||
|
cmp(1025, 1024);
|
||||||
|
|
||||||
|
cmp(-1024, -1024);
|
||||||
|
cmp(-1024, -1025);
|
||||||
|
cmp(-1025, -1024);
|
||||||
|
|
||||||
|
cmp( 1024, -1024);
|
||||||
|
cmp( 1024, -1025);
|
||||||
|
cmp( 1025, -1024);
|
||||||
|
|
||||||
|
cmp(-1024, 1024);
|
||||||
|
cmp(-1024, 1025);
|
||||||
|
cmp(-1025, 1024);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
}
|
121
include/crt.c
121
include/crt.c
|
@ -38,7 +38,31 @@ incip:
|
||||||
|
|
||||||
#pragma startup(startup)
|
#pragma startup(startup)
|
||||||
|
|
||||||
// divide accu by tmp
|
__asm negaccu
|
||||||
|
{
|
||||||
|
sec
|
||||||
|
lda #0
|
||||||
|
sbc accu
|
||||||
|
sta accu
|
||||||
|
lda #0
|
||||||
|
sbc accu + 1
|
||||||
|
sta accu + 1
|
||||||
|
rts
|
||||||
|
}
|
||||||
|
|
||||||
|
__asm negtmp
|
||||||
|
{
|
||||||
|
sec
|
||||||
|
lda #0
|
||||||
|
sbc tmp
|
||||||
|
sta tmp
|
||||||
|
lda #0
|
||||||
|
sbc tmp + 1
|
||||||
|
sta tmp + 1
|
||||||
|
rts
|
||||||
|
}
|
||||||
|
|
||||||
|
// divide accu by tmp result in accu, remainder in tmp + 2
|
||||||
|
|
||||||
__asm divmod
|
__asm divmod
|
||||||
{
|
{
|
||||||
|
@ -69,6 +93,77 @@ W1: dey
|
||||||
rts
|
rts
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Multiply accu by tmp result in tmp + 2
|
||||||
|
|
||||||
|
__asm mul16
|
||||||
|
{
|
||||||
|
lda #0
|
||||||
|
sta tmp + 2
|
||||||
|
sta tmp + 3
|
||||||
|
|
||||||
|
ldx #16
|
||||||
|
L1: lsr tmp + 1
|
||||||
|
ror tmp
|
||||||
|
bcc W1
|
||||||
|
clc
|
||||||
|
lda tmp + 2
|
||||||
|
adc accu
|
||||||
|
sta tmp + 2
|
||||||
|
lda tmp + 3
|
||||||
|
adc accu + 1
|
||||||
|
sta tmp + 3
|
||||||
|
W1: asl accu
|
||||||
|
rol accu + 1
|
||||||
|
dex
|
||||||
|
bne L1
|
||||||
|
rts
|
||||||
|
}
|
||||||
|
|
||||||
|
__asm divs16
|
||||||
|
{
|
||||||
|
bit accu + 1
|
||||||
|
bpl L1
|
||||||
|
jsr negaccu
|
||||||
|
bit tmp + 1
|
||||||
|
bpl L2
|
||||||
|
jsr negtmp
|
||||||
|
L3: jmp divmod
|
||||||
|
L1: bit tmp + 1
|
||||||
|
bpl L3
|
||||||
|
jsr negtmp
|
||||||
|
L2: jsr divmod
|
||||||
|
jmp negaccu
|
||||||
|
}
|
||||||
|
|
||||||
|
__asm mods16
|
||||||
|
{
|
||||||
|
bit accu + 1
|
||||||
|
bpl L1
|
||||||
|
jsr negaccu
|
||||||
|
bit tmp + 1
|
||||||
|
bpl L2
|
||||||
|
jsr negtmp
|
||||||
|
L3: jmp divmod
|
||||||
|
L1: bit tmp + 1
|
||||||
|
bpl L3
|
||||||
|
jsr negtmp
|
||||||
|
L2: jsr divmod
|
||||||
|
sec
|
||||||
|
lda #0
|
||||||
|
sbc tmp + 2
|
||||||
|
sta tmp + 2
|
||||||
|
lda #0
|
||||||
|
sbc tmp + 3
|
||||||
|
sta tmp + 3
|
||||||
|
rts
|
||||||
|
}
|
||||||
|
|
||||||
|
#pragma runtime(mul16, mul16);
|
||||||
|
#pragma runtime(divu16, divmod);
|
||||||
|
#pragma runtime(modu16, divmod);
|
||||||
|
#pragma runtime(divs16, divs16);
|
||||||
|
#pragma runtime(mods16, mods16);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
!align 255, 0
|
!align 255, 0
|
||||||
inptable
|
inptable
|
||||||
|
@ -983,30 +1078,6 @@ __asm inp_binop_modr_u16
|
||||||
|
|
||||||
#pragma bytecode(BC_BINOP_MODR_U16, inp_binop_modr_u16)
|
#pragma bytecode(BC_BINOP_MODR_U16, inp_binop_modr_u16)
|
||||||
|
|
||||||
__asm negaccu
|
|
||||||
{
|
|
||||||
sec
|
|
||||||
lda #0
|
|
||||||
sbc accu
|
|
||||||
sta accu
|
|
||||||
lda #0
|
|
||||||
sbc accu + 1
|
|
||||||
sta accu + 1
|
|
||||||
rts
|
|
||||||
}
|
|
||||||
|
|
||||||
__asm negtmp
|
|
||||||
{
|
|
||||||
sec
|
|
||||||
lda #0
|
|
||||||
sbc tmp
|
|
||||||
sta tmp
|
|
||||||
lda #0
|
|
||||||
sbc tmp + 1
|
|
||||||
sta tmp + 1
|
|
||||||
rts
|
|
||||||
}
|
|
||||||
|
|
||||||
__asm inp_binop_divr_s16
|
__asm inp_binop_divr_s16
|
||||||
{
|
{
|
||||||
lda (ip), y
|
lda (ip), y
|
||||||
|
|
|
@ -187,6 +187,7 @@ void ByteCodeInstruction::Assemble(ByteCodeGenerator* generator, ByteCodeBasicBl
|
||||||
rl.mUpper = true;
|
rl.mUpper = true;
|
||||||
rl.mIndex = mVIndex;
|
rl.mIndex = mVIndex;
|
||||||
rl.mOffset = mValue;
|
rl.mOffset = mValue;
|
||||||
|
rl.mRuntime = nullptr;
|
||||||
block->mRelocations.Push(rl);
|
block->mRelocations.Push(rl);
|
||||||
block->PutWord(0);
|
block->PutWord(0);
|
||||||
}
|
}
|
||||||
|
@ -233,6 +234,7 @@ void ByteCodeInstruction::Assemble(ByteCodeGenerator* generator, ByteCodeBasicBl
|
||||||
rl.mUpper = true;
|
rl.mUpper = true;
|
||||||
rl.mIndex = mVIndex;
|
rl.mIndex = mVIndex;
|
||||||
rl.mOffset = mValue;
|
rl.mOffset = mValue;
|
||||||
|
rl.mRuntime = nullptr;
|
||||||
block->mRelocations.Push(rl);
|
block->mRelocations.Push(rl);
|
||||||
block->PutWord(0);
|
block->PutWord(0);
|
||||||
}
|
}
|
||||||
|
@ -253,6 +255,7 @@ void ByteCodeInstruction::Assemble(ByteCodeGenerator* generator, ByteCodeBasicBl
|
||||||
rl.mUpper = true;
|
rl.mUpper = true;
|
||||||
rl.mIndex = mVIndex;
|
rl.mIndex = mVIndex;
|
||||||
rl.mOffset = mValue;
|
rl.mOffset = mValue;
|
||||||
|
rl.mRuntime = nullptr;
|
||||||
block->mRelocations.Push(rl);
|
block->mRelocations.Push(rl);
|
||||||
block->PutWord(0);
|
block->PutWord(0);
|
||||||
}
|
}
|
||||||
|
@ -410,6 +413,7 @@ void ByteCodeInstruction::Assemble(ByteCodeGenerator* generator, ByteCodeBasicBl
|
||||||
rl.mUpper = true;
|
rl.mUpper = true;
|
||||||
rl.mIndex = mVIndex;
|
rl.mIndex = mVIndex;
|
||||||
rl.mOffset = 0;
|
rl.mOffset = 0;
|
||||||
|
rl.mRuntime = nullptr;
|
||||||
block->mRelocations.Push(rl);
|
block->mRelocations.Push(rl);
|
||||||
|
|
||||||
block->PutWord(0);
|
block->PutWord(0);
|
||||||
|
@ -1484,6 +1488,22 @@ void ByteCodeBasicBlock::CallAssembler(InterCodeProcedure* proc, const InterInst
|
||||||
bins.mFunction = ins.mMemory == IM_PROCEDURE;
|
bins.mFunction = ins.mMemory == IM_PROCEDURE;
|
||||||
mIns.Push(bins);
|
mIns.Push(bins);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (ins.mTTemp >= 0)
|
||||||
|
{
|
||||||
|
if (ins.mTType == IT_FLOAT)
|
||||||
|
{
|
||||||
|
ByteCodeInstruction bins(BC_STORE_REG_32);
|
||||||
|
bins.mRegister = BC_REG_TMP + proc->mTempOffset[ins.mTTemp];
|
||||||
|
mIns.Push(bins);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ByteCodeInstruction bins(BC_STORE_REG_16);
|
||||||
|
bins.mRegister = BC_REG_TMP + proc->mTempOffset[ins.mTTemp];
|
||||||
|
mIns.Push(bins);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ByteCode ByteCodeBasicBlock::RelationalOperator(InterCodeProcedure* proc, const InterInstruction& ins)
|
ByteCode ByteCodeBasicBlock::RelationalOperator(InterCodeProcedure* proc, const InterInstruction& ins)
|
||||||
|
|
|
@ -146,6 +146,7 @@ public:
|
||||||
uint16 mAddr;
|
uint16 mAddr;
|
||||||
bool mFunction, mLower, mUpper;
|
bool mFunction, mLower, mUpper;
|
||||||
uint16 mIndex, mOffset;
|
uint16 mIndex, mOffset;
|
||||||
|
const char * mRuntime;
|
||||||
};
|
};
|
||||||
|
|
||||||
class ByteCodeBasicBlock;
|
class ByteCodeBasicBlock;
|
||||||
|
|
|
@ -9,6 +9,7 @@ CompilationUnits::CompilationUnits(Errors * errors)
|
||||||
mCompilationUnits = nullptr;
|
mCompilationUnits = nullptr;
|
||||||
mPendingUnits = nullptr;
|
mPendingUnits = nullptr;
|
||||||
mScope = new DeclarationScope(nullptr);
|
mScope = new DeclarationScope(nullptr);
|
||||||
|
mRuntimeScope = new DeclarationScope(nullptr);
|
||||||
mStartup = nullptr;
|
mStartup = nullptr;
|
||||||
|
|
||||||
for (int i = 0; i < 128; i++)
|
for (int i = 0; i < 128; i++)
|
||||||
|
|
|
@ -24,6 +24,8 @@ public:
|
||||||
Declaration* mStartup;
|
Declaration* mStartup;
|
||||||
Declaration* mByteCodes[128];
|
Declaration* mByteCodes[128];
|
||||||
|
|
||||||
|
DeclarationScope* mRuntimeScope;
|
||||||
|
|
||||||
bool AddUnit(Location & location, const char* name, const char * from);
|
bool AddUnit(Location & location, const char* name, const char * from);
|
||||||
CompilationUnit* PendingUnit(void);
|
CompilationUnit* PendingUnit(void);
|
||||||
protected:
|
protected:
|
||||||
|
|
|
@ -120,6 +120,45 @@ bool Compiler::GenerateCode(void)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Compile used runtime functions
|
||||||
|
|
||||||
|
for (int i = 0; i < mByteCodeGenerator->mRelocations.Size(); i++)
|
||||||
|
{
|
||||||
|
if (mByteCodeGenerator->mRelocations[i].mRuntime)
|
||||||
|
{
|
||||||
|
Declaration* bcdec = mCompilationUnits->mRuntimeScope->Lookup(Ident::Unique(mByteCodeGenerator->mRelocations[i].mRuntime));
|
||||||
|
if (bcdec)
|
||||||
|
{
|
||||||
|
int index = -1, offset = 0;
|
||||||
|
if (bcdec->mType == DT_CONST_ASSEMBLER)
|
||||||
|
{
|
||||||
|
if (bcdec->mVarIndex < 0)
|
||||||
|
mInterCodeGenerator->TranslateAssembler(mInterCodeModule, bcdec->mValue);
|
||||||
|
index = bcdec->mVarIndex;
|
||||||
|
}
|
||||||
|
else if (bcdec->mType == DT_LABEL)
|
||||||
|
{
|
||||||
|
if (bcdec->mBase->mVarIndex < 0)
|
||||||
|
mInterCodeGenerator->TranslateAssembler(mInterCodeModule, bcdec->mBase->mValue);
|
||||||
|
index = bcdec->mBase->mVarIndex;
|
||||||
|
offset = bcdec->mInteger;
|
||||||
|
}
|
||||||
|
|
||||||
|
assert(index > 0);
|
||||||
|
mInterCodeModule->UseGlobal(index);
|
||||||
|
|
||||||
|
mByteCodeGenerator->mRelocations[i].mIndex = index;
|
||||||
|
mByteCodeGenerator->mRelocations[i].mOffset = offset;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mErrors->Error(loc, "Missing runtime code implementation", mByteCodeGenerator->mRelocations[i].mRuntime);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Compile used byte code functions
|
||||||
|
|
||||||
for (int i = 0; i < 128; i++)
|
for (int i = 0; i < 128; i++)
|
||||||
{
|
{
|
||||||
if (mByteCodeGenerator->mByteCodeUsed[i])
|
if (mByteCodeGenerator->mByteCodeUsed[i])
|
||||||
|
@ -152,8 +191,15 @@ bool Compiler::GenerateCode(void)
|
||||||
rel.mUpper = true;
|
rel.mUpper = true;
|
||||||
rel.mIndex = index;
|
rel.mIndex = index;
|
||||||
rel.mOffset = offset;
|
rel.mOffset = offset;
|
||||||
|
rel.mRuntime = nullptr;
|
||||||
mByteCodeGenerator->mRelocations.Push(rel);
|
mByteCodeGenerator->mRelocations.Push(rel);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
char n[10];
|
||||||
|
sprintf_s(n, "%d", i);
|
||||||
|
mErrors->Error(loc, "Missing byte code implementation", n);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -177,6 +223,7 @@ bool Compiler::GenerateCode(void)
|
||||||
rel.mUpper = ref.mUpper;
|
rel.mUpper = ref.mUpper;
|
||||||
rel.mIndex = ref.mIndex;
|
rel.mIndex = ref.mIndex;
|
||||||
rel.mOffset = ref.mOffset;
|
rel.mOffset = ref.mOffset;
|
||||||
|
rel.mRuntime = nullptr;
|
||||||
mByteCodeGenerator->mRelocations.Push(rel);
|
mByteCodeGenerator->mRelocations.Push(rel);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,6 +7,7 @@ typedef signed char int8;
|
||||||
typedef signed short int16;
|
typedef signed short int16;
|
||||||
typedef signed short int32;
|
typedef signed short int32;
|
||||||
|
|
||||||
|
static const uint8 BC_REG_WORK = 0x03;
|
||||||
static const uint8 BC_REG_IP = 0x19;
|
static const uint8 BC_REG_IP = 0x19;
|
||||||
static const uint8 BC_REG_ACCU = 0x1b;
|
static const uint8 BC_REG_ACCU = 0x1b;
|
||||||
static const uint8 BC_REG_ADDR = 0x1f;
|
static const uint8 BC_REG_ADDR = 0x1f;
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -10,12 +10,14 @@ class NativeCodeInstruction
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
NativeCodeInstruction(AsmInsType type = ASMIT_INV, AsmInsMode mode = ASMIM_IMPLIED, int address = 0, int varIndex = -1, bool lower = true, bool upper = true);
|
NativeCodeInstruction(AsmInsType type = ASMIT_INV, AsmInsMode mode = ASMIM_IMPLIED, int address = 0, int varIndex = -1, bool lower = true, bool upper = true);
|
||||||
|
NativeCodeInstruction(const char* runtime);
|
||||||
|
|
||||||
AsmInsType mType;
|
AsmInsType mType;
|
||||||
AsmInsMode mMode;
|
AsmInsMode mMode;
|
||||||
|
|
||||||
int mAddress, mVarIndex;
|
int mAddress, mVarIndex;
|
||||||
bool mLower, mUpper;
|
bool mLower, mUpper;
|
||||||
|
const char * mRuntime;
|
||||||
|
|
||||||
void Assemble(NativeCodeBasicBlock* block);
|
void Assemble(NativeCodeBasicBlock* block);
|
||||||
};
|
};
|
||||||
|
@ -46,17 +48,18 @@ public:
|
||||||
|
|
||||||
void CopyCode(NativeCodeProcedure* proc, uint8* target);
|
void CopyCode(NativeCodeProcedure* proc, uint8* target);
|
||||||
void Assemble(void);
|
void Assemble(void);
|
||||||
void Compile(InterCodeProcedure* iproc, NativeCodeProcedure* proc, InterCodeBasicBlock* block);
|
|
||||||
void Close(NativeCodeBasicBlock* trueJump, NativeCodeBasicBlock* falseJump, AsmInsType branch);
|
void Close(NativeCodeBasicBlock* trueJump, NativeCodeBasicBlock* falseJump, AsmInsType branch);
|
||||||
|
|
||||||
void PutByte(uint8 code);
|
void PutByte(uint8 code);
|
||||||
void PutWord(uint16 code);
|
void PutWord(uint16 code);
|
||||||
|
|
||||||
|
void LoadValueToReg(InterCodeProcedure* proc, const InterInstruction& ins, int reg, const NativeCodeInstruction * ainsl, const NativeCodeInstruction* ainsh);
|
||||||
|
|
||||||
void LoadConstant(InterCodeProcedure* proc, const InterInstruction& ins);
|
void LoadConstant(InterCodeProcedure* proc, const InterInstruction& ins);
|
||||||
void StoreValue(InterCodeProcedure* proc, const InterInstruction& ins);
|
void StoreValue(InterCodeProcedure* proc, const InterInstruction& ins);
|
||||||
void LoadValue(InterCodeProcedure* proc, const InterInstruction& ins);
|
void LoadValue(InterCodeProcedure* proc, const InterInstruction& ins);
|
||||||
void LoadStoreValue(InterCodeProcedure* proc, const InterInstruction& rins, const InterInstruction& wins);
|
void LoadStoreValue(InterCodeProcedure* proc, const InterInstruction& rins, const InterInstruction& wins);
|
||||||
void BinaryOperator(InterCodeProcedure* proc, const InterInstruction& ins);
|
void BinaryOperator(InterCodeProcedure* proc, const InterInstruction& ins, const InterInstruction* sins1, const InterInstruction* sins0);
|
||||||
void UnaryOperator(InterCodeProcedure* proc, const InterInstruction& ins);
|
void UnaryOperator(InterCodeProcedure* proc, const InterInstruction& ins);
|
||||||
void RelationalOperator(InterCodeProcedure* proc, const InterInstruction& ins, NativeCodeBasicBlock* trueJump, NativeCodeBasicBlock * falseJump);
|
void RelationalOperator(InterCodeProcedure* proc, const InterInstruction& ins, NativeCodeBasicBlock* trueJump, NativeCodeBasicBlock * falseJump);
|
||||||
void LoadEffectiveAddress(InterCodeProcedure* proc, const InterInstruction& ins);
|
void LoadEffectiveAddress(InterCodeProcedure* proc, const InterInstruction& ins);
|
||||||
|
@ -73,12 +76,17 @@ class NativeCodeProcedure
|
||||||
|
|
||||||
int mProgStart, mProgSize, mIndex;
|
int mProgStart, mProgSize, mIndex;
|
||||||
bool mNoFrame;
|
bool mNoFrame;
|
||||||
|
int mTempBlocks;
|
||||||
|
|
||||||
GrowingArray<ByteCodeRelocation> mRelocations;
|
GrowingArray<ByteCodeRelocation> mRelocations;
|
||||||
|
|
||||||
void Compile( ByteCodeGenerator * generator, InterCodeProcedure* proc);
|
void Compile( ByteCodeGenerator * generator, InterCodeProcedure* proc);
|
||||||
NativeCodeBasicBlock* CompileBlock(InterCodeProcedure* iproc, InterCodeBasicBlock* block);
|
NativeCodeBasicBlock* CompileBlock(InterCodeProcedure* iproc, InterCodeBasicBlock* block);
|
||||||
|
NativeCodeBasicBlock* AllocateBlock(void);
|
||||||
NativeCodeBasicBlock* TransientBlock(void);
|
NativeCodeBasicBlock* TransientBlock(void);
|
||||||
|
|
||||||
|
void CompileInterBlock(InterCodeProcedure* iproc, InterCodeBasicBlock* iblock, NativeCodeBasicBlock*block);
|
||||||
|
|
||||||
|
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -2186,6 +2186,56 @@ void Parser::ParsePragma(void)
|
||||||
}
|
}
|
||||||
ConsumeToken(TK_CLOSE_PARENTHESIS);
|
ConsumeToken(TK_CLOSE_PARENTHESIS);
|
||||||
}
|
}
|
||||||
|
else if (!strcmp(mScanner->mTokenIdent->mString, "runtime"))
|
||||||
|
{
|
||||||
|
mScanner->NextToken();
|
||||||
|
ConsumeToken(TK_OPEN_PARENTHESIS);
|
||||||
|
const Ident* rtident = nullptr;
|
||||||
|
|
||||||
|
if (mScanner->mToken == TK_IDENT)
|
||||||
|
{
|
||||||
|
rtident = mScanner->mTokenIdent;
|
||||||
|
mScanner->NextToken();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
mErrors->Error(mScanner->mLocation, "Identifier expected");
|
||||||
|
|
||||||
|
ConsumeToken(TK_COMMA);
|
||||||
|
if (mScanner->mToken == TK_IDENT)
|
||||||
|
{
|
||||||
|
Declaration* dec = mGlobals->Lookup(mScanner->mTokenIdent);
|
||||||
|
if (dec && dec->mType == DT_CONST_ASSEMBLER)
|
||||||
|
{
|
||||||
|
mScanner->NextToken();
|
||||||
|
if (ConsumeTokenIf(TK_DOT))
|
||||||
|
{
|
||||||
|
if (mScanner->mToken == TK_IDENT)
|
||||||
|
{
|
||||||
|
Declaration* ndec = dec->mBase->mScope->Lookup(mScanner->mTokenIdent);
|
||||||
|
if (ndec)
|
||||||
|
dec = ndec;
|
||||||
|
else
|
||||||
|
mErrors->Error(mScanner->mLocation, "Label not found in assembler code");
|
||||||
|
mScanner->NextToken();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
mErrors->Error(mScanner->mLocation, "Identifier expected");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (rtident)
|
||||||
|
{
|
||||||
|
mCompilationUnits->mRuntimeScope->Insert(rtident, dec);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
mErrors->Error(mScanner->mLocation, "Runtime function not found");
|
||||||
|
mScanner->NextToken();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
ConsumeToken(TK_CLOSE_PARENTHESIS);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
mScanner->NextToken();
|
mScanner->NextToken();
|
||||||
|
|
Loading…
Reference in New Issue