X-Git-Url: http://shamusworld.gotdns.org/cgi-bin/gitweb.cgi?p=rmac;a=blobdiff_plain;f=mach.c;h=b3e36c7dc382c93b84599a1979f8da85920c7280;hp=fac29e30d1bbc89197ed2d30596cb63fa5d249a2;hb=917bfc1503181b7e762b73b9560bb834c12c64fa;hpb=d09274f3e3d4dca122c308a621ea8edc100b7d99 diff --git a/mach.c b/mach.c index fac29e3..b3e36c7 100644 --- a/mach.c +++ b/mach.c @@ -3,7 +3,7 @@ // MACH.C - Code Generation // Copyright (C) 199x Landon Dyer, 2011 Reboot and Friends // RMAC derived from MADMAC v1.07 Written by Landon Dyer, 1986 -// Source Utilised with the Kind Permission of Landon Dyer +// Source utilised with the kind permission of Landon Dyer // #include "mach.h" @@ -12,26 +12,55 @@ #include "direct.h" #include "token.h" #include "procln.h" -#include "risca.h" +#include "riscasm.h" +#include "rmac.h" #define DEF_KW #include "kwtab.h" + +// Fucntion prototypes +int m_unimp(WORD, WORD), m_badmode(WORD, WORD), m_bad6mode(WORD, WORD), m_bad6inst(WORD, WORD); +int m_self(WORD, WORD); +int m_abcd(WORD, WORD); +int m_reg(WORD, WORD); +int m_imm(WORD, WORD); +int m_imm8(WORD, WORD); +int m_shi(WORD, WORD); +int m_shr(WORD, WORD); +int m_bitop(WORD, WORD); +int m_exg(WORD, WORD); +int m_ea(WORD, WORD); +int m_br(WORD, WORD); +int m_dbra(WORD, WORD); +int m_link(WORD, WORD); +int m_adda(WORD, WORD); +int m_addq(WORD, WORD); +//int m_move(WORD, int); +int m_move(WORD, WORD); +int m_moveq(WORD, WORD); +int m_usp(WORD, WORD); +int m_movep(WORD, WORD); +int m_trap(WORD, WORD); +int m_movem(WORD, WORD); +int m_clra(WORD, WORD); + // Common error messages -char * range_error = "expression out of range"; -char * abs_error = "illegal absolute expression"; -char * seg_error = "bad (section) expression"; -char * rel_error = "illegal relative address"; -char * siz_error = "bad size specified"; -char * undef_error = "undefined expression"; -char * fwd_error = "forward or undefined expression"; +char range_error[] = "expression out of range"; +char abs_error[] = "illegal absolute expression"; +char seg_error[] = "bad (section) expression"; +char rel_error[] = "illegal relative address"; +char siz_error[] = "bad size specified"; +char undef_error[] = "undefined expression"; +char fwd_error[] = "forward or undefined expression"; extern int ea0gen(WORD); extern int ea1gen(WORD); // Include code tables MNTAB machtab[] = { - { (WORD)-1, (unsigned long)-1L, (unsigned long)-1L, 0x0000, 0, m_badmode }, // 0 +// { (WORD)-1, (unsigned long)-1L, (unsigned long)-1L, 0x0000, 0, m_badmode }, // 0 + { 0xFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0x0000, 0, m_badmode }, // 0 #include "68ktab.h" { 0, 0L, 0L, 0x0000, 0, m_unimp } // Last entry }; @@ -83,19 +112,20 @@ WORD am_6[] = { // Error messages -int m_unimp(void) +int m_unimp(WORD unused1, WORD unused2) { return (int)error("unimplemented mnemonic"); } -int m_badmode(void) +//int m_badmode(void) +int m_badmode(WORD unused1, WORD unused2) { return (int)error("inappropriate addressing mode"); } -int m_self(WORD inst) +int m_self(WORD inst, WORD usused) { D_word(inst); return 0; @@ -121,43 +151,47 @@ int m_self(WORD inst) // int m_ea(WORD inst, WORD siz) { - WORD flg; - - flg = inst; // Save flag bits - inst &= ~0x3f; // Clobber flag bits in instr + WORD flg = inst; // Save flag bits + inst &= ~0x3F; // Clobber flag bits in instr - if (flg & 4) // Install "standard" instr size bits + // Install "standard" instr size bits + if (flg & 4) inst |= siz_6[siz]; if (flg & 16) - { // OR-in register number + { + // OR-in register number if (flg & 8) { - inst |= reg_9[a1reg]; // ea1reg in bits 9..11 + inst |= reg_9[a1reg]; // ea1reg in bits 9..11 } else { - inst |= reg_9[a0reg]; // ea0reg in bits 9..11 + inst |= reg_9[a0reg]; // ea0reg in bits 9..11 } } if (flg & 1) - { // Use am1 - inst |= am1 | a1reg; // Get ea1 into instr - D_word(inst); // Deposit instr + { + // Use am1 + inst |= am1 | a1reg; // Get ea1 into instr + D_word(inst); // Deposit instr - if (flg & 2) // Generate ea0 if requested + // Generate ea0 if requested + if (flg & 2) ea0gen(siz); - ea1gen(siz); // Generate ea1 + ea1gen(siz); // Generate ea1 } else - { // Use am0 - inst |= am0 | a0reg; // Get ea0 into instr - D_word(inst); // Deposit instr - ea0gen(siz); // Generate ea0 + { + // Use am0 + inst |= am0 | a0reg; // Get ea0 into instr + D_word(inst); // Deposit instr + ea0gen(siz); // Generate ea0 - if (flg & 2) // Generate ea1 if requested + // Generate ea1 if requested + if (flg & 2) ea1gen(siz); } @@ -172,8 +206,9 @@ int m_ea(WORD inst, WORD siz) int m_abcd(WORD inst, WORD siz) { if (inst & 1) - { // Install size bits - --inst; + { + // Install size bits + inst--; inst |= siz_6[siz]; } @@ -191,7 +226,7 @@ int m_adda(WORD inst, WORD siz) { inst |= am0 | a0reg | lwsiz_8[siz] | reg_9[a1reg]; D_word(inst); - ea0gen(siz); // Gen EA + ea0gen(siz); // Generate EA return 0; } @@ -203,14 +238,16 @@ int m_adda(WORD inst, WORD siz) // int m_reg(WORD inst, WORD siz) { - if (inst & 1) // Install size bits + if (inst & 1) + // Install size bits inst |= siz_6[siz]; - if (inst & 2) // Install other register (9..11) + if (inst & 2) + // Install other register (9..11) inst |= reg_9[a1reg]; - inst &= ~7; // Clear off crufty bits - inst |= a0reg; // Install first register + inst &= ~7; // Clear off crufty bits + inst |= a0reg; // Install first register D_word(inst); return 0; @@ -271,7 +308,7 @@ int m_shi(WORD inst, WORD siz) } else { - fixup(FU_QUICK, sloc, a0expr); + AddFixup(FU_QUICK, sloc, a0expr); D_word(inst); } @@ -286,11 +323,11 @@ int m_bitop(WORD inst, WORD siz) { // Enforce instruction sizes if (am1 == DREG) - { // X,Dn must be .n or .l - if (siz & (SIZB|SIZW)) + { // X,Dn must be .n or .l + if (siz & (SIZB | SIZW)) return error(siz_error); } - else if (siz & (SIZW|SIZL)) // X,ea must be .n or .b + else if (siz & (SIZW | SIZL)) // X,ea must be .n or .b return error(siz_error); // Construct instr and EAs @@ -299,7 +336,7 @@ int m_bitop(WORD inst, WORD siz) if (am0 == IMMED) { D_word(inst); - ea0gen(SIZB); // Immediate bit number + ea0gen(SIZB); // Immediate bit number } else { @@ -307,7 +344,8 @@ int m_bitop(WORD inst, WORD siz) D_word(inst); } - ea1gen(SIZB); // ea to bit-munch + // ea to bit-munch + ea1gen(SIZB); return 0; } @@ -335,7 +373,7 @@ int m_dbra(WORD inst, WORD siz) } else { - fixup(FU_WORD|FU_PCREL|FU_ISBRA, sloc, a1expr); + AddFixup(FU_WORD | FU_PCREL | FU_ISBRA, sloc, a1expr); D_word(0); } @@ -395,13 +433,19 @@ int m_link(WORD inst, WORD siz) // // Optimize MOVE.L #,D0 to a MOVEQ // -int m_move(WORD inst, int siz) +//int m_move(WORD inst, int siz) +int m_move(WORD inst, WORD size) { + // Cast the passed in value to an int + int siz = (int)size; + // Try to optimize to MOVEQ - if (siz == SIZL && am0 == IMMED && am1 == DREG + if (optim_flag && siz == SIZL && am0 == IMMED && am1 == DREG && (a0exattr & (TDB|DEFINED)) == DEFINED && a0exval + 0x80 < 0x100) { m_moveq((WORD)0x7000, (WORD)0); + if (sbra_flag) + warn("move.l #size,dx converted to moveq"); } else { @@ -428,9 +472,9 @@ int m_usp(WORD inst, WORD siz) siz = siz; if (am0 == AM_USP) - inst |= a1reg; // USP,An + inst |= a1reg; // USP, An else - inst |= a0reg; // An,USP + inst |= a0reg; // An, USP D_word(inst); @@ -445,15 +489,16 @@ int m_moveq(WORD inst, WORD siz) { siz = siz; + // Arrange for future fixup if (!(a0exattr & DEFINED)) - { // Arrange for future fixup - fixup(FU_BYTE|FU_SEXT, sloc+1, a0expr); + { + AddFixup(FU_BYTE | FU_SEXT, sloc + 1, a0expr); a0exval = 0; } else if (a0exval + 0x100 >= 0x200) return error(range_error); - inst |= reg_9[a1reg] | (a0exval & 0xff); + inst |= reg_9[a1reg] | (a0exval & 0xFF); D_word(inst); return 0; @@ -461,12 +506,10 @@ int m_moveq(WORD inst, WORD siz) // -// movep Dn,disp(An) -- movep disp(An),Dn +// movep Dn, disp(An) -- movep disp(An), Dn // int m_movep(WORD inst, WORD siz) { - //WORD k; - if (siz == SIZL) inst |= 0x0040; @@ -476,9 +519,7 @@ int m_movep(WORD inst, WORD siz) D_word(inst); if (am1 == AIND) - { - D_word(0); - } + D_word(0) else ea1gen(siz); } @@ -488,9 +529,7 @@ int m_movep(WORD inst, WORD siz) D_word(inst); if (am0 == AIND) - { - D_word(0); - } + D_word(0) else ea0gen(siz); } @@ -509,21 +548,28 @@ int m_br(WORD inst, WORD siz) if (a0exattr & DEFINED) { if ((a0exattr & TDB) != cursect) +//{ +//printf("m_br(): a0exattr = %X, cursect = %X, a0exval = %X, sloc = %X\n", a0exattr, cursect, a0exval, sloc); return error(rel_error); +//} v = a0exval - (sloc + 2); // Optimize branch instr. size if (siz == SIZN) { - if (v != 0 && v + 0x80 < 0x100) - { // Fits in .B - inst |= v & 0xff; + if (optim_flag && v != 0 && v + 0x80 < 0x100) + { + // Fits in .B + inst |= v & 0xFF; D_word(inst); + if (sbra_flag) + warn("Bcc.w/BSR.w converted to .s"); return 0; } else - { // Fits in .W + { + // Fits in .W if (v + 0x8000 > 0x10000) return error(range_error); @@ -538,7 +584,7 @@ int m_br(WORD inst, WORD siz) if (v + 0x80 >= 0x100) return error(range_error); - inst |= v & 0xff; + inst |= v & 0xFF; D_word(inst); } else @@ -556,15 +602,17 @@ int m_br(WORD inst, WORD siz) siz = SIZW; if (siz == SIZB) - { // .B - fixup(FU_BBRA|FU_PCREL|FU_SEXT, sloc, a0expr); + { + // .B + AddFixup(FU_BBRA | FU_PCREL | FU_SEXT, sloc, a0expr); D_word(inst); return 0; } else - { // .W + { + // .W D_word(inst); - fixup(FU_WORD|FU_PCREL|FU_LBRA|FU_ISBRA, sloc, a0expr); + AddFixup(FU_WORD | FU_PCREL | FU_LBRA | FU_ISBRA, sloc, a0expr); D_word(0); } @@ -589,7 +637,7 @@ int m_addq(WORD inst, WORD siz) } else { - fixup(FU_QUICK, sloc, a0expr); + AddFixup(FU_QUICK, sloc, a0expr); D_word(inst); } @@ -641,8 +689,9 @@ int m_movem(WORD inst, WORD siz) inst |= 0x0040; if (*tok == '#') - { // Handle #,ea - ++tok; + { + // Handle #, ea + tok++; if (abs_expr(&eval) != OK) return 0; @@ -655,7 +704,8 @@ int m_movem(WORD inst, WORD siz) } if (*tok >= KW_D0 && *tok <= KW_A7) - { // ,ea + { + // , ea if (reglist(&rmask) < 0) return 0; @@ -668,7 +718,7 @@ immed1: inst |= am0 | a0reg; - if (!(amsktab[am0] & (C_ALTCTRL|M_APREDEC))) + if (!(amsktab[am0] & (C_ALTCTRL | M_APREDEC))) return error("invalid addressing mode"); // If APREDEC, reverse register mask @@ -682,7 +732,8 @@ immed1: } } else - { // ea, + { + // ea, if (amode(0) < 0) return 0; @@ -695,8 +746,9 @@ immed1: return error("missing register list"); if (*tok == '#') - { // ea,# - ++tok; + { + // ea, # + tok++; if (abs_expr(&eval) != OK) return 0; @@ -709,7 +761,7 @@ immed1: else if (reglist(&rmask) < 0) return 0; - if (!(amsktab[am0] & (C_CTRL|M_APOSTINC))) + if (!(amsktab[am0] & (C_CTRL | M_APOSTINC))) return error("invalid addressing mode"); } @@ -731,3 +783,4 @@ int m_clra(WORD inst, WORD siz) return 0; } +