kerpow1 wrote:Hi, I am trying to list all ways a driver could be located on the system, so far;
ZwQuerySystemInformation
EnumDeviceDrivers
QueryDosDevice
GetDeviceDriverFileName
Discuss
If you mean loaded drivers then it is
NtQuerySystemInformation. PSAPI uses it.
QueryDosDevice is used for symbolic links that driver may not have. SCM maintain it own database in the user mode. Driver and device object names can be quered through
NtQueryDirectoryObject.
If your plan is hiding your driver then look on Sirefef 2010 edition which uses
ObMakeTemporaryObject on it device object to hide presence from object directory and look on TDL3 which utilises more advanced hiding. Best approach - do not use a driver loaded list, symbolic links and device/driver objects. Load your driver, allocate memory and copy payload executive part on it, call it and after this unload your driver. To exchange data and commands between user mode and your piece of kernel code - use section with on the fly session generated name. If your driver uses hooking (splice or simple address change in some kernel structures) - use a small callgates inside available loaded drivers (see Rustock.B as example) to fool simple dump/compare scan. I would also suggest a dynamic relocation of your piece of code -> for example your rootkit worked for a few minutes and then it relocated itself to a new memory address, removing footprints. To survive reboot/reset - install yourself in registry under randomly named entry. Your software should handle the situation when your rootkit is already loaded -> for example check presence of communication channel. Rootkit should be able to unload itself by request. Unloading drivers is unsafe, unloading rootkits is x2 unsafe. Remember that everything this is a perversion and BSOD-generation friendly.