2012-05-22 25 views
5

Quindi ho una DLL C++, che sto usando nella mia applicazione C#, per monitorare i messaggi di Windows. Voglio sapere se WM_CLOSE e WM_QUERYENDSESSION vengono inviati perché non riesco a vederlo da un'applicazione C#. Se ricevo uno di questi messaggi, voglio fare un po 'di pulizia con i miei file, ma il problema è che quando lo uccido con TM le funzioni non funzionano. Sembra che non ricevo i messaggi. Penso che il problema è che Task Manager invia un messaggio all'app C# e non alla DLL C++.Quale messaggio ricevo quando cancello il mio programma con il task manager

Alcuni Codice:

C++:

typedef void (*CLOSING_FUNCTION)(); 
CLOSING_FUNCTION myClosingFunction; 

typedef void (*SHUTDOWN_FUNCTION)(); 
SHUTDOWN_FUNCTION myShutdownFunction; 

LRESULT CALLBACK WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) 
{ 
    switch(message) 
    { 

    case WM_CREATE: 
     return 0; 

    case WM_CLOSE: 
     myClosingFunction(); 
     return 0; 

    case WM_QUERYENDSESSION: 
     myShutdownFunction(); 
     return 1; 

    case WM_DESTROY: 
     myClosingFunction(); 
     PostQuitMessage(0); 
     return 0; 
    } 

    return DefWindowProc(hwnd, message, wParam, lParam); 
} 

C#:

[UnmanagedFunctionPointer(CallingConvention.Cdecl)] 
private delegate void Close_Function(); 
private static Close_Function myCloseDelegate; 

[UnmanagedFunctionPointer(CallingConvention.Cdecl)] 
private delegate void Shutdown_Function(); 
private static Shutdown_Function myShutdownDelegate; 
static void StartMonotoring() 
{ 
     myCloseDelegate = Close; 
     myShutdownDelegate = Shutdown; 

     InterceptMessages(myCloseDelegate, myShutdownDelegate); 
} 

static void Close(); 
static void Shutdown(); 
+2

Si ottiene WM_CLOSE solo quando si utilizza la scheda Applicazioni in Gestione attività. Ucciderlo dalla scheda Processi è una conclusione maleducata. Il modo in cui il messaggio finisce nel codice C++ è molto poco chiaro, l'interfaccia utente è in genere eseguita in C#. –

+2

Oppure riceverai un evento 'CTRL_CLOSE_EVENT' nelle applicazioni della console. Collegamento obbligatorio al precedente oggetto precedente [post di blog] (http://blogs.msdn.com/b/oldnewthing/archive/2004/07/22/191123.aspx) –

risposta

3

Il vostro processo non sarà possibile ottenere alcun messaggio nel caso in cui se viene ucciso. Avviare TerminateProcess - vedere il mio highlight:

La funzione TerminateProcess viene utilizzata per causare incondizionatamente l'uscita di un processo. Lo stato dei dati globali gestiti da librerie a collegamento dinamico (DLL) può essere compromesso se viene utilizzato TerminateProcess anziché ExitProcess.

Questa funzione interrompe l'esecuzione di tutte le discussioni all'interno del processo e richiede la cancellazione di tutte le richieste di I O ...

EDIT /: Hans Passant commento su compiti modo terminato - si ottiene solo quando si utilizza WM_CLOSE la scheda Applicazioni nel task manager. Ucciderlo dalla scheda Processi è una terminazione maleducata (TerminateProcess).

+0

E in caso di arresto avviato WM_QUERYENDSESSION? – Thanatos

+1

si. Nota a margine sul task manager: penso che ci siano (erano?) Casi in cui il task manager tenta di arrestare correttamente il processo prima di terminare, ma mi aspetterei che TerminateProcess sia usato in processo se è importante per te. –

+0

Allora sai un modo per scoprire se l'arresto è stato avviato usando C#? in Winapi ho usato la queryendsesion ma qui? – Thanatos

Problemi correlati