diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..93de617 --- /dev/null +++ b/.gitignore @@ -0,0 +1,11 @@ +# GCC/G++ related + +obj/ +bin/ + +*.o +*.a +*.lib + +# Editors/IDE related +.vscode/ diff --git a/src/Eagle.cpp b/src/Eagle.cpp index 7e66a57..c2f8613 100644 --- a/src/Eagle.cpp +++ b/src/Eagle.cpp @@ -7,6 +7,7 @@ #include +#include "Eagle_asm_z80.hpp" #include "Eagle.hpp" Eagle::Eagle() @@ -77,6 +78,8 @@ Eagle::Eagle() this->keywords[".data.f"] = EAGLE_keywords::DATAF; this->keywords[".data.d"] = EAGLE_keywords::DATAD; + this->asm_z80 = new EagleAsmZ80(*this, this->ilabel); + this->asm_z80->initialize(); this->filetext.reserve(0x200000); this->text_code.reserve(0x200000); @@ -136,6 +139,11 @@ Eagle::Eagle() this->snes_checksum = false; } +Eagle::~Eagle() { + delete this->asm_z80; + this->asm_z80 = nullptr; +} + uint64_t Eagle::alloc(EAGLE_keywords type,int n) { int value; diff --git a/src/Eagle.hpp b/src/Eagle.hpp index 90bd5de..c16088f 100644 --- a/src/Eagle.hpp +++ b/src/Eagle.hpp @@ -16,7 +16,7 @@ typedef struct //Variable -typedef struct +typedef struct EagleVariable { int64_t immediate; // valeur immediate (si bimm == true) double dimmediate; // pareil mais en type double @@ -99,10 +99,13 @@ typedef struct }EAGLE_MNEMONIQUE; +class EagleAsmZ80; + class Eagle { public: Eagle(void); + ~Eagle(void); void parser_word(void); void load_file(const char *path); void write_file(const char *path,std::string text); @@ -172,11 +175,8 @@ class Eagle void asm_call_jump_80186(const EAGLE_VARIABLE &var,int narg,int type); //---------z80-------------- - void asm_return_z80(const EAGLE_VARIABLE &ret,bool retvoid); - void asm_alu_z80(const EAGLE_VARIABLE &dst,const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const char operator1,const char operator2); - void asm_bru_z80(const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const char operator1,const char operator2,int type,int clabel); - void asm_call_jump_z80(const EAGLE_VARIABLE &var,int narg,int type); + EagleAsmZ80 *asm_z80; //---------AltairX-------------- void asm_return_AltairX(const EAGLE_VARIABLE &ret,bool retvoid); diff --git a/src/Eagle_asm.cpp b/src/Eagle_asm.cpp index 52a4c70..baaea92 100644 --- a/src/Eagle_asm.cpp +++ b/src/Eagle_asm.cpp @@ -10,6 +10,7 @@ #include #include "Eagle.hpp" +#include "Eagle_asm_z80.hpp" void Eagle::asm_bru(const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const char operator1,const char operator2,int type,int clabel) { @@ -20,7 +21,7 @@ void Eagle::asm_bru(const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const asm_bru_6502(src1,src2,operator1,operator2,type,clabel); if(this->target == TARGET_Z80) - asm_bru_z80(src1,src2,operator1,operator2,type,clabel); + this->asm_z80->asm_bru(src1,src2,operator1,operator2,type,clabel); if(this->target == TARGET_AltairX) asm_bru_AltairX(src1,src2,operator1,operator2,type,clabel); @@ -35,7 +36,7 @@ void Eagle::asm_call_jump(const EAGLE_VARIABLE &src,int ninst,int type) asm_call_jump_6502(src,ninst,type); if(this->target == TARGET_Z80) - asm_call_jump_z80(src,ninst,type); + this->asm_z80->asm_call_jump(src, ninst, type, this->labelcall); if(this->target == TARGET_AltairX) asm_call_jump_AltairX(src,ninst,type); @@ -50,8 +51,7 @@ void Eagle::asm_return(const EAGLE_VARIABLE &ret,bool retvoid) asm_return_6502(ret,retvoid); if(this->target == TARGET_Z80) - asm_return_z80(ret,retvoid); - + this->asm_z80->asm_return(ret,retvoid); if(this->target == TARGET_AltairX) asm_return_AltairX(ret,retvoid); @@ -66,7 +66,7 @@ void Eagle::asm_alu(const EAGLE_VARIABLE &dst,const EAGLE_VARIABLE &src1,const E asm_alu_6502(dst,src1,src2,operator1,operator2); if(this->target == TARGET_Z80) - asm_alu_z80(dst,src1,src2,operator1,operator2); + this->asm_z80->asm_alu(dst,src1,src2,operator1,operator2); if(this->target == TARGET_AltairX) asm_alu_AltairX(dst,src1,src2,operator1,operator2); diff --git a/src/Eagle_asm_z80.cpp b/src/Eagle_asm_z80.cpp index f455e34..d52f6cb 100644 --- a/src/Eagle_asm_z80.cpp +++ b/src/Eagle_asm_z80.cpp @@ -7,13 +7,20 @@ #include +#include "Eagle_asm_z80.hpp" #include "Eagle.hpp" #define TYPE_LOOP 0 #define TYPE_WHILE 1 #define TYPE_IF 2 -void Eagle::asm_bru_z80(const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const char operator1,const char operator2,int type,int clabel) +EagleAsmZ80::EagleAsmZ80(Eagle &eagle, int &ilabel) : eagle(eagle), ilabel(ilabel) {} + +void EagleAsmZ80::initialize() { + // more to come here +} + +void EagleAsmZ80::asm_bru(const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const char operator1,const char operator2,int type,int clabel) { std::string label_adr = ".label_b"+std::to_string(clabel); @@ -25,19 +32,22 @@ void Eagle::asm_bru_z80(const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,co if(src1.type == EAGLE_keywords::IDX) { - this->text_code += "dex \n"; + this->eagle.text_code += "dex \n"; }else if(src1.type == EAGLE_keywords::IDY) { - this->text_code += "dey \n"; + this->eagle.text_code += "dey \n"; } - this->text_code += "cp \n"; + this->eagle.text_code += "cp \n"; - this->text_code += "jp " + label_adr + "\n"; + this->eagle.text_code += "jp " + label_adr + "\n"; } -void Eagle::asm_call_jump_z80(const EAGLE_VARIABLE &src,int ninst,int type) +void EagleAsmZ80::asm_call_jump(const EAGLE_VARIABLE &src, + int ninst, + int type, + std::string &labelcall) { std::string mnemonic = "jp ",mne1,mne2,saddress,saddress2; if(type >= 1) @@ -50,7 +60,7 @@ void Eagle::asm_call_jump_z80(const EAGLE_VARIABLE &src,int ninst,int type) } //------ - std::string src1value = this->labelcall; + std::string src1value = labelcall; if(src.bimm == true) { src1value = std::to_string(src.immediate); @@ -61,7 +71,7 @@ void Eagle::asm_call_jump_z80(const EAGLE_VARIABLE &src,int ninst,int type) if(src.type == EAGLE_keywords::UINT16) { - this->text_code += "ld hl," + std::to_string(src.address) +"\n"; + this->eagle.text_code += "ld hl," + std::to_string(src.address) +"\n"; src1value = "(hl)"; } @@ -77,40 +87,40 @@ void Eagle::asm_call_jump_z80(const EAGLE_VARIABLE &src,int ninst,int type) } } - this->text_code += mnemonic + src1value +"\n"; + this->eagle.text_code += mnemonic + src1value +"\n"; } -void Eagle::asm_return_z80(const EAGLE_VARIABLE &ret,bool retvoid) +void EagleAsmZ80::asm_return(const EAGLE_VARIABLE &ret,bool retvoid) { if(retvoid == true) { - this->text_code += "ret\n"; + this->eagle.text_code += "ret\n"; }else { if(ret.type == EAGLE_keywords::IDX) { - this->text_code += "ld a,IX\n"; + this->eagle.text_code += "ld a,IX\n"; } if(ret.type == EAGLE_keywords::IDY) { - this->text_code += "ld a,IY\n"; + this->eagle.text_code += "ld a,IY\n"; } if(ret.type != EAGLE_keywords::ACC) { if(ret.bimm == true) - this->text_code += "ld a,"+ std::to_string(ret.immediate&0xFF) +"\n"; + this->eagle.text_code += "ld a,"+ std::to_string(ret.immediate&0xFF) +"\n"; else - this->text_code += "lda a,("+ std::to_string(ret.address) +")\n"; + this->eagle.text_code += "lda a,("+ std::to_string(ret.address) +")\n"; } - this->text_code += "ret\n"; + this->eagle.text_code += "ret\n"; } } -void Eagle::asm_alu_z80(const EAGLE_VARIABLE &dst,const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const char operator1,const char operator2) +void EagleAsmZ80::asm_alu(const EAGLE_VARIABLE &dst,const EAGLE_VARIABLE &src1,const EAGLE_VARIABLE &src2,const char operator1,const char operator2) { std::string mnemonic; std::string src1value,dstvalue; @@ -146,8 +156,8 @@ void Eagle::asm_alu_z80(const EAGLE_VARIABLE &dst,const EAGLE_VARIABLE &src1,con if(operator1 == '=') { - this->text_code += "ld a," + src2value + "\n"; - this->text_code += "ld " + dstvalue + ",a\n"; + this->eagle.text_code += "ld a," + src2value + "\n"; + this->eagle.text_code += "ld " + dstvalue + ",a\n"; return; } @@ -184,10 +194,10 @@ void Eagle::asm_alu_z80(const EAGLE_VARIABLE &dst,const EAGLE_VARIABLE &src1,con } - this->text_code += "ld a," + src1value + "\n"; - this->text_code += "ld b," + src2value + "\n"; + this->eagle.text_code += "ld a," + src1value + "\n"; + this->eagle.text_code += "ld b," + src2value + "\n"; - this->text_code += mnemonic + reg +"\n"; + this->eagle.text_code += mnemonic + reg +"\n"; - this->text_code += "ld " + dstvalue + ",a\n"; + this->eagle.text_code += "ld " + dstvalue + ",a\n"; } diff --git a/src/Eagle_asm_z80.hpp b/src/Eagle_asm_z80.hpp new file mode 100644 index 0000000..e1bd4be --- /dev/null +++ b/src/Eagle_asm_z80.hpp @@ -0,0 +1,47 @@ +#pragma once + +// Forward declarations -------------------------------------------------------- + +typedef struct EagleVariable EAGLE_VARIABLE; +class Eagle; + + +// Types ----------------------------------------------------------------------- + +// EagleZ80 - assembly code generation for Z80 +class EagleAsmZ80 { + public: + EagleAsmZ80(Eagle &eagle, int &ilabel); + + // initialize the Z80 translation engine. Resets all the internal states. + void initialize(void); + + // asm_return_z80 translates a return operation + void asm_return(const EAGLE_VARIABLE &ret, bool retvoid); + + // asm_alu_z80 translates an ALU operation + void asm_alu(const EAGLE_VARIABLE &dst, + const EAGLE_VARIABLE &src1, + const EAGLE_VARIABLE &src2, + const char operator1, + const char operator2); + + // asm_bru_z80 translates a local control structures, IF, WHILE, DO etc. + void asm_bru(const EAGLE_VARIABLE &src1, + const EAGLE_VARIABLE &src2, + const char operator1, + const char operator2, + int type, + int clabel); + + // asm_call_jump_z80 translates a CALL or JMP operation + void asm_call_jump(const EAGLE_VARIABLE &var, + int narg, + int type, + std::string &labelcall); + + private: + Eagle &eagle; + // temporary hack, needs to be discussed + int &ilabel; +}; diff --git a/src/constant_folding.cpp b/src/constant_folding.cpp index c34f5cf..1843e8d 100644 --- a/src/constant_folding.cpp +++ b/src/constant_folding.cpp @@ -253,6 +253,7 @@ void Constant_folding::apply_operation() //----------------------- +__attribute__((unused)) static std::string formatExpression(const std::string& expression) { std::string result;