intercept API

Just starting out? Need help? Post your questions and find answers here.
registrymechanic22
Enthusiast
Enthusiast
Posts: 176
Joined: Sun Jun 28, 2009 7:07 pm
Location: RUS

intercept API

Post by registrymechanic22 »

Hi all

Code: Select all

Procedure.s PutDirektorii(PutPapka); #CSIDL_SYSTEM
Put$=Space(#MAX_PATH):SHGetSpecialFolderLocation_(0,PutPapka,@Raz)
SHGetPathFromIDList_(Raz, @Put$):ProcedureReturn Trim(Put$)
EndProcedure

Procedure HookedProcedure(a,b)
; newmessagebox:
; Debug a
; Debug b
; Debug c
; Debug d
MessageRequester("!!!!", "+++++++++++++++++++++++")
ProcedureReturn
EndProcedure

Procedure Hook(process,library$,function$,HookedProcAddr)
   dwAddr=GetProcAddress_(GetModuleHandle_(library$),function$)
   Debug dwaddr
   ReadProcessMemory_(process,dwAddr,@Backup(0),6,@readbytes)
   Dim a.b(6) : a(0)=$68 : a(5)=$C3 : dwCalc=HookedProcAddr-dwAddr-5
   CopyMemory(@dwCalc,@a(1),4)
;    VirtualProtect_(dwAddr,8,#PAGE_EXECUTE_READWRITE,@oldP) 
   WriteProcessMemory_(process,dwAddr,@a(0),6,@written)
EndProcedure

Procedure OpenWindow_Window_0()
Protected res=0
  If OpenWindow(0, 100, 100, 145, 260, "HookMe", #PB_Window_SystemMenu)
    ButtonGadget(1, 40,  60,  60, 25, "Delete")
    ButtonGadget(2, 40,  20,  60, 25, "Create")
    ButtonGadget(3, 40,  100,  60, 25, "MSB")
    StringGadget(4, 40,  140, 60, 25, Str(GetCurrentProcessId_()), #PB_String_ReadOnly)
    ButtonGadget(5, 40,  180,  60, 25, "inject")
    ButtonGadget(6, 40,  220,  60, 25, "Hook")
    res=1
  EndIf
ProcedureReturn res
EndProcedure

  If OpenWindow_Window_0()
    Repeat
      Event = WaitWindowEvent()
      Select Event
        Case #PB_Event_Gadget
          EventGadget = EventGadget()
          Select EventGadget
            Case 1 : f$="c:\test.txt" : DeleteFile_(f$)
            Case 2 : f$="c:\test.txt" : CreateFile(0,f$) : WriteString(0,"hi") : CloseFile(0) 
            Case 3 : MessageBox_(0," О  п  а .            ","В н и м а н и е !", #MB_ICONHAND)  
;             Case 5 : InjectDll("scan.dll")  
            Case 6
                    hProcess = OpenProcess_(#PROCESS_ALL_ACCESS, 0, Val(GetGadgetText(4)))
                    Hook(hProcess,"kernel32.dll","DeleteFileA",@HookedProcedure())
          EndSelect
      EndSelect
    Until Event=#PB_Event_CloseWindow
  EndIf
End
program crashes... :(
What am I doing wrong?
Correctly find the address of the procedure, why it does not work??

Thanks for your help in advance!
Jihugen
User
User
Posts: 45
Joined: Mon Jun 07, 2010 11:36 pm
Location: Normandy, France

Re: intercept API

Post by Jihugen »

Interesting/fun piece of code.
What seems to be wrong for me:
- You were using $68 (PUSH). I think you intended to use $E9 (CALL). ;)
- Remove the all parameter from HookedProcedure() (I think you're not pushing any parameter on the stack with your patch).
If you want to intercept the parameters given to DeleteFileA(), it's probably more complicated.

The code below is working (replace those 2 procedures in your code).

Code: Select all

Procedure HookedProcedure()                   ; <--- No parameter here
MessageRequester("!!!!", "+++++++++++++++++++++++")
ProcedureReturn
EndProcedure

Procedure Hook(process,library$,function$,HookedProcAddr)
   dwAddr=GetProcAddress_(GetModuleHandle_(library$),function$)
   Debug dwaddr
   Debug Hex(PeekL(dwaddr))
   ReadProcessMemory_(process,dwAddr,@Backup(0),6,@readbytes)
   Dim a.b(5) : a(0)=$E8 : a(5)=$c3 : dwCalc=HookedProcAddr-dwAddr-5    ; <--- fixed line
   CopyMemory(@dwCalc,@a(1),4)
   WriteProcessMemory_(process,dwAddr,@a(0),6,@written)
 EndProcedure
registrymechanic22
Enthusiast
Enthusiast
Posts: 176
Joined: Sun Jun 28, 2009 7:07 pm
Location: RUS

Re: intercept API

Post by registrymechanic22 »

Jihugen wrote:
Hi.
Thank you.

How then can intercept the parameters given to DeleteFileA(?) ?


Yours sincerely.
registrymechanic22
Enthusiast
Enthusiast
Posts: 176
Joined: Sun Jun 28, 2009 7:07 pm
Location: RUS

Re: intercept API

Post by registrymechanic22 »

alternatively can use this:

Code: Select all

Global Dim Backup(0)

Global buf1.s
Global buf11,buf2,buf3.s,buf4.s,buf5

Procedure.s PutDirektorii(PutPapka); #CSIDL_SYSTEM
Put$=Space(#MAX_PATH):SHGetSpecialFolderLocation_(0,PutPapka,@Raz)
SHGetPathFromIDList_(Raz, @Put$):ProcedureReturn Trim(Put$)
EndProcedure

Procedure HookedProcedure1()

 ! mov eax,[esp+8] 
 ! mov dword[v_buf1],eax

Debug "DeleteFile_("+Chr($22)+buf1+Chr($22)+")"

EndProcedure
Procedure HookedProcedure2()

 ! mov eax,[esp+8] 
 ! mov dword[v_buf2],eax
 ! mov eax,[esp+12] 
 ! mov dword[v_buf3],eax
 ! mov eax,[esp+16] 
 ! mov dword[v_buf4],eax
 ! mov eax,[esp+20] 
 ! mov dword[v_buf5],eax

Debug "MessageBox("+Str(buf2)+", "+Chr($22)+buf3+Chr($22)+", "+Chr($22)+buf4+Chr($22)+", "+Str(buf5)+")"

EndProcedure

Procedure Hook(process,library$,function$,HookedProcAddr)
   dwAddr=GetProcAddress_(GetModuleHandle_(library$),function$)
   ReadProcessMemory_(process,dwAddr,@Backup(0),6,@readbytes)
   Dim a.b(5) : a(0)=$E8 : a(5)=$c3 : dwCalc=HookedProcAddr-dwAddr-5    ; <--- fixed line
   CopyMemory(@dwCalc,@a(1),4)
   WriteProcessMemory_(process,dwAddr,@a(0),6,@written)
EndProcedure
Procedure OpenWindow_Window_0()
Protected res=0
  If OpenWindow(0, 100, 100, 145, 260, "HookMe", #PB_Window_SystemMenu)
    ButtonGadget(1, 40,  60,  60, 25, "Delete")
    ButtonGadget(2, 40,  20,  60, 25, "Create")
    ButtonGadget(3, 40,  100,  60, 25, "MSB")
    StringGadget(4, 40,  140, 60, 25, Str(GetCurrentProcessId_()), #PB_String_ReadOnly)
    ButtonGadget(5, 40,  180,  60, 25, "inject")
    ButtonGadget(6, 40,  220,  60, 25, "Hook")
    res=1
  EndIf
ProcedureReturn res
EndProcedure

  If OpenWindow_Window_0()
    Repeat
      Event = WaitWindowEvent()
      Select Event
        Case #PB_Event_Gadget
          EventGadget = EventGadget()
          Select EventGadget
            Case 1 : f$="c:\test1.txt" : DeleteFile_(f$)
            Case 2 : f$="c:\test.txt" : CreateFile(0,f$) : WriteString(0,"hi") : CloseFile(0) 
            Case 3 : MessageBox_(0," О  п  а .            ","В н и м а н и е !", #MB_ICONHAND)  
;             Case 5 : InjectDll("scan.dll")  
            Case 6
                    hProcess = OpenProcess_(#PROCESS_ALL_ACCESS, 0, Val(GetGadgetText(4)))
                    Hook(hProcess,"kernel32.dll","DeleteFileA",@HookedProcedure1())
                    Hook(hProcess,"user32.dll","MessageBoxA",@HookedProcedure2())
          EndSelect
      EndSelect
    Until Event=#PB_Event_CloseWindow
  EndIf
End
BUT, I do not want to use ASM... :(
than can replace these inserts from ASM?? :?:
Jihugen
User
User
Posts: 45
Joined: Mon Jun 07, 2010 11:36 pm
Location: Normandy, France

Re: intercept API

Post by Jihugen »

registrymechanic22 wrote:BUT, I do not want to use ASM... :(
than can replace these inserts from ASM?? :?:
I don't know if there is another feasible way (but well, I'm far from an expert in this field :? ).
Why not use ASM?
In this case it seems actually pertinent, no?
registrymechanic22
Enthusiast
Enthusiast
Posts: 176
Joined: Sun Jun 28, 2009 7:07 pm
Location: RUS

Re: intercept API

Post by registrymechanic22 »

I do not know ASM? I can not work with him .... :oops:

in HookedProcedure () to add to intercept functions, its treatment, and return it to either suspend or continue.

.. Sorry for my english... :oops:

Code: Select all

Procedure UnHook(library$,function$)
  dwAddr=GetProcAddress_(GetModuleHandle_(library$),function$)
  WriteProcessMemory_(GetCurrentProcess_(),dwAddr,@Backup(0),6,@written)
EndProcedure

Procedure HookedProcedure1()

! mov eax,[esp+8]
! mov dword[v_buf1],eax

UnHook("kernel32.dll","DeleteFileA")
DeleteFile_(buf2) ; or stop!
Hook("kernel32.dll","DeleteFileA",@NewDeleteFile())
EndProcedure
I think there's a lot extra, and how to make beautiful, myself can not understand
Thorium
Addict
Addict
Posts: 1271
Joined: Sat Aug 15, 2009 6:59 pm

Re: intercept API

Post by Thorium »

If you hook API functions you can just put the parameter in the hook procedure as normal parameters. No assembler needed, if it's StdCall.
SFSxOI
Addict
Addict
Posts: 2970
Joined: Sat Dec 31, 2005 5:24 pm
Location: Where ya would never look.....

Re: intercept API

Post by SFSxOI »

Whats the whole thing look like? I lost track between the asm conversions and the replacement procedures as to what exactly you were trying to accomplish. And whats 'backup' look like?
The advantage of a 64 bit operating system over a 32 bit operating system comes down to only being twice the headache.
registrymechanic22
Enthusiast
Enthusiast
Posts: 176
Joined: Sun Jun 28, 2009 7:07 pm
Location: RUS

Re: intercept API

Post by registrymechanic22 »

Prompt please example (code), to correct my mistake?
I do not know how to implement it.... :(

Fhanks in advance.


PS:
********* executable EXE *********

Code: Select all

Procedure.s PutDirektorii(PutPapka)
; PutPapka=#CSIDL_SYSTEMX86
Put$=Space(#MAX_PATH):SHGetSpecialFolderLocation_(0,PutPapka,@Raz)
SHGetPathFromIDList_(Raz, @Put$):ProcedureReturn Trim(Put$)
EndProcedure

Procedure InjectDll(NameDll.s)
   hProcess=OpenProcess_(#PROCESS_CREATE_THREAD | #PROCESS_VM_OPERATION | #PROCESS_VM_READ | #PROCESS_VM_WRITE,0,Val(GetGadgetText(4)))
   LL=GetProcAddress_(GetModuleHandle_(PutDirektorii(#CSIDL_SYSTEM)+"\kernel32.dll"),"LoadLibraryA")
   VA=VirtualAllocEx_(hProcess,0,12,#MEM_RESERVE | #MEM_COMMIT,#PAGE_READWRITE)
   WriteProcessMemory_(hProcess,VA,NameDll.s,12,0)
   CreateRemoteThread_(hProcess,0,0,LL,VA,0,0)
   CloseHandle_(hProcess)
EndProcedure

Procedure OpenWindow_Window_0()
Protected res=0
  If OpenWindow(0, 100, 100, 145, 260, "HookMe", #PB_Window_SystemMenu)
    ButtonGadget(1, 40,  60,  60, 25, "Delete")
    ButtonGadget(2, 40,  20,  60, 25, "Create")
    ButtonGadget(3, 40,  100,  60, 25, "MSB")
    StringGadget(4, 40,  140, 60, 25, Str(GetCurrentProcessId_()), #PB_String_ReadOnly)
    ButtonGadget(5, 40,  180,  60, 25, "inject")
    ButtonGadget(6, 40,  220,  60, 25, "Hook")
    res=1
  EndIf
ProcedureReturn res
EndProcedure

  If OpenWindow_Window_0()
    Repeat
      Event = WaitWindowEvent()
      Select Event
        Case #PB_Event_Gadget
          EventGadget = EventGadget()
          Select EventGadget
            Case 1 : f$="c:\test.txt" : DeleteFile_(f$)
            Case 2 : f$="c:\test.txt" : CreateFile(0,f$) : WriteString(0,"hi") : CloseFile(0) 
            Case 3 : MessageBox_(0," О  п  а .            ","В н и м а н и е !", #MB_ICONHAND)  
            Case 5 : InjectDll("scan.dll")  
            Case 6
;                     hProcess = OpenProcess_(#PROCESS_ALL_ACCESS, 0, 1448)
;                     Hook(hProcess,"kernel32.dll","DeleteFileA",@HookedProcedure1())
;                     Hook(hProcess,"user32.dll","MessageBoxA",@HookedProcedure2())
          EndSelect
      EndSelect
    Until Event=#PB_Event_CloseWindow
  EndIf
End
********* DLL *********

Code: Select all

Global Dim Backup(0)

Global oldP

Global buf1.s,buf2.s,buf3.s,buf4.s,buf5.s,buf6.s

Declare NewDeleteFile() 

Procedure EnableDebugPrivilege()
If OpenProcessToken_(GetCurrentProcess_(),#TOKEN_ADJUST_PRIVILEGES|#TOKEN_QUERY,@hToken)
tp.TOKEN_PRIVILEGES : tp\PrivilegeCount=1
If LookupPrivilegeValue_(#Null,"SeDebugPrivilege",tp\Privileges[0]\Luid)
tp\Privileges[0]\Attributes = #SE_PRIVILEGE_ENABLED
If AdjustTokenPrivileges_(hToken,#False,@tp,SizeOf(tp),#Null,#Null)
EndIf : EndIf : EndIf
EndProcedure
EnableDebugPrivilege()


Procedure.s PutDirektorii(PutPapka)
Protected Put.s
PutPapka=#CSIDL_SYSTEMX86
Put.s=Space(#MAX_PATH):SHGetSpecialFolderLocation_(0,PutPapka,@Raz)
SHGetPathFromIDList_(Raz, @Put):ProcedureReturn Trim(Put)
EndProcedure

Procedure Hook(library$,function$,HookedProcAddr)
Protected dwAddr, old
Protected process = OpenProcess_(#PROCESS_ALL_ACCESS, 0, GetCurrentProcessId_())
old=GetModuleHandle_(library$)
dwAddr=GetProcAddress_(old,function$)
ReadProcessMemory_(process,dwAddr,@Backup(0),6,@readbytes)
Dim a.b(5) : a(0)=$E8 : a(5)=$c3 : dwCalc=HookedProcAddr-dwAddr-5    ; <--- fixed line
CopyMemory(@dwCalc,@a(1),4)
WriteProcessMemory_(process,dwAddr,@a(0),6,@written)
EndProcedure

Procedure UnHook(library$,function$)
  dwAddr=GetProcAddress_(GetModuleHandle_(library$),function$)
  WriteProcessMemory_(GetCurrentProcess_(),dwAddr,@Backup(0),6,@written)
EndProcedure


ProcedureDLL AttachProcess(Instance) 

Hook("kernel32.dll","DeleteFileA",@NewDeleteFile())

EndProcedure 

; *******************************************************
; user32.dll


Procedure NewMessageBox() 

         ! mov eax,[esp+4] 
         ! mov dword[v_buf1],eax         ;hwnd 
         ! mov eax,[esp+8] 
         ! mov dword[v_buf2],eax      ;text 
         ! mov eax,[esp+12] 
         ! mov dword[v_buf3],eax      ;caption 
         ! mov eax,[esp+16] 
         ! mov dword[v_buf4],eax         ;type 
          
         OpenFile(1,"qqqqq.txt") 
         FileSeek(1,Lof(1)) 
         WriteStringN(1, "MessageBox("+Str(v_buf1)+", "+Chr($22)+buf2+Chr($22)+", "+Chr($22)+buf3+Chr($22)+", "+Str(v_buf4)+")" ) 
         CloseFile(1) 
         
; call_newmessagebox=delta_newmessagebox+NewUser32 
; ! jmp dword[v_call_newmessagebox] 
EndProcedure 



; *******************************************************
; kernel32.dll

Procedure NewDeleteFile() 

;          ! mov eax,[esp+4] 
;          ! mov dword[v_buf1],eax         ;name 
         ! mov eax,[esp+8] 
         ! mov dword[v_buf2],eax         ;name 


         OpenFile(1,"qqqqq.txt") 
         FileSeek(1,Lof(1)) 
         WriteStringN(1, buf2) 
         CloseFile(1) 
; MessageRequester("",buf2)

; call_newdeletefile =delta_newdeletefile+NewKernel32 
; ! jmp dword[v_call_newdeletefile] 

UnHook("kernel32.dll","DeleteFileA")
; DeleteFile_(buf2)
OpenLibrary(1,"kernel32.dll")
CallFunction(1, "DeleteFileA", buf2)
CloseLibrary(1)
Hook("kernel32.dll","DeleteFileA",@NewDeleteFile())
EndProcedure

; *******************************************************
; !jmp @F
; !MP10 ;3 по счету
; !MP12 ;4
; !@@:
; *******************************************************
; *******************************************************
???
Last edited by registrymechanic22 on Fri Jun 25, 2010 9:29 pm, edited 1 time in total.
Thorium
Addict
Addict
Posts: 1271
Joined: Sat Aug 15, 2009 6:59 pm

Re: intercept API

Post by Thorium »

SFSxOI wrote:Whats the whole thing look like? I lost track between the asm conversions and the replacement procedures as to what exactly you were trying to accomplish. And whats 'backup' look like?
'backup' is the original code fragment he is overwriting. It's needed if he wants to call the original procedure and to uninstall the hook. However it's not good in his code. He just uses a length of 6 byte for the backup, which can lead to a crash if the procedure don't starts with the code he is expecting. If the instructions are longer or shorter and not match the 6 byte border he will not be able to call the original procedure without uninstalling his hook. The normal solution to that is using a simple disassembler engine to get the length of the instructions.
Thorium
Addict
Addict
Posts: 1271
Joined: Sat Aug 15, 2009 6:59 pm

Re: intercept API

Post by Thorium »

Code: Select all

Procedure NewMessageBox(hwnd.i, text.s, caption.s, type.i)

         OpenFile(1,"qqqqq.txt")
         FileSeek(1,Lof(1))
         WriteStringN(1, "MessageBox("+Str(v_buf1)+", "+Chr($22)+buf2+Chr($22)+", "+Chr($22)+buf3+Chr($22)+", "+Str(v_buf4)+")" )
         CloseFile(1)
         
; call_newmessagebox=delta_newmessagebox+NewUser32
; ! jmp dword[v_call_newmessagebox]
EndProcedure 
Not tested but thats what i mean with the parameters.
SFSxOI
Addict
Addict
Posts: 2970
Joined: Sat Dec 31, 2005 5:24 pm
Location: Where ya would never look.....

Re: intercept API

Post by SFSxOI »

Thorium wrote:
SFSxOI wrote:Whats the whole thing look like? I lost track between the asm conversions and the replacement procedures as to what exactly you were trying to accomplish. And whats 'backup' look like?
'backup' is the original code fragment he is overwriting. It's needed if he wants to call the original procedure and to uninstall the hook. However it's not good in his code. He just uses a length of 6 byte for the backup, which can lead to a crash if the procedure don't starts with the code he is expecting. If the instructions are longer or shorter and not match the 6 byte border he will not be able to call the original procedure without uninstalling his hook. The normal solution to that is using a simple disassembler engine to get the length of the instructions.

Ahhhh...ok, got it. Thanks

But why even use ASM to begin with, what he wants to do is just StdCall isn't it ?
The advantage of a 64 bit operating system over a 32 bit operating system comes down to only being twice the headache.
Jihugen
User
User
Posts: 45
Joined: Mon Jun 07, 2010 11:36 pm
Location: Normandy, France

Re: intercept API

Post by Jihugen »

SFSxOI wrote:But why even use ASM to begin with, what he wants to do is just StdCall isn't it ?
The goal was to write a Call to HookedProcedure() directly at the beginning of the DeleteFileA function, so that each call to DeleteFileA will be forwarded to HookedProcedure.
It's fast, dirty and fun... There is probably other (and better) ways.

Thorium wrote:However it's not good in his code. He just uses a length of 6 byte for the backup, which can lead to a crash if the procedure don't starts with the code he is expecting. If the instructions are longer or shorter and not match the 6 byte border he will not be able to call the original procedure without uninstalling his hook. The normal solution to that is using a simple disassembler engine to get the length of the instructions.
Sorry, Thorium, but I don't understand what you mean here.
For me, 6 bytes is enough for the backup, and it seems clear that calling the original procedure without uninstalling the hook is impossible. What did I get wrong?
registrymechanic22
Enthusiast
Enthusiast
Posts: 176
Joined: Sun Jun 28, 2009 7:07 pm
Location: RUS

Re: intercept API

Post by registrymechanic22 »

Thorium wrote:

Code: Select all

Procedure NewMessageBox(hwnd.i, text.s, caption.s, type.i)
......................
EndProcedure 
Not tested but thats what i mean with the parameters.
... Tried, not working, the program crashes :?
Thorium
Addict
Addict
Posts: 1271
Joined: Sat Aug 15, 2009 6:59 pm

Re: intercept API

Post by Thorium »

Calling the original procedure without uninstalling the hook is not only possible, its a normal thing. It's not that hard. You just need to copy the correct number of bytes on hook installation. The code you will write to the procedure is likely 5 byte. What you need to do is copy the complete instructions that you overwrite. There can be some shorter instructions or one bigger. But you cant expect them to allways end at byte 6. You need a intact code fragment not a cutted instruction. Therefor you need to get the length of the intructions you overwrite to copy them intact. Thats easy with the Error Lib of PB.
Once you have that intact code fragment you may need to fix it. For example if there is a jump in it you have to recalculate the destination, because its saved relative to the instruction. Then you write a jmp to the end of the copied code that jumps right after your patched code in the original procedure. Now you just need to call the copied code to Call the original procedure.
Most people skip the part of fixing instructions because its very unlikely that there is a jump in the first 5 byte.

I hope thats better understandable, sorry english is not my nativ language.
Post Reply