// // Decode the instruction and return an enum describing it // static or1kInstructionType decode(Uns32 instruction) { // get the OR1K decode table static vmidDecodeTableP decodeTable; if(!decodeTable) { decodeTable = createDecodeTable(); } // decode the instruction to get the type or1kInstructionType type = vmidDecode(decodeTable, instruction); // some arguments to l.sf and l.sfi are invalid: filter them here if((type==OR1K_IT_SF) && !getCmpInfo(OP5_CMPOP(instruction))->name) { type = OR1K_IT_LAST; } else if((type==OR1K_IT_SFI) && !getCmpInfo(OP6_CMPOP(instruction))->name) { type = OR1K_IT_LAST; } return type; }
// // Return the size of the instruction at the passed address in bytes // Uns32 microblazeGetInstructionBytes( microblazeP microblaze, microblazeAddr thisPC ) { vmiProcessorP processor = (vmiProcessorP)microblaze; // // Initialize the 32 bit decoder table // static vmidDecodeTableP decodeTable32; if(!decodeTable32) { decodeTable32 = microblazeCreateDecodeTable32(); } Uns64 instr4 = vmicxtFetch4Byte(processor, thisPC); Uns32 type = MICROBLAZE_IT_LAST; type = vmidDecode(decodeTable32, instr4); if (type == MICROBLAZE_IT_IMM_TYPEI1) { return 8; } else { return 4; } }
// // Decoder function for a given address // void ppc32Decode( ppc32P ppc32, ppc32Addr thisPC, ppc32InstructionInfoP info ) { // // Initialize the following info fields before table creation // info->thisPC = thisPC; info->arch = ppc32->configInfo.arch; vmiProcessorP processor = (vmiProcessorP)ppc32; // // Initialize the UISA decoder table // static vmidDecodeTableP decodeTable_UISA_16Bit; if(!decodeTable_UISA_16Bit) { if(ppc32->params.UISA_I_VLE) { decodeTable_UISA_16Bit = ppc32CreateDecodeTable_I_VLE_16Bit(decodeTable_UISA_16Bit, False); } } static vmidDecodeTableP decodeTable_UISA_32Bit; if(!decodeTable_UISA_32Bit) { if(ppc32->params.UISA_I_B) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_B_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_BCDA) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_BCDA_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_S) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_S_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_E) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_E_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_E_PC) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_E_PC_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_E_PD) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_E_PD_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_FP) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_FP_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_DFP) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_DFP_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_MA) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_MA_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_SP) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_SP_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_V) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_V_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_LMA) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_LMA_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_WT) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_WT_32Bit(decodeTable_UISA_32Bit, False); } if(ppc32->params.UISA_I_VLE) { decodeTable_UISA_32Bit = ppc32CreateDecodeTable_I_VLE_32Bit(decodeTable_UISA_32Bit, False); } } // // Initialize the mpc82x_32Bit decoder table // static vmidDecodeTableP decodeTable_mpc82x_32Bit; if(!decodeTable_mpc82x_32Bit && (info->arch == VARIANT_MPC82X)) { decodeTable_mpc82x_32Bit = ppc32CreateDecodeTable_I_B_32Bit(decodeTable_mpc82x_32Bit, False); decodeTable_mpc82x_32Bit = ppc32CreateDecodeTable_I_E_32Bit(decodeTable_mpc82x_32Bit, False); decodeTable_mpc82x_32Bit = ppc32CreateDecodeTable_I_MA_32Bit(decodeTable_mpc82x_32Bit, False); } // // Initialize the following info fields before lookup // info->instrsize = 0; info->type = PPC32_IT_LAST; Uns64 instruction = 0; if (info->arch == VARIANT_UISA) { if (info->type == PPC32_IT_LAST) info->type = PPC32_IT_INSTR16; // // Attempt to match a UISA 16 Bit instruction // if (info->type == PPC32_IT_INSTR16) { instruction = (Uns64)vmicxtFetch2Byte(processor, thisPC+0) | (instruction << 0); info->type = PPC32_IT_LAST; if (decodeTable_UISA_16Bit) { info->type = vmidDecode(decodeTable_UISA_16Bit, instruction); } else { info->type = PPC32_IT_INSTR32; } info->nextPC = info->thisPC + 2; info->instrsize = 2; info->instruction = instruction; } // // Attempt to match a UISA 32 Bit instruction // if (info->type == PPC32_IT_INSTR32) { instruction = (Uns64)vmicxtFetch2Byte(processor, thisPC+2) | (instruction << 16); info->type = PPC32_IT_LAST; if (decodeTable_UISA_32Bit) { info->type = vmidDecode(decodeTable_UISA_32Bit, instruction); } info->nextPC = info->thisPC + 4; info->instrsize = 4; info->instruction = instruction; } } if (info->arch == VARIANT_MPC82X) { if (info->type == PPC32_IT_LAST) info->type = PPC32_IT_INSTR32; // // Attempt to match a mpc82x 32 Bit instruction // if (info->type == PPC32_IT_INSTR32) { instruction = (Uns64)vmicxtFetch4Byte(processor, thisPC+0) | (instruction << 0); info->type = PPC32_IT_LAST; info->type = vmidDecode(decodeTable_mpc82x_32Bit, instruction); info->nextPC = info->thisPC + 4; info->instrsize = 4; info->instruction = instruction; } } ppc32GenInstructionInfo(info); }
// // Decoder function for a given address // void microblazeDecode( microblazeP microblaze, microblazeAddr thisPC, microblazeInstructionInfoP info ) { // // Initialize the 32 bit decoder table // static vmidDecodeTableP decodeTable32; if(!decodeTable32) { decodeTable32 = microblazeCreateDecodeTable32(); } vmiProcessorP processor = (vmiProcessorP)microblaze; // // Initialize the following info fields before lookup // info->type = MICROBLAZE_IT_INSTR32; info->thisPC = thisPC; info->arch = microblaze->configInfo.arch; Uns64 instruction = 0; info->instrsize = 0; // // Attempt to match a 32 bit instruction // if (info->type == MICROBLAZE_IT_INSTR32) { Uns64 instr4 = vmicxtFetch4Byte(processor, thisPC); info->type = MICROBLAZE_IT_LAST; info->type = vmidDecode(decodeTable32, instr4); info->nextPC = info->thisPC + 4; instruction = instr4; info->instrsize = 4; info->instruction = instr4; } // // Fatal if there was a match failure // if (info->type == MICROBLAZE_IT_LAST && MICROBLAZE_DISASSEMBLE(microblaze)) { vmiMessage("F", "DECODE_FAIL", "Address=0x" FMT_640Nx " Instruction = 0x" FMT_640Nx, (Uns64)thisPC, instruction); } microblazeGenInstructionInfo(info, instruction); // // If this is a decode of an IMM instruction, we decode the next instruction // if (info->type == MICROBLAZE_IT_IMM_TYPEI1) { Uns64 instr4 = vmicxtFetch4Byte(processor, info->nextPC); info->type = MICROBLAZE_IT_LAST; info->type = vmidDecode(decodeTable32, instr4); info->thisPC = info->nextPC; info->nextPC = info->thisPC + 4; instruction = instr4; info->instrsize = 8; info->instruction = instr4; // // Fatal if there was a match failure // if (info->type == MICROBLAZE_IT_LAST && MICROBLAZE_DISASSEMBLE(microblaze)) { vmiMessage("F", "DECODE_FAIL", "Address=0x" FMT_640Nx " Instruction = 0x" FMT_640Nx, (Uns64)info->nextPC, instruction); } // // get the fields for the TYPEB instruction // microblazeGenInstructionInfo(info, instruction); } else { // Indicate that the simmhi is unset info->simmhi = 0x0000ffff; } }