How to catch Terminate Process in my Application with MadCod

c++ / delphi package - dll injection and api hooking
cool_tester
Posts: 75
Joined: Sun Oct 31, 2004 5:45 am

How to catch Terminate Process in my Application with MadCod

Post by cool_tester »

Hello there,
i have an EXE in Delphi that installs a Hook using a DLL, now my problem is that when i terminate the Application trough Task Manager, using End Process the application terminates without doing any Cleaning, basically Destroy Form is never called.... nor finalization, which causes problems when i try to restart the application, is there anyway to catch the destroy of my application so i can clean up.... though about the terminate process dll that comes with MadCodeHook but that an over kill since I'm only interested in catching my own application termination, so can that be adapted to one application?

Thanks.
madshi
Site Admin
Posts: 10764
Joined: Sun Mar 21, 2004 5:25 pm

Post by madshi »

The problem is that *any* running process could theoretically call TerminateProcess on your process. In this specific case (namely "end process" in the taskmanager) it happens to be the taskmanager.

If you are satisfied with only blocking "end task" of the taskmanager then you need to hook TerminateProcess/NtTerminateProcess in the context of the taskmanager. If you want to go the safe way and hook all running apps, you need all the power of the HookProcessTermination madCodeHook demo. If you are satisfied with only hooking the taskmanager you still have the problem that you must find out when it is started. In that moment you have to inject your hook dll into it.
Runner
Posts: 90
Joined: Tue Dec 14, 2004 1:04 pm

Post by Runner »

Just curious, I had similar problem but with ddls. When my aplication, that loaded the system wide keyboard hook, was terminated the hook dll stayed in memory and was still active. Is there a way to clean up the dlls from another aplication in any way?
madshi
Site Admin
Posts: 10764
Joined: Sun Mar 21, 2004 5:25 pm

Post by madshi »

When using SetWindowsHookEx with WH_GETMESSAGE you can use PostMessage(HWND_BROADCAST, WM_NULL, 0, 0) to get rid of the dlls. Not sure about how to "flush" the dlls for keyboard hooks, though.

You could try using madCodeHook's UninjectLibrary, but I'm not sure whether SetWindowsHookEx would really like that.
Runner
Posts: 90
Joined: Tue Dec 14, 2004 1:04 pm

Post by Runner »

I will try it out. Thanks :D
cool_tester
Posts: 75
Joined: Sun Oct 31, 2004 5:45 am

Post by cool_tester »

Well the problem is when someone terminates the application let's say by ysing Task Manager and end process, my application doesn't receive any messages, indicating that it is being shut down, so how can it broadcast messages if it doesn't know it is being killed? or do you know what message code Task Manager sends to the application when it ends it? i tried to listen to WM_Destroy with no luck....


To Runner:
here is a function that will unload a dll from memory:

Code: Select all

function KillDll(aDllName: string): Boolean; 
var
  hDLL: THandle;
  aName: array[0..10] of char;
  FoundDLL: Boolean;
begin
  StrPCopy(aName, aDllName);
  FoundDLL := False;
  repeat
    hDLL := GetModuleHandle(aName);
    if hDLL = 0 then
      Break;
    FoundDLL := True;
    FreeLibrary(hDLL);
  until False;
  if FoundDLL then
   result := true
    //MessageDlg('Success!', mtInformation, [mbOK], 0)
  else
   result := false;
    //MessageDlg('DLL not found!', mtInformation, [mbOK], 0);
end;
madshi
Site Admin
Posts: 10764
Joined: Sun Mar 21, 2004 5:25 pm

Post by madshi »

There's no message at all when the Task Manager uses "end process". It just calls TerminateProcess, which will leave your application no chance to react.
cool_tester
Posts: 75
Joined: Sun Oct 31, 2004 5:45 am

Post by cool_tester »

What a brilliant idea from Microsoft.. hummmm i wonder what was really going on in their heads when they decided to do that?????
madshi
Site Admin
Posts: 10764
Joined: Sun Mar 21, 2004 5:25 pm

Post by madshi »

Well, that feature to "end process" is meant for deadlocked processes mainly. If the API would try to contact such a process before shutting it down, there'd only be senseless delay. TerminateProcess is intended to not contact the process before shutting it down, and it is documented to behave that way. I think every OS needs such a strict API, otherwise there'd be no chance to kill a crashed/deadlocked process.
cool_tester
Posts: 75
Joined: Sun Oct 31, 2004 5:45 am

Post by cool_tester »

That's true, but i think they could have given it a simple time frame for the application to response, and if it doesn't then kill it, kind of like what WMQueryEndSession Does..... oh well i'm sure there is a good reason for it to be there. and indead it does come in handy every now and then...
linden
Posts: 36
Joined: Tue Mar 08, 2005 9:17 am
Location: Japan

Post by linden »

Well, there is a way to prevent your app from being terminated. You can write a kernel mode driver and hook ZwOpenProcess() by patching the ServiceDescriptorTable. Then, tell your driver about which process ID you would like to protect, and then supervise for that process ID in the hook callback function for ZwOpenProcess(); return ACCESS_DENIED if the process ID is that of the protected application. This way, you can stop ALL attempts to terminate your application.

That was the easiest way. But if there is a need for other apps to open a handle to your process, then hook ZwTerminateProcess() instead of ZwOpenProcess(). The coding is going to be a bit more complicated though.
madshi
Site Admin
Posts: 10764
Joined: Sun Mar 21, 2004 5:25 pm

Post by madshi »

Yeah, linden is right. However: You can hook those mentioned APIs either in kernel mode and in application land. Of course hooking them in kernel mode is more effective, but it's also more difficult to do. Hooking them in application land it easier (by using madCodeHook at least), and that's exactly what the HookProcessTermination demo does which is shipping with madCodeHook.
cool_tester
Posts: 75
Joined: Sun Oct 31, 2004 5:45 am

Post by cool_tester »

Thanks linden for the info, well i'm not really trying to prevent it from terminating but i just want to catch the TerminateProcess when it is send to my application so i can do some cleaning, but i understand what you are saying, unfortunatly i never did any kernel mode driver coding in delphi. Can you even use delphi to write kernel mode drivers?

madshi i just think it's an over kill to install a system wide hook just so i can have a clean shut down of my application... but i guess that is the only way.
madshi
Site Admin
Posts: 10764
Joined: Sun Mar 21, 2004 5:25 pm

Post by madshi »

Yeah, probably it's overkill. You should try to get along without it, if possible.
hexa
Posts: 3
Joined: Tue Apr 19, 2005 12:11 pm

Post by hexa »

The HookProcessTermination demo seems to be "vulnerable" to EndItAll 2. I don't understand how can EndItAll shut down the demo's process when the hook is in place... :o
Post Reply