📚 OpenRCE is preserved as a read-only archive. Launched at RECon Montreal in 2005. Registration and posting are disabled.








Flag: Tornado! Hurricane!

 Forums >>  IDA Pro  >>  IDA idc jmp table scanning

Topic created on: October 30, 2005 15:31 CST by bkparadox .

I was wondering if someone could help me.
I can't for the life of me wade through all the functions
to find the right one.
What im trying to achieve is as follows:
p.s I Know this is upx and its easily unpacked but this is
an example..
UPX0:00401000 loc_401000:                             ; CODE XREF: UPX1:00405938j
UPX0:00401000 push    0
UPX0:00401002 call    sub_401DF6
UPX0:00401007 mov     dword_403319, eax
UPX0:0040100C call    sub_401DF0
UPX0:00401011 mov     dword_40331D, eax
UPX0:00401016 push    0Ah
UPX0:00401018 push    dword_40331D
UPX0:0040101E push    0
UPX0:00401020 push    dword_403319
UPX0:00401026 call    sub_401031
UPX0:0040102B push    eax
UPX0:0040102C call    sub_401DEA

Now I want to find what refrences to the call
e.g. the first call goes to
UPX0:00401DF6 sub_401DF6 proc near                    ; CODE XREF: UPX0:00401002p
UPX0:00401DF6 jmp     off_402014
UPX0:00401DF6 sub_401DF6 endp

I want the Name of (off_402014) and to rename sub_401DF6 to the name it gives.. in this case
UPX0:00402014 off_402014 dd offset kernel32_GetModuleHandleA
; DATA XREF: sub_401DF6r

I tried this.. but obviously its poorly written on my part
:(
// Paradox's Deep function gather. for those pesky packed or encrypted apps that use
// Getmoudlehandle This will grab the name of the kernel or w/e function
// and make code more readable
#include <idc.idc>

static find_func(){
    auto ea, x, xrefme, backup, start_loc, end_loc;
    start_loc = SelStart();
    end_loc = SelEnd();
    Message("\n***Changing deep functions names for area***\n");
    
    Message("***" + atoa(start_loc) + " to " + atoa(end_loc) + "***\n");
    for( ea = start_loc; ea < end_loc; ea = NextAddr(ea)){
     x = Rfirst(ea);
x = Rnext(ea,x);
if(x != BADADDR){
backup = ea;
ea = x;
x = Rfirst(ea);
Message(atoa(ea) + " " + Name(x) + atoa(x) +"\n");
x = Rnext(ea,x);
if(x != BADADDR){
xrefme = XrefType();
if ( xrefme == fl_JF ){
     MakeNameEx(ea,Name(x),SN_AUTO);
     }
     Message(atoa(ea) + " refers to " + Name(x) + " : " + atoa(x) + "\n");
     }
    
     ea = backup;
     }
    }
    Message("End of output. \n");

}

Thanks in advance.. im sure its something simple..
Just that i dont know the function set properly or w/e.
Appreciate any help even if it just points me to a function.
I dont mind doing the leg work


  ero     November 1, 2005 16:09.34 CST

I'd use NextHead instead of NexAddr. NextHead will iterate through all defined elements. You can then do a isCode(GetFlags(ea)) to check whether you are in code or elsewhere.

Another way, for isntance, could be going through all funcs with NextFunction(ea) and getting the function end with FindFuncEnd(ea) to calculate whether it can only fit the jmp instruction. Then a GetMnem(ea)=="jmp" and if so go get the name and do the MakeName(ea, reference)

If writing the script in IDAPython several convenience functions exist, such as Functions() which can be used to easily iterate through all "for f in Functions()" as well as CodeRefsFrom and CodeRefsTo to gather references.

Hope it helps.

BTW, did you have some trouble with that script or you just were looking to write it tighter?

  bkparadox   November 4, 2005 22:33.30 CST
Well it was giving false positives..
Because it was poorly written
For example the jmp table
UPX0:00402008 off_402008 dd offset kernel32_lstrcmp   ; DATA XREF: sub_401E08r
UPX0:0040200C off_40200C dd offset ntdll_RtlZeroMemory ; DATA XREF: sub_401E02r
UPX0:00402010 off_402010 dd offset kernel32_ReadFile  ; DATA XREF: sub_401DFCr
UPX0:00402014 off_402014 dd offset kernel32_GetModuleHandleA ; DATA XREF: sub_401DF6r
UPX0:00402018 off_402018 dd offset kernel32_GetCommandLineA ; DATA XREF: sub_401DF0r
UPX0:0040201C off_40201C dd offset kernel32_ExitProcess ; DATA XREF: sub_401DEAr
UPX0:00402020 off_402020 dd offset kernel32_CreateFileA ; DATA XREF: sub_401DE4r
UPX0:00402024 off_402024 dd offset kernel32_CloseHandle ; DATA XREF: sub_401DDEr

If i got the refrence sometimes it wud goto the next one other times it wudnt..
All i needed was a way to grap the addr of the jmp and then find out what the name of that is..
e.g.
UPX0:00401DF6 sub_401DF6 proc near                    ; CODE XREF: UPX0:00401002p
UPX0:00401DF6 jmp     off_402014
UPX0:00401DF6 sub_401DF6 endp

I want the Name of (off_402014) and to rename sub_401DF6 to the name it gives.. in this case
UPX0:00402014 off_402014 dd offset kernel32_GetModuleHandleA
; DATA XREF: sub_401DF6r
So from off_402014 i cud grab kernel32_GetModuleHandleA
And then i cud rename the sub to kernel32_GetModuleHandleA
To make it readable from the main code..
An easy way to deal with a jmp table.. Which most packers seem to have

  bkparadox   November 4, 2005 23:12.36 CST
Message(GetMnem(ea) + " " + GetOpnd(ea,0) + "\n" );
I can now get

***Changing deep functions names for area***
***UPX0:00401000 to UPX0:00401016***
UPX0:00401DF6 kernel32_CloseHandledebug074:77E41C83
jmp off_402014
UPX0:00401DF0 kernel32_CloseHandledebug074:77E41C83
jmp off_402018
End of output.
So i guess if I use GetOperandValue i will have th address for the name of the jmp..
Then all i need to do is find out howto get that name..
Can u help me out there..
Help me starting from bx= address of
UPX0:00402014 off_402014 dd offset kernel32_GetModuleHandleA
; DATA XREF: sub_401DF6r
so bx is pointing to 00402014 now how do i get kernel32_GetModuleHandleA cheers

  bkparadox   November 4, 2005 23:49.44 CST
#include <idc.idc>
static find_func(){
    auto ea, x,test, start_loc, end_loc;
    start_loc = SelStart();
    end_loc = SelEnd();
    Message("\n***Changing deep functions names for area***\n");
    
    Message("***" + atoa(start_loc) + " to " + atoa(end_loc) + "***\n");
    for( ea = start_loc; ea < end_loc; ea = NextAddr(ea)){
     x = Rfirst(ea);
x = Rnext(ea,x);
if(x != BADADDR){
Message("Found:" + GetMnem(x) + " " + GetOpnd(x,0) + "\n" );
test= GetOperandValue(x,0);
Message("Pwn? " + atoa(test) +"\n");
// insert Get name from address here..
//MakeName etc...
     }
    }
    Message("End of output. \n");

}
so close... just have to find that last function.. to get the name kernel32_GetModuleHandleA
The naming convention doesnt help me out..
Appreciate the help.. this will finnish off the start of my project then i can move on.. and keep on building on top of it

  bkparadox   November 12, 2005 18:04.12 CST
Woot i finnished it ^_^ Hope this comes in handy..
Found quite a few files that use jump tables
// Paradox's Deep function gather. for those pesky packed or encrypted apps that use
// Getmoudlehandle This will grab the name of the kernel or w/e function
// and make code more readable
// Thanks to ero on openrce
#include <idc.idc>

static main(){
Message("Loaded Deep function script\nCreated by: Paradox\n");
}

static find_func(){
    auto ea, x, name, start_loc, end_loc;
    start_loc = SelStart();
    end_loc = SelEnd();
    Message("\n***Changing deep functions names for area***\n");
    
    Message("***" + atoa(start_loc) + " to " + atoa(end_loc) + "***\n");
    for( ea = start_loc; ea < end_loc; ea = NextAddr(ea)){
     x = Rfirst(ea);
x = Rnext(ea,x);
if(x != BADADDR){
name = Name(Dword(Dfirst(x))); //Take the offset and make it a Dword for Name
name = substr(name, strstr(name, "_")+1, -1); //get rid of dll name
Message("Found:" + GetMnem(x) + " " + GetOpnd(x,0) +
" Refers to -> " + name +"\n" ); //Display what has transpired
MakeName(x, name); //Make the name ^_^
     }
    }
    Message("End of output. \n");

}

Just Make a hotkey
Shift+F2 AddHotkey("Alt-f8", "find_func");
then Alt+F2 To load the file
Select the range you want to check for deep functions
like those used in jmp tables.
And press Alt-F8 ^_^ comments and questions welcome

  bkparadox   November 14, 2005 22:58.28 CST
// Paradox's Deep function gather. for those pesky packed or encrypted apps that use
// Getmoudlehandle This will grab the name of the kernel or w/e function
// and make code more readable
// Updated made it covert all the segment addresses..
// so you don't have to do it manually with select
// Thanks to ero on openrce.org
#include <ida.idc>
static main(){
Message("Loaded Deep function script\nCreated by: Paradox\n");
}

static find_func(){
    auto ea, x, name;
    Message("\n***Changing deep functions names for Section " + SegName(ScreenEA()) + "***\n");
    Message("***" + atoa(SegStart(ScreenEA())) + " to " + atoa(SegEnd(ScreenEA())) + "***\n");
    for ( ea=SegStart(ScreenEA()); ea < SegEnd(ScreenEA()); ea = NextAddr(ea) ){
     x = Rfirst(ea);
x = Rnext(ea,x);
if(x != BADADDR){
name = Name(Dword(Dfirst(x))); //Take the offset and make it a Dword for Name
name = substr(name, strstr(name, "_")+1, -1); //get rid of dll name
if(GetMnem(x)!="jmp") continue;
Message("Found:" + GetMnem(x) + " " + GetOpnd(x,0) +
" Refers to -> " + name +"\n" ); //Display what has transpired
MakeName(x, name); //Make the name ^_^
     }
    }
    Message("End of output. \n");

}

Example output

Loaded Deep function script
Created by: Paradox

***Changing deep functions names for Section PDOX***
***PDOX:00401000 to __u_____:00406000***
Found:jmp off_402000 Refers to -> GetModuleHandleA
Found:jmp off_402004 Refers to -> GetCommandLineA
Found:jmp off_402008 Refers to -> ExitProcess
Found:jmp off_40201C Refers to -> LoadIconA
Found:jmp off_402018 Refers to -> LoadCursorA
Found:jmp off_40204C Refers to -> RegisterClassExA
Found:jmp off_402014 Refers to -> GetSystemMetrics
Found:jmp off_402014 Refers to -> GetSystemMetrics
Found:jmp off_402044 Refers to -> CreateWindowExA
Found:jmp off_402020 Refers to -> LoadMenuA
Found:jmp off_402034 Refers to -> SetMenu
Found:jmp off_402038 Refers to -> ShowWindow
Found:jmp off_402040 Refers to -> UpdateWindow
Found:jmp off_40202C Refers to -> GetMessageA
Found:jmp off_40203C Refers to -> TranslateMessage
Found:jmp off_402028 Refers to -> DispatchMessageA
End of output.

Now all the names show up ^_^

Note: Registration is required to post to the forums.

There are 31,328 total registered users.


Recently Created Topics
[help] Unpacking VMP...
Mar/12
Reverse Engineering ...
Jul/06
let 'IDAPython' impo...
Sep/24
set 'IDAPython' as t...
Sep/24
GuessType return une...
Sep/20
About retrieving the...
Sep/07
How to find specific...
Aug/15
How to get data depe...
Jul/07
Identify RVA data in...
May/06
Question about memor...
Dec/12


Recent Forum Posts
Finding the procedur...
rolEYder
Question about debbu...
rolEYder
Identify RVA data in...
sohlow
let 'IDAPython' impo...
sohlow
How to find specific...
hackgreti
Problem with ollydbg
sh3dow
How can I write olly...
sh3dow
New LoadMAP plugin v...
mefisto...
Intel pin in loaded ...
djnemo
OOP_RE tool available?
Bl4ckm4n


Recent Blog Entries
halsten
Mar/14
Breaking IonCUBE VM

oleavr
Oct/24
Anatomy of a code tracer

hasherezade
Sep/24
IAT Patcher - new tool for ...

oleavr
Aug/27
CryptoShark: code tracer ba...

oleavr
Jun/25
Build a debugger in 5 minutes

More ...


Recent Blog Comments
nieo on:
Mar/22
IAT Patcher - new tool for ...

djnemo on:
Nov/17
Kernel debugger vs user mod...

acel on:
Nov/14
Kernel debugger vs user mod...

pedram on:
Dec/21
frida.github.io: scriptable...

capadleman on:
Jun/19
Using NtCreateThreadEx for ...

More ...


Imagery
SoySauce Blueprint
Jun 6, 2008

[+] expand

View Gallery (11) / Submit