📄 arm.isa
字号:
ASGN_C ((val32 & (1<<29)) != 0); ASGN_V ((val32 & (1<<28)) != 0); } else{ WRITE_REG($rd$,val32); }"}op ldc1(----110:ldc_mode1:----:cp_num:imm8){execute=" offset = $imm8$; $ldc_mode1$; if (emu->copro[$cp_num$] == NULL){ ABORT2(UndefinedInstrV); } if (!CP_ACCESS_ALLOWED ($cp_num$)) { ABORT2(UndefinedInstrV); } cpab = emu->copro[$cp_num$]->LDC(ARMul_FIRST, $inst$, 0); while (cpab == ARMul_BUSY) { if (emu->int_pending ()) { cpab = emu->copro[$cp_num$]->LDC(ARMul_INTERRUPT, $inst$, 0); } else cpab = emu->copro[$cp_num$]->LDC(ARMul_BUSY, $inst$, 0); } if (cpab == ARMul_CANT){ ABORT2(UndefinedInstrV); } cpab = emu->copro[$cp_num$]->LDC(ARMul_TRANSFER, $inst$, 0); MMU_READ_WORD(address,&rslt32); if(fault){ ABORT( DataAbortV ); } cpab = emu->copro[$cp_num$]->LDC(ARMul_DATA, $inst$, rslt32); while (cpab == ARMul_INC) { address += 4; MMU_READ_WORD(address,&rslt32); if(fault){ ABORT( DataAbortV ); } cpab = emu->copro[$cp_num$]->LDC(ARMul_DATA, $inst$, rslt32); }" }op ldc2(----110:ldc_mode2:rn:----:cp_num:imm8){execute=" offset = $imm8$; base_addr = READ_REG($rn$); $ldc_mode2$; if (emu->copro[$cp_num$] == NULL){ ABORT2(UndefinedInstrV); } if (!CP_ACCESS_ALLOWED ($cp_num$)) { ABORT2(UndefinedInstrV); } cpab = emu->copro[$cp_num$]->LDC(ARMul_FIRST, $inst$, 0); while (cpab == ARMul_BUSY) { if (emu->int_pending ()) { cpab = emu->copro[$cp_num$]->LDC(ARMul_INTERRUPT, $inst$, 0); } else cpab = emu->copro[$cp_num$]->LDC(ARMul_BUSY, $inst$, 0); } if (cpab == ARMul_CANT){ ABORT2(UndefinedInstrV); } WRITE_REG($rn$, address); cpab = emu->copro[$cp_num$]->LDC(ARMul_TRANSFER, $inst$, 0); MMU_READ_WORD(address,&rslt32); if(fault){ WRITE_REG($rn$, base_addr); ABORT( DataAbortV ); } address = start_addr; cpab = emu->copro[$cp_num$]->LDC(ARMul_DATA, $inst$, rslt32); while (cpab == ARMul_INC) { address += 4; MMU_READ_WORD(address,&rslt32); if(fault){ WRITE_REG($rn$, base_addr); ABORT( DataAbortV ); } cpab = emu->copro[$cp_num$]->LDC(ARMul_DATA, $inst$, rslt32); }" }op stc1(----110:stc_mode1:----:cp_num:imm8){execute=" offset = $imm8$; $stc_mode1$; if (emu->copro[$cp_num$] == NULL){ ABORT2(UndefinedInstrV); } if (!CP_ACCESS_ALLOWED ($cp_num$)) { ABORT2(UndefinedInstrV); } cpab = emu->copro[$cp_num$]->STC(ARMul_FIRST, $inst$, &rslt32); while (cpab == ARMul_BUSY) { if (emu->int_pending ()) { cpab = emu->copro[$cp_num$]->STC(ARMul_INTERRUPT, $inst$, 0); } else cpab = emu->copro[$cp_num$]->STC(ARMul_BUSY, $inst$, &rslt32); } if (cpab == ARMul_CANT){ ABORT2(UndefinedInstrV); } cpab = emu->copro[$cp_num$]->STC(ARMul_DATA, $inst$, &rslt32); MMU_WRITE_WORD(address,rslt32); if(fault){ ABORT( DataAbortV ); } while (cpab == ARMul_INC) { address += 4; cpab = emu->copro[$cp_num$]->STC(ARMul_DATA, $inst$, &rslt32); MMU_WRITE_WORD(address,rslt32); if(fault){ ABORT( DataAbortV ); } }" }op stc2(----110:stc_mode2:rn:----:cp_num:imm8){execute=" offset = $imm8$; base_addr = READ_REG($rn$); $stc_mode2$; if (emu->copro[$cp_num$] == NULL){ ABORT2(UndefinedInstrV); } if (!CP_ACCESS_ALLOWED ($cp_num$)) { ABORT2(UndefinedInstrV); } cpab = emu->copro[$cp_num$]->STC(ARMul_FIRST, $inst$, &rslt32); while (cpab == ARMul_BUSY) { if (emu->int_pending ()) { cpab = emu->copro[$cp_num$]->STC(ARMul_INTERRUPT, $inst$, 0); } else cpab = emu->copro[$cp_num$]->STC(ARMul_BUSY, $inst$, &rslt32); } if (cpab == ARMul_CANT){ ABORT2(UndefinedInstrV); } WRITE_REG($rn$, address); address = start_addr; cpab = emu->copro[$cp_num$]->STC(ARMul_DATA, $inst$, &rslt32); MMU_WRITE_WORD(address,rslt32); if(fault){ WRITE_REG($rn$, base_addr); ABORT( DataAbortV ); } while (cpab == ARMul_INC) { address += 4; cpab = emu->copro[$cp_num$]->STC(ARMul_DATA, $inst$, &rslt32); MMU_WRITE_WORD(address,rslt32); if(fault){ WRITE_REG($rn$, base_addr); ABORT( DataAbortV ); } }" }op mra(----1100:0101:rn:rd:0000:0000:0000){execute=" if (emu->is_xscale()) { /* XScale MRA insn. Move accumulator into two registers. */ val32 = (emu->accumulator >> 32) & 255; if (val32 & 128) val32 -= 256; WRITE_REG($rd$,emu->accumulator); WRITE_REG($rn$,val32); } else ABORT2(UndefinedInstrV);"}op mar(----1100:0100:rn:rd:0000:0000:0000){execute=" if (emu->is_xscale()) { /* XScale MAR insn. Move two registers into accumulator. */ emu->accumulator = READ_REG($rd$); emu->accumulator += (uint64_t)READ_REG($rn$)<<32; } else ABORT2(UndefinedInstrV);"}op clz(----00010110:1111:rd:1111:0001:rm){execute=" if (emu->is_xscale()) { val32=READ_REG($rm$); if(val32==0){ WRITE_REG($rd$,32); } else{ for(rslt32=0;(val32 & 0x80000000) == 0; val32 <<=1) rslt32++; WRITE_REG($rd$,rslt32); } } else ABORT2(UndefinedInstrV);" }op ldd_imm(----0000:ufld:1:-:0:rn:rd:imm4_1:1101:imm4_2){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = ($imm4_1$ << 4) | $imm4_2$; address = READ_REG($rn$); fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_READ_WORD(address,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$, rslt32); MMU_READ_WORD(address+4,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$+1, rslt32); WRITE_REG($rn$, $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset); } else ABORT2(UndefinedInstrV);"}op ldd_imm_p(----0001:ufld:1:wfld:0:rn:rd:imm4_1:1101:imm4_2){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = ($imm4_1$ << 4) | $imm4_2$; address = $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset; fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_READ_WORD(address,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$, rslt32); MMU_READ_WORD(address+4,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$+1, rslt32); if ($wfld$) WRITE_REG($rn$, address); } else ABORT2(UndefinedInstrV);"}op ldd_reg(----0000:ufld:0:-:0:rn:rd:0000:1101:rm){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = READ_REG($rm$); address = READ_REG($rn$); fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_READ_WORD(address,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$, rslt32); MMU_READ_WORD(address+4,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$+1, rslt32); WRITE_REG($rn$, $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset); } else ABORT2(UndefinedInstrV);"}op ldd_reg_p(----0001:ufld:0:wfld:0:rn:rd:0000:1101:rm){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = READ_REG($rm$); address = $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset; fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_READ_WORD(address,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$, rslt32); MMU_READ_WORD(address+4,&rslt32); if(fault){ ABORT( DataAbortV ); } WRITE_REG($rd$+1, rslt32); if ($wfld$) WRITE_REG($rn$, address); } else ABORT2(UndefinedInstrV);"}op std_imm(----0000:ufld:1-0:rn:rd:imm4_1:1111:imm4_2){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = ($imm4_1$ << 4) | $imm4_2$; address = READ_REG($rn$); fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_WRITE_WORD(address, READ_REG($rd$)); if (fault){ ABORT( DataAbortV ); } MMU_WRITE_WORD(address+4, READ_REG($rd$+1)); if (fault){ ABORT( DataAbortV ); } WRITE_REG($rn$, $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset); } else ABORT2(UndefinedInstrV);"}op std_imm_p(----0001:ufld:1:wfld:0:rn:rd:imm4_1:1111:imm4_2){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = ($imm4_1$ << 4) | $imm4_2$; address = $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset; fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_WRITE_WORD(address, READ_REG($rd$)); if (fault){ ABORT( DataAbortV ); } MMU_WRITE_WORD(address+4, READ_REG($rd$+1)); if (fault){ ABORT( DataAbortV ); } if ($wfld$) WRITE_REG($rn$, address); } else ABORT2(UndefinedInstrV);"}op std_reg(----0000:ufld:0-0:rn:rd:00001111:rm){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = READ_REG($rm$); address = READ_REG($rn$); fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_WRITE_WORD(address, READ_REG($rd$)); if (fault){ ABORT( DataAbortV ); } MMU_WRITE_WORD(address+4, READ_REG($rd$+1)); if (fault){ ABORT( DataAbortV ); } WRITE_REG($rn$, $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset); } else ABORT2(UndefinedInstrV);"}op std_reg_p(----0001:ufld:0:wfld:0:rn:rd:00001111:rm){execute=" if (emu->is_xscale() ) { if($rd$ & 1) ABORT2(UndefinedInstrV); offset = READ_REG($rm$); address = $ufld$?READ_REG($rn$)+offset:READ_REG($rn$)-offset; fault = NO_FAULT; if(address & 7)/* Alignment violation. */ ABORT( DataAbortV ); MMU_WRITE_WORD(address, READ_REG($rd$)); if (fault){ ABORT( DataAbortV ); } MMU_WRITE_WORD(address+4, READ_REG($rd$+1)); if (fault){ ABORT( DataAbortV ); } if ($wfld$) WRITE_REG($rn$, address); } else ABORT2(UndefinedInstrV);"}op smla_xy(----00010000:rd:rn:rs:1:y_bit:x_bit:0:rm){execute=" if (emu->is_xscale() ) { /* SMLAxy insn. */ val32 = READ_REG($rn$); op1 = READ_REG($rm$); op2 = READ_REG($rs$); op1 = $x_bit$ ? op1>>16 : op1&0xFFFF; op2 = $y_bit$ ? op2>>16 : op2&0xFFFF; if (op1 & 0x8000) op1 -= 65536; if (op2 & 0x8000) op2 -= 65536; tmp32 = op1 * op2; rslt32 = val32 + tmp32; WRITE_REG($rd$, rslt32); ASGN_Q((val32^tmp32^-1) & (val32^rslt32)); } else ABORT2(UndefinedInstrV);"}op smlal_xy(----00010100:rn:rd:rs:1:y_bit:x_bit:0:rm){execute=" if (emu->is_xscale() ) { /* SMLALxy insn. */ op1 = READ_REG($rm$); op2 = READ_REG($rs$); op1 = $x_bit$ ? op1>>16 : op1&0xFFFF; op2 = $y_bit$ ? op2>>16 : op2&0xFFFF; if (op1 & 0x8000) op1 -= 65536; if (op2 & 0x8000) op2 -= 65536; rslt64 = ((uint64_t)READ_REG($rn$)<<32) + (uint64_t)READ_REG($rd$); rslt64 = (int64_t)op1 * (int64_t)op2 +rslt64; WRITE_REG($rn$, (uint32_t)(rslt64>>32)); WRITE_REG($rd$, (uint32_t)rslt64); } else ABORT2(UndefinedInstrV);"}op smlaw_y(----00010010:rd:rn:rs:1:y_bit:0:0:rm){execute=" if (emu->is_xscale() ) { /* SMLAWy insn. */ val32 = READ_REG($rn$); op2 = READ_REG($rs$); op2 = $y_bit$ ? op2>>16 : op2&0xFFFF; if (op2 & 0x8000) op2 -= 65536; tmp32 = (uint32_t)( (int64_t)READ_REG($rm$)*op2 >> 16); rslt32 = val32 + tmp32; WRITE_REG($rd$,rslt32); ASGN_Q((val32^tmp32^-1) & (val32^rslt32)); } else ABORT2(UndefinedInstrV);"}op smul_xy(----00010110:rd:0000:rs:1:y_bit:x_bit:0:rm){execute=" if (emu->is_xscale() ) { /* SMULxy insn. */ op1 = READ_REG($rm$); op2 = READ_REG($rs$); op1 = $x_bit$ ? op1>>16 : op1&0xFFFF; op2 = $y_bit$ ? op2>>16 : op2&0xFFFF; if (op1 & 0x8000) op1 -= 65536; if (op2 & 0x8000) op2 -= 65536; WRITE_REG($rd$,op1 * op2); } else ABORT2(UndefinedInstrV);"}op smulw_y(----00010010:rd:0000:rs:1:y_bit:0:0:rm){execute=" if (emu->is_xscale() ) { /* SMULWy insn. */ op2 = READ_REG($rs$); op2 = $y_bit$ ? op2>>16 : op2&0xFFFF; if (op2 & 0x8000) op2 -= 65536; rslt32 = (uint32_t)( (int64_t)READ_REG($rm$)*op2 >> 16); WRITE_REG($rd$,rslt32); } else ABORT2(UndefinedInstrV);"}op qadd(----00010000:rn:rd:0000:0101:rm){execute=" if (emu->is_xscale() ) { /* QADD insn. */ val32 = READ_REG($rm$); tmp32 = READ_REG($rn$); rslt32 = val32 + tmp32; if ((val32^tmp32^-1) & (val32^rslt32)){ rslt32 = (rslt32 & 0x80000000)? 0x7fffffff:0x80000000; SET_Q; } WRITE_REG($rd$,rslt32); } else ABORT2(UndefinedInstrV);"}op qdadd(----00010100:rn:rd:0000:0101:rm){execute=" if (emu->is_xscale() ) { /* QDADD insn. */ val32 = READ_REG($rm$); tmp32 = READ_REG($rn$); if ((tmp32^tmp32^-1) & (tmp32^(tmp32<<1))){ tmp32 = ((tmp32<<2) & 0x80000000)? 0x7fffffff:0x80000000; SET_Q; } else tmp32<<=1; rslt32 = val32 + tmp32; if ((val32^tmp32^-1) & (val32^rslt32)){ rslt32 = (rslt32 & 0x80000000)? 0x7fffffff:0x80000000; SET_Q; } WRITE_REG($rd$,rslt32); } else ABORT2(UndefinedInstrV);"}op qsub(----00010010:rn:rd:0000:0101:rm){execute=" if (emu->is_xscale() ) { /* QSUB insn. */ val32 = READ_REG($rm$); tmp32 = READ_REG($rn$); rslt32 = val32 - tmp32; if ((val32^tmp32) & (val32^rslt32)){ rslt32 = (rslt32 & 0x80000000)? 0x7fffffff:0x80000000; SET_Q; } WRITE_REG($rd$,rslt32); } else ABORT2(UndefinedInstrV);"}op qdsub(----00010110:rn:rd:0000:0101:rm){execute=" if (emu->is_xscale() ) { /* QDSUB insn. */ val32 = READ_REG($rm$); tmp32 = READ_REG($rn$); if ((tmp32^tmp32^-1) & (tmp32^(tmp32<<1))){ tmp32 = ((tmp32<<2) & 0x80000000)? 0x7fffffff:0x80000000; SET_Q; } else tmp32<<=1; rslt32 = val32 - tmp32; if ((val32^tmp32) & (val32^rslt32)){ rslt32 = (rslt32 & 0x80000000)? 0x7fffffff:0x80000000; SET_Q; } WRITE_REG($rd$,rslt32); } else ABORT2(UndefinedInstrV);"}}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -