Here is the scenario.
I am on windows 8 Machine/ Also have tried this on windows 7 machine.
I working on a driver(mirror driver/Remote display Driver). I should say I am going to start working on it as I am stuck.
So I followed the MSDN example of KmdfSmall
http://msdn.microsoft.com/en-us/library/windows/hardware/hh439665(v=vs.85).aspx
I got the driver code compiled. Got the remote debugging also going.
I do not see any of the debug messages on the host( I have set the register IHVDRIVER to 0x8
I also set the DEFAULT to 0xf to be able to use DbgPrint
Further more. My real goal is start my driver as a service
http://www.codeproject.com/Articles/9504/Driver-Development-Part-1-Introduction-to-Drivers
And I want to test it on the LOCAL machine. I do not want to have a target and host to debug. Plain oldschool single machine.
Questions
1) When service starts the driver via CreateService and OpenService, does it call the DriverEntry function or does it wait until someone user level app uses the driver.
2) When I run the app to load the driver as a server where would the DbgPrintEx suppose to print
DebugView or WinDbg or else where.
3) If I am using
CreateService
does my sys file has to be in windows/system32/drivers folder ? I read somewhere that in 64 bit machine CreateService only loads from system folder.
4) when I start it as a service am I suppose to see it on the task Manager
5)If DriverEntry is called to init a driver, can it be called again or it has to wait until it unloads ? So I load my driver and forget to gracefully unload it and run my program again will it call DriverEntry ?
I know there are a lot of questions here. Thanks in advance
KMDF driver cannot be installed using old style API. Check this sample from MSDN.
You also need to think about what kind of driver it is, filter driver or actual device driver etc.
1) When service starts the driver via CreateService and OpenService,
does it call the DriverEntry function or does it wait until someone
user level app uses the driver.
As soon as the driver is loaded, its DriverEntry routine is called.
2) When I run the app to load the driver as a server where would the
DbgPrintEx suppose to print DebugView or WinDbg or else where.
When none of DebugView or WinDbg is running, the output is lost and not printed/logged anywhere.
3) If I am using CreateService does my sys file has to be in windows/system32/drivers
folder ? I read somewhere that in 64 bit machine CreateService only
loads from system folder.
Newer windows has such kind of restriction.
4) when I start it as a service am I suppose to see it on the task
Manager
Kernel drivers are not listed in task manager as they are actually part of OS not a separate application. However, if you have user level service, it will be listed in task manager when its running.
5)If DriverEntry is called to init a driver, can it be called again or
it has to wait until it unloads ? So I load my driver and forget to
gracefully unload it and run my program again will it call DriverEntry ?
DriverEntry is called each time the driver is loaded. If the driver is demand load, it will run each time the driver is loaded/started, even if driver does not unload gracefully (e.g. leaking memory/locks etc). But you may end up in unstable system and BSOD if driver doesn't unload neatly.
Related
I have a custom windows kernel driver I have compiled. I sign it with a test cert, create the cat file from the cdf, stamp the inx into a inf file, then load it with pnputil. I then create a software device with SwDeviceCreate so the OS will pair my driver and the driver. This works fine.
The problem is if i screw up something in the compilation and get something like an error code 39 (viewable in device manager), I do not see that error. Instead the OS seems to try to fix the error by loading the previously working version of the driver. In order to see that error, I have to purge the driver and device using pnputil /d oem42.inf along with a pnputil /remove-device, then restart my PC, that seems to fix the issue. This is difficult because it means i have to restart my PC every time i run a test. I know crashing a kernel driver can cause a panic anyway and cause me to restart, but there seems to be instances where this is not the case and the OS tries to rectify the issue without me (as it probably should).
So my question is this. Is there a way to completely purge my driver without a complete restart in-between installations/tests so I can correctly break it. I know I am suppose to use another machine and remote debug kernel drivers, but i do not have access to another machine right now that can support windows 11.
I've added some code to the Windows Filtering Platform MSNMNTR sample for my own application, but it still has the same structure. I've compiled the driver and the application for Win8 64-bit and production-signed the driver. On the (virtual) machine that I built the code on, the sample works fine and monitors correctly. When I copy the inf, sys and exe to another machine, the sample does NOT monitor. Through traceview output, I can see that on the second machine, DriverEntry() is not called, therefore the flow controls are never set up. The two machines are running the release version of Win8. It doesn't appear to be an issue with my new code, since the driver works fine on machine #1, and it doesn't appear to be a signature problem because when I turn off signature enforcement on machine #2 I still have the problem. Both the release and debug versions of the code have the same issue. The steps I use to set up and run the code are below. What are some things that might cause this behavior?
Copy driver .pdbs to a folder for traceview.
Right-click .inf and choose "Install"
Run "net start msnmntr" from an elevated command prompt.
Start traceview as administrator.
Run "monitor monitor "C:\Program Files\Internet Explorer\iexplore.exe"" from an elevated command prompt.
P.S. I haven't put windbg on this yet, but I will update the question with the results as soon as I try it.
Edited to add: OK, I ran the kernel-mode debugger on both machines and saw a difference in behavior. First of all, DriverEntry does get called on both machines. I was mistaken about that. However, on the machine where the code works (i.e. monitors web traffic) DriverEntry gets called when monitor.exe is run (step 5 above), and on the machine where the code does not work DriverEntry gets called when "net start msnmntr" (step 3 above) is executed.
The problem was that I had not installed the callouts via "monitor addcallouts" on the second machine. Since this is a one-time step, I had forgotten I did it weeks ago on the original machine.
Given that unloading a file system filter driver requires a reboot, what is the best way to test one?
Is there a better/less painful way than rebooting a VM every single time?
This might be helpful: File System Filter Driver Tutorial
Set driver unload routine
The last part of the driver initialization sets an unload routine.
Setting the driver unload routine makes the driver unloadable, and you
can load/unload it multiple times without system restart. However,
this driver is made unloadable only for debugging purpose, because
file system filters can’t be unloaded safely. Never do this in
production code.
I am writing a driver (legacy I believe) that creates a virtual hard drive from a file, however when I try to unload my driver some times it and most times it hangs. The driver unloads cleanly if it hasn't received any irps yet but as soon as it does I can't unload it. have read that the unload routine isn't called unless the driver has nothing referencing it. I believe there may be another driver(a file system driver) referencing it however I don't know which driver it is. How can I see if my driver is getting referenced and if so how can i stop that driver from referencing mine?
Check the "HandleCount" and "PointerCount" of your driver's "DriverObject" and "DeviceObject" using windbg.
Useful Windbg commands are: !drvobj and !devobj.
Is there a way to create a user-mode process from kernel-mode on Windows NT platform (XP-W7)?
EDIT: I must install only the driver. This is a specific of the project.
To create a valid win32 process the driver must communicate with CSRSS (what is completely undocumented). So I ended up by queuing a user-mode APC and allocating virtual memory for the APC code in the context of the existing win32 process (that code will call CreateProcess and do the job).
It is a tricky way but it works.
I don't know an easier way to achieve this. But what about having a Windows service running which makes an overlapped DeviceIoControl into your driver? On return the service could examine the data it has received from the driver and start the according application.
This can't be directly done - Creating a win32 process requires some set up by the user mode part of CreateProcess, not just creating the process object in kernel mode.
You need some user mode code here - either a service, a desktop app, or so on, to launch the your user mode application.