adds changes from latest CoreDSL description
This commit is contained in:
parent
98dd329833
commit
a8a2782329
|
@ -1727,9 +1727,14 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
int64_t res = (int64_t)(int32_t)*(X+rs1 % traits::RFS) * (int64_t)(int32_t)*(X+rs2 % traits::RFS);
|
raise(0, 2);
|
||||||
*(X+rd % traits::RFS) = (uint32_t)res;
|
}
|
||||||
|
else {
|
||||||
|
int64_t res = (int64_t)(int32_t)*(X+rs1) * (int64_t)(int32_t)*(X+rs2);
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = (uint32_t)res;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_MUL:break;
|
TRAP_MUL:break;
|
||||||
|
@ -1750,9 +1755,14 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
int64_t res = (int64_t)(int32_t)*(X+rs1 % traits::RFS) * (int64_t)(int32_t)*(X+rs2 % traits::RFS);
|
raise(0, 2);
|
||||||
*(X+rd % traits::RFS) = (uint32_t)(res >> traits::XLEN);
|
}
|
||||||
|
else {
|
||||||
|
int64_t res = (int64_t)(int32_t)*(X+rs1) * (int64_t)(int32_t)*(X+rs2);
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = (uint32_t)(res >> traits::XLEN);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_MULH:break;
|
TRAP_MULH:break;
|
||||||
|
@ -1773,9 +1783,14 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
int64_t res = (int64_t)(int32_t)*(X+rs1 % traits::RFS) * (uint64_t)*(X+rs2 % traits::RFS);
|
raise(0, 2);
|
||||||
*(X+rd % traits::RFS) = (uint32_t)(res >> traits::XLEN);
|
}
|
||||||
|
else {
|
||||||
|
int64_t res = (int64_t)(int32_t)*(X+rs1) * (uint64_t)*(X+rs2);
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = (uint32_t)(res >> traits::XLEN);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_MULHSU:break;
|
TRAP_MULHSU:break;
|
||||||
|
@ -1796,9 +1811,14 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
uint64_t res = (uint64_t)*(X+rs1 % traits::RFS) * (uint64_t)*(X+rs2 % traits::RFS);
|
raise(0, 2);
|
||||||
*(X+rd % traits::RFS) = (uint32_t)(res >> traits::XLEN);
|
}
|
||||||
|
else {
|
||||||
|
uint64_t res = (uint64_t)*(X+rs1) * (uint64_t)*(X+rs2);
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = (uint32_t)(res >> traits::XLEN);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_MULHU:break;
|
TRAP_MULHU:break;
|
||||||
|
@ -1819,18 +1839,25 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
if(*(X+rs2 % traits::RFS) != 0) {
|
raise(0, 2);
|
||||||
uint32_t MMIN = 1 << (traits::XLEN - 1);
|
|
||||||
if(*(X+rs1 % traits::RFS) == MMIN && (int32_t)*(X+rs2 % traits::RFS) == - 1) {
|
|
||||||
*(X+rd % traits::RFS) = MMIN;
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
*(X+rd % traits::RFS) = (int32_t)*(X+rs1 % traits::RFS) / (int32_t)*(X+rs2 % traits::RFS);
|
int32_t dividend = (int32_t)*(X+rs1);
|
||||||
|
int32_t divisor = (int32_t)*(X+rs2);
|
||||||
|
if(rd != 0) {
|
||||||
|
if(divisor != 0) {
|
||||||
|
uint32_t MMIN = ((uint32_t)1) << (traits::XLEN - 1);
|
||||||
|
if(*(X+rs1) == MMIN && divisor == - 1) {
|
||||||
|
*(X+rd) = MMIN;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
*(X+rd) = dividend / divisor;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
*(X+rd % traits::RFS) = - 1;
|
*(X+rd) = (int32_t)- 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1852,12 +1879,19 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
if(*(X+rs2 % traits::RFS) != 0) {
|
raise(0, 2);
|
||||||
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) / *(X+rs2 % traits::RFS);
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
*(X+rd % traits::RFS) = - 1;
|
if(*(X+rs2) != 0) {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = *(X+rs1) / *(X+rs2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = (int32_t)- 1;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1879,18 +1913,27 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
if(*(X+rs2 % traits::RFS) != 0) {
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(*(X+rs2) != 0) {
|
||||||
uint32_t MMIN = 1 << (traits::XLEN - 1);
|
uint32_t MMIN = 1 << (traits::XLEN - 1);
|
||||||
if(*(X+rs1 % traits::RFS) == MMIN && (int32_t)*(X+rs2 % traits::RFS) == - 1) {
|
if(*(X+rs1) == MMIN && (int32_t)*(X+rs2) == - 1) {
|
||||||
*(X+rd % traits::RFS) = 0;
|
if(rd != 0) {
|
||||||
}
|
*(X+rd) = 0;
|
||||||
else {
|
|
||||||
*(X+rd % traits::RFS) = (int32_t)*(X+rs1 % traits::RFS) % (int32_t)*(X+rs2 % traits::RFS);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS);
|
if(rd != 0) {
|
||||||
|
*(X+rd) = (int32_t)*(X+rs1) % (int32_t)*(X+rs2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = *(X+rs1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1912,12 +1955,19 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 4;
|
*NEXT_PC = *PC + 4;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS || rs1 >= traits::RFS || rs2 >= traits::RFS) {
|
||||||
if(*(X+rs2 % traits::RFS) != 0) {
|
raise(0, 2);
|
||||||
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS) % *(X+rs2 % traits::RFS);
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
*(X+rd % traits::RFS) = *(X+rs1 % traits::RFS);
|
if(*(X+rs2) != 0) {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = *(X+rs1) % *(X+rs2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = *(X+rs1);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -2007,8 +2057,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rs1 % traits::RFS) != 0) {
|
if(rs1 >= traits::RFS) {
|
||||||
*(X+rs1 % traits::RFS) = *(X+rs1 % traits::RFS) + (int8_t)sext<6>(imm);
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rs1 != 0) {
|
||||||
|
*(X+rs1) = *(X+rs1) + (int8_t)sext<6>(imm);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_CADDI:break;
|
TRAP_CADDI:break;
|
||||||
|
@ -2061,8 +2116,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS) {
|
||||||
*(X+rd % traits::RFS) = (int8_t)sext<6>(imm);
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = (int8_t)sext<6>(imm);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_CLI:break;
|
TRAP_CLI:break;
|
||||||
|
@ -2082,11 +2142,11 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if(imm == 0) {
|
if(imm == 0 || rd >= traits::RFS) {
|
||||||
raise(0, 2);
|
raise(0, 2);
|
||||||
}
|
}
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd != 0) {
|
||||||
*(X+rd % traits::RFS) = (int32_t)sext<18>(imm);
|
*(X+rd) = (int32_t)sext<18>(imm);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_CLUI:break;
|
TRAP_CLUI:break;
|
||||||
|
@ -2345,8 +2405,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if(nzuimm) {
|
if(rs1 >= traits::RFS) {
|
||||||
*(X+rs1 % traits::RFS) = *(X+rs1 % traits::RFS) << nzuimm;
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rs1 != 0) {
|
||||||
|
*(X+rs1) = *(X+rs1) << nzuimm;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_CSLLI:break;
|
TRAP_CSLLI:break;
|
||||||
|
@ -2366,14 +2431,14 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if(rd % traits::RFS) {
|
if(rd >= traits::RFS || rd == 0) {
|
||||||
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
int32_t read_res = super::template read_mem<int32_t>(traits::MEM, *(X+2) + uimm);
|
int32_t read_res = super::template read_mem<int32_t>(traits::MEM, *(X+2) + uimm);
|
||||||
if(this->core.trap_state>=0x80000000UL) goto TRAP_CLWSP;
|
if(this->core.trap_state>=0x80000000UL) goto TRAP_CLWSP;
|
||||||
int32_t res = read_res;
|
int32_t res = read_res;
|
||||||
*(X+rd % traits::RFS) = (int32_t)res;
|
*(X+rd) = (int32_t)res;
|
||||||
}
|
|
||||||
else {
|
|
||||||
raise(0, 2);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_CLWSP:break;
|
TRAP_CLWSP:break;
|
||||||
|
@ -2393,8 +2458,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS) {
|
||||||
*(X+rd % traits::RFS) = *(X+rs2 % traits::RFS);
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = *(X+rs2);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_CMV:break;
|
TRAP_CMV:break;
|
||||||
|
@ -2413,7 +2483,7 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if(rs1) {
|
if(rs1 && rs1 < traits::RFS) {
|
||||||
*NEXT_PC = *(X+rs1 % traits::RFS) & ~ 0x1;
|
*NEXT_PC = *(X+rs1 % traits::RFS) & ~ 0x1;
|
||||||
super::ex_info.branch_taken=true;
|
super::ex_info.branch_taken=true;
|
||||||
}
|
}
|
||||||
|
@ -2451,8 +2521,13 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
if((rd % traits::RFS) != 0) {
|
if(rd >= traits::RFS) {
|
||||||
*(X+rd % traits::RFS) = *(X+rd % traits::RFS) + *(X+rs2 % traits::RFS);
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if(rd != 0) {
|
||||||
|
*(X+rd) = *(X+rd) + *(X+rs2);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
TRAP_CADD:break;
|
TRAP_CADD:break;
|
||||||
|
@ -2471,11 +2546,16 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
uint32_t new_pc = *(X+rs1 % traits::RFS);
|
if(rs1 >= traits::RFS) {
|
||||||
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
uint32_t new_pc = *(X+rs1);
|
||||||
*(X+1) = *PC + 2;
|
*(X+1) = *PC + 2;
|
||||||
*NEXT_PC = new_pc & ~ 0x1;
|
*NEXT_PC = new_pc & ~ 0x1;
|
||||||
super::ex_info.branch_taken=true;
|
super::ex_info.branch_taken=true;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
TRAP_CJALR:break;
|
TRAP_CJALR:break;
|
||||||
}// @suppress("No break at end of case")
|
}// @suppress("No break at end of case")
|
||||||
case arch::traits<ARCH>::opcode_e::CEBREAK: {
|
case arch::traits<ARCH>::opcode_e::CEBREAK: {
|
||||||
|
@ -2506,10 +2586,15 @@ typename vm_base<ARCH>::virt_addr_t vm_impl<ARCH>::execute_inst(finish_cond_e co
|
||||||
*NEXT_PC = *PC + 2;
|
*NEXT_PC = *PC + 2;
|
||||||
// execute instruction
|
// execute instruction
|
||||||
{
|
{
|
||||||
|
if(rs2 >= traits::RFS) {
|
||||||
|
raise(0, 2);
|
||||||
|
}
|
||||||
|
else {
|
||||||
uint32_t offs = *(X+2) + uimm;
|
uint32_t offs = *(X+2) + uimm;
|
||||||
super::template write_mem<uint32_t>(traits::MEM, offs, (uint32_t)*(X+rs2 % traits::RFS));
|
super::template write_mem<uint32_t>(traits::MEM, offs, (uint32_t)*(X+rs2));
|
||||||
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSWSP;
|
if(this->core.trap_state>=0x80000000UL) goto TRAP_CSWSP;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
TRAP_CSWSP:break;
|
TRAP_CSWSP:break;
|
||||||
}// @suppress("No break at end of case")
|
}// @suppress("No break at end of case")
|
||||||
case arch::traits<ARCH>::opcode_e::DII: {
|
case arch::traits<ARCH>::opcode_e::DII: {
|
||||||
|
|
Loading…
Reference in New Issue