diff --git a/contrib/instr/TGC5C_instr.yaml b/contrib/instr/TGC5C_instr.yaml index 1663d37..c28b051 100644 --- a/contrib/instr/TGC5C_instr.yaml +++ b/contrib/instr/TGC5C_instr.yaml @@ -20,7 +20,7 @@ RVI: mask: 0b00000000000000000000000001111111 size: 32 branch: true - delay: 1 + delay: [1,1] JALR: index: 3 encoding: 0b00000000000000000000000001100111 diff --git a/gen_input/templates/tcc/CORENAME.cpp.gtl b/gen_input/templates/tcc/CORENAME.cpp.gtl index f736293..40db6d4 100644 --- a/gen_input/templates/tcc/CORENAME.cpp.gtl +++ b/gen_input/templates/tcc/CORENAME.cpp.gtl @@ -99,6 +99,10 @@ protected: void gen_wait(tu_builder& tu, unsigned type); + inline void gen_set_tval(tu_builder& tu, uint64_t new_tval); + + inline void gen_set_tval(tu_builder& tu, value new_tval); + inline void gen_trap_check(tu_builder& tu) { tu("if(*trap_state!=0) goto trap_entry;"); } @@ -169,6 +173,7 @@ private: pc=pc+ ${instr.length/8}; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); <%instr.behavior.eachLine{%>${it} <%}%> tu.close_scope(); @@ -304,10 +309,17 @@ template void vm_impl::gen_leave_trap(tu_builder& tu, unsi template void vm_impl::gen_wait(tu_builder& tu, unsigned type) { } +template void vm_impl::gen_set_tval(tu_builder& tu, uint64_t new_tval) { + tu(fmt::format("tval = {};", new_tval)); +} +template void vm_impl::gen_set_tval(tu_builder& tu, value new_tval) { + tu(fmt::format("tval = {};", new_tval.str)); +} + template void vm_impl::gen_trap_behavior(tu_builder& tu) { tu("trap_entry:"); this->gen_sync(tu, POST_SYNC, -1); - tu("enter_trap(core_ptr, *trap_state, *pc, 0);"); + tu("enter_trap(core_ptr, *trap_state, *pc, tval);"); tu.store(traits::LAST_BRANCH, tu.constant(std::numeric_limits::max(),32)); tu("return *next_pc;"); } diff --git a/src/vm/tcc/vm_tgc5c.cpp b/src/vm/tcc/vm_tgc5c.cpp index b02372d..6483ec1 100644 --- a/src/vm/tcc/vm_tgc5c.cpp +++ b/src/vm/tcc/vm_tgc5c.cpp @@ -99,6 +99,10 @@ protected: void gen_wait(tu_builder& tu, unsigned type); + inline void gen_set_tval(tu_builder& tu, uint64_t new_tval); + + inline void gen_set_tval(tu_builder& tu, value new_tval); + inline void gen_trap_check(tu_builder& tu) { tu("if(*trap_state!=0) goto trap_entry;"); } @@ -345,6 +349,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -380,6 +385,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -415,21 +421,26 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } else{ - if(imm%static_cast(traits:: INSTR_ALIGNMENT)){ this->gen_raise_trap(tu, 0, 0); - } - else{ - if(rd!=0) { - tu.store(rd + traits::X0, - tu.constant((uint32_t)(PC+4),32)); - } - auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int32_t)sext<21>(imm)),32); - tu.store(traits::NEXT_PC, PC_val_v); - tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + auto new_pc = tu.assignment(tu.constant((uint32_t)(PC+(int32_t)sext<21>(imm)),32),32); + tu.open_if(tu.urem( + new_pc, + tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); + this->gen_raise_trap(tu, 0, 0); + tu.open_else(); + if(rd!=0) { + tu.store(rd + traits::X0, + tu.constant((uint32_t)(PC+4),32)); } + auto PC_val_v = tu.assignment("PC_val", new_pc,32); + tu.store(traits::NEXT_PC, PC_val_v); + tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + tu.close_scope(); } auto returnValue = std::make_tuple(BRANCH); @@ -458,6 +469,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -471,6 +483,7 @@ private: tu.open_if(tu.urem( new_pc, tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); this->gen_raise_trap(tu, 0, 0); tu.open_else(); if(rd!=0) { @@ -509,6 +522,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -516,13 +530,17 @@ private: tu.open_if(tu.icmp(ICmpInst::ICMP_EQ, tu.load(rs1+ traits::X0, 0), tu.load(rs2+ traits::X0, 0))); - if(imm%static_cast(traits:: INSTR_ALIGNMENT)){ this->gen_raise_trap(tu, 0, 0); - } - else{ - auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<13>(imm)),32); - tu.store(traits::NEXT_PC, PC_val_v); - tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); - } + auto new_pc = tu.assignment(tu.constant((uint32_t)(PC+(int16_t)sext<13>(imm)),32),32); + tu.open_if(tu.urem( + new_pc, + tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); + this->gen_raise_trap(tu, 0, 0); + tu.open_else(); + auto PC_val_v = tu.assignment("PC_val", new_pc,32); + tu.store(traits::NEXT_PC, PC_val_v); + tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + tu.close_scope(); tu.close_scope(); } auto returnValue = std::make_tuple(BRANCH); @@ -552,6 +570,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -559,13 +578,17 @@ private: tu.open_if(tu.icmp(ICmpInst::ICMP_NE, tu.load(rs1+ traits::X0, 0), tu.load(rs2+ traits::X0, 0))); - if(imm%static_cast(traits:: INSTR_ALIGNMENT)){ this->gen_raise_trap(tu, 0, 0); - } - else{ - auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<13>(imm)),32); - tu.store(traits::NEXT_PC, PC_val_v); - tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); - } + auto new_pc = tu.assignment(tu.constant((uint32_t)(PC+(int16_t)sext<13>(imm)),32),32); + tu.open_if(tu.urem( + new_pc, + tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); + this->gen_raise_trap(tu, 0, 0); + tu.open_else(); + auto PC_val_v = tu.assignment("PC_val", new_pc,32); + tu.store(traits::NEXT_PC, PC_val_v); + tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + tu.close_scope(); tu.close_scope(); } auto returnValue = std::make_tuple(BRANCH); @@ -595,6 +618,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -602,13 +626,17 @@ private: tu.open_if(tu.icmp(ICmpInst::ICMP_SLT, tu.ext(tu.load(rs1+ traits::X0, 0),32,true), tu.ext(tu.load(rs2+ traits::X0, 0),32,true))); - if(imm%static_cast(traits:: INSTR_ALIGNMENT)){ this->gen_raise_trap(tu, 0, 0); - } - else{ - auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<13>(imm)),32); - tu.store(traits::NEXT_PC, PC_val_v); - tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); - } + auto new_pc = tu.assignment(tu.constant((uint32_t)(PC+(int16_t)sext<13>(imm)),32),32); + tu.open_if(tu.urem( + new_pc, + tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); + this->gen_raise_trap(tu, 0, 0); + tu.open_else(); + auto PC_val_v = tu.assignment("PC_val", new_pc,32); + tu.store(traits::NEXT_PC, PC_val_v); + tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + tu.close_scope(); tu.close_scope(); } auto returnValue = std::make_tuple(BRANCH); @@ -638,6 +666,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -645,13 +674,17 @@ private: tu.open_if(tu.icmp(ICmpInst::ICMP_SGE, tu.ext(tu.load(rs1+ traits::X0, 0),32,true), tu.ext(tu.load(rs2+ traits::X0, 0),32,true))); - if(imm%static_cast(traits:: INSTR_ALIGNMENT)){ this->gen_raise_trap(tu, 0, 0); - } - else{ - auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<13>(imm)),32); - tu.store(traits::NEXT_PC, PC_val_v); - tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); - } + auto new_pc = tu.assignment(tu.constant((uint32_t)(PC+(int16_t)sext<13>(imm)),32),32); + tu.open_if(tu.urem( + new_pc, + tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); + this->gen_raise_trap(tu, 0, 0); + tu.open_else(); + auto PC_val_v = tu.assignment("PC_val", new_pc,32); + tu.store(traits::NEXT_PC, PC_val_v); + tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + tu.close_scope(); tu.close_scope(); } auto returnValue = std::make_tuple(BRANCH); @@ -681,6 +714,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -688,13 +722,17 @@ private: tu.open_if(tu.icmp(ICmpInst::ICMP_ULT, tu.load(rs1+ traits::X0, 0), tu.load(rs2+ traits::X0, 0))); - if(imm%static_cast(traits:: INSTR_ALIGNMENT)){ this->gen_raise_trap(tu, 0, 0); - } - else{ - auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<13>(imm)),32); - tu.store(traits::NEXT_PC, PC_val_v); - tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); - } + auto new_pc = tu.assignment(tu.constant((uint32_t)(PC+(int16_t)sext<13>(imm)),32),32); + tu.open_if(tu.urem( + new_pc, + tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); + this->gen_raise_trap(tu, 0, 0); + tu.open_else(); + auto PC_val_v = tu.assignment("PC_val", new_pc,32); + tu.store(traits::NEXT_PC, PC_val_v); + tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + tu.close_scope(); tu.close_scope(); } auto returnValue = std::make_tuple(BRANCH); @@ -724,6 +762,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -731,13 +770,17 @@ private: tu.open_if(tu.icmp(ICmpInst::ICMP_UGE, tu.load(rs1+ traits::X0, 0), tu.load(rs2+ traits::X0, 0))); - if(imm%static_cast(traits:: INSTR_ALIGNMENT)){ this->gen_raise_trap(tu, 0, 0); - } - else{ - auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<13>(imm)),32); - tu.store(traits::NEXT_PC, PC_val_v); - tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); - } + auto new_pc = tu.assignment(tu.constant((uint32_t)(PC+(int16_t)sext<13>(imm)),32),32); + tu.open_if(tu.urem( + new_pc, + tu.constant(static_cast(traits:: INSTR_ALIGNMENT),32))); + this->gen_set_tval(tu, new_pc); + this->gen_raise_trap(tu, 0, 0); + tu.open_else(); + auto PC_val_v = tu.assignment("PC_val", new_pc,32); + tu.store(traits::NEXT_PC, PC_val_v); + tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); + tu.close_scope(); tu.close_scope(); } auto returnValue = std::make_tuple(BRANCH); @@ -767,6 +810,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -807,6 +851,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -847,6 +892,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -887,6 +933,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -927,6 +974,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -967,6 +1015,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1003,6 +1052,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1039,6 +1089,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1075,6 +1126,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1113,6 +1165,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1151,6 +1204,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1189,6 +1243,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1227,6 +1282,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1265,6 +1321,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1303,6 +1360,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1341,6 +1399,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1379,6 +1438,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1417,6 +1477,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1455,6 +1516,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1493,6 +1555,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1533,6 +1596,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1571,6 +1635,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1609,6 +1674,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1647,6 +1713,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1687,6 +1754,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1727,6 +1795,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1765,6 +1834,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1805,6 +1875,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.write_mem(traits::FENCE, static_cast(traits:: fence), tu.constant((uint8_t)pred<<4|succ,8)); auto returnValue = std::make_tuple(CONT); @@ -1827,6 +1898,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_raise_trap(tu, 0, 11); auto returnValue = std::make_tuple(TRAP); @@ -1849,6 +1921,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_raise_trap(tu, 0, 3); auto returnValue = std::make_tuple(TRAP); @@ -1871,6 +1944,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_leave_trap(tu, 3); auto returnValue = std::make_tuple(TRAP); @@ -1893,6 +1967,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_wait(tu, 1); auto returnValue = std::make_tuple(CONT); @@ -1921,6 +1996,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -1962,6 +2038,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2005,6 +2082,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2048,6 +2126,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2086,6 +2165,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2128,6 +2208,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2170,6 +2251,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.write_mem(traits::FENCE, static_cast(traits:: fencei), tu.constant(imm,16)); auto returnValue = std::make_tuple(FLUSH); @@ -2198,6 +2280,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2237,6 +2320,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2278,6 +2362,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2319,6 +2404,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2360,6 +2446,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2418,6 +2505,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2465,6 +2553,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2526,6 +2615,7 @@ private: pc=pc+ 4; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rs1>=static_cast(traits:: RFS)||rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2572,6 +2662,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(imm) { tu.store(rd+8 + traits::X0, tu.ext((tu.add( @@ -2608,6 +2699,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); auto offs = tu.assignment(tu.ext((tu.add( tu.load(rs1+8+ traits::X0, 0), tu.constant(uimm,8))),32,false),32); @@ -2640,6 +2732,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); auto offs = tu.assignment(tu.ext((tu.add( tu.load(rs1+8+ traits::X0, 0), tu.constant(uimm,8))),32,false),32); @@ -2670,6 +2763,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2703,6 +2797,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); auto returnValue = std::make_tuple(CONT); tu.close_scope(); @@ -2728,6 +2823,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.store(1 + traits::X0, tu.constant((uint32_t)(PC+2),32)); auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<12>(imm)),32); @@ -2759,6 +2855,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2794,6 +2891,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(imm==0||rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -2826,6 +2924,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(nzimm) { tu.store(2 + traits::X0, tu.ext((tu.add( @@ -2857,6 +2956,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); auto returnValue = std::make_tuple(CONT); @@ -2884,6 +2984,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.store(rs1+8 + traits::X0, tu.lshr( tu.load(rs1+8+ traits::X0, 0), @@ -2914,6 +3015,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(shamt){ tu.store(rs1+8 + traits::X0, tu.ext((tu.ashr( (tu.ext(tu.load(rs1+8+ traits::X0, 0),32,true)), @@ -2952,6 +3054,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.store(rs1+8 + traits::X0, tu.ext((tu.bitwise_and( tu.load(rs1+8+ traits::X0, 0), @@ -2982,6 +3085,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.store(rd+8 + traits::X0, tu.ext((tu.sub( tu.load(rd+8+ traits::X0, 0), @@ -3012,6 +3116,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.store(rd+8 + traits::X0, tu.bitwise_xor( tu.load(rd+8+ traits::X0, 0), @@ -3042,6 +3147,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.store(rd+8 + traits::X0, tu.bitwise_or( tu.load(rd+8+ traits::X0, 0), @@ -3072,6 +3178,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.store(rd+8 + traits::X0, tu.bitwise_and( tu.load(rd+8+ traits::X0, 0), @@ -3101,6 +3208,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); auto PC_val_v = tu.assignment("PC_val", (uint32_t)(PC+(int16_t)sext<12>(imm)),32); tu.store(traits::NEXT_PC, PC_val_v); tu.store(traits::LAST_BRANCH, tu.constant(2U, 2)); @@ -3130,6 +3238,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.open_if(tu.icmp(ICmpInst::ICMP_EQ, tu.load(rs1+8+ traits::X0, 0), tu.constant(0,8))); @@ -3163,6 +3272,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); tu.open_if(tu.icmp(ICmpInst::ICMP_NE, tu.load(rs1+8+ traits::X0, 0), tu.constant(0,8))); @@ -3196,6 +3306,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -3233,6 +3344,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)||rd==0) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -3269,6 +3381,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -3303,6 +3416,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs1&&rs1(traits:: RFS)){ auto addr_mask = tu.assignment(tu.constant((uint32_t)- 2,32),32); auto PC_val_v = tu.assignment("PC_val", tu.bitwise_and( tu.load(rs1%static_cast(traits:: RFS)+ traits::X0, 0), @@ -3334,6 +3448,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_raise_trap(tu, 0, 2); auto returnValue = std::make_tuple(CONT); @@ -3361,6 +3476,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rd>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -3397,6 +3513,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs1>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -3432,6 +3549,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_raise_trap(tu, 0, 3); auto returnValue = std::make_tuple(CONT); @@ -3459,6 +3577,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); if(rs2>=static_cast(traits:: RFS)) { this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); } @@ -3489,6 +3608,7 @@ private: pc=pc+ 2; gen_set_pc(tu, pc, traits::NEXT_PC); tu.open_scope(); + this->gen_set_tval(tu, instr); this->gen_raise_trap(tu, 0, static_cast(traits:: RV_CAUSE_ILLEGAL_INSTRUCTION)); auto returnValue = std::make_tuple(CONT); @@ -3625,10 +3745,17 @@ template void vm_impl::gen_leave_trap(tu_builder& tu, unsi template void vm_impl::gen_wait(tu_builder& tu, unsigned type) { } +template void vm_impl::gen_set_tval(tu_builder& tu, uint64_t new_tval) { + tu(fmt::format("tval = {};", new_tval)); +} +template void vm_impl::gen_set_tval(tu_builder& tu, value new_tval) { + tu(fmt::format("tval = {};", new_tval.str)); +} + template void vm_impl::gen_trap_behavior(tu_builder& tu) { tu("trap_entry:"); this->gen_sync(tu, POST_SYNC, -1); - tu("enter_trap(core_ptr, *trap_state, *pc, 0);"); + tu("enter_trap(core_ptr, *trap_state, *pc, tval);"); tu.store(traits::LAST_BRANCH, tu.constant(std::numeric_limits::max(),32)); tu("return *next_pc;"); }