adapt to latest changes in SCC

This commit is contained in:
Eyck Jentzsch 2022-12-05 09:15:48 +01:00
parent f585489ff5
commit 8c701d55c1
2 changed files with 467 additions and 246 deletions

View File

@ -8,6 +8,7 @@ include(GNUInstallDirs)
find_package(elfio QUIET)
find_package(Boost COMPONENTS coroutine)
find_package(jsoncpp)
if(WITH_LLVM)
if(DEFINED ENV{LLVM_HOME})

View File

@ -358,8 +358,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (int32_t)imm;
if(rd >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = (int32_t)imm;
}
}
}
TRAP_LUI:break;
@ -379,8 +384,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *PC + (int32_t)imm;
if(rd >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *PC + (int32_t)imm;
}
}
}
TRAP_AUIPC:break;
@ -400,17 +410,22 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *PC + 4;
}
*NEXT_PC = *PC + (int32_t)sext<21>(imm);
super::ex_info.branch_taken=true;
}
}
if(rd >= traits::RFS) {
raise(0, 2);
}
else {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
if(rd != 0) {
*(X+rd) = *PC + 4;
}
*NEXT_PC = *PC + (int32_t)sext<21>(imm);
super::ex_info.branch_taken=true;
}
}
}
TRAP_JAL:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::JALR: {
@ -429,18 +444,23 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t new_pc = (*(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm)) & ~ 0x1;
if(new_pc % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *PC + 4;
}
*NEXT_PC = new_pc & ~ 0x1;
super::ex_info.branch_taken=true;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t new_pc = (*(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm)) & ~ 0x1;
if(new_pc % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
if(rd != 0) {
*(X+rd) = *PC + 4;
}
*NEXT_PC = new_pc & ~ 0x1;
super::ex_info.branch_taken=true;
}
}
}
TRAP_JALR:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::BEQ: {
@ -459,16 +479,21 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if(*(X+rs1 % traits::RFS) == *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(*(X+rs1 % traits::RFS) == *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
}
TRAP_BEQ:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::BNE: {
@ -487,16 +512,21 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if(*(X+rs1 % traits::RFS) != *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(*(X+rs1 % traits::RFS) != *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
}
TRAP_BNE:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::BLT: {
@ -515,16 +545,21 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((int32_t)*(X+rs1 % traits::RFS) < (int32_t)*(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if((int32_t)*(X+rs1 % traits::RFS) < (int32_t)*(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
}
TRAP_BLT:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::BGE: {
@ -543,16 +578,21 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((int32_t)*(X+rs1 % traits::RFS) >= (int32_t)*(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if((int32_t)*(X+rs1 % traits::RFS) >= (int32_t)*(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
}
TRAP_BGE:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::BLTU: {
@ -571,16 +611,21 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if(*(X+rs1 % traits::RFS) < *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(*(X+rs1 % traits::RFS) < *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
}
TRAP_BLTU:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::BGEU: {
@ -599,16 +644,21 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if(*(X+rs1 % traits::RFS) >= *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(*(X+rs1 % traits::RFS) >= *(X+rs2 % traits::RFS)) {
if(imm % traits::INSTR_ALIGNMENT) {
raise(0, 0);
}
else {
*NEXT_PC = *PC + (int16_t)sext<13>(imm);
super::ex_info.branch_taken=true;
}
}
}
}
TRAP_BGEU:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::LB: {
@ -627,14 +677,19 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
int8_t read_res = super::template read_mem<int8_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LB;
int8_t res = (int8_t)read_res;
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (int32_t)res;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
int8_t read_res = super::template read_mem<int8_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LB;
int8_t res = (int8_t)read_res;
if(rd != 0) {
*(X+rd) = (int32_t)res;
}
}
}
TRAP_LB:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::LH: {
@ -653,14 +708,19 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
int16_t read_res = super::template read_mem<int16_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LH;
int16_t res = (int16_t)read_res;
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (int32_t)res;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
int16_t read_res = super::template read_mem<int16_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LH;
int16_t res = (int16_t)read_res;
if(rd != 0) {
*(X+rd) = (int32_t)res;
}
}
}
TRAP_LH:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::LW: {
@ -679,14 +739,19 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
int32_t read_res = super::template read_mem<int32_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LW;
int32_t res = (int32_t)read_res;
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (int32_t)res;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
int32_t read_res = super::template read_mem<int32_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LW;
int32_t res = (int32_t)read_res;
if(rd != 0) {
*(X+rd) = (int32_t)res;
}
}
}
TRAP_LW:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::LBU: {
@ -705,14 +770,19 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
uint8_t read_res = super::template read_mem<uint8_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LBU;
uint8_t res = (uint8_t)read_res;
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (uint32_t)res;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
uint8_t read_res = super::template read_mem<uint8_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LBU;
uint8_t res = (uint8_t)read_res;
if(rd != 0) {
*(X+rd) = (uint32_t)res;
}
}
}
TRAP_LBU:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::LHU: {
@ -731,14 +801,19 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
uint16_t read_res = super::template read_mem<uint16_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LHU;
uint16_t res = (uint16_t)read_res;
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (uint32_t)res;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t load_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
uint16_t read_res = super::template read_mem<uint16_t>(traits::MEM, load_address);
if(this->core.trap_state>=0x80000000UL) goto TRAP_LHU;
uint16_t res = (uint16_t)read_res;
if(rd != 0) {
*(X+rd) = (uint32_t)res;
}
}
}
TRAP_LHU:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::SB: {
@ -757,10 +832,15 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t store_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
super::template write_mem<uint8_t>(traits::MEM, store_address, (int8_t)*(X+rs2 % traits::RFS));
if(this->core.trap_state>=0x80000000UL) goto TRAP_SB;
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t store_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
super::template write_mem<uint8_t>(traits::MEM, store_address, (int8_t)*(X+rs2 % traits::RFS));
if(this->core.trap_state>=0x80000000UL) goto TRAP_SB;
}
}
TRAP_SB:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::SH: {
@ -779,10 +859,15 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t store_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
super::template write_mem<uint16_t>(traits::MEM, store_address, (int16_t)*(X+rs2 % traits::RFS));
if(this->core.trap_state>=0x80000000UL) goto TRAP_SH;
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t store_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
super::template write_mem<uint16_t>(traits::MEM, store_address, (int16_t)*(X+rs2 % traits::RFS));
if(this->core.trap_state>=0x80000000UL) goto TRAP_SH;
}
}
TRAP_SH:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::SW: {
@ -801,10 +886,15 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t store_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
super::template write_mem<uint32_t>(traits::MEM, store_address, (int32_t)*(X+rs2 % traits::RFS));
if(this->core.trap_state>=0x80000000UL) goto TRAP_SW;
}
if(rs2 >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t store_address = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
super::template write_mem<uint32_t>(traits::MEM, store_address, (int32_t)*(X+rs2 % traits::RFS));
if(this->core.trap_state>=0x80000000UL) goto TRAP_SW;
}
}
TRAP_SW:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::ADDI: {
@ -823,8 +913,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) + (int16_t)sext<12>(imm);
}
}
}
TRAP_ADDI:break;
@ -845,8 +940,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = ((int32_t)*(X+rs1 % traits::RFS) < (int16_t)sext<12>(imm))? 1 : 0;
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = ((int32_t)*(X+rs1 % traits::RFS) < (int16_t)sext<12>(imm))? 1 : 0;
}
}
}
TRAP_SLTI:break;
@ -867,8 +967,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (*(X+rs1 % traits::RFS) < (uint32_t)((int16_t)sext<12>(imm)))? 1 : 0;
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = (*(X+rs1 % traits::RFS) < (uint32_t)((int16_t)sext<12>(imm)))? 1 : 0;
}
}
}
TRAP_SLTIU:break;
@ -889,8 +994,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) ^ (int16_t)sext<12>(imm);
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) ^ (int16_t)sext<12>(imm);
}
}
}
TRAP_XORI:break;
@ -911,8 +1021,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) | (int16_t)sext<12>(imm);
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) | (int16_t)sext<12>(imm);
}
}
}
TRAP_ORI:break;
@ -933,8 +1048,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) & (int16_t)sext<12>(imm);
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) & (int16_t)sext<12>(imm);
}
}
}
TRAP_ANDI:break;
@ -955,8 +1075,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) << shamt;
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) << shamt;
}
}
}
TRAP_SLLI:break;
@ -977,8 +1102,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) >> shamt;
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) >> shamt;
}
}
}
TRAP_SRLI:break;
@ -999,8 +1129,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (int32_t)*(X+rs1 % traits::RFS) >> shamt;
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = (int32_t)*(X+rs1 % traits::RFS) >> shamt;
}
}
}
TRAP_SRAI:break;
@ -1021,8 +1156,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) + *(X+rs2 % traits::RFS);
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) + *(X+rs2 % traits::RFS);
}
}
}
TRAP_ADD:break;
@ -1043,8 +1183,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) - *(X+rs2 % traits::RFS);
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) - *(X+rs2 % traits::RFS);
}
}
}
TRAP_SUB:break;
@ -1065,8 +1210,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) << (*(X+rs2 % traits::RFS) & (traits::XLEN - 1));
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) << (*(X+rs2 % traits::RFS) & (traits::XLEN - 1));
}
}
}
TRAP_SLL:break;
@ -1087,8 +1237,18 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (int32_t)*(X+rs1 % traits::RFS) < (int32_t)*(X+rs2 % traits::RFS)? 1 : 0;
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = (int32_t)*(X+rs1 % traits::RFS) < (int32_t)*(X+rs2 % traits::RFS)? 1 : 0;
}
}
}
}
TRAP_SLT:break;
@ -1109,8 +1269,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (uint32_t)*(X+rs1 % traits::RFS) < (uint32_t)*(X+rs2 % traits::RFS)? 1 : 0;
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = (uint32_t)*(X+rs1 % traits::RFS) < (uint32_t)*(X+rs2 % traits::RFS)? 1 : 0;
}
}
}
TRAP_SLTU:break;
@ -1131,8 +1296,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) ^ *(X+rs2 % traits::RFS);
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) ^ *(X+rs2 % traits::RFS);
}
}
}
TRAP_XOR:break;
@ -1153,8 +1323,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) >> (*(X+rs2 % traits::RFS) & (traits::XLEN - 1));
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) >> (*(X+rs2 % traits::RFS) & (traits::XLEN - 1));
}
}
}
TRAP_SRL:break;
@ -1175,8 +1350,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = (int32_t)*(X+rs1 % traits::RFS) >> (*(X+rs2 % traits::RFS) & (traits::XLEN - 1));
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = (int32_t)*(X+rs1 % traits::RFS) >> (*(X+rs2 % traits::RFS) & (traits::XLEN - 1));
}
}
}
TRAP_SRA:break;
@ -1197,8 +1377,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) | *(X+rs2 % traits::RFS);
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) | *(X+rs2 % traits::RFS);
}
}
}
TRAP_OR:break;
@ -1219,8 +1404,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) & *(X+rs2 % traits::RFS);
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
raise(0, 2);
}
else {
if(rd != 0) {
*(X+rd) = *(X+rs1 % traits::RFS) & *(X+rs2 % traits::RFS);
}
}
}
TRAP_AND:break;
@ -1315,20 +1505,25 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t xrs1 = *(X+rs1 % traits::RFS);
if((rd % traits::RFS) != 0) {
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRW;
uint32_t xrd = read_res;
super::template write_mem<uint32_t>(traits::CSR, csr, xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRW;
*(X+rd % traits::RFS) = xrd;
}
else {
super::template write_mem<uint32_t>(traits::CSR, csr, xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRW;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t xrs1 = *(X+rs1 % traits::RFS);
if(rd != 0) {
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRW;
uint32_t xrd = read_res;
super::template write_mem<uint32_t>(traits::CSR, csr, xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRW;
*(X+rd) = xrd;
}
else {
super::template write_mem<uint32_t>(traits::CSR, csr, xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRW;
}
}
}
TRAP_CSRRW:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::CSRRS: {
@ -1347,18 +1542,23 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRS;
uint32_t xrd = read_res;
uint32_t xrs1 = *(X+rs1 % traits::RFS);
if(rs1 != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd | xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRS;
}
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = xrd;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRS;
uint32_t xrd = read_res;
uint32_t xrs1 = *(X+rs1 % traits::RFS);
if(rs1 != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd | xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRS;
}
if(rd != 0) {
*(X+rd) = xrd;
}
}
}
TRAP_CSRRS:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::CSRRC: {
@ -1377,18 +1577,23 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRC;
uint32_t xrd = read_res;
uint32_t xrs1 = *(X+rs1 % traits::RFS);
if(rs1 != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd & ~ xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRC;
}
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = xrd;
}
}
if(rd >= traits::RFS || rs1 >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRC;
uint32_t xrd = read_res;
uint32_t xrs1 = *(X+rs1 % traits::RFS);
if(rs1 != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd & ~ xrs1);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRC;
}
if(rd != 0) {
*(X+rd) = xrd;
}
}
}
TRAP_CSRRC:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::CSRRWI: {
@ -1407,15 +1612,20 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRWI;
uint32_t xrd = read_res;
super::template write_mem<uint32_t>(traits::CSR, csr, (uint32_t)zimm);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRWI;
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = xrd;
}
}
if(rd >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRWI;
uint32_t xrd = read_res;
super::template write_mem<uint32_t>(traits::CSR, csr, (uint32_t)zimm);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRWI;
if(rd != 0) {
*(X+rd) = xrd;
}
}
}
TRAP_CSRRWI:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::CSRRSI: {
@ -1434,17 +1644,22 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRSI;
uint32_t xrd = read_res;
if(zimm != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd | (uint32_t)zimm);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRSI;
}
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = xrd;
}
}
if(rd >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRSI;
uint32_t xrd = read_res;
if(zimm != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd | (uint32_t)zimm);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRSI;
}
if(rd != 0) {
*(X+rd) = xrd;
}
}
}
TRAP_CSRRSI:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::CSRRCI: {
@ -1463,17 +1678,22 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
*NEXT_PC = *PC + 4;
// execute instruction
{
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRCI;
uint32_t xrd = read_res;
if(zimm != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd & ~ ((uint32_t)zimm));
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRCI;
}
if((rd % traits::RFS) != 0) {
*(X+rd % traits::RFS) = xrd;
}
}
if(rd >= traits::RFS) {
raise(0, 2);
}
else {
uint32_t read_res = super::template read_mem<uint32_t>(traits::CSR, csr);
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRCI;
uint32_t xrd = read_res;
if(zimm != 0) {
super::template write_mem<uint32_t>(traits::CSR, csr, xrd & ~ ((uint32_t)zimm));
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSRRCI;
}
if(rd != 0) {
*(X+rd) = xrd;
}
}
}
TRAP_CSRRCI:break;
}// @suppress("No break at end of case")
case arch::traits<ARCH>::opcode_e::FENCE_I: {