From 7a2ce3ee37377931313dad2b7892daa6dacaa9a4 Mon Sep 17 00:00:00 2001 From: cdkersey Date: Sun, 27 Sep 2015 22:01:29 -0600 Subject: [PATCH 1/2] Thanks, Si! --- doc/harp_iset.tex | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/doc/harp_iset.tex b/doc/harp_iset.tex index 4cd881f4..23a8f457 100644 --- a/doc/harp_iset.tex +++ b/doc/harp_iset.tex @@ -302,8 +302,8 @@ The flags register used by \texttt{tlbadd} stores, in its least-significant four \texttt{and} \%dest, \%src1, \%src2&And.\\ \texttt{or} \%dest, \%src1, \%src2&Or.\\ \texttt{xor} \%dest, \%src1, \%src2&Xor.\\ -\texttt{neg} \%dest, \%src1, \%src2&Two's complement.\\ -\texttt{not} \%dest, \%src1, \%src2&Bitwise complement.\\ +\texttt{neg} \%dest, \%src1&Two's complement.\\ +\texttt{not} \%dest, \%src1&Bitwise complement.\\ \end{tabular} \end{center} From 4840bf3ebd43ce50b8a677a573e49d39145ff037 Mon Sep 17 00:00:00 2001 From: cdkersey Date: Tue, 29 Sep 2015 13:23:57 -0600 Subject: [PATCH 2/2] Checking of assembly input for operand type correctness. --- src/Makefile | 4 ++-- src/include/asm-tokens.h | 5 +++++ src/include/obj.h | 6 ++++++ src/obj.cpp | 34 ++++++++++++++++++++++++++++++++-- 4 files changed, 45 insertions(+), 4 deletions(-) diff --git a/src/Makefile b/src/Makefile index 794a5928..a170f29c 100644 --- a/src/Makefile +++ b/src/Makefile @@ -27,9 +27,9 @@ harptool.o : harptool.cpp include/types.h include/core.h include/enc.h \ include/instruction.h include/mem.h include/obj.h \ include/archdef.h include/args.h include/help.h include/debug.h instruction.o : instruction.cpp include/instruction.h include/obj.h \ - include/core.h include/debug.h + include/core.h include/debug.h include/asm-tokens.h obj.o : obj.cpp include/types.h include/obj.h include/util.h \ - include/asm-tokens.h include/debug.h + include/asm-tokens.h include/debug.h include/instruction.h util.o : util.cpp include/types.h include/util.h mem.o : mem.cpp include/types.h include/util.h include/mem.h include/debug.h \ include/core.h diff --git a/src/include/asm-tokens.h b/src/include/asm-tokens.h index 2550d44b..f28a598b 100644 --- a/src/include/asm-tokens.h +++ b/src/include/asm-tokens.h @@ -1,3 +1,6 @@ +#ifndef HARPTOOL_ASM_TOKENS +#define HARPTOOL_ASM_TOKENS + namespace HarpTools { enum AsmTokens { ASM_T_DIR_DEF = 1, ASM_T_DIR_PERM, ASM_T_DIR_BYTE, ASM_T_DIR_WORD, @@ -9,3 +12,5 @@ namespace HarpTools { ASM_T_REG_FP, ASM_T_LIT, ASM_T_SYM, ASM_T_PEXP }; }; + +#endif diff --git a/src/include/obj.h b/src/include/obj.h index 5cb9741c..bfea8576 100644 --- a/src/include/obj.h +++ b/src/include/obj.h @@ -12,7 +12,9 @@ #include "types.h" #include "archdef.h" +#include "instruction.h" #include "enc.h" +#include "asm-tokens.h" namespace Harp { class Decoder; @@ -174,6 +176,10 @@ namespace Harp { virtual Obj *read(std::istream &input); private: Size wordSize, nRegs; + + // Operand type sequences indexed by argument class + enum ArgType {AT_END, AT_REG, AT_PREG, AT_LIT}; + static ArgType operandtype_table[][4]; // ArgClass -> ArgType[arg_idx] }; class HOFReader : public ObjReader { diff --git a/src/obj.cpp b/src/obj.cpp index bdb66edc..c98b7f29 100644 --- a/src/obj.cpp +++ b/src/obj.cpp @@ -111,6 +111,22 @@ static uint64_t readParenExpression(bool &valid, const string &s, return rPE(valid, s, d, 0, s.length()); } +AsmReader::ArgType AsmReader::operandtype_table[][4] = { + {AT_END}, // AC_NONE + {AT_REG, AT_REG, AT_END}, // AC_2REG + {AT_REG, AT_LIT, AT_END}, // AC_2IMM + {AT_REG, AT_REG, AT_REG, AT_END}, // AC_3REG + {AT_PREG, AT_PREG, AT_PREG, AT_END}, // AC_3PREG + {AT_REG, AT_REG, AT_LIT, AT_END}, // AC_3IMM + {AT_REG, AT_REG, AT_REG, AT_END}, // AC_3REGSRC + {AT_LIT, AT_END}, // AC_1IMM + {AT_REG, AT_END}, // AC_1REG + {AT_REG, AT_REG, AT_LIT, AT_END}, // AC_3IMMSRC + {AT_PREG, AT_REG, AT_END}, // AC_PREG_REG + {AT_PREG, AT_PREG, AT_END}, // AC_2PREG + {AT_REG, AT_REG, AT_END} // AC_2REGSRC +}; + int lexerFloatBytes; Obj *AsmReader::read(std::istream &input) { lexerFloatBytes = wordSize; @@ -146,6 +162,8 @@ Obj *AsmReader::read(std::istream &input) { Size next_chunk_align(0); uint64_t num_arg; RegNum nextPredNum; + Instruction::ArgClass ac; + int argPos; AsmTokens t; while ((t = (AsmTokens)f->yylex()) != 0) { @@ -346,7 +364,9 @@ Obj *AsmReader::read(std::istream &input) { break; case ASM_T_INST: if (state == ST_INIT) { - map::iterator opcIterator = opMap.find(yylval.s); + map::iterator + opcIterator = opMap.find(yylval.s); + if (opcIterator == opMap.end()) asmReaderError(yyline, "Invalid Instruction"); Instruction::Opcode opc = opcIterator->second; @@ -362,14 +382,18 @@ Obj *AsmReader::read(std::istream &input) { } curInst = new Instruction(); curInst->setOpcode(opc); + ac = Instruction::instTable[opc].argClass; + argPos = 0; if (nextPred) { nextPred = false; curInst->setPred(nextPredNum); } state = Instruction::instTable[opc].allSrcArgs?ST_INST2:ST_INST1; - } else { asmReaderError(yyline, "Unexpected token"); } + } else { asmReaderError(yyline, "Unexpected instruction"); } break; case ASM_T_PREG: + if (operandtype_table[ac][argPos++] != AT_PREG) + asmReaderError(yyline, "Unexpected predicate register"); switch (state) { case ST_INST1: curInst->setDestPReg(yylval.u); state = ST_INST2; @@ -394,6 +418,8 @@ Obj *AsmReader::read(std::istream &input) { case ASM_T_REG: continue_reg: + if (operandtype_table[ac][argPos++] != AT_REG) + asmReaderError(yyline, "Unexpected register operand."); switch (state) { case ST_INST1: curInst->setDestReg(yylval.u); state = ST_INST2; @@ -410,6 +436,8 @@ Obj *AsmReader::read(std::istream &input) { if (!valid) asmReaderError(yyline, "Invalid paren expression"); } case ASM_T_LIT: + if (operandtype_table[ac][argPos++] != AT_LIT) + asmReaderError(yyline, "Unexpected literal operand."); switch (state) { case ST_INST1: asmReaderError(yyline, "Unexpected literal"); case ST_INST2: curInst->setSrcImm(yylval.u); @@ -418,6 +446,8 @@ Obj *AsmReader::read(std::istream &input) { } break; case ASM_T_SYM: + if (operandtype_table[ac][argPos++] != AT_LIT) + asmReaderError(yyline, "Unexpected symbol operand."); switch (state) { case ST_INST1: asmReaderError(yyline, "Unexpected symbol"); case ST_INST2: if (defs.find(yylval.s) != defs.end()) {