-
Notifications
You must be signed in to change notification settings - Fork 2.6k
SpinLock.TryEnter fail fast for timeout 0 #6952
Conversation
|
@stephentoub seeing similar effects to the previous for threadpool i.e. not much change or improvements |
|
The threadpool contention it resolves is when a single threadpool thread has a full local queue of dependent sub tasks and all the other queues are empty. Most other situations its fine with. |
|
I see @stephentoub reviewed #6944 |
|
@danmosemsft this was a less dramatic change that produced mostly the same overall effect (as suggested by @stephentoub) |
|
Build machine went offline @dotnet-bot test Linux ARM Emulator Cross Release Build |
|
|
||
| if (Interlocked.CompareExchange(ref m_owner, observedOwner | 1, observedOwner, ref lockTaken) == observedOwner) | ||
| if (Interlocked.CompareExchange(ref m_owner, observedOwner | 1, observedOwner, ref lockTaken) == observedOwner || | ||
| millisecondsTimeout == 0) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The millisecondsTimeout == 0 check should be after EndCriticalRegion - it will break the full framework build otherwise.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed
When 1ms unlikely to have passed
d76dc69 to
b9df723
Compare
| #if !FEATURE_CORECLR | ||
| Thread.EndCriticalRegion(); | ||
| #endif | ||
| if (millisecondsTimeout == 0) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Would it make sense to check for millisecondsTimeout in TryEnter as well - right before ContinueTryEnter?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Probably rather than attempting a double acquire. It would mean adding another Thread.EndCriticalRegion() on a not acquire branch.
However its a pretty heavily stacked function which does currently always inline; maybe revisit as an enhancement? (i.e. would need some balancing to get right and keep it inlining)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Make sense.
* SpinLock.TryEnter fail fast for timeout 0 (2) * Don't over check SpinLock timeout When 1ms unlikely to have passed
* SpinLock.TryEnter fail fast for timeout 0 (2) * Don't over check SpinLock timeout When 1ms unlikely to have passed Commit migrated from dotnet/coreclr@0855b70
Previously the timeout 0 would Interlocked.Add to set the waiters then CAS spin to unset it immediately after; now it exits before trying to set the waiters so skips both.
As timeout zero is tested early, removed the first time check as the next minimum time of 1ms is unlikely to have passed.
Moved the second time check into the spinning
if, as if not spinning, again, 1ms is unlikely to have passed by this point.Passes corefx tests
1M iters (single thread, uncontended but locked) for code