I was thinking about a solution to hook a function in DLL, so I'll be able to detect function invocation from any user-land process or a service. The functions are part of a custom DLL which basically have send/recv functions (that I would like to hook), which send something to the server on the Internet and recv a response from the server.
There are a number of techniques I could use including the following:
- AppInit_DLLs: I could inject a DLL into every process depending upon user32.dll, and then go through a list of imported function to see whether the desired function from a specific module gets loaded. This option has a few disadvantages, because it won't detect if the function is called dynamically inside a process. Also, the DLL won't be injected into processes not using user32.dll.
- Starting Own Processes: we can start the process inside a debugger or some other master process, but I also want to detect processes when being controlled by the user: if a user invokes a program from Desktop (but also when he writes a cronjob that starts a process using this function)
- Hooking All Processes: we can hook all of the user-mode functions, so we'll be able to control the process creation at which point we can inject an additional DLL into every process that basically checks for the presence of a function call.
- Hooking System Processes: I could hook the privileged user-mode system processes like csrss.exe process by hooking the CsrCreateProcess function (exported by csrsrv.dll) where the process gets created. At this point I could inject a DLL into every process being started which would check for the function call.
- Hooking EAT: I don't want to use this technique as it would require me to change the DLL; I don't want to change the DLL, but want the solution to work seamlessly.
- Kernel Driver: I know this is the best solution, but I would like to stay in the user-mode; I have administrative privileges in user-mode, so that should be enough to do what I want/need.
- IFEO: only works for executables, but not DLLs; if I want this to work, I would need to know the name of the process beforehand, as I can only hook DLL loading of a process which has BeingDebugged in PEB set to 1 (the IsDebuggerPresent returns true - this isn't true when a user clicks on a program in the Desktop, since it wasn't started under a debugger).
- Windows Filtering Platform: I could scan for network packets with WFP, but I'm not sure whether this would work in real-time. The process could be alive for a really short time, so I could miss the opportunity to hook it before it's done executing. I'm guessing with WFP I could only scan Application/Transport/Internet OSI layer, which would require me to know the exact server hostname/IP where the process sends data and receives data from. Let me know if I'm mistaken on this?
If somebody knows of a better way please let me know.