Button in Fremdes Programm einfügen



  • Hey,
    ich habe vor einen kleinen Button in ein fremdes PRogramm einzufügen.

    Hier mal der Code der DLL die iniziert wird:

    // dllmain.cpp : Definiert den Einstiegspunkt für die DLL-Anwendung.
    #include "stdafx.h"
    #include <iostream>
    #include <fstream>
    #include <sstream>
    #include <time.h>
    using namespace std;
    
    static HWND hWnd;
    LONG p;
    static int hWndI = 0;
    
    LRESULT CALLBACK NewWndProc (HWND, UINT, WPARAM, LPARAM);
    
    BOOL APIENTRY DllMain( HMODULE hModule,
                           DWORD  ul_reason_for_call,
                           LPVOID lpReserved
    					 )
    {
    	switch (ul_reason_for_call)
    	{
    	case DLL_PROCESS_ATTACH:
    		hWnd = FindWindowA(0, "AceDB 2.0");
    		p = GetWindowLong(hWnd, GWL_WNDPROC);
    		SetWindowLongA(hWnd, GWL_WNDPROC, (long)NewWndProc);
    
    		break;
    	case DLL_THREAD_ATTACH:
    	case DLL_THREAD_DETACH:
    	case DLL_PROCESS_DETACH:
    		break;
    	}
    	return TRUE;
    }
    
    LRESULT CALLBACK NewWndProc (HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam)
    {
    	static HWND			hButton;
    	switch(message)
    	{
    	case WM_COMMAND:
             if (lParam == (LPARAM)hButton)
    		 {
    		return 0;
    		 }
    		 else
    		 {
    		return CallWindowProcA((WNDPROC)p,hwnd, message,wParam, lParam);
    		 }
    	case WM_CREATE:
    		hButton = CreateWindowA("Button","OBJ", BS_PUSHBUTTON | WS_CHILD | WS_VISIBLE, 10, 20, 100,100,hWnd,NULL,((LPCREATESTRUCT) lParam) -> hInstance,NULL);
    		hWndI++;
    		return CallWindowProcA((WNDPROC)p,hwnd, message,wParam, lParam);
    	}
    
    	return CallWindowProcA((WNDPROC)p,hwnd, message,wParam, lParam);
    
    }
    

    Aber der Button will einfach nicht erscheinen 😞

    Was muss ich tun dass der Button sichtbar wird?
    MFG!



  • Probier mal UpdateWindow()



  • DU meinst so?:

    case WM_CREATE:
            hButton = CreateWindowA("Button","OBJ", BS_PUSHBUTTON | WS_CHILD | WS_VISIBLE, 10, 20, 100,100,hWnd,NULL,((LPCREATESTRUCT) lParam) -> hInstance,NULL);
            hWndI++;
    UpdateWindow(hWnd);
            return CallWindowProcA((WNDPROC)p,hwnd, message,wParam, lParam);
    

    Geht auch nicht 😞



  • An ein bereits exestieredes Fenster wird niemals WM_CREATE gesendet!
    Erstell den Button vor SetWindowLong().



  • Ok, aber wenn ich das so mache entsteht ein Fehler bei dem Parameter

    ((LPCREATESTRUCT) lParam) -> hInstance
    

    Wie kann ich das dann beheben?

    PS:

    switch (ul_reason_for_call)
    	{
    	case DLL_PROCESS_ATTACH:
    		hWnd = FindWindowA(0, "AceDB 2.0");
    		p = GetWindowLong(hWnd, GWL_WNDPROC);
    		hButton = CreateWindowA("Button","OBJ", BS_PUSHBUTTON | WS_CHILD | WS_VISIBLE, 10, 20, 100,100,hWnd,NULL,((LPCREATESTRUCT) lParam) -> hInstance,NULL);
    		SetWindowLongA(hWnd, GWL_WNDPROC, (long)NewWndProc);
    ...
    ...
    

    Ich denke du meinst an dieser Stelle.



  • hWnd+GetWindowLong+GWL_HINSTANCE



  • Ok, ich habe es jetzt so:

    static LONG h;
    
    h = GetWindowLong(hWnd, GWL_HINSTANCE);
    HWND hWnd = FindWindowA(0, "...");
    hButton = CreateWindowA("Button","OBJ", BS_PUSHBUTTON | WS_CHILD | WS_VISIBLE, 10, 20, 100,100,hWnd,NULL,(HINSTANCE)h,NULL);
    

    Funktioniert aber immernoch nicht... Der Button erscheint nicht 😞

    EDIT:

    Ich habe jetzt noch

    ShowWindow(hWnd, SW_SHOW);
    		ShowWindow(hButton, SW_SHOW);
    		UpdateWindow(hWnd);
    		UpdateWindow(hButton);
    

    drangehängt, wenn ich jetzt die DLL injiziere erscheint der Button für ca. ne halbe Sekunde und verschwindet wieder 😞



  • Weiß denn garniemand was ich tun muss dass der Button bleibt??



  • vieleich einfach das richtige Instance-Handle übergeben? Welches hWnd benutz du den mit GWL_HINSTANCE?



  • Ich hole mir das Handle von dem Programm, dann die Instanz und dann erstelle ich den Button:

    HWND hWnd = FindWindowA(0, "Programm");             //Handle
    LONG h = GetWindowLong(hWnd, GWL_HINSTANCE);        //Instanz
    hButton = CreateWindowA("Button","OBJ", BS_PUSHBUTTON | WS_CHILD | WS_VISIBLE, 10, 20, 100,100,hWnd,NULL,(HINSTANCE)h,NULL);
    


  • Hier ist der Fehler mal reproduziert:

    format PE GUI 4.0 DLL
    entry start
    
    include 'win32a.inc'
    
    section '.code' code readable executable
    
      start:
            cmp     byte [esp+8],DLL_PROCESS_ATTACH
            jnz     .fin
            push    0
            push    0
            push    0
            push    thread
            push    0
            push    0
            call    [CreateThread]
        .fin:
            mov     eax,1
            retn    0Ch
    
      thread:
            push    0
            push    _class
            call    [FindWindow]
            mov     edi,eax
    
            push    wndproc
            push    GWL_WNDPROC
            push    edi
            call    [SetWindowLongW]
            mov     [oldwndproc],eax
    
            push    GCL_HMODULE
            push    edi
            call    [GetClassLongW]
    
            push    eax
    
            push    0
            push    eax
            push    0
            push    edi
            push    18
            push    50
            push    4
            push    4
            push    WS_CHILD+WS_VISIBLE
            push    _xyz
            push    _button
            push    0
            call    [CreateWindowEx]
            mov     [hButton],eax
    
            push    eax
            call    [GetLastError]
            push    eax
            push    _fmt
            push    _buffer
            call    [wsprintf]
            add     esp,14h
            push    MB_OK
            push    0
            push    _buffer
            push    0
            call    [MessageBox]
    
            retn
    
    proc wndproc hwnd,msg,wparam,lparam
            cmp     [msg],WM_COMMAND
            jnz     .def
            ;mov     eax,[hButton]
            ;cmp     [lparam],eax
            ;jnz     .def
    
            cmp     word [wparam+2],BN_CLICKED
            jnz     .def
    
            push    [hButton]
            call    [IsWindow]
    
            push    eax
            push    _fmt2
            push    _buffer
            call    [wsprintf]
            add     esp,0Ch
            push    MB_OK
            push    0
            push    _buffer
            push    [hwnd]
            call    [MessageBox]
    
            xor     eax,eax
            jmp     .fin
    
        .def:
            push    [lparam]
            push    [wparam]
            push    [msg]
            push    [hwnd]
            push    [oldwndproc]
            call    [CallWindowProcW]
        .fin:
            ret
    endp
    
    section '.data' data readable writeable
    
      _title db '',0
      _class db 'Notepad',0
      _button db 'button',0
      _xyz db 'xyz',0
      _fmt db 'error: %d  button: %d  hinstance: %x',0
      _fmt2 db 'IsWindow: %d',0
      _buffer rb 255
      oldwndproc dd ?
      hButton dd ?
    
    section '.idata' import data readable
    
      library kernel32,'KERNEL32.DLL',\
              user32,'USER32.DLL'
    
      include 'api\kernel32.inc'
      include 'api\user32.inc'
    
    section '.reloc' fixups discardable
    

    mit FASM assemblieren und die Dll dann ins Notepad injizieren.
    Die erste MessageBox berichtet
    error: 0 button: 4462904 hinstance: 120000
    und die zweite
    IsWindow: 0

    Heisst also, dass CreateWindow zwar funktioniert, der Button erstellt wird und das Handle kurzzeitig valid ist, aber anscheinend unmittelbar danach dann nicht mehr



  • Hmm, aber wie kann das sein? Ich hab's doch als static erstellt 😮



  • Killur schrieb:

    Ich hab's doch als static erstellt 😮

    Killur schrieb:

    ...
    HWND hWnd = FindWindowA(0, "Programm");             //Handle
    ...
    

    Was, bitteschön, hast Du als static erstellt?
    Ich sehe da nix, aber ich sehe wo static erforderlich wäre 🙄
    Na, ist Dir ein Licht dabei aufgegangen? 💡

    HTH,
    Martin



  • Die DLL gehört mit eigener Instanz zur Anwendung. Jedenfalls im Datenbereich ist das so. Wenn du über die Daten hinaus in der Anwendung etwas veranlassen willst, empfiehlt sich eine userdefined Message mit SendMessage der DLL an die Anwendung. Dafür musst du der DLL das Handle HWND der Anwendung mitteilen.


  • Mod

    Dir ist klar, dass ein Fenster immer zu einem Thread gehört. Sobald Dein Thread aufhört zu existieren wird auch das Fenster vernichtet.

    Mit CreateRemoteThread kann es folgerichtig niemals klappen.
    Wie injiziert Du die DLL?



  • Killur schrieb:

    ...
    HWND hWnd = FindWindowA(0, "Programm");             //Handle
    ...
    

    Was, bitteschön, hast Du als static erstellt?
    Ich sehe da nix, aber ich sehe wo static erforderlich wäre 🙄
    Na, ist Dir ein Licht dabei aufgegangen? 💡

    HTH,
    Martin

    Bei mir siehts so aus:

    static HWND hWnd;
    ...
    ...
    hWnd = FindWindow....
    

    Ich injiziere die DLL wie in diesem Tutorial beschrieben:
    Klick

    Aber dort wird CreateRemoteThread benutzt.. Wie kann ich es ohne machen? Hat jmd ein Link zu einem guten Tutorial?


  • Mod

    Du kannst in keinem Fall CreateRemoteThread verwenden.
    Wie die Funktion schon sagt, es wird ein eigener Thread erzeugt und dieser müsste dann so lange leben wie Dein fenster und eine eigene Message-Loop haben.

    Du müsstest einen Hook verwenden, der dann im Threadkontext aufgerufen wird.
    z.B. WH_GETMESSAGE/WH_CALLWNDPROC etc.

    Werde Dir bitte erstmal klar, wie Fenster, Prozess und Threads in einem Windows System funktionieren.



  • Kannst du mir erklären wie ich das mit WH_GETMESSAGE mache?


  • Mod

    Nein. Das kann und will ich nicht. Warum auch (siehe unten).

    Siehe SetWindowsHook Doku:
    http://msdn.microsoft.com/en-us/library/ms644990(VS.85).aspx
    und mindestens 100 Beiträge dazu hier und woanders im Netz.

    Und es ist immer wieder toll was man so findet:
    http://lmgtfy.com/?q=wh_getmessage+sample

    Der zweite Link ist ein vollständiges Beispiel einer entsprechenden Injection incl. einer kompletten Beschreibung.
    Irrsinnig wie tief man im Netzt graben muss um zu finden was Du suchst, oder ? 🤡


Anmelden zum Antworten