Driver Problems? Questions? Issues?
Put OSR's experience to work for you! Contact us for assistance with:
  • Creating the right design for your requirements
  • Reviewing your existing driver code
  • Analyzing driver reliability/performance issues
  • Custom training mixed with consulting and focused directly on your specific areas of interest/concern.
Check us out. OSR, the Windows driver experts.

Monthly Seminars at OSR Headquarters

East Coast USA
Windows Internals and SW Drivers, Dulles (Sterling) VA, 13 November 2017

Kernel Debugging & Crash Analysis for Windows, Nashua (Amherst) NH, 4 December 2017

Writing WDF Drivers I: Core Concepts, Nashua (Amherst) NH, 8 January 2018

WDF Drivers II: Advanced Implementation Techniques, Nashua (Amherst) NH, 15 January 2018


Go Back   OSR Online Lists > ntdev
Welcome, Guest
You must login to post to this list
  Message 1 of 28  
12 Sep 17 09:13
jolyon wright
xxxxxx@gmail.com
Join Date: 18 Oct 2013
Posts To This List: 12
multiple spinlocks and KeLowerIrql()... really?!

I have a pair of spinlocks and am hoping for some clarification of whether this is correct/ safe. Is this a normalish idiom for dealing with multiple spinlocks?... it seems a bit offbeat to me... hm KIRQL irqlOnEntry = KeGetCurrentIrql(); WdfSpinLockAcquire(Lock1); WdfSpinLockAcquire(Lock2); DoSomethingRequiringLock1And2Held(); WdfSpinLockRelease(1); // now at irqlOnEntry // is it ok to lower irql by side effect while we are holding Lock2? DoSomethingRequiringLock2Held(); WdfSpinLockRelease(Lock2); // now at dispatch because that was the irql when we acquired // but we need to restore the orignal, original irql KeLowerIrql(irqlOnEntry); // shudder! return;
  Message 2 of 28  
12 Sep 17 10:09
Mark Roddy
xxxxxx@gmail.com
Join Date: 25 Feb 2000
Posts To This List: 4019
multiple spinlocks and KeLowerIrql()... really?!

As WdfSpinLockAcquire is really just a thin wrapper around KeAcquireSpinlock (and same for lockrelease) I would use the legacy interfaces here to do the right thing with respect to irql levels. This assumes that for other reasons you need the lock order to be 1..2 rather than 2..1. Mark Roddy On Tue, Sep 12, 2017 at 9:12 AM, xxxxx@gmail.com < xxxxx@lists.osr.com> wrote: > I have a pair of spinlocks and am hoping for some clarification of whether > this is correct/ safe. Is this a normalish idiom for dealing with multiple > spinlocks?... it seems a bit offbeat to me... hm > > KIRQL irqlOnEntry = KeGetCurrentIrql(); > > WdfSpinLockAcquire(Lock1); > WdfSpinLockAcquire(Lock2); > DoSomethingRequiringLock1And2Held(); > <...excess quoted lines suppressed...> --
  Message 3 of 28  
12 Sep 17 10:25
jolyon wright
xxxxxx@gmail.com
Join Date: 18 Oct 2013
Posts To This List: 12
multiple spinlocks and KeLowerIrql()... really?!

Thanks Mark - I did consider this; but the documentation for KeReleaseSpinLock says I must supply the IRQL returned from the associated call to AcquireSpinLock; humph -- A colleague came up with the novel suggestion of a third spinlock to "scope" the other two ie the IRQL would be correct in my snippet and releasing the third one would restore IRQL correctly. I need a big black cup of coffee to decide whether this is brilliant or whether it is a large sledge hammer to crack a small nut :) jolyon
  Message 4 of 28  
12 Sep 17 10:42
Jan Bottorff
xxxxxx@pmatrix.com
Join Date: 16 Apr 2013
Posts To This List: 394
multiple spinlocks and KeLowerIrql()... really?!

That will be bad, as when you release Lock1, you return to the IRQL things = were at before acquiring Lock1, which may be PASSIVE_LEVEL. If you then jus= t dropped to PASSIVE_LEVEL, you are executing with Lock2 held while at PASS= IVE_LEVE. Let's then say a DPC fires, interrupting you code at PASSIVE_LEV= EL, that holds Lock2, and that DPC tried to acquire Lock2. Your system is n= ow deadlocked, as the DPC can't acquire Lock2, and the PASSIVE_LEVEL thread= will stay interrupted by the DPC, so is never able to release Lock2. A workaround could be to manually raise the IRQL to DISPATCH_LEVEL before a= cquiring Lock1. Adding a third spinlock around everything will indirectly guarantee you acq= uire Lock1 and Lock2 at DISPATCH_LEVEL, assuring both Lock1 and Lock2 relea= se to the same IRQL, so you can keep using the KMDF lock APIs. I usually try really hard to keep locks very consistent, as having lock spe= cial cases just makes future maintenance more error prone. Jan -----Original Message----- From: xxxxx@lists.osr.com [mailto:bounce-637766-145174@lists= .osr.com] On Behalf Of xxxxx@gmail.com xxxxx@lists.osr.com Sent: Tuesday, September 12, 2017 6:12 AM To: Windows System Software Devs Interest List <xxxxx@lists.osr.com> Subject: [ntdev] multiple spinlocks and KeLowerIrql()... really?! I have a pair of spinlocks and am hoping for some clarification of whether = this is correct/ safe. Is this a normalish idiom for dealing with multiple = spinlocks?... it seems a bit offbeat to me... hm KIRQL irqlOnEntry =3D KeGetCurrentIrql(); WdfSpinLockAcquire(Lock1); WdfSpinLockAcquire(Lock2); DoSomethingRequiringLock1And2Held(); WdfSpinLockRelease(1); // now at irqlOnEntry // is it ok to lower irql by side effect while we are holding Lock2? DoSomethingRequiringLock2Held(); =20 WdfSpinLockRelease(Lock2); // now at dispatch because that was the irql when we acquired // but we need to restore the orignal, original irql KeLowerIrql(irqlOnEntry); // shudder! return; --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=3Dnt= dev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and softwar= e drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.= osronline.com/page.cfm?name=3DListServer>
  Message 5 of 28  
12 Sep 17 10:50
W. D.
xxxxxx@gmail.com
Join Date: 12 Oct 2017
Posts To This List: 40
multiple spinlocks and KeLowerIrql()... really?!

Yes, you should release locks in the reverse order. As Jan said, if lock 1 is acquired at passive level and if you release lock 1 before lock 2 then you will hold lock 2 at passive level which is a fatal error. Look at KeLowerIrql's documentation, you have: "It is a fatal error to call KeLowerIrql using an input NewIrql that was not returned by the immediately preceding call to KeRaiseIrql". I don't know if this code passes Static Driver Verifier analysis but you should test it.
  Message 6 of 28  
12 Sep 17 10:50
Alex Grig
xxxxxx@broadcom.com
Join Date: 14 Apr 2008
Posts To This List: 3218
multiple spinlocks and KeLowerIrql()... really?!

What you should do is raise IRQL to DISPATCH_LEVEL on entry, and lower it back on exit. Then IRQL will be consistent. You'll also be able to use a bit faster variants of spinlock calls which don't do IRQL change.
  Message 7 of 28  
12 Sep 17 11:36
jolyon wright
xxxxxx@gmail.com
Join Date: 18 Oct 2013
Posts To This List: 12
multiple spinlocks and KeLowerIrql()... really?!

thanks for your thoughts folks - I am playing with the Spinlock Three idea which is currently looking good... I figure that anything is better than directly manipulating IRQL... even juggling another spinlock! The reason for the release order is dictated by another part of the code - I am trying to avoid deadlock and excessive changes to existing code I am in error prone maintenance mode :) today anyway - tomorrow, of course, i will be in everything works like a charm mode (ho ho) thanks again, jolyon
  Message 8 of 28  
12 Sep 17 11:48
Phil Barila
xxxxxx@logrhythm.com
Join Date: 07 Feb 2012
Posts To This List: 118
multiple spinlocks and KeLowerIrql()... really?!

> -----Original Message----- > Sent: Tuesday, September 12, 2017 9:35 AM > Subject: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! >=20 > thanks for your thoughts folks - I am playing with the Spinlock Three ide= a > which is currently looking good... I figure that anything is better than > directly manipulating IRQL... even juggling another spinlock! >=20 > The reason for the release order is dictated by another part of the code = - > I am trying to avoid deadlock and excessive changes to existing code If you don't wrap every reference to locks 1 and/or 2 inside 3, you still r= un the risk of deadlock. Either always release in reverse order, or just use one lock. Anything els= e is a partially loaded revolver. Phil Not speaking for LogRhythm=20 Philip D Barila=20 Senior Software Engineer=20 720.881.5364 (W) =A0=20 LogRhythm.com=20 =A0 =A0 =A0 =A0
  Message 9 of 28  
12 Sep 17 12:40
Peter Viscarola (OSR)
xxxxxx@osr.com
Join Date:
Posts To This List: 5949
List Moderator
multiple spinlocks and KeLowerIrql()... really?!

<quote> Thanks Mark - I did consider this; but the documentation for KeReleaseSpinLock says I must supply the IRQL returned from the associated call to AcquireSpinLock; humph -- A colleague came up with the novel suggestion of a third spinlock to "scope" the other two </quote> If the documentation says that, it's mistaken and needs fixed. It is very silly to use an additional spin lock in this case. Your choices to me are clear: a) Do as Mr. Roddy suggests. This works, it's always worked, and always will work. If the documentation suggests otherwise, file a bug. b) Always release the spin locks in the inverse order that you acquire them. Option A, above, has the advantage of being more technically concise. But it requires you write a lot of comments to explain what you're doing. In my experience, when you quick read (correct) code that implements option A, it LOOKS like a bug... so you'll need to excessively comment your actions. Option B, above, has the advantage of being instantly understandable during maintenance. But it has the disadvantage of being somewhat less efficient. All things considered, unless the efficiencies gained by Option A are significant enough to outweigh the disadvantages, just bite the bullet and go with Option B. Peter OSR @OSRDrivers
  Message 10 of 28  
12 Sep 17 14:11
W. D.
xxxxxx@gmail.com
Join Date: 12 Oct 2017
Posts To This List: 40
multiple spinlocks and KeLowerIrql()... really?!

I also think that a third spin is not the right decision. Holding two spin locks is not recommended, so holding three is not something you should try. You can't do what you want at DISPATCH_LEVEL. Bug check 0x133 with first parameter set to 1 is trigerred when "the system cumulatively spent an extended period of time at IRQL DISPATCH_LEVEL". You should move toward the single lock direction. Typically lock L1 protects access to resource R1 while lock L2 protects access to resource R2. If you have to access R2 while L1 is held than you should consider that resources R1 and R2 make the same resource R and that a single lock L should be acquired whenever L1 or L2 (that is L) is accessed.
  Message 11 of 28  
12 Sep 17 17:05
anton bassov
xxxxxx@hotmail.com
Join Date: 16 Jul 2006
Posts To This List: 4399
multiple spinlocks and KeLowerIrql()... really?!

>.....but the documentation for KeReleaseSpinLock says I must supply the IRQL > returned from the associated call to AcquireSpinLock; KeAcquireSpinLock() is,basically, just a wrapper for the following sequence: old_irql=KeRaiseIrql(DISPATCH_LEVEL); KeAcquireSpinLocAt DpcLevel(); * p_old_irql=old_irql; Therefore,KeReleaseSpinLock() does the following: KeReleaseSpinLockFromDpcLevel(); KeLowerIqrl( old_irql); I hope the above lines are sufficient for realising that, although you can release spinlocks in any order that you wish, irql parameter should be provided in the reverse order of lock acquisition, unless you are absolutely sure the first lock always gets acquired at elevated IRQL (for example, you acquire all your locks in context of DPC routine). In your particular case you should do the following ( I assume you are not doing it in context of DPC routine): KeAcquireSpinLock(& lock1, &old_irql1); KeAcquireSpinLock(& lock2, &old_irql2); ...... KeReleaseSpinLock(lock1, old_irql2); KeReleaseSpinLock(lock2, old_irql1); Alternatively, you can simply call KeRaiseIrql(DISPATCH_LEVEL) before you proceed to spinlock acquisition and KeLowerIrql()after both locks have been released. In such case you can simply ignore old_irql parameter, because it becomes meaningless in this scenario (or, even better, use XXXXDpcLevel() routines). I think this approach is better simply because it saves you extra confusion. What you should NEVER do is the following( again, unless you are 100% sure you always do it at elevated IRQL) KeAcquireSpinLock(& lock1, &old_irql1); KeAcquireSpinLock(& lock2, &old_irql2); ...... KeReleaseSpinLock(lock1, old_irql1; KeReleaseSpinLock(lock2, old_irql2); If you do it this way and your original IRQL is not elevated you will end up with a spinlock held at IRQL<DISPATCH_LEVEL, which is a fatal error because it may result in a deadlock Anton Bassov
  Message 12 of 28  
12 Sep 17 17:17
anton bassov
xxxxxx@hotmail.com
Join Date: 16 Jul 2006
Posts To This List: 4399
multiple spinlocks and KeLowerIrql()... really?!

<quote> You should move toward the single lock direction. Typically lock L1 protects access to resource R1 while lock L2 protects access to resource R2. If you have to access R2 while L1 is held than you should consider that resources R1 and R2 make the same resource R and that a single lock L should be acquired whenever L1 or L2 (that is L) is accessed. </quote> It really depends..... Although the above is true in vast majority of the cases there are some scenarios when you may want to achieve finer-grained locking. There are some (admittedly rare, but still existing) situations when having a single lock will result in a "hot lock" that is heavily contended for, while nested locking will lead to the situation when all the locks in a chain may be acquired without any contention in vast majority of cases(albeit at the cost of extra code complexity). In other words, this is just a usual dilemma of whether potential improvements in terms of efficiency justify the additional code complexity Anton Bassov
  Message 13 of 28  
12 Sep 17 17:50
M M
xxxxxx@hotmail.com
Join Date: 21 Oct 2010
Posts To This List: 744
multiple spinlocks and KeLowerIrql()... really?!

While there are a few legitimate cases for releasing locks in an order that is different than the acquisition order, almost certainly this is the wrong approach The use of a third lock solution, is equivalent to replacing lock 1 & lock 2 with lock 3 and might help you with a short term problem hos to fix broken code, but is not a solution to the multiple lock problem If you can tell us more, we may be able to help you better, but otherwise the general rule is don?t do this. Sent from Mail<https://go.microsoft.com/fwlink/?LinkId=550986> for Windows 10 From: Phil Barila<mailto:xxxxx@logrhythm.com> Sent: September 12, 2017 11:46 AM To: Windows System Software Devs Interest List<mailto:xxxxx@lists.osr.com> Subject: RE: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! > -----Original Message----- > Sent: Tuesday, September 12, 2017 9:35 AM > Subject: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! > > thanks for your thoughts folks - I am playing with the Spinlock Three idea > which is currently looking good... I figure that anything is better than > directly manipulating IRQL... even juggling another spinlock! > > The reason for the release order is dictated by another part of the code - > I am trying to avoid deadlock and excessive changes to existing code If you don't wrap every reference to locks 1 and/or 2 inside 3, you still run the risk of deadlock. Either always release in reverse order, or just use one lock. Anything else is a partially loaded revolver. Phil Not speaking for LogRhythm Philip D Barila Senior Software Engineer 720.881.5364 (W) LogRhythm.com --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=ntdev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.osronline.com/page.cfm?name=ListServer> --
  Message 14 of 28  
12 Sep 17 18:04
Mark Roddy
xxxxxx@gmail.com
Join Date: 25 Feb 2000
Posts To This List: 4019
multiple spinlocks and KeLowerIrql()... really?!

There really is nothing wrong with unordered *lock* release as long as in NT you maintain the correct irql levels. Ordering is required on acquisition, not release. But if you can demonstrate an example of wrongness about unordered release I'd be happy to revise my view on this. Mark Roddy On Tue, Sep 12, 2017 at 4:49 PM, Marion Bond <xxxxx@hotmail.com> < xxxxx@lists.osr.com> wrote: > While there are a few legitimate cases for releasing locks in an order > that is different than the acquisition order, almost certainly this is the > wrong approach > > > > The use of a third lock solution, is equivalent to replacing lock 1 & lock > 2 with lock 3 and might help you with a short term problem hos to fix > broken code, but is not a solution to the multiple lock problem > <...excess quoted lines suppressed...> --
  Message 15 of 28  
12 Sep 17 19:56
M M
xxxxxx@hotmail.com
Join Date: 21 Oct 2010
Posts To This List: 744
multiple spinlocks and KeLowerIrql()... really?!

Leave ?wrongness? aside for a moment and think about ?usefulness?. Perhaps you can think better than me, but when is it useful to release locks out of order? I have done this in a _few_ cases where the locking scheme was very complex and there was an interaction between the data structure that must be protected from corruption and the data element that is being accessed, but the general rule is still don?t do it ? if for no other reason that it will leave others very much confused and likely to break your code. Without a clear benefit of some kind, this is a good reason not to Sent from Mail<https://go.microsoft.com/fwlink/?LinkId=550986> for Windows 10 From: Mark Roddy<mailto:xxxxx@hollistech.com> Sent: September 12, 2017 6:04 PM To: Windows System Software Devs Interest List<mailto:xxxxx@lists.osr.com> Subject: Re: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! There really is nothing wrong with unordered *lock* release as long as in NT you maintain the correct irql levels. Ordering is required on acquisition, not release. But if you can demonstrate an example of wrongness about unordered release I'd be happy to revise my view on this. Mark Roddy On Tue, Sep 12, 2017 at 4:49 PM, Marion Bond <xxxxx@hotmail.com<mailto:xxxxx@hotmail.com>> <xxxxx@lists.osr.com<mailto:xxxxx@lists.osr.com>> wrote: While there are a few legitimate cases for releasing locks in an order that is different than the acquisition order, almost certainly this is the wrong approach The use of a third lock solution, is equivalent to replacing lock 1 & lock 2 with lock 3 and might help you with a short term problem hos to fix broken code, but is not a solution to the multiple lock problem If you can tell us more, we may be able to help you better, but otherwise the general rule is don?t do this. Sent from Mail<https://go.microsoft.com/fwlink/?LinkId=550986> for Windows 10 From: Phil Barila<mailto:xxxxx@logrhythm.com> Sent: September 12, 2017 11:46 AM To: Windows System Software Devs Interest List<mailto:xxxxx@lists.osr.com> Subject: RE: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! > -----Original Message----- > Sent: Tuesday, September 12, 2017 9:35 AM > Subject: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! > > thanks for your thoughts folks - I am playing with the Spinlock Three idea > which is currently looking good... I figure that anything is better than > directly manipulating IRQL... even juggling another spinlock! > > The reason for the release order is dictated by another part of the code - > I am trying to avoid deadlock and excessive changes to existing code If you don't wrap every reference to locks 1 and/or 2 inside 3, you still run the risk of deadlock. Either always release in reverse order, or just use one lock. Anything else is a partially loaded revolver. Phil Not speaking for LogRhythm Philip D Barila Senior Software Engineer 720.881.5364<tel:(720)%20881-5364> (W) LogRhythm.com --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=ntdev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.osronline.com/page.cfm?name=ListServer> --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=ntdev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.osronline.com/page.cfm?name=ListServer> --- NTDEV is sponsored by OSR Visit the list online at: MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at To unsubscribe, visit the List Server section of OSR Online at --
  Message 16 of 28  
12 Sep 17 22:25
Mark Roddy
xxxxxx@gmail.com
Join Date: 25 Feb 2000
Posts To This List: 4019
multiple spinlocks and KeLowerIrql()... really?!

The case was already discussed: resource1 is "hot" and its lock needs to be held to safely acquire the lock for resource2. Having acquired the lock for resource2 you want to drop the lock for resource1. Mark Roddy On Tue, Sep 12, 2017 at 6:55 PM, Marion Bond <xxxxx@hotmail.com> < xxxxx@lists.osr.com> wrote: > Leave ???wrongness??? aside for a moment and think about ?=80?usefulness???. > Perhaps you can think better than me, but when is it useful to release > locks out of order? > > > > I have done this in a _*few*_ cases where the locking scheme was very > complex and there was an interaction between the data structure that must > be protected from corruption and the data element that is being accessed, > but the general rule is still don???t do it ??? if for no other reason that it <...excess quoted lines suppressed...> --
  Message 17 of 28  
12 Sep 17 22:30
Jan Bottorff
xxxxxx@pmatrix.com
Join Date: 16 Apr 2013
Posts To This List: 394
multiple spinlocks and KeLowerIrql()... really?!

I'd agree a third spinlock is silly, EXCEPT this might be a driver that req= uires pure WDF calls to pass WHQL certification, in which case you can't ju= st call the native IRQL control functions. I'm not sure what the current st= atus on requiring pure WDF drivers is for certification. I thought some cla= sses of devices were flexible, and you were free to use many non WDF APIs, = but some device classes were not flexible and calling any non WDF APIs is i= nstant certification failure.=20 I'm still pondering if I agree with Phil's comment that using the 3rd outer= spinlock will require always locking that third spinlock. Offhand, it's no= t obvious to me why this is a problem, assuming the third spinlock is only = used in this case, as an indirect way to assure DISPATCH_LEVEL when Lock1 i= s acquired. The third spinlock makes me uncomfortable, but at the same time= I can't offhand describe the exact case where it's a problem. I have been = writing JavaScript code for a week, which is all single threaded, so my bra= in may be on a concurrency vacation. Certainly the best solution would be arrange the code so the two spinlocks= are released in lifo order. Schedule pressure might be such that a tempora= ry fix now is more appropriate than a better fix in a few days. If course o= nce the fire is out, the priority of going back and doing a better fix may = not be very high. Jan -----Original Message----- From: xxxxx@lists.osr.com [mailto:bounce-637793-145174@lists= .osr.com] On Behalf Of xxxxx@osr.com xxxxx@lists.osr.com Sent: Tuesday, September 12, 2017 9:39 AM To: Windows System Software Devs Interest List <xxxxx@lists.osr.com> Subject: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! <quote> Thanks Mark - I did consider this; but the documentation for KeReleaseSpinL= ock says I must supply the IRQL returned from the associated call to Acquir= eSpinLock; humph -- A colleague came up with the novel suggestion of a thir= d spinlock to "scope" the other two </quote> If the documentation says that, it's mistaken and needs fixed. It is very silly to use an additional spin lock in this case. Your choices to me are clear: a) Do as Mr. Roddy suggests. This works, it's always worked, and always wi= ll work. If the documentation suggests otherwise, file a bug. b) Always release the spin locks in the inverse order that you acquire them= .=20 Option A, above, has the advantage of being more technically concise. But = it requires you write a lot of comments to explain what you're doing. In = my experience, when you quick read (correct) code that implements option A,= it LOOKS like a bug... so you'll need to excessively comment your actions. Option B, above, has the advantage of being instantly understandable during= maintenance. But it has the disadvantage of being somewhat less efficient= . All things considered, unless the efficiencies gained by Option A are signi= ficant enough to outweigh the disadvantages, just bite the bullet and go w= ith Option B. Peter OSR @OSRDrivers --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=3Dnt= dev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and softwar= e drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.= osronline.com/page.cfm?name=3DListServer>
  Message 18 of 28  
13 Sep 17 06:30
Mark Roddy
xxxxxx@gmail.com
Join Date: 25 Feb 2000
Posts To This List: 4019
multiple spinlocks and KeLowerIrql()... really?!

I don't know of any WHQL test that requires "pure WDF". If there are then the WDF doc team should change the docs that clearly state that using WDM interfaces is fine. For example: https://docs.microsoft.com/en-us/windows-hardware/drivers/wdf/accessing-wdm-inter faces-in-kmdf-drivers Mark Roddy On Tue, Sep 12, 2017 at 9:30 PM, Jan Bottorff <xxxxx@pmatrix.com> < xxxxx@lists.osr.com> wrote: > I'd agree a third spinlock is silly, EXCEPT this might be a driver that > requires pure WDF calls to pass WHQL certification, in which case you can't > just call the native IRQL control functions. I'm not sure what the current > status on requiring pure WDF drivers is for certification. I thought some > classes of devices were flexible, and you were free to use many non WDF > APIs, but some device classes were not flexible and calling any non WDF > APIs is instant certification failure. > > I'm still pondering if I agree with Phil's comment that using the 3rd > outer spinlock will require always locking that third spinlock. Offhand, <...excess quoted lines suppressed...> --
  Message 19 of 28  
13 Sep 17 11:17
W. D.
xxxxxx@gmail.com
Join Date: 12 Oct 2017
Posts To This List: 40
multiple spinlocks and KeLowerIrql()... really?!

The use of WDM spin locks in KMDF is legitimate but my understanding of the "Spinlock rule (kmdf)" is that you can't hold two spin locks: "The Spinlock rule specifies that calls to KeAcquireSpinLock or KeAcquireSpinLockRaiseToDpc and KeReleaseSpinlock are used in strict alternation." https://msdn.microsoft.com/en-us/library/windows/hardware/ff819092(v=vs.85).aspx The same apply for KMDF spin locks: "The WdfSpinlock rule specifies that calls to the WdfSpinLockAcquire method are used in strict alternation with WdfSpinlockRelease. At the end of any KMDF callback routine, the driver should not hold the framework spinlock object that was obtained by a previous call to WdfSpinLockAcquire." https://msdn.microsoft.com/en-us/library/windows/hardware/ff556105(v=vs.85).aspx To me "strict alternation" means that you must call KeReleaseSpinlock or WdfSpinlockRelease before calling KeAcquireSpinLock(RaiseToDpc) or WdfSpinLockAcquire again.
  Message 20 of 28  
13 Sep 17 11:47
Mark Roddy
xxxxxx@gmail.com
Join Date: 25 Feb 2000
Posts To This List: 4019
multiple spinlocks and KeLowerIrql()... really?!

I have no idea what that means, but it would be crazy wrong to require "no more than one lock held at a time". Consider an object that contains a collection of objects. Forcing the locking to the container object's lock for each item in the collection is idiotic. The restriction on not holding a lock at the completion of a callback is fine. Mark Roddy On Wed, Sep 13, 2017 at 11:16 AM, xxxxx@gmail.com <xxxxx@lists.osr.com> wrote: > The use of WDM spin locks in KMDF is legitimate but my understanding of > the "Spinlock rule (kmdf)" is that you can't hold two spin locks: > > "The Spinlock rule specifies that calls to KeAcquireSpinLock or > KeAcquireSpinLockRaiseToDpc and KeReleaseSpinlock are used in strict > alternation." > > https://msdn.microsoft.com/en-us/library/windows/hardware/ > ff819092(v=vs.85).aspx > <...excess quoted lines suppressed...> --
  Message 21 of 28  
13 Sep 17 12:02
Peter Viscarola (OSR)
xxxxxx@osr.com
Join Date:
Posts To This List: 5949
List Moderator
multiple spinlocks and KeLowerIrql()... really?!

I have trouble believing that we're actually having this discussion in a group of what I assume are senior, experienced, kernel-mode developers. OF COURSE it's OK to release Spin Locks in an arbitrary order. As I say in class when I explain this (quoting Tony Mason, in fact) "Nobody has ever deadlocked as a result of a RELEASE operation." The only constraint in Windows is the one that Mr. Roddy cited: You must keep the IRQLs straight. Duh. OF COURSE it can be useful to do this. As I said previously, and as Mr. Roddy clarified, if you acquire Lock1 and then Lock2, and if Lock1 is HOT, and you need to do significantly more processing that requires just Lock2... you should absolutely release Lock1 before you release Lock2. However... HOWEVER, as I also said previously and to the point Mr M M noted, this code tends to "look" wrong when you read it casually. So, there's a maintenance cost involved. You have an obligation to "comment the shit out of this code" so that those who come after you understand what you're doing. So, in general, it's easier to "go with the flow" and release locks in the inverse order in which they were acquired. In fact, the WDF Spin Lock functions require this. And, let's state for the record: There is absolutely no requirement to avoid the use of WDM function calls in a general-purpose KMDF driver. C'mon, people! How many of you call ExAllocatePool instead of WdfMemoryCreate? Get a block of device memory, and want to map it into kernel virtual address space? What do you call from your KMDF driver? You call MmMapIoSpace. There isn't a WDF equivalent. In fact, one of the primary the ADVANTAGES of having access to WDM functions, is that the WDF team doesn't have to create meaningless abstractions for every single WDM function that could be useful. Are we seriously supposed to live without reader/writer locks, and just use WDFSPINLOCK and WDFWAITLOCK? OF COURSE NOT. <quote> To me "strict alternation" means that you must call KeReleaseSpinlock or WdfSpinlockRelease before calling KeAcquireSpinLock(RaiseToDpc) or WdfSpinLockAcquire again. </quote> Let's first acknowledge that "strict alternation" is a specific algorithm in CS. And, frankly, I have no idea how it applies here. Spin Locks, by the very nature, achieve "strict alternation." Let's further state that given the above interpretation of "strict alternation", we could never have nested spin locks This is, of course, blatantly incorrect. So, either our interpretation of "strict alternation" is incorrect, or the cited rule is incorrect. To me, it doesn't really matter. Finally, let me again state that if there's anything in the docs, or in the static analysis tools, that requires you ONLY release spin locks in the inverse order in which they were acquired, that documentation or tool is WRONG. Plain and simple. This has never, not ever, been a requirement in Windows (because the idea of *requiring* the locks to be released in any given order is plainly silly). Peter OSR @OSRDrivers
  Message 22 of 28  
13 Sep 17 12:17
Phil Barila
xxxxxx@logrhythm.com
Join Date: 07 Feb 2012
Posts To This List: 118
multiple spinlocks and KeLowerIrql()... really?!

> -----Original Message----- > Sent: Wednesday, September 13, 2017 10:01 AM > To: Windows System Software Devs Interest List <xxxxx@lists.osr.com> > Subject: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! > Finally, let me again state that if there's anything in the docs, or in > the static analysis tools, that requires you ONLY release spin locks in > the inverse order in which they were acquired, that documentation or tool > is WRONG. Plain and simple. This has never, not ever, been a requiremen= t > in Windows (because the idea of *requiring* the locks to be released in > any given order is plainly silly). Since I made a statement that was pretty much to that effect, allow me to w= ithdraw that statement. If I could strike it from the record ... In further pondering, it becomes clear (again, since I knew that long ago) = that you can only deadlock if you *acquire* in the wrong order. As stated by you, Tony Mason, and many others. Phil Not speaking for LogRhythm=20 Philip D Barila=20 Senior Software Engineer=20 720.881.5364 (W) =A0=20 LogRhythm.com=20 =A0 =A0 =A0 =A0
  Message 23 of 28  
13 Sep 17 18:14
M M
xxxxxx@hotmail.com
Join Date: 21 Oct 2010
Posts To This List: 744
multiple spinlocks and KeLowerIrql()... really?!

Okay, I must have missed that part. I thought the OP was working to repair / merge old code and these locks were artifacts. But it does not matter. This use case is invalid. If it is possible to do something useful while holding only lock 2, then it is possible to acquire it without holding lock 1 and the two locks can be completely separated. That is obviously a very broad and sweeping statement for which I have provided no evidence, but think about it. What could possibly be safe to do while holding only lock 2 if it is always a direct subordinate of lock 1? Lock 2 would be a completely useless lock. To be useful therefore, the lock must be acquirable independently. If the lock is acquirable independently, then it will be possible to remove the convolution between the locks. This is true of any two locks in any programming model including Windows KM where the extra complications of IRQL are involved. The is a very important pattern where lock 1 protects the data structure and while holding it one must ?acquire a reference? to something stored in it and this is a key pattern when removing the convolution between locks. Again I have stated a thesis and provided only the briefest of justifications. None of this has anything to do with KM programming specifically and it may not help the OP in the slightest. Sent from Mail<https://go.microsoft.com/fwlink/?LinkId=550986> for Windows 10 From: Mark Roddy<mailto:xxxxx@hollistech.com> Sent: September 12, 2017 10:25 PM To: Windows System Software Devs Interest List<mailto:xxxxx@lists.osr.com> Subject: Re: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! The case was already discussed: resource1 is "hot" and its lock needs to be held to safely acquire the lock for resource2. Having acquired the lock for resource2 you want to drop the lock for resource1. Mark Roddy On Tue, Sep 12, 2017 at 6:55 PM, Marion Bond <xxxxx@hotmail.com<mailto:xxxxx@hotmail.com>> <xxxxx@lists.osr.com<mailto:xxxxx@lists.osr.com>> wrote: Leave ?wrongness? aside for a moment and think about ?usefulness?. Perhaps you can think better than me, but when is it useful to release locks out of order? I have done this in a _few_ cases where the locking scheme was very complex and there was an interaction between the data structure that must be protected from corruption and the data element that is being accessed, but the general rule is still don?t do it ? if for no other reason that it will leave others very much confused and likely to break your code. Without a clear benefit of some kind, this is a good reason not to Sent from Mail<https://go.microsoft.com/fwlink/?LinkId=550986> for Windows 10 From: Mark Roddy<mailto:xxxxx@hollistech.com> Sent: September 12, 2017 6:04 PM To: Windows System Software Devs Interest List<mailto:xxxxx@lists.osr.com> Subject: Re: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! There really is nothing wrong with unordered *lock* release as long as in NT you maintain the correct irql levels. Ordering is required on acquisition, not release. But if you can demonstrate an example of wrongness about unordered release I'd be happy to revise my view on this. Mark Roddy On Tue, Sep 12, 2017 at 4:49 PM, Marion Bond <xxxxx@hotmail.com<mailto:xxxxx@hotmail.com>> <xxxxx@lists.osr.com<mailto:xxxxx@lists.osr.com>> wrote: While there are a few legitimate cases for releasing locks in an order that is different than the acquisition order, almost certainly this is the wrong approach The use of a third lock solution, is equivalent to replacing lock 1 & lock 2 with lock 3 and might help you with a short term problem hos to fix broken code, but is not a solution to the multiple lock problem If you can tell us more, we may be able to help you better, but otherwise the general rule is don?t do this. Sent from Mail<https://go.microsoft.com/fwlink/?LinkId=550986> for Windows 10 From: Phil Barila<mailto:xxxxx@logrhythm.com> Sent: September 12, 2017 11:46 AM To: Windows System Software Devs Interest List<mailto:xxxxx@lists.osr.com> Subject: RE: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! > -----Original Message----- > Sent: Tuesday, September 12, 2017 9:35 AM > Subject: RE:[ntdev] multiple spinlocks and KeLowerIrql()... really?! > > thanks for your thoughts folks - I am playing with the Spinlock Three idea > which is currently looking good... I figure that anything is better than > directly manipulating IRQL... even juggling another spinlock! > > The reason for the release order is dictated by another part of the code - > I am trying to avoid deadlock and excessive changes to existing code If you don't wrap every reference to locks 1 and/or 2 inside 3, you still run the risk of deadlock. Either always release in reverse order, or just use one lock. Anything else is a partially loaded revolver. Phil Not speaking for LogRhythm Philip D Barila Senior Software Engineer 720.881.5364<tel:(720)%20881-5364> (W) LogRhythm.com --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=ntdev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.osronline.com/page.cfm?name=ListServer> --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=ntdev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.osronline.com/page.cfm?name=ListServer> --- NTDEV is sponsored by OSR Visit the list online at: MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at To unsubscribe, visit the List Server section of OSR Online at --- NTDEV is sponsored by OSR Visit the list online at: <http://www.osronline.com/showlists.cfm?list=ntdev> MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at <http://www.osr.com/seminars> To unsubscribe, visit the List Server section of OSR Online at <http://www.osronline.com/page.cfm?name=ListServer> --- NTDEV is sponsored by OSR Visit the list online at: MONTHLY seminars on crash dump analysis, WDF, Windows internals and software drivers! Details at To unsubscribe, visit the List Server section of OSR Online at --
  Message 24 of 28  
14 Sep 17 02:03
Jan Bottorff
xxxxxx@pmatrix.com
Join Date: 16 Apr 2013
Posts To This List: 394
multiple spinlocks and KeLowerIrql()... really?!

>And, let's state for the record: There is absolutely no requirement to av= oid > the use of WDM function calls in a general-purpose KMDF driver.=20 I think the important qualifier here is "general-purpose KMDF driver". SDV = does not support three-way hybrid drivers, so a KMDF-WDM hybrid, NDIS-KMDF = hybrid or NDIS-WDM hybrid are all ok A NDIS-KMDF-WDM hybrid is not ok. Las= t year I was working on a complex virtual NDIS NIC miniport, which I was be= ginning to run WHQL tests on and made this not so well documented discovery= . Initially the driver used some KMDF and WDM functionality, but was mostly a= n NDIS driver. The KMDF functionality was used to interface to a parent vir= tual bus as a target device, and the unique WDM only functionality was to q= ueue a DPC on a specific processor. KDMF has no way to queue a directed DPC= , so I had to remove the KMDF calls to get SDV to accept the WDM calls.=20 It seems possible (but no direct experience) this limitation may also apply= to other classes of drivers with miniport/frameworks, like a stoport-KMDF = driver possibly can't be a storport-KMDF-WDM hybrid. =20 So, my direct experience is that if you had a NDIS-KMDF driver, you could n= ot just stir in some WDM calls to fill the gaps in KMDF. A NDIS-KMDF-WDM dr= iver might work just fine, but it will be impossible to pass certification = tests, due to limitations in SDV. Jan
  Message 25 of 28  
14 Sep 17 11:47
Peter Viscarola (OSR)
xxxxxx@osr.com
Join Date:
Posts To This List: 5949
List Moderator
multiple spinlocks and KeLowerIrql()... really?!

<quote> I think the important qualifier here is "general-purpose KMDF driver". </quote> Absolutely. That's why I wrote it that way ;-) <quote> if you had a NDIS-KMDF driver, you could not just stir in some WDM calls to fill the gaps in KMDF </quote> Absolutely correct, Mr. Bottorff. You're correct in pointing this out. Let's be clear here, though. This isn't a KMDF issue. It's an NDIS issue. You can't call arbitrary kernel functions in ANY NDIS driver (and pass the HLK tests), whether it's got a KMDF portion or not. Of course, the vast majority of KMDF drivers are not in this position. They're *just* KMDF drivers. Peter OSR @OSRDrivers
  Message 26 of 28  
15 Sep 17 16:32
anton bassov
xxxxxx@hotmail.com
Join Date: 16 Jul 2006
Posts To This List: 4399
multiple spinlocks and KeLowerIrql()... really?!

<quote> Let's be clear here, though. This isn't a KMDF issue. It's an NDIS issue. You can't call arbitrary kernel functions in ANY NDIS driver (and pass the HLK tests), whether it's got a KMDF portion or not. Let's be clear here, though. This isn't a KMDF issue. It's an NDIS issue. You can't call arbitrary kernel functions in ANY NDIS driver (and pass the HLK tests), whether it's got a KMDF portion or not. Let's be clear here, though. This isn't a KMDF issue. It's an NDIS issue. You can't call arbitrary kernel functions in ANY NDIS driver (and pass the HLK tests), whether it's got a KMDF portion or not. </quote> What about a layered miniport driver that exposes NDIS interface on its upper edge and deals with WDM driver of the ACTUAL hardware device on its lower one by sending IRPs to it? What about a miniport driver that registers its control device with NdisRegisterDeviceEx() and gets a pointer to a "regular" WDM DEVICE_OBJECT that has to be accessed in "a regular" WDM-style fashion? Are they going to fail HLK test as well just because of making WDM calls in NDIS driver? Anton Bassov
  Message 27 of 28  
16 Sep 17 16:27
Alex Grig
xxxxxx@broadcom.com
Join Date: 14 Apr 2008
Posts To This List: 3218
multiple spinlocks and KeLowerIrql()... really?!

HLK only fails limited number of imports (in NDISTEST 6.0). A lot of imports, including spinlock and IRQL functions are OK. Because these are what NDIS macros expand to.
  Message 28 of 28  
16 Sep 17 23:38
Jeffrey Tippet [MSFT]
xxxxxx@microsoft.com
Join Date: 29 Mar 2010
Posts To This List: 427
multiple spinlocks and KeLowerIrql()... really?!

And that line of thinking is on its way out. If you've looked at the NetAd= apter preview, you've seen that NDIS miniports will be moving to regular KM= DF, with no "forbidden" APIs. =20 Even for classic NDIS 6 miniport drivers, we are not hard-liners on calling= out into WDM APIs. The blocklist of imported APIs is mostly there to prev= ent you from shooting yourself in the foot (e.g., calling IoCreateDevice, w= hen NDIS has overridden your dispatch table). If you are in a situation wh= ere NDISTest is being unreasonable about an imported WDM API, send us a mai= l.
Posting Rules  
You may not post new threads
You may not post replies
You may not post attachments
You must login to OSR Online AND be a member of the ntdev list to be able to post.

All times are GMT -5. The time now is 04:10.


Copyright ©2015, OSR Open Systems Resources, Inc.
Based on vBulletin Copyright ©2000 - 2005, Jelsoft Enterprises Ltd.
Modified under license