Skip to content

Commit

Permalink
Refactor Table class into assembler and disassembler
Browse files Browse the repository at this point in the history
  • Loading branch information
tgtakaoka committed Jan 29, 2025
1 parent bd47e7a commit 074874d
Show file tree
Hide file tree
Showing 98 changed files with 2,457 additions and 2,586 deletions.
25 changes: 23 additions & 2 deletions src/asm_cdp1802.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -185,6 +185,27 @@ Error AsmCdp1802::parseOperand(StrScanner &scan, Operand &op) const {
return op.getError();
}

bool acceptMode(AddrMode opr, AddrMode table) {
if (opr == table)
return true;
if (opr == M_REGN)
return table == M_REG1;
if (opr == M_ADDR)
return table == M_REGN || table == M_REG1 || table == M_IMM8 || table == M_PAGE ||
table == M_IOAD || table == M_SHRT || table == M_LONG;
return false;
}

bool acceptModes(AsmInsn &insn, const Entry *entry) {
const auto table = entry->readFlags();
return acceptMode(insn.op1.mode, table.mode1()) && acceptMode(insn.op2.mode, table.mode2());
}

Error searchName(CpuType cpuType, AsmInsn &insn) {
TABLE.cpu(cpuType)->searchName(insn, acceptModes);
return insn.getError();
}

Error AsmCdp1802::encodeImpl(StrScanner &scan, Insn &_insn) const {
AsmInsn insn(_insn);
if (parseOperand(scan, insn.op1) && insn.op1.hasError())
Expand All @@ -195,8 +216,8 @@ Error AsmCdp1802::encodeImpl(StrScanner &scan, Insn &_insn) const {
scan.skipSpaces();
}

if (_insn.setErrorIf(insn.op1, TABLE.searchName(cpuType(), insn)))
return _insn.getError();
if (searchName(cpuType(), insn))
return _insn.setError(insn.op1, insn);

emitOperand(insn, insn.mode1(), insn.op1);
if (insn.mode2() == M_ADDR) {
Expand Down
37 changes: 34 additions & 3 deletions src/asm_f3850.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -161,9 +161,40 @@ void AsmF3850::encodeOperand(AsmInsn &insn, const Operand &op, AddrMode mode) co
}
}

bool acceptAll(AsmInsn &, const Entry *) {
return true;
}

bool hasOperand(CpuType cpuType, AsmInsn &insn) {
TABLE.cpu(cpuType)->searchName(insn, acceptAll);
return insn.isOK() && insn.mode1() != M_NONE;
}

bool acceptMode(AddrMode opr, AddrMode table) {
if (opr == table)
return true;
if (opr == M_J)
return table == M_REG;
if (opr == M_C1 || opr == M_C4 || opr == M_IM3 || opr == M_IM4 || opr == M_IM8 || opr == M_ADDR)
return table == M_C1 || table == M_C4 || table == M_IM3 || table == M_IM4 ||
table == M_IM8 || table == M_ADDR || table == M_REL || table == M_REG ||
table == M_IOS || table == M_IOA;
return false;
}

bool acceptModes(AsmInsn &insn, const Entry *entry) {
const auto table = entry->readFlags();
return acceptMode(insn.op1.mode, table.mode1()) && acceptMode(insn.op2.mode, table.mode2());
}

Error searchName(CpuType cpuType, AsmInsn &insn) {
TABLE.cpu(cpuType)->searchName(insn, acceptModes);
return insn.getError();
}

Error AsmF3850::encodeImpl(StrScanner &scan, Insn &_insn) const {
AsmInsn insn(_insn);
if (TABLE.hasOperand(cpuType(), insn)) {
if (hasOperand(cpuType(), insn)) {
if (parseOperand(scan, insn.op1) && insn.op1.hasError())
return _insn.setError(insn.op1);
if (scan.skipSpaces().expect(',')) {
Expand All @@ -173,8 +204,8 @@ Error AsmF3850::encodeImpl(StrScanner &scan, Insn &_insn) const {
}
scan.skipSpaces();

if (_insn.setErrorIf(insn.op1, TABLE.searchName(cpuType(), insn)))
return _insn.getError();
if (searchName(cpuType(), insn))
return _insn.setError(insn.op1, insn);

encodeOperand(insn, insn.op1, insn.mode1());
encodeOperand(insn, insn.op2, insn.mode2());
Expand Down
26 changes: 24 additions & 2 deletions src/asm_i8048.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -231,6 +231,28 @@ void AsmI8048::encodeOperand(AsmInsn &insn, const AddrMode mode, const Operand &
}
}

bool acceptMode(AddrMode opr, AddrMode table) {
if (opr == table)
return true;
if (opr == M_IMM8)
return table == M_BIT8;
if (opr == M_AD11)
return table == M_AD08 || table == M_BITN;
if (opr == M_P1 || opr == M_P2)
return table == M_P12;
return false;
}

bool acceptModes(AsmInsn &insn, const Entry *entry) {
const auto table = entry->readFlags();
return acceptMode(insn.dstOp.mode, table.dst()) && acceptMode(insn.srcOp.mode, table.src());
}

Error searchName(CpuType cpuType, AsmInsn &insn) {
TABLE.cpu(cpuType)->searchName(insn, acceptModes);
return insn.getError();
}

Error AsmI8048::encodeImpl(StrScanner &scan, Insn &_insn) const {
AsmInsn insn(_insn);
if (parseOperand(scan, insn.dstOp) && insn.dstOp.hasError())
Expand All @@ -241,8 +263,8 @@ Error AsmI8048::encodeImpl(StrScanner &scan, Insn &_insn) const {
scan.skipSpaces();
}

if (_insn.setErrorIf(insn.dstOp, TABLE.searchName(cpuType(), insn)))
return _insn.getError();
if (searchName(cpuType(), insn))
return _insn.setError(insn.dstOp, insn);

encodeOperand(insn, insn.dst(), insn.dstOp);
encodeOperand(insn, insn.src(), insn.srcOp);
Expand Down
25 changes: 23 additions & 2 deletions src/asm_i8051.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -254,6 +254,27 @@ void AsmI8051::encodeOperand(AsmInsn &insn, AddrMode mode, const Operand &op) co
}
}

bool acceptMode(AddrMode opr, AddrMode table) {
if (opr == table)
return true;
if (opr == M_IMM16)
return table == M_IMM8;
if (opr == M_ADR16)
return table == M_ADR8 || table == M_ADR11 || table == M_REL || table == M_BITAD;
return false;
}

bool acceptModes(AsmInsn &insn, const Entry *entry) {
const auto table = entry->readFlags();
return acceptMode(insn.dstOp.mode, table.dst()) && acceptMode(insn.srcOp.mode, table.src()) &&
acceptMode(insn.extOp.mode, table.ext());
}

Error searchName(CpuType cpuType, AsmInsn &insn) {
TABLE.cpu(cpuType)->searchName(insn, acceptModes);
return insn.getError();
}

Error AsmI8051::encodeImpl(StrScanner &scan, Insn &_insn) const {
AsmInsn insn(_insn);
if (parseOperand(scan, insn.dstOp) && insn.dstOp.hasError())
Expand All @@ -269,8 +290,8 @@ Error AsmI8051::encodeImpl(StrScanner &scan, Insn &_insn) const {
scan.skipSpaces();
}

if (_insn.setErrorIf(insn.dstOp, TABLE.searchName(cpuType(), insn)))
return _insn.getError();
if (searchName(cpuType(), insn))
return _insn.setError(insn.dstOp, insn);

const auto dst = insn.dst();
const auto src = insn.src();
Expand Down
63 changes: 61 additions & 2 deletions src/asm_i8080.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -255,6 +255,65 @@ Error AsmI8080::processPseudo(StrScanner &scan, Insn &insn) {
return Assembler::processPseudo(scan, insn);
}

bool acceptIntelMode(AddrMode opr, AddrMode table) {
if (opr == table)
return true;
if (opr == M_SRC)
return table == M_DST;
if (opr == M_IDX || opr == R_H)
return table == M_PTR || table == M_STK || table == M_SRC || table == M_DST;
if (opr == M_IM16)
return table == M_IM8 || table == M_ABS || table == M_IOA || table == M_VEC;
return false;
}

bool acceptIntelModes(AsmInsn &insn, const Entry *entry) {
const auto table = entry->readFlags();
return acceptIntelMode(insn.dstOp.mode, table.dst()) &&
acceptIntelMode(insn.srcOp.mode, table.src());
}

bool acceptZilogMode(AddrMode opr, AddrMode table) {
if (opr == table)
return true;
if (opr == M_SRC || opr == R_A)
return table == M_DST || table == M_SRC || table == M_DST || table == M_SRC;
if (opr == I_HL)
return table == M_SRC || table == M_DST;
if (opr == R_C)
return table == M_SRC || table == M_DST || table == M_CC;
if (opr == R_BC || opr == R_DE)
return table == M_PTR || table == M_STK;
if (opr == R_HL)
return table == M_PTR || table == M_STK;
if (opr == R_SP)
return table == M_PTR;
if (opr == R_AF)
return table == M_STK;
if (opr == M_IM16)
return table == M_IM8 || table == M_VEC;
if (opr == M_ABS)
return table == M_IOA;
return false;
}

bool acceptZilogModes(AsmInsn &insn, const Entry *entry) {
const auto table = entry->readFlags();
if (acceptZilogMode(insn.dstOp.mode, table.dst()) &&
acceptZilogMode(insn.srcOp.mode, table.src())) {
if (table.undefined())
insn.setErrorIf(OPERAND_NOT_ALLOWED);
return true;
}
return false;
}

Error searchName(CpuType cpuType, AsmInsn &insn, bool zilog) {
auto acceptModes = zilog ? acceptZilogModes : acceptIntelModes;
TABLE.cpu(cpuType, zilog)->searchName(insn, acceptModes);
return insn.getError();
}

Error AsmI8080::encodeImpl(StrScanner &scan, Insn &_insn) const {
AsmInsn insn(_insn);
if (parseOperand(scan, insn.dstOp) && insn.dstOp.hasError())
Expand All @@ -265,8 +324,8 @@ Error AsmI8080::encodeImpl(StrScanner &scan, Insn &_insn) const {
scan.skipSpaces();
}

if (_insn.setErrorIf(insn.dstOp, TABLE.searchName(cpuType(), insn, _zilogSyntax)))
return _insn.getError();
if (searchName(cpuType(), insn, _zilogSyntax))
return _insn.setError(insn.dstOp, insn);

encodeOperand(insn, insn.dstOp, insn.dst());
encodeOperand(insn, insn.srcOp, insn.src());
Expand Down
36 changes: 34 additions & 2 deletions src/asm_i8096.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -255,6 +255,38 @@ void AsmI8096::emitOperand(AsmInsn &insn, AddrMode mode, const Operand &op) cons
}
}

bool acceptMode(AddrMode opr, AddrMode table) {
if (opr == table)
return true;
if (opr == M_ADDR)
return table == M_BREG || table == M_WREG || table == M_LREG || table == M_BAOP ||
table == M_WAOP || table == M_REL8 || table == M_REL11 || table == M_REL16 ||
table == M_COUNT || table == M_BITNO;
if (opr == M_IMM16)
return table == M_BAOP || table == M_WAOP || table == M_COUNT;
if (opr == M_INDIR)
return table == M_BAOP || table == M_WAOP;
if (opr == M_IDX16)
return table == M_BAOP || table == M_WAOP;
return false;
}

bool acceptModes(AsmInsn &insn, const Entry *entry) {
const auto table = entry->readFlags();
if (acceptMode(insn.dstOp.mode, table.dst()) && acceptMode(insn.src1Op.mode, table.src1()) &&
acceptMode(insn.src2Op.mode, table.src2())) {
if (table.undefined())
insn.setErrorIf(OPERAND_NOT_ALLOWED);
return true;
}
return false;
}

Error searchName(CpuType cpuType, AsmInsn &insn) {
TABLE.cpu(cpuType)->searchName(insn, acceptModes);
return insn.getError();
}

Error AsmI8096::encodeImpl(StrScanner &scan, Insn &_insn) const {
AsmInsn insn(_insn);
if (parseOperand(scan, insn.dstOp) && insn.dstOp.hasError())
Expand All @@ -270,8 +302,8 @@ Error AsmI8096::encodeImpl(StrScanner &scan, Insn &_insn) const {
scan.skipSpaces();
}

if (_insn.setErrorIf(insn.dstOp, TABLE.searchName(cpuType(), insn)))
return _insn.getError();
if (searchName(cpuType(), insn))
return _insn.setError(insn.dstOp, insn);

const auto jbx_djnz = insn.src2() == M_REL8 || insn.src1() == M_REL8;
if (!jbx_djnz) {
Expand Down
78 changes: 51 additions & 27 deletions src/asm_ins8060.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -154,6 +154,35 @@ Error AsmIns8060::parseOperand(StrScanner &scan, Operand &op) const {
return OK;
}

Error AsmIns8060::encodeOperand(AsmInsn &insn, const Operand &op) const {
insn.setErrorIf(insn.op);
switch (insn.addrMode()) {
case M_NONE:
insn.emitInsn();
break;
case M_REL8:
encodeRel8(insn, insn.op);
break;
case M_PNTR:
insn.embed(encodePointerReg(insn.op.reg));
insn.emitInsn();
break;
case M_DISP:
case M_INDX:
encodeIndx(insn, insn.op);
break;
case M_IMM8:
if (insn.op.val.overflowUint8())
insn.setErrorIf(insn.op, OVERFLOW_RANGE);
insn.emitInsn();
insn.emitByte(insn.op.val.getUnsigned());
break;
default:
break;
}
return insn.getError();
}

Error AsmIns8060::defineAddrConstant(StrScanner &scan, Insn &insn) {
do {
auto p = scan.skipSpaces();
Expand All @@ -173,42 +202,37 @@ Error AsmIns8060::processPseudo(StrScanner &scan, Insn &insn) {
return Assembler::processPseudo(scan, insn);
}

bool acceptMode(AsmInsn &insn, const Entry *entry) {
const auto opr = insn.op.mode;
const auto table = entry->readFlags().mode();
if (opr == table)
return true;
if (opr == M_REL8)
return table == M_IMM8 || table == M_DISP || table == M_INDX;
if (opr == M_DISP)
return table == M_REL8 || table == M_INDX;
return false;
}

Error searchName(CpuType cpuType, AsmInsn &insn) {
TABLE.cpu(cpuType)->searchName(insn, acceptMode);
return insn.getError();
}

Error AsmIns8060::encodeImpl(StrScanner &scan, Insn &_insn) const {
AsmInsn insn(_insn);
if (parseOperand(scan, insn.op) && insn.op.hasError())
return _insn.setError(insn.op);
scan.skipSpaces();

if (_insn.setErrorIf(insn.op, TABLE.searchName(cpuType(), insn)))
return _insn.getError();
if (searchName(cpuType(), insn))
return _insn.setError(insn.op, insn);

encodeOperand(insn, insn.op);

insn.setErrorIf(insn.op);
switch (insn.addrMode()) {
case M_NONE:
insn.emitInsn();
break;
case M_REL8:
encodeRel8(insn, insn.op);
break;
case M_PNTR:
insn.embed(encodePointerReg(insn.op.reg));
insn.emitInsn();
break;
case M_DISP:
case M_INDX:
encodeIndx(insn, insn.op);
break;
case M_IMM8:
if (insn.op.val.overflowUint8())
insn.setErrorIf(insn.op, OVERFLOW_RANGE);
insn.emitInsn();
insn.emitByte(insn.op.val.getUnsigned());
break;
default:
break;
}
if (insn.length() > 0 && page(insn.address()) != page(insn.address() + insn.length() - 1))
insn.setErrorIf(insn.op, OVERWRAP_SEGMENT);

return _insn.setError(insn);
}

Expand Down
Loading

0 comments on commit 074874d

Please sign in to comment.