From ec39f85a7aaf277b389fcb492b574cda34689aab Mon Sep 17 00:00:00 2001 From: UbitUmarov Date: Tue, 7 Mar 2023 14:33:42 +0000 Subject: [PATCH] cosmetics --- .../OSHttpServer/ContextTimeoutManager.cs | 14 +- .../SmartThreadPool/CanceledWorkItemsGroup.cs | 2 +- .../SmartThreadPool/STPEventWaitHandle.cs | 9 +- ThirdParty/SmartThreadPool/SmartThreadPool.cs | 53 ++-- .../WorkItem.WorkItemResult.cs | 6 +- ThirdParty/SmartThreadPool/WorkItem.cs | 293 ++++++++---------- ThirdParty/SmartThreadPool/WorkItemFactory.cs | 104 +++---- ThirdParty/SmartThreadPool/WorkItemsGroup.cs | 19 +- ThirdParty/SmartThreadPool/WorkItemsQueue.cs | 57 ++-- 9 files changed, 242 insertions(+), 315 deletions(-) diff --git a/OpenSim/Framework/Servers/HttpServer/OSHttpServer/ContextTimeoutManager.cs b/OpenSim/Framework/Servers/HttpServer/OSHttpServer/ContextTimeoutManager.cs index e2c3dc2139..dbf0c2d596 100644 --- a/OpenSim/Framework/Servers/HttpServer/OSHttpServer/ContextTimeoutManager.cs +++ b/OpenSim/Framework/Servers/HttpServer/OSHttpServer/ContextTimeoutManager.cs @@ -43,12 +43,12 @@ namespace OSHttpServer /// Use a Thread or a Timer to monitor the ugly /// private static Thread m_internalThread = null; - private static object m_threadLock = new object(); - private static ConcurrentQueue m_contexts = new ConcurrentQueue(); - private static ConcurrentQueue m_highPrio = new ConcurrentQueue(); - private static ConcurrentQueue m_midPrio = new ConcurrentQueue(); - private static ConcurrentQueue m_lowPrio = new ConcurrentQueue(); - private static AutoResetEvent m_processWaitEven = new AutoResetEvent(false); + private static readonly object m_threadLock = new(); + private static readonly ConcurrentQueue m_contexts = new(); + private static readonly ConcurrentQueue m_highPrio = new(); + private static readonly ConcurrentQueue m_midPrio = new(); + private static readonly ConcurrentQueue m_lowPrio = new(); + private static AutoResetEvent m_processWaitEven = new(false); private static bool m_shuttingDown; private static int m_ActiveSendingCount; @@ -100,7 +100,7 @@ namespace OSHttpServer break; double now = GetTimeStamp(); - if(m_contexts.Count > 0) + if(!m_contexts.IsEmpty) { ProcessSendQueues(); diff --git a/ThirdParty/SmartThreadPool/CanceledWorkItemsGroup.cs b/ThirdParty/SmartThreadPool/CanceledWorkItemsGroup.cs index 5752957878..6eb7b88e56 100644 --- a/ThirdParty/SmartThreadPool/CanceledWorkItemsGroup.cs +++ b/ThirdParty/SmartThreadPool/CanceledWorkItemsGroup.cs @@ -2,7 +2,7 @@ namespace Amib.Threading.Internal { internal class CanceledWorkItemsGroup { - public readonly static CanceledWorkItemsGroup NotCanceledWorkItemsGroup = new CanceledWorkItemsGroup(); + public readonly static CanceledWorkItemsGroup NotCanceledWorkItemsGroup = new(); public CanceledWorkItemsGroup() { diff --git a/ThirdParty/SmartThreadPool/STPEventWaitHandle.cs b/ThirdParty/SmartThreadPool/STPEventWaitHandle.cs index 9ddb3ccf6a..fe9645aace 100644 --- a/ThirdParty/SmartThreadPool/STPEventWaitHandle.cs +++ b/ThirdParty/SmartThreadPool/STPEventWaitHandle.cs @@ -1,4 +1,5 @@ using System; +using System.Runtime.CompilerServices; using System.Threading; namespace Amib.Threading.Internal @@ -7,25 +8,25 @@ namespace Amib.Threading.Internal { public const int WaitTimeout = Timeout.Infinite; - [System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.AggressiveInlining)] + [MethodImpl(MethodImplOptions.AggressiveInlining)] internal static bool WaitAll(WaitHandle[] waitHandles, int millisecondsTimeout, bool exitContext) { return WaitHandle.WaitAll(waitHandles, millisecondsTimeout, exitContext); } - [System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.AggressiveInlining)] + [MethodImpl(MethodImplOptions.AggressiveInlining)] internal static int WaitAny(WaitHandle[] waitHandles) { return WaitHandle.WaitAny(waitHandles); } - [System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.AggressiveInlining)] + [MethodImpl(MethodImplOptions.AggressiveInlining)] internal static int WaitAny(WaitHandle[] waitHandles, int millisecondsTimeout, bool exitContext) { return WaitHandle.WaitAny(waitHandles, millisecondsTimeout, exitContext); } - [System.Runtime.CompilerServices.MethodImpl(System.Runtime.CompilerServices.MethodImplOptions.AggressiveInlining)] + [MethodImpl(MethodImplOptions.AggressiveInlining)] internal static bool WaitOne(WaitHandle waitHandle, int millisecondsTimeout, bool exitContext) { return waitHandle.WaitOne(millisecondsTimeout, exitContext); diff --git a/ThirdParty/SmartThreadPool/SmartThreadPool.cs b/ThirdParty/SmartThreadPool/SmartThreadPool.cs index f928026225..d7a6a9fbc4 100644 --- a/ThirdParty/SmartThreadPool/SmartThreadPool.cs +++ b/ThirdParty/SmartThreadPool/SmartThreadPool.cs @@ -98,7 +98,6 @@ using System; using System.Security; using System.Threading; -using System.Collections; using System.Collections.Concurrent; using System.Collections.Generic; using System.Diagnostics; @@ -335,9 +334,7 @@ namespace Amib.Threading /// /// Idle timeout in milliseconds /// Upper limit of threads in the pool - public SmartThreadPool( - int idleTimeout, - int maxWorkerThreads) + public SmartThreadPool(int idleTimeout, int maxWorkerThreads) { m_stpStartInfo = new STPStartInfo { @@ -353,10 +350,7 @@ namespace Amib.Threading /// Idle timeout in milliseconds /// Upper limit of threads in the pool /// Lower limit of threads in the pool - public SmartThreadPool( - int idleTimeout, - int maxWorkerThreads, - int minWorkerThreads) + public SmartThreadPool(int idleTimeout, int maxWorkerThreads, int minWorkerThreads) { m_stpStartInfo = new STPStartInfo { @@ -445,10 +439,7 @@ namespace Amib.Threading /// private WorkItem Dequeue() { - WorkItem workItem = - m_workItemsQueue.DequeueWorkItem(m_stpStartInfo.IdleTimeout, m_shuttingDownEvent); - - return workItem; + return m_workItemsQueue.DequeueWorkItem(m_stpStartInfo.IdleTimeout, m_shuttingDownEvent); } /// @@ -458,7 +449,7 @@ namespace Amib.Threading internal override void Enqueue(WorkItem workItem) { // Make sure the workItem is not null - Debug.Assert(null != workItem); + Debug.Assert(workItem is not null); IncrementWorkItemsCount(); @@ -510,7 +501,7 @@ namespace Amib.Threading internal void UnregisterWorkItemsGroup(IWorkItemsGroup workItemsGroup) { - m_workItemsGroups.TryRemove(workItemsGroup.localID, out WorkItemsGroup dummy); + m_workItemsGroups.TryRemove(workItemsGroup.localID, out WorkItemsGroup _); } /// @@ -519,10 +510,7 @@ namespace Amib.Threading /// private void InformCompleted() { - // There is no need to lock the two methods together - // since only the current thread removes itself - // and the _workerThreads is a synchronized dictionary - if (m_workerThreads.TryRemove(Thread.CurrentThread.ManagedThreadId, out ThreadEntry te)) + if (m_workerThreads.TryRemove(Environment.CurrentManagedThreadId, out ThreadEntry te)) { te.Clean(); } @@ -584,8 +572,7 @@ namespace Amib.Threading workerThread.SetApartmentState(m_stpStartInfo.ApartmentState); workerThread.Priority = m_stpStartInfo.ThreadPriority; - - workerThread.Name = string.Format("STP:{0}:{1}", Name, m_threadCounter); + workerThread.Name = $"STP:{Name}:{m_threadCounter}"; Interlocked.Exchange(ref m_lastThreadCreateTS, DateTime.UtcNow.Ticks); ++m_threadCounter; @@ -606,7 +593,7 @@ namespace Amib.Threading { // Keep the entry of the dictionary as thread's variable to avoid the synchronization locks // of the dictionary. - CurrentThreadEntry = m_workerThreads[Thread.CurrentThread.ManagedThreadId]; + CurrentThreadEntry = m_workerThreads[Environment.CurrentManagedThreadId]; bool informedCompleted = false; FireOnThreadInitialization(); @@ -646,7 +633,7 @@ namespace Amib.Threading WorkItem workItem = Dequeue(); // On timeout or shut down. - if (workItem == null) + if (workItem is null) { // Double lock for quit. if (m_workerThreads.Count > minworkers) @@ -753,7 +740,7 @@ namespace Amib.Threading */ catch (Exception e) { - Debug.Assert(null != e); + Debug.Assert(e is not null); } finally { @@ -783,7 +770,7 @@ namespace Amib.Threading private void ValidateWaitForIdle() { - if (null != CurrentThreadEntry && CurrentThreadEntry.AssociatedSmartThreadPool == this) + if (CurrentThreadEntry is not null && CurrentThreadEntry.AssociatedSmartThreadPool == this) { throw new NotSupportedException( "WaitForIdle cannot be called from a thread on its SmartThreadPool, it causes a deadlock"); @@ -792,15 +779,15 @@ namespace Amib.Threading internal static void ValidateWorkItemsGroupWaitForIdle(IWorkItemsGroup workItemsGroup) { - if (CurrentThreadEntry != null) + if (CurrentThreadEntry is not null) ValidateWorkItemsGroupWaitForIdleImpl(workItemsGroup, CurrentThreadEntry.CurrentWorkItem); } [MethodImpl(MethodImplOptions.NoInlining)] private static void ValidateWorkItemsGroupWaitForIdleImpl(IWorkItemsGroup workItemsGroup, WorkItem workItem) { - if ((null != workItemsGroup) && - (null != workItem) && + if ((workItemsGroup is not null) && + (workItem is not null) && workItem.WasQueuedBy(workItemsGroup)) { throw new NotSupportedException("WaitForIdle cannot be called from a thread on its SmartThreadPool, it causes a deadlock"); @@ -855,7 +842,7 @@ namespace Amib.Threading // Each iteration we update the time left for the timeout. foreach (ThreadEntry te in threadEntries) { - if (te == null) + if (te is null) continue; Thread thread = te.WorkThread; @@ -889,11 +876,11 @@ namespace Amib.Threading // Abort the threads in the pool foreach (ThreadEntry te in threadEntries) { - if (te == null) + if (te is null) continue; Thread thread = te.WorkThread; - if ((thread != null) && thread.IsAlive ) + if (thread is not null && thread.IsAlive ) { try { @@ -1310,14 +1297,14 @@ namespace Amib.Threading Shutdown(); } - if (null != m_shuttingDownEvent) + if (m_shuttingDownEvent is not null) { m_shuttingDownEvent.Close(); m_shuttingDownEvent = null; } m_workerThreads.Clear(); - if (null != m_isIdleWaitHandle) + if (m_isIdleWaitHandle is not null) { m_isIdleWaitHandle.Close(); m_isIdleWaitHandle = null; @@ -1418,7 +1405,7 @@ namespace Amib.Threading if(threadEntry.AssociatedSmartThreadPool == this) { WorkItem workItem = threadEntry.CurrentWorkItem; - if (null != workItem && !workItem.IsCanceled) + if (workItem is not null && !workItem.IsCanceled) { threadEntry.CurrentWorkItem.GetWorkItemResult().Cancel(true); } diff --git a/ThirdParty/SmartThreadPool/WorkItem.WorkItemResult.cs b/ThirdParty/SmartThreadPool/WorkItem.WorkItemResult.cs index 2d2ac61bfa..6374d94ed6 100644 --- a/ThirdParty/SmartThreadPool/WorkItem.WorkItemResult.cs +++ b/ThirdParty/SmartThreadPool/WorkItem.WorkItemResult.cs @@ -1,6 +1,4 @@ using System; -using System.Collections.Generic; -using System.Text; using System.Threading; namespace Amib.Threading.Internal @@ -108,7 +106,7 @@ namespace Amib.Threading.Internal { get { - return _workItem._state; + return _workItem.m_state; } } @@ -127,7 +125,7 @@ namespace Amib.Threading.Internal /// public object Exception { - get { return _workItem._exception; } + get { return _workItem.m_exception; } } #endregion diff --git a/ThirdParty/SmartThreadPool/WorkItem.cs b/ThirdParty/SmartThreadPool/WorkItem.cs index 787b0501d2..e0b106f38b 100644 --- a/ThirdParty/SmartThreadPool/WorkItem.cs +++ b/ThirdParty/SmartThreadPool/WorkItem.cs @@ -1,6 +1,6 @@ using System; -using System.Threading; using System.Diagnostics; +using System.Threading; namespace Amib.Threading.Internal { @@ -54,92 +54,92 @@ namespace Amib.Threading.Internal /// /// Callback delegate for the callback. /// - private WorkItemCallback _callback; - private WaitCallback _callbackNoResult; + private WorkItemCallback m_callback; + private WaitCallback m_callbackNoResult; /// /// State with which to call the callback delegate. /// - private object _state; + private object m_state; /// /// Stores the caller's context /// - private ExecutionContext _callerContext = null; + private ExecutionContext m_callerContext = null; /// /// Holds the result of the mehtod /// - private object _result; + private object m_result; /// /// Hold the exception if the method threw it /// - private Exception _exception; + private Exception m_exception; /// /// Hold the state of the work item /// - private WorkItemState _workItemState; + private WorkItemState m_workItemState; /// /// A ManualResetEvent to indicate that the result is ready /// - private ManualResetEvent _workItemCompleted; + private ManualResetEvent m_workItemCompleted; /// /// A reference count to the _workItemCompleted. /// When it reaches to zero _workItemCompleted is Closed /// - private int _workItemCompletedRefCount; + private int m_workItemCompletedRefCount; /// /// Represents the result state of the work item /// - private readonly WorkItemResult _workItemResult; + private readonly WorkItemResult m_workItemResult; /// /// Work item info /// - private readonly WorkItemInfo _workItemInfo; + private readonly WorkItemInfo m_workItemInfo; /// /// Called when the WorkItem starts /// - private event WorkItemStateCallback _workItemStartedEvent; + private event WorkItemStateCallback m_workItemStartedEvent; /// /// Called when the WorkItem completes /// - private event WorkItemStateCallback _workItemCompletedEvent; + private event WorkItemStateCallback m_workItemCompletedEvent; /// /// A reference to an object that indicates whatever the /// WorkItemsGroup has been canceled /// - private CanceledWorkItemsGroup _canceledWorkItemsGroup = CanceledWorkItemsGroup.NotCanceledWorkItemsGroup; + private CanceledWorkItemsGroup m_canceledWorkItemsGroup = CanceledWorkItemsGroup.NotCanceledWorkItemsGroup; /// /// A reference to an object that indicates whatever the /// SmartThreadPool has been canceled /// - private CanceledWorkItemsGroup _canceledSmartThreadPool = CanceledWorkItemsGroup.NotCanceledWorkItemsGroup; + private CanceledWorkItemsGroup m_canceledSmartThreadPool = CanceledWorkItemsGroup.NotCanceledWorkItemsGroup; /// /// The work item group this work item belong to. /// - private readonly IWorkItemsGroup _workItemsGroup; + private readonly IWorkItemsGroup m_workItemsGroup; /// /// The thread that executes this workitem. /// This field is available for the period when the work item is executed, before and after it is null. /// - private Thread _executingThread; + private Thread m_executingThread; /// /// The absulote time when the work item will be timeout /// - private long _expirationTime; + private long m_expirationTime; #region Performance Counter fields @@ -179,7 +179,7 @@ namespace Amib.Threading.Internal { get { - return _workItemInfo; + return m_workItemInfo; } } @@ -199,42 +199,46 @@ namespace Amib.Threading.Internal /// that meant to run the callback public WorkItem(IWorkItemsGroup workItemsGroup, WorkItemInfo workItemInfo, WorkItemCallback callback, object state) { - _workItemsGroup = workItemsGroup; - _workItemInfo = workItemInfo; + m_workItemsGroup = workItemsGroup; + m_workItemInfo = workItemInfo; - if (_workItemInfo.UseCallerCallContext && !ExecutionContext.IsFlowSuppressed()) + if (m_workItemInfo.UseCallerCallContext && !ExecutionContext.IsFlowSuppressed()) { ExecutionContext ec = ExecutionContext.Capture(); - if (ec != null) - _callerContext = ec.CreateCopy(); - ec.Dispose(); - ec = null; + if (ec is not null) + { + m_callerContext = ec.CreateCopy(); + ec.Dispose(); + ec = null; + } } - _callback = callback; - _callbackNoResult = null; - _state = state; - _workItemResult = new WorkItemResult(this); + m_callback = callback; + m_callbackNoResult = null; + m_state = state; + m_workItemResult = new WorkItemResult(this); Initialize(); } public WorkItem(IWorkItemsGroup workItemsGroup, WorkItemInfo workItemInfo, WaitCallback callback, object state) { - _workItemsGroup = workItemsGroup; - _workItemInfo = workItemInfo; + m_workItemsGroup = workItemsGroup; + m_workItemInfo = workItemInfo; - if (_workItemInfo.UseCallerCallContext && !ExecutionContext.IsFlowSuppressed()) + if (m_workItemInfo.UseCallerCallContext && !ExecutionContext.IsFlowSuppressed()) { ExecutionContext ec = ExecutionContext.Capture(); - if (ec != null) - _callerContext = ec.CreateCopy(); - ec.Dispose(); - ec = null; + if (ec is not null) + { + m_callerContext = ec.CreateCopy(); + ec.Dispose(); + ec = null; + } } - _callbackNoResult = callback; - _state = state; - _workItemResult = new WorkItemResult(this); + m_callbackNoResult = callback; + m_state = state; + m_workItemResult = new WorkItemResult(this); Initialize(); } @@ -242,18 +246,18 @@ namespace Amib.Threading.Internal { // The _workItemState is changed directly instead of using the SetWorkItemState // method since we don't want to go throught IsValidStateTransition. - _workItemState = WorkItemState.InQueue; + m_workItemState = WorkItemState.InQueue; - _workItemCompleted = null; - _workItemCompletedRefCount = 0; + m_workItemCompleted = null; + m_workItemCompletedRefCount = 0; _waitingOnQueueStopwatch = new Stopwatch(); _processingStopwatch = new Stopwatch(); - _expirationTime = _workItemInfo.Timeout > 0 ? DateTime.UtcNow.Ticks + _workItemInfo.Timeout * TimeSpan.TicksPerMillisecond : long.MaxValue; + m_expirationTime = m_workItemInfo.Timeout > 0 ? DateTime.UtcNow.Ticks + m_workItemInfo.Timeout * TimeSpan.TicksPerMillisecond : long.MaxValue; } internal bool WasQueuedBy(IWorkItemsGroup workItemsGroup) { - return (workItemsGroup == _workItemsGroup); + return (workItemsGroup == m_workItemsGroup); } @@ -263,14 +267,14 @@ namespace Amib.Threading.Internal internal CanceledWorkItemsGroup CanceledWorkItemsGroup { - get { return _canceledWorkItemsGroup; } - set { _canceledWorkItemsGroup = value; } + get { return m_canceledWorkItemsGroup; } + set { m_canceledWorkItemsGroup = value; } } internal CanceledWorkItemsGroup CanceledSmartThreadPool { - get { return _canceledSmartThreadPool; } - set { _canceledSmartThreadPool = value; } + get { return m_canceledSmartThreadPool; } + set { m_canceledSmartThreadPool = value; } } /// @@ -289,8 +293,8 @@ namespace Amib.Threading.Internal { if (IsCanceled) { - if ((_workItemInfo.PostExecuteWorkItemCallback != null) && - ((_workItemInfo.CallToPostExecute & CallToPostExecute.WhenWorkItemCanceled) == CallToPostExecute.WhenWorkItemCanceled)) + if ((m_workItemInfo.PostExecuteWorkItemCallback is not null) && + ((m_workItemInfo.CallToPostExecute & CallToPostExecute.WhenWorkItemCanceled) == CallToPostExecute.WhenWorkItemCanceled)) { return true; } @@ -301,7 +305,7 @@ namespace Amib.Threading.Internal Debug.Assert(WorkItemState.InQueue == GetWorkItemState()); // No need for a lock yet, only after the state has changed to InProgress - _executingThread = Thread.CurrentThread; + m_executingThread = Thread.CurrentThread; SetWorkItemState(WorkItemState.InProgress); } @@ -332,7 +336,7 @@ namespace Amib.Threading.Internal } // Run the post execute as needed - if ((currentCallToPostExecute & _workItemInfo.CallToPostExecute) != 0) + if ((currentCallToPostExecute & m_workItemInfo.CallToPostExecute) != 0) { PostExecute(); } @@ -344,7 +348,7 @@ namespace Amib.Threading.Internal { try { - _workItemCompletedEvent?.Invoke(this); + m_workItemCompletedEvent?.Invoke(this); } catch // Suppress exceptions { } @@ -354,7 +358,7 @@ namespace Amib.Threading.Internal { try { - _workItemStartedEvent?.Invoke(this); + m_workItemStartedEvent?.Invoke(this); } catch // Suppress exceptions { } @@ -372,32 +376,24 @@ namespace Amib.Threading.Internal { try { - if(_callbackNoResult == null) + if(m_callbackNoResult is null) { - if(_callerContext == null) - result = _callback(_state); + if(m_callerContext is null) + result = m_callback(m_state); else { - ContextCallback _ccb = new ContextCallback( o => - { - result =_callback(o); - }); - - ExecutionContext.Run(_callerContext, _ccb, _state); + ContextCallback _ccb = new( o => { result =m_callback(o); }); + ExecutionContext.Run(m_callerContext, _ccb, m_state); } } else { - if (_callerContext == null) - _callbackNoResult(_state); + if (m_callerContext is null) + m_callbackNoResult(m_state); else { - ContextCallback _ccb = new ContextCallback(o => - { - _callbackNoResult(o); - }); - - ExecutionContext.Run(_callerContext, _ccb, _state); + ContextCallback _ccb = new(o => { m_callbackNoResult(o); }); + ExecutionContext.Run(m_callerContext, _ccb, m_state); } } } @@ -410,9 +406,9 @@ namespace Amib.Threading.Internal // Remove the value of the execution thread, so it will be impossible to cancel the work item, // since it is already completed. // Cancelling a work item that already completed may cause the abortion of the next work item!!! - Thread executionThread = Interlocked.CompareExchange(ref _executingThread, null, _executingThread); + Thread executionThread = Interlocked.CompareExchange(ref m_executingThread, null, m_executingThread); - if (null == executionThread) + if (executionThread is null) { // Oops! we are going to be aborted..., Wait here so we can catch the ThreadAbortException Thread.Sleep(60 * 1000); @@ -443,15 +439,15 @@ namespace Amib.Threading.Internal /// private void PostExecute() { - if (null != _workItemInfo.PostExecuteWorkItemCallback) + if (m_workItemInfo.PostExecuteWorkItemCallback is not null) { try { - _workItemInfo.PostExecuteWorkItemCallback(_workItemResult); + m_workItemInfo.PostExecuteWorkItemCallback(m_workItemResult); } catch (Exception e) { - Debug.Assert(null != e); + Debug.Assert(e is not null); } } } @@ -464,8 +460,8 @@ namespace Amib.Threading.Internal /// if there was no exception. internal void SetResult(object result, Exception exception) { - _result = result; - _exception = exception; + m_result = result; + m_exception = exception; SignalComplete(false); } @@ -475,7 +471,7 @@ namespace Amib.Threading.Internal /// The work item result internal IWorkItemResult GetWorkItemResult() { - return _workItemResult; + return m_workItemResult; } /// @@ -502,7 +498,7 @@ namespace Amib.Threading.Internal WaitHandle[] waitHandles = new WaitHandle[waitableResults.Length]; GetWaitHandles(waitableResults, waitHandles); - if ((null == cancelWaitHandle) && (waitHandles.Length <= 64)) + if ((cancelWaitHandle is null) && (waitHandles.Length <= 64)) { success = STPEventWaitHandle.WaitAll(waitHandles, millisecondsTimeout, exitContext); } @@ -512,15 +508,9 @@ namespace Amib.Threading.Internal int millisecondsLeft = millisecondsTimeout; Stopwatch stopwatch = Stopwatch.StartNew(); - WaitHandle[] whs; - if (null != cancelWaitHandle) - { - whs = new WaitHandle[] { null, cancelWaitHandle }; - } - else - { - whs = new WaitHandle[] { null }; - } + WaitHandle[] whs = cancelWaitHandle is null ? + new WaitHandle[] { null } : + new WaitHandle[] { null, cancelWaitHandle }; bool waitInfinitely = (Timeout.Infinite == millisecondsTimeout); // Iterate over the wait handles and wait for each one to complete. @@ -569,15 +559,11 @@ namespace Amib.Threading.Internal /// /// The array index of the work item result that satisfied the wait, or WaitTimeout if no work item result satisfied the wait and a time interval equivalent to millisecondsTimeout has passed or the work item has been canceled. /// - internal static int WaitAny( - IWaitableResult[] waitableResults, - int millisecondsTimeout, - bool exitContext, - WaitHandle cancelWaitHandle) + internal static int WaitAny( IWaitableResult[] waitableResults, int millisecondsTimeout, + bool exitContext, WaitHandle cancelWaitHandle) { WaitHandle[] waitHandles; - - if (null != cancelWaitHandle) + if (cancelWaitHandle is not null) { waitHandles = new WaitHandle[waitableResults.Length + 1]; GetWaitHandles(waitableResults, waitHandles); @@ -592,7 +578,7 @@ namespace Amib.Threading.Internal int result = STPEventWaitHandle.WaitAny(waitHandles, millisecondsTimeout, exitContext); // Treat cancel as timeout - if (null != cancelWaitHandle) + if (cancelWaitHandle is not null) { if (result == waitableResults.Length) { @@ -610,14 +596,13 @@ namespace Amib.Threading.Internal /// /// An array of work item results /// An array of wait handles to fill - private static void GetWaitHandles( - IWaitableResult[] waitableResults, + private static void GetWaitHandles(IWaitableResult[] waitableResults, WaitHandle[] waitHandles) { for (int i = 0; i < waitableResults.Length; ++i) { WorkItemResult wir = waitableResults[i].GetWorkItemResult() as WorkItemResult; - Debug.Assert(null != wir, "All waitableResults must be WorkItemResult objects"); + Debug.Assert(wir is not null, "All waitableResults must be WorkItemResult objects"); waitHandles[i] = wir.GetWorkItem().GetWaitHandle(); } @@ -645,23 +630,23 @@ namespace Amib.Threading.Internal { lock (this) { - if (WorkItemState.Completed == _workItemState) + if (WorkItemState.Completed == m_workItemState) { - return _workItemState; + return m_workItemState; } if (WorkItemState.Canceled != _workItemState && DateTime.UtcNow.Ticks > _expirationTime) { - _workItemState = WorkItemState.Canceled; - return _workItemState; + m_workItemState = WorkItemState.Canceled; + return m_workItemState; } - if(WorkItemState.InProgress != _workItemState) + if(WorkItemState.InProgress != m_workItemState) { if (CanceledSmartThreadPool.IsCanceled || CanceledWorkItemsGroup.IsCanceled) { return WorkItemState.Canceled; } } - return _workItemState; + return m_workItemState; } } @@ -674,9 +659,9 @@ namespace Amib.Threading.Internal { lock (this) { - if (IsValidStatesTransition(_workItemState, workItemState)) + if (IsValidStatesTransition(m_workItemState, workItemState)) { - _workItemState = workItemState; + m_workItemState = workItemState; } } } @@ -691,10 +676,7 @@ namespace Amib.Threading.Internal lock (this) { // If someone is waiting then signal. - if (null != _workItemCompleted) - { - _workItemCompleted.Set(); - } + m_workItemCompleted?.Set(); } } @@ -724,8 +706,8 @@ namespace Amib.Threading.Internal //Debug.WriteLine("Work item already canceled"); if (abortExecution) { - Thread executionThread = Interlocked.CompareExchange(ref _executingThread, null, _executingThread); - if (null != executionThread) + Thread executionThread = Interlocked.CompareExchange(ref m_executingThread, null, m_executingThread); + if (executionThread is not null) { //executionThread.Abort(); // "Cancel" // No need to signalComplete, because we already cancelled this work item @@ -741,8 +723,8 @@ namespace Amib.Threading.Internal case WorkItemState.InProgress: if (abortExecution) { - Thread executionThread = Interlocked.CompareExchange(ref _executingThread, null, _executingThread); - if (null != executionThread) + Thread executionThread = Interlocked.CompareExchange(ref m_executingThread, null, m_executingThread); + if (executionThread is not null) { //executionThread.Abort(); // "Cancel" success = true; @@ -789,14 +771,11 @@ namespace Amib.Threading.Internal /// In case of error the method throws and exception /// /// The result of the work item - private object GetResult( - int millisecondsTimeout, - bool exitContext, + private object GetResult(int millisecondsTimeout, bool exitContext, WaitHandle cancelWaitHandle) { - Exception e; - object result = GetResult(millisecondsTimeout, exitContext, cancelWaitHandle, out e); - if (null != e) + object result = GetResult(millisecondsTimeout, exitContext, cancelWaitHandle, out Exception e); + if (e is not null) { throw new WorkItemResultException("The work item caused an excpetion, see the inner exception for details", e); } @@ -809,11 +788,8 @@ namespace Amib.Threading.Internal /// In case of error the e argument is filled with the exception /// /// The result of the work item - private object GetResult( - int millisecondsTimeout, - bool exitContext, - WaitHandle cancelWaitHandle, - out Exception e) + private object GetResult( int millisecondsTimeout, bool exitContext, + WaitHandle cancelWaitHandle, out Exception e) { e = null; @@ -826,12 +802,12 @@ namespace Amib.Threading.Internal // Check for completion if (IsCompleted) { - e = _exception; - return _result; + e = m_exception; + return m_result; } // If no cancelWaitHandle is provided - if (null == cancelWaitHandle) + if (cancelWaitHandle is null) { WaitHandle wh = GetWaitHandle(); @@ -875,10 +851,10 @@ namespace Amib.Threading.Internal Debug.Assert(IsCompleted); - e = _exception; + e = m_exception; // Return the result - return _result; + return m_result; } /// @@ -888,26 +864,26 @@ namespace Amib.Threading.Internal { lock (this) { - if (null == _workItemCompleted) + if (m_workItemCompleted is null) { - _workItemCompleted = new ManualResetEvent(IsCompleted); + m_workItemCompleted = new ManualResetEvent(IsCompleted); } - ++_workItemCompletedRefCount; + ++m_workItemCompletedRefCount; } - return _workItemCompleted; + return m_workItemCompleted; } private void ReleaseWaitHandle() { lock (this) { - if (null != _workItemCompleted) + if (m_workItemCompleted is not null) { - --_workItemCompletedRefCount; - if (0 == _workItemCompletedRefCount) + --m_workItemCompletedRefCount; + if (0 == m_workItemCompletedRefCount) { - _workItemCompleted.Close(); - _workItemCompleted = null; + m_workItemCompleted.Close(); + m_workItemCompleted = null; } } } @@ -949,11 +925,11 @@ namespace Amib.Threading.Internal { add { - _workItemStartedEvent += value; + m_workItemStartedEvent += value; } remove { - _workItemStartedEvent -= value; + m_workItemStartedEvent -= value; } } @@ -961,39 +937,38 @@ namespace Amib.Threading.Internal { add { - _workItemCompletedEvent += value; + m_workItemCompletedEvent += value; } remove { - _workItemCompletedEvent -= value; + m_workItemCompletedEvent -= value; } } public void DisposeOfState() { - if(_callerContext != null) + if(m_callerContext is not null) { - _callerContext.Dispose(); - _callerContext = null; + m_callerContext.Dispose(); + m_callerContext = null; } - if(_workItemCompleted != null) + if(m_workItemCompleted is not null) { - _workItemCompleted.Dispose(); - _workItemCompleted = null; + m_workItemCompleted.Dispose(); + m_workItemCompleted = null; } - if (_workItemInfo.DisposeOfStateObjects) + if (m_workItemInfo.DisposeOfStateObjects) { - IDisposable disp = _state as IDisposable; - if (null != disp) + if (m_state is IDisposable disp) { disp.Dispose(); - _state = null; + m_state = null; } } - _callback = null; - _callbackNoResult = null; + m_callback = null; + m_callbackNoResult = null; } } } diff --git a/ThirdParty/SmartThreadPool/WorkItemFactory.cs b/ThirdParty/SmartThreadPool/WorkItemFactory.cs index 8f17706482..539ae58ec8 100644 --- a/ThirdParty/SmartThreadPool/WorkItemFactory.cs +++ b/ThirdParty/SmartThreadPool/WorkItemFactory.cs @@ -1,5 +1,7 @@ using System; using System.Threading; +using System.Runtime.CompilerServices; + namespace Amib.Threading.Internal { @@ -13,14 +15,8 @@ namespace Amib.Threading.Internal { ValidateCallback(callback); ValidateCallback(workItemInfo.PostExecuteWorkItemCallback); + return new WorkItem(workItemsGroup, new WorkItemInfo(workItemInfo), callback, state); - WorkItem workItem = new WorkItem( - workItemsGroup, - new WorkItemInfo(workItemInfo), - callback, - state); - - return workItem; } public static WorkItem CreateWorkItem(IWorkItemsGroup workItemsGroup, WIGStartInfo wigStartInfo, @@ -28,7 +24,7 @@ namespace Amib.Threading.Internal { ValidateCallback(callback); - WorkItemInfo workItemInfo = new WorkItemInfo() + WorkItemInfo workItemInfo = new() { UseCallerCallContext = wigStartInfo.UseCallerCallContext, PostExecuteWorkItemCallback = wigStartInfo.PostExecuteWorkItemCallback, @@ -36,12 +32,7 @@ namespace Amib.Threading.Internal DisposeOfStateObjects = wigStartInfo.DisposeOfStateObjects, }; - WorkItem workItem = new WorkItem( - workItemsGroup, - workItemInfo, - callback, - state); - return workItem; + return new WorkItem(workItemsGroup, workItemInfo, callback, state); } /// @@ -51,6 +42,7 @@ namespace Amib.Threading.Internal /// Work item group start information /// A callback to execute /// Returns a work item + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static WorkItem CreateWorkItem( IWorkItemsGroup workItemsGroup, WIGStartInfo wigStartInfo, WorkItemCallback callback) { return CreateWorkItem(workItemsGroup, wigStartInfo, callback, null); @@ -64,15 +56,11 @@ namespace Amib.Threading.Internal /// Work item info /// A callback to execute /// Returns a work item + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static WorkItem CreateWorkItem( IWorkItemsGroup workItemsGroup, WIGStartInfo wigStartInfo, WorkItemInfo workItemInfo, WorkItemCallback callback) { - return CreateWorkItem( - workItemsGroup, - wigStartInfo, - workItemInfo, - callback, - null); + return CreateWorkItem(workItemsGroup, wigStartInfo, workItemInfo, callback, null); } /// @@ -85,12 +73,13 @@ namespace Amib.Threading.Internal /// The context object of the work item. Used for passing arguments to the work item. /// /// Returns a work item + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static WorkItem CreateWorkItem( IWorkItemsGroup workItemsGroup, WIGStartInfo wigStartInfo, WorkItemCallback callback, object state) { ValidateCallback(callback); - WorkItemInfo workItemInfo = new WorkItemInfo() + WorkItemInfo workItemInfo = new() { UseCallerCallContext = wigStartInfo.UseCallerCallContext, PostExecuteWorkItemCallback = wigStartInfo.PostExecuteWorkItemCallback, @@ -98,12 +87,7 @@ namespace Amib.Threading.Internal DisposeOfStateObjects = wigStartInfo.DisposeOfStateObjects, }; - WorkItem workItem = new WorkItem( - workItemsGroup, - workItemInfo, - callback, - state); - return workItem; + return new WorkItem( workItemsGroup, workItemInfo, callback, state); } /// @@ -117,13 +101,14 @@ namespace Amib.Threading.Internal /// The context object of the work item. Used for passing arguments to the work item. /// /// Returns a work item + [MethodImpl(MethodImplOptions.AggressiveInlining)] public static WorkItem CreateWorkItem( IWorkItemsGroup workItemsGroup, WIGStartInfo wigStartInfo, WorkItemInfo workItemInfo, WorkItemCallback callback, object state) { ValidateCallback(callback); ValidateCallback(workItemInfo.PostExecuteWorkItemCallback); - WorkItem workItem = new WorkItem( + WorkItem workItem = new( workItemsGroup, new WorkItemInfo(workItemInfo), callback, @@ -145,29 +130,22 @@ namespace Amib.Threading.Internal /// A delegate to call after the callback completion /// /// Returns a work item - public static WorkItem CreateWorkItem( - IWorkItemsGroup workItemsGroup, - WIGStartInfo wigStartInfo, - WorkItemCallback callback, - object state, - PostExecuteWorkItemCallback postExecuteWorkItemCallback) + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static WorkItem CreateWorkItem(IWorkItemsGroup workItemsGroup, WIGStartInfo wigStartInfo, + WorkItemCallback callback, object state,PostExecuteWorkItemCallback postExecuteWorkItemCallback) { ValidateCallback(callback); ValidateCallback(postExecuteWorkItemCallback); - WorkItemInfo workItemInfo = new WorkItemInfo(); - workItemInfo.UseCallerCallContext = wigStartInfo.UseCallerCallContext; - workItemInfo.PostExecuteWorkItemCallback = postExecuteWorkItemCallback; - workItemInfo.CallToPostExecute = wigStartInfo.CallToPostExecute; - workItemInfo.DisposeOfStateObjects = wigStartInfo.DisposeOfStateObjects; + WorkItemInfo workItemInfo = new() + { + UseCallerCallContext = wigStartInfo.UseCallerCallContext, + PostExecuteWorkItemCallback = postExecuteWorkItemCallback, + CallToPostExecute = wigStartInfo.CallToPostExecute, + DisposeOfStateObjects = wigStartInfo.DisposeOfStateObjects + }; - WorkItem workItem = new WorkItem( - workItemsGroup, - workItemInfo, - callback, - state); - - return workItem; + return new WorkItem( workItemsGroup, workItemInfo, callback, state); } /// @@ -184,35 +162,29 @@ namespace Amib.Threading.Internal /// /// Indicates on which cases to call to the post execute callback /// Returns a work item - public static WorkItem CreateWorkItem( - IWorkItemsGroup workItemsGroup, - WIGStartInfo wigStartInfo, - WorkItemCallback callback, - object state, - PostExecuteWorkItemCallback postExecuteWorkItemCallback, - CallToPostExecute callToPostExecute) + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static WorkItem CreateWorkItem(IWorkItemsGroup workItemsGroup,WIGStartInfo wigStartInfo, + WorkItemCallback callback, object state, + PostExecuteWorkItemCallback postExecuteWorkItemCallback, CallToPostExecute callToPostExecute) { ValidateCallback(callback); ValidateCallback(postExecuteWorkItemCallback); - WorkItemInfo workItemInfo = new WorkItemInfo(); - workItemInfo.UseCallerCallContext = wigStartInfo.UseCallerCallContext; - workItemInfo.PostExecuteWorkItemCallback = postExecuteWorkItemCallback; - workItemInfo.CallToPostExecute = callToPostExecute; - workItemInfo.DisposeOfStateObjects = wigStartInfo.DisposeOfStateObjects; + WorkItemInfo workItemInfo = new() + { + UseCallerCallContext = wigStartInfo.UseCallerCallContext, + PostExecuteWorkItemCallback = postExecuteWorkItemCallback, + CallToPostExecute = callToPostExecute, + DisposeOfStateObjects = wigStartInfo.DisposeOfStateObjects + }; - WorkItem workItem = new WorkItem( - workItemsGroup, - workItemInfo, - callback, - state); - - return workItem; + return new WorkItem(workItemsGroup, workItemInfo, callback, state); } + [MethodImpl(MethodImplOptions.AggressiveInlining)] private static void ValidateCallback(Delegate callback) { - if (callback != null && callback.GetInvocationList().Length > 1) + if (callback is not null && callback.GetInvocationList().Length > 1) { throw new NotSupportedException("SmartThreadPool doesn't support delegates chains"); } diff --git a/ThirdParty/SmartThreadPool/WorkItemsGroup.cs b/ThirdParty/SmartThreadPool/WorkItemsGroup.cs index 5321bb62a7..e22756313e 100644 --- a/ThirdParty/SmartThreadPool/WorkItemsGroup.cs +++ b/ThirdParty/SmartThreadPool/WorkItemsGroup.cs @@ -16,7 +16,7 @@ namespace Amib.Threading.Internal { #region Private members - private readonly object _lock = new object(); + private readonly object _lock = new(); /// /// A reference to the SmartThreadPool instance that created this @@ -67,22 +67,19 @@ namespace Amib.Threading.Internal /// /// Signaled when all of the WorkItemsGroup's work item completed. /// - private readonly ManualResetEvent _isIdleWaitHandle = new ManualResetEvent(true); + private readonly ManualResetEvent _isIdleWaitHandle = new(true); /// /// A common object for all the work items that this work items group /// generate so we can mark them to cancel in O(1) /// - private CanceledWorkItemsGroup _canceledWorkItemsGroup = new CanceledWorkItemsGroup(); + private CanceledWorkItemsGroup _canceledWorkItemsGroup = new(); #endregion #region Construction - public WorkItemsGroup( - SmartThreadPool stp, - int concurrency, - WIGStartInfo wigStartInfo) + public WorkItemsGroup(SmartThreadPool stp, int concurrency, WIGStartInfo wigStartInfo) { if (concurrency <= 0) { @@ -236,10 +233,8 @@ namespace Amib.Threading.Internal [MethodImpl(MethodImplOptions.NoInlining)] private void FireOnIdleImpl(WorkItemsGroupIdleHandler onIdle) { - if(null == onIdle) - { + if(onIdle is null) return; - } Delegate[] delegates = onIdle.GetInvocationList(); foreach(WorkItemsGroupIdleHandler eh in delegates) @@ -298,7 +293,7 @@ namespace Amib.Threading.Internal } // If the work item is not null then enqueue it - if (null != workItem) + if (workItem is not null) { workItem.CanceledWorkItemsGroup = _canceledWorkItemsGroup; @@ -323,7 +318,7 @@ namespace Amib.Threading.Internal _stp.UnregisterWorkItemsGroup(this); IsIdle = true; _isIdleWaitHandle.Set(); - if (decrementWorkItemsInStpQueue && _onIdle != null && _onIdle.GetInvocationList().Length > 0) + if (decrementWorkItemsInStpQueue && _onIdle is not null && _onIdle.GetInvocationList().Length > 0) { _stp.QueueWorkItem(new WorkItemCallback(FireOnIdle)); } diff --git a/ThirdParty/SmartThreadPool/WorkItemsQueue.cs b/ThirdParty/SmartThreadPool/WorkItemsQueue.cs index f7a031ae3c..38bed47d8a 100644 --- a/ThirdParty/SmartThreadPool/WorkItemsQueue.cs +++ b/ThirdParty/SmartThreadPool/WorkItemsQueue.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using System.Threading; +using System.Runtime.CompilerServices; namespace Amib.Threading.Internal { @@ -16,7 +17,7 @@ namespace Amib.Threading.Internal /// /// Waiters queue (implemented as stack). /// - private readonly WaiterEntry _headWaiterEntry = new WaiterEntry(); + private readonly WaiterEntry _headWaiterEntry = new(); /// /// Waiters count @@ -26,7 +27,7 @@ namespace Amib.Threading.Internal /// /// Work items queue /// - private readonly Queue _workItems = new Queue(); + private readonly Queue _workItems = new(); /// /// Indicate that work items are allowed to be queued @@ -79,7 +80,7 @@ namespace Amib.Threading.Internal { // A work item cannot be null, since null is used in the // WaitForWorkItem() method to indicate timeout or cancel - if (workItem == null) + if (workItem is null) { throw new ArgumentNullException("workItem", "workItem cannot be null"); } @@ -112,7 +113,7 @@ namespace Amib.Threading.Internal public void CloseThreadWaiter() { - if(_waiterEntry != null) + if(_waiterEntry is not null) { _waiterEntry.Close(); _waiterEntry = null; @@ -187,8 +188,7 @@ namespace Amib.Threading.Internal // On success return the work item WorkItem workItem = waiterEntry.WorkItem; - if (workItem == null) - workItem = _workItems.Dequeue(); + workItem ??= _workItems.Dequeue(); return workItem; } @@ -262,7 +262,7 @@ namespace Amib.Threading.Internal /// objects each thread has its own WaiterEntry object. private static WaiterEntry GetThreadWaiterEntry() { - if (_waiterEntry == null) + if (_waiterEntry is null) { _waiterEntry = new WaiterEntry(); } @@ -284,7 +284,7 @@ namespace Amib.Threading.Internal RemoveWaiter(newWaiterEntry, false); // If the stack is empty then newWaiterEntry is the new head of the stack - if (null == _headWaiterEntry._nextWaiterEntry) + if (_headWaiterEntry._nextWaiterEntry is null) { _headWaiterEntry._nextWaiterEntry = newWaiterEntry; newWaiterEntry._prevWaiterEntry = _headWaiterEntry; @@ -325,7 +325,7 @@ namespace Amib.Threading.Internal // Update the new stack head _headWaiterEntry._nextWaiterEntry = newHeadWaiterEntry; - if (newHeadWaiterEntry != null) + if (newHeadWaiterEntry is not null) { newHeadWaiterEntry._prevWaiterEntry = _headWaiterEntry; } @@ -357,7 +357,7 @@ namespace Amib.Threading.Internal // If the waiter entry had a prev link then update it. // It also means that the waiter is already in the list and we // need to decrement the waiters count. - if (prevWaiterEntry != null) + if (prevWaiterEntry is not null) { prevWaiterEntry._nextWaiterEntry = nextWaiterEntry; popDecrement = true; @@ -366,7 +366,7 @@ namespace Amib.Threading.Internal // If the waiter entry had a next link then update it. // It also means that the waiter is already in the list and we // need to decrement the waiters count. - if (nextWaiterEntry != null) + if (nextWaiterEntry is not null) { nextWaiterEntry._prevWaiterEntry = prevWaiterEntry; popDecrement = true; @@ -391,7 +391,7 @@ namespace Amib.Threading.Internal /// /// Event to signal the waiter that it got the work item. /// - private AutoResetEvent _waitHandle = new AutoResetEvent(false); + private AutoResetEvent _waitHandle = new(false); /// /// Flag to know if this waiter already quited from the queue @@ -450,15 +450,14 @@ namespace Amib.Threading.Internal { lock (this) { - if (!_isTimedout) - { - _workItem = workItem; - _isSignaled = true; - _waitHandle.Set(); - return true; - } + if (_isTimedout) + return false; + + _workItem = workItem; + _isSignaled = true; + _waitHandle.Set(); + return true; } - return false; } /// @@ -472,15 +471,14 @@ namespace Amib.Threading.Internal { // Time out can happen only if the waiter wasn't marked as // signaled - if (!_isSignaled) - { - // We don't remove the waiter from the queue, the DequeueWorkItem - // method skips _waiters that were timed out. - _isTimedout = true; - return true; - } + if (_isSignaled) + return false; + + // We don't remove the waiter from the queue, the DequeueWorkItem + // method skips _waiters that were timed out. + _isTimedout = true; + return true; } - return false; } /// @@ -500,7 +498,7 @@ namespace Amib.Threading.Internal public void Close() { _workItem = null; - if (null != _waitHandle) + if (_waitHandle is not null) { _waitHandle.Close(); _waitHandle = null; @@ -546,6 +544,7 @@ namespace Amib.Threading.Internal } } + [MethodImpl(MethodImplOptions.AggressiveInlining)] private void ValidateNotDisposed() { if (_isDisposed)