void make_vector(ea_t addr, char *name) { doDwrd(addr, 4); create_insn(get_long(addr)); add_func(get_long(addr), BADADDR); add_cref(addr, get_long(addr), fl_CF); if (name != NULL) set_name(addr, name); }
//--------------------------------------------------------------------------- static void idaapi ch_enter(void *obj, uint32 n) { x86seh_ctx_t *ctx = (x86seh_ctx_t *)obj; if ( --n < ctx->handlers.size() ) { ea_t ea = ctx->handlers[n]; if ( !isCode(get_flags_novalue(ea)) ) create_insn(ea); jumpto(ea); } }
//--------------------------------------------------------------------------- // The main function - called when the user selects the menu item static bool idaapi callback(void *) { // Calculate the default values to display in the form ea_t screen_ea = get_screen_ea(); segment_t *s = getseg(screen_ea); if ( s == NULL || !isCode(get_flags_novalue(screen_ea)) ) { warning("AUTOHIDE NONE\nThe cursor must be on the table jump instruction"); return false; } ea_t startea = screen_ea; while ( true ) { ea_t prev = prev_not_tail(startea); if ( !is_switch_insn(prev) ) break; startea = prev; } ea_t jumps = get_first_dref_from(screen_ea); uval_t jelsize = s->abytes(); uval_t jtsize = 0; if ( jumps != BADADDR ) { decode_insn(screen_ea); jtsize = guess_table_size(jumps); } uval_t shift = 0; uval_t elbase = 0; char input[MAXSTR]; input[0] = '\0'; ea_t defea = BADADDR; uval_t lowcase = 0; ushort jflags = 0; ushort vflags = 0; ea_t vtable = BADADDR; ea_t vtsize = 0; ea_t velsize = s->abytes(); reg_info_t ri; ri.size = 0; // If switch information is present in the database, use it for defaults switch_info_ex_t si; if ( get_switch_info_ex(screen_ea, &si, sizeof(si)) > 0 ) { jumps = si.jumps; jtsize = si.ncases; startea = si.startea; elbase = si.elbase; jelsize = si.get_jtable_element_size(); shift = si.get_shift(); defea = (si.flags & SWI_DEFAULT) ? si.defjump : BADADDR; if ( si.regnum != -1 ) get_reg_name(si.regnum, get_dtyp_size(si.regdtyp), input, sizeof(input)); if ( si.flags & SWI_SIGNED ) jflags |= 2; if ( si.flags2 & SWI2_SUBTRACT ) jflags |= 4; if ( si.flags & SWI_SPARSE ) { jflags |= 1; vtable = si.values; vtsize = jtsize; velsize = si.get_vtable_element_size(); if ( si.flags2 & SWI2_INDIRECT ) { vflags |= 1; jtsize = si.jcases; } if ( si.flags & SWI_JMP_INV ) vflags |= 2; } else { lowcase = si.lowcase; } } // Now display the form and let the user edit the attributes while ( AskUsingForm_c(main_form, &jumps, &jtsize, &jelsize, &shift, &elbase, &startea, input, &lowcase, &defea, &jflags) ) { if ( !check_table(jumps, jelsize, jtsize) ) continue; if ( shift > 3 ) { warning("AUTOHIDE NONE\nInvalid shift value (allowed values are 0..3)"); continue; } if ( !isCode(get_flags_novalue(startea)) ) { warning("AUTOHIDE NONE\nInvalid switch idiom start %a (must be an instruction", startea); continue; } ri.reg = -1; if ( input[0] != '\0' && !parse_reg_name(input, &ri) ) { warning("AUTOHIDE NONE\nUnknown input register: %s", input); continue; } if ( defea != BADADDR && !isCode(get_flags_novalue(defea)) ) { warning("AUTOHIDE NONE\nInvalid default jump %a (must be an instruction", defea); continue; } if ( jflags & 1 ) // value table is present { bool vok = false; while ( AskUsingForm_c(value_form, &vflags, &vtable, &vtsize, &velsize) ) { if ( (vflags & 1) == 0 ) vtsize = jtsize; if ( check_table(vtable, velsize, vtsize) ) { vok = true; break; } } if ( !vok ) break; } // ok, got and validated all params -- fill the structure si.flags = SWI_EXTENDED; si.flags2 = 0; if ( jflags & 2 ) si.flags |= SWI_SIGNED; if ( jflags & 4 ) si.flags2 |= SWI2_SUBTRACT; si.jumps = jumps; si.ncases = ushort(jtsize); si.startea = startea; si.elbase = elbase; if ( elbase != 0 ) si.flags |= SWI_ELBASE; si.set_jtable_element_size((int)jelsize); si.set_shift((int)shift); if ( defea != BADADDR ) { si.flags |= SWI_DEFAULT; si.defjump = defea; } if ( ri.reg != -1 ) si.set_expr(ri.reg, get_dtyp_by_size(ri.size)); if ( jflags & 1 ) // value table is present { si.flags |= SWI_SPARSE; si.values = vtable; si.set_vtable_element_size((int)velsize); if ( (vflags & 1) != 0 ) { si.flags2 |= SWI2_INDIRECT; si.jcases = (int)jtsize; si.ncases = (ushort)vtsize; } if ( (vflags & 2) != 0 ) si.flags |= SWI_JMP_INV; } else { si.lowcase = lowcase; } // ready, store it set_switch_info_ex(screen_ea, &si); create_switch_table(screen_ea, &si); setFlbits(screen_ea, FF_JUMP); create_insn(screen_ea); info("AUTOHIDE REGISTRY\nSwitch information has been stored"); break; } return true; }
int idaapi emu() { char szLabel[MAXSTR]; insn_t saved; segment_t* pSegment; ea_t ea, length, offset; flags_t flags; uint32 dwFeature, i; dwFeature = cmd.get_canon_feature(); fFlow = !(dwFeature & CF_STOP); if (dwFeature & CF_USE1) op_emu(cmd.Op1, 1); if (dwFeature & CF_USE2) op_emu(cmd.Op2, 1); if (dwFeature & CF_CHG1) op_emu(cmd.Op1, 0); if (dwFeature & CF_CHG2) op_emu(cmd.Op2, 0); saved = cmd; switch (cmd.itype) { case M8B_MOV: if (!cmd.Op1.is_reg(rPSP)) break; case M8B_SWAP: if (cmd.itype == M8B_SWAP && !cmd.Op2.is_reg(rDSP)) break; for (i = 0; i < 5; ++i) { ea = decode_prev_insn(cmd.ea); if (ea == BADADDR) break; if (cmd.itype == M8B_MOV && cmd.Op1.is_reg(rA) && cmd.Op2.type == o_imm) { ea = toRAM(cmd.Op2.value); if (ea != BADADDR) { qsnprintf(szLabel, sizeof(szLabel), "%s_%0.2X", cmd.itype == M8B_MOV ? "psp" : "dsp", cmd.Op2.value); ua_add_dref(cmd.Op2.offb, ea, dr_O); set_name(ea, szLabel, SN_NOWARN); } break; } } break; case M8B_JACC: pSegment = getseg(cmd.ea); if (!pSegment) break; length = pSegment->endEA - cmd.ea; if (length > 256) length = 256; for (offset = 2; offset < length; offset += 2) { ea = toROM(saved.Op1.addr + offset); if (ea == BADADDR) break; flags = getFlags(ea); if (!hasValue(flags) || (has_any_name(flags) || hasRef(flags)) || !create_insn(ea)) break; switch (cmd.itype) { case M8B_JMP: case M8B_RET: case M8B_RETI: case M8B_IPRET: add_cref(saved.ea, ea, fl_JN); break; default: offset = length; } } break; case M8B_IORD: case M8B_IOWR: case M8B_IOWX: for (i = 0; i < 5; ++i) { ea = (saved.itype == M8B_IORD) ? decode_insn(cmd.ea + cmd.size) : decode_prev_insn(cmd.ea); if (ea == BADADDR) break; if (cmd.Op1.is_reg(rA) && cmd.Op2.type == o_imm) { qsnprintf(szLabel, sizeof(szLabel), "[A=%0.2Xh] ", cmd.Op2.value); if (get_portbits_sym(szLabel + qstrlen(szLabel), saved.Op1.addr, cmd.Op2.value)) set_cmt(saved.ea, szLabel, false); break; } } } cmd = saved; if ((cmd.ea & 0xFF) == 0xFF) { switch (cmd.itype) { case M8B_RET: case M8B_RETI: case M8B_XPAGE: break; default: QueueMark(Q_noValid, cmd.ea); } } if (fFlow) ua_add_cref(0, cmd.ea + cmd.size, fl_F); return 1; }