Windows System Software -- Consulting, Training, Development -- Unique Expertise, Guaranteed Results
The free OSR Learning Library has more than 50 articles on a wide variety of topics about writing and debugging device drivers and Minifilters. From introductory level to advanced. All the articles have been recently reviewed and updated, and are written using the clear and definitive style you've come to expect from OSR over the years.
Check out The OSR Learning Library at: https://www.osr.com/osr-learning-library/
I created 4 events for DeviceIoControl() and wait for it with WaitForMultipleObjects() function.
But this last function does not return. It remains in the non-signaled state. I read that when calling CreateEventA () you need to assign the access right "SYNCHRONIZE".
Can anyone help me how to assign the "SYNCHRONIZE" access right to the CreateEventA() security descriptor.
And the second question.
Do I need to call GetOverlappedResult() after WaitForMultipleObjects()
Upcoming OSR Seminars | ||
---|---|---|
OSR has suspended in-person seminars due to the Covid-19 outbreak. But, don't miss your training! Attend via the internet instead! | ||
Internals & Software Drivers | 19-23 June 2023 | Live, Online |
Writing WDF Drivers | 10-14 July 2023 | Live, Online |
Kernel Debugging | 16-20 October 2023 | Live, Online |
Developing Minifilters | 13-17 November 2023 | Live, Online |
Comments
There is not nearly enough information here. So, you created 4 events. Did you then store those events in 4 OVERLAPPED structures, and submit 4 DeviceIoControl calls using those structures? Did you open the file with FILE_FLAG_OVERLAPPED? What does the WaitForMultipleObjects call look like? Are these calls going to your own driver? You're sure the requests are being completed?
Check the documentation. CreateEvent, by default, uses EVENT_ALL_ACCESS access rights, which includes SYNCHRONIZE.
Yes, after WFMO returns, you must call GetOverlappedResult. Otherwise, you have no idea whether the request succeeded or failed.
Tim Roberts, [email protected]
Providenza & Boekelheide, Inc.
Thank you. Yes, everything you said, I did, and it works correctly. Yes indeed SYNCHRONIZATION was assigned by default. As for GetOverlappedResult, the program works without it. I can not understand why, but I'll add it. WaitForMultipleObjects returns, when one or more events are signaled. And after it, when I check output buffer from overlapped DeviceIoControl, it is correct. How can I understand, WaitForMultipleObjects and GetOverlappedResult functions are for the same purpose.
Yes, it works without GetOverlappedResult, but without it, you don't know whether the requests succeeded or not. That's not very good practice.
Tim Roberts, [email protected]
Providenza & Boekelheide, Inc.
OK.
The GetOverlappedResult function exists to extract values from the Internal and InternalHigh members of the OVERLAPPED struct. The usage of these members has become so well know, that Microsoft have even documented them so that they can be used directly. But it is still appropriate to use GetOverlappedResult because there is no reason not to do it properly
Thanks. Mr. Bond.
Where to put GetOverlappedResult. It is working fine without GetOverlappedResult.
As the first thing in the "WAIT_OBJECT_0" case. As we've said before, if you don't do that, you don't know if the request actually succeeded.
Tim Roberts, [email protected]
Providenza & Boekelheide, Inc.
Thank You very much. Mr. Tim_Robers. I will think about it.
Mr Tim_Robers. I finished the driver. It works well. But there is a nuance. Installs fine.
Change adapter settings->Ethernet->Properties->Install->Service->choose my driver
But when I try to uninstall the driver it hangs. How to understand why? Maybe I let some garbage in (not freed memory or not completed Irp. I don’t know). Please help me understand. What tools should I use to find out what the problem is
And the second question. As I said, I've been getting DPC_WATCHDOG_VIOLATION when using NdisFSendNetBufferLists() in a driver dispatch routine (a single DPC or ISR has exceeded its time limit. The offending component can usually be identified with a stack trace).
After I raised Irql before NdisFSendNetBufferLists() and lowered it after it in the dispatch procedure(level 0). And the problem is gone. Is this a good decision. Thank you
In my program, two times I make large copies. One from the outgoing payload buffer to the IRP buffer, and the second from the IRP buffer to the outgoing payload buffer. whether to think about DMA. Can I use DMA instead of NdisMoveMemory()?
Is the driver still in use when it hangs? Have you run this in a debugger to find out what's going on?
The average driver should not be dinking with IRQLs at all. Why do you have to be at dispatch? Is it strictly for using spin locks? Perhaps you should use some other kind of synchronization. A watchdog violation can only happen if you spend too much time at an elevated IRQL.
Not for memory-to-memory moves. DMA refers to having a PCI or PCIe device do the transfers.
(Pedants will note that there now IS a system DMA facility available on some chipsets. I discount that, because (a) it's not available on most computers, and (b) it is a limited resource and therefore cannot be relied on.)
Tim Roberts, [email protected]
Providenza & Boekelheide, Inc.
Thank you Mr. Tim_Roberts.
Well, that's simply not right. There are essentially NO scenarios in which a driver should call KeRaiseIrql or KeLowerIrql. FILTER_ACQUIRE_LOCK will raise the IRQL for you, if it's not there already, but there's no reason why you should need to when you call NdisFSendNetBufferLists. The right answer is to figure out where your crashes are coming from, not randomly patch them.
Tim Roberts, [email protected]
Providenza & Boekelheide, Inc.
Well. Thank You Mr. Tim_Roberts.
you should call GetOverlappedResult in your switch case statement in the WAIT_OBJECT_0 case. Or possibly the CallConvert function
KeRaiseIrql may appear to solve your problem, but likely it just masks an underlying problem
Yes. Thank You Mr. MBond2
Mr Mbond2. I took a close look at WaitForSingleObject and GetOverlappedResult. I think they are the same and when you use WaitForSingleObject there is no need to use GetOverlappedResult. I'm sorry, but if I'm wrong, please explain why you should use GetOverlappedResult.
And second.
You say "Or perhaps the CallConvert KeRaiseIrql function could solve your problem, but it's more likely just masking the underlying problem."
The xxxDeviceIoControl function is a driver dispatch function, but CallConvert is in a user mode program. They are not related to each other. And in this program I have no problems. My question was about KeRaiseIrql but Mr. Tim_Roberts explained to me.
Thank You.
Because if you don't, you have no way of knowing whether the request succeeded or failed. It is the the same as calling an API and ignoring its result.
Tim Roberts, [email protected]
Providenza & Boekelheide, Inc.
you should call GetOverlappedResult or inspect the now documented members of the OVERLAPPED struct to determine the result of your request
Thanks
Mr. Tim_Roberts and Mr. MBond2. What do you think. Will writing the driver in assembly language (instead of C) will increase the performance?. In 1995 we compared and got about 1.5 (Turbo C and assembler).
Now on my computer I have about 27 for upload and the same for download without my driver. When I push my filter driver into the network stack it is 26.26. It's good or try to write on assembler.
No. Optimizing compilers have improved to the point that they can outperform all but the most elite assembler experts. I consider myself to be an expert, but I haven't written an assembler module in more than a decade.
Tim Roberts, [email protected]
Providenza & Boekelheide, Inc.
if your code is expected to run on one specific hardware configuration, and you have a LOT of time on your hands, you might be able to hand craft assembly code that out performs the MSVC emitted code. But you need both the certainty of the hardware platform and the sublime skill of a savant to do better. And even if you do, it will not represent an order of magnitude gain, but at most a few percentage points
Certianty of hardware is a VERY important factor. Hardly anyone ever has this. Aerospace and medical applications might, but any commodity hardware never does. And the averages built into optimizers are usually better than hand crafted solutions - especially since the hardware guys optimize the hardware for the commonly emitted patterns
Thank You Mr. Tim_Roberts and Mr. MBond2. I've stopped thinking about writing a driver in a lower level language and will try to write a driver for a USB "data converter" to call it from the NDIS Filter driver, instead of sending the data to the user mode and calling the convert function on the USB device there. I think, it will increase performance significantly.