internal CancellationTokenRegistration InternalRegister(Action <object> callback, object stateForCallback, SynchronizationContext targetSyncContext, ExecutionContext executionContext) { this.ThrowIfDisposed(); if (!this.IsCancellationRequested) { int num = Thread.CurrentThread.ManagedThreadId % CancellationTokenSource.s_nLists; CancellationCallbackInfo cancellationCallbackInfo = new CancellationCallbackInfo(callback, stateForCallback, targetSyncContext, executionContext, this); if (this.m_registeredCallbacksLists == null) { SparselyPopulatedArray <CancellationCallbackInfo>[] value = new SparselyPopulatedArray <CancellationCallbackInfo> [CancellationTokenSource.s_nLists]; Interlocked.CompareExchange <SparselyPopulatedArray <CancellationCallbackInfo>[]>(ref this.m_registeredCallbacksLists, value, null); } if (this.m_registeredCallbacksLists[num] == null) { SparselyPopulatedArray <CancellationCallbackInfo> value2 = new SparselyPopulatedArray <CancellationCallbackInfo>(4); Interlocked.CompareExchange <SparselyPopulatedArray <CancellationCallbackInfo> >(ref this.m_registeredCallbacksLists[num], value2, null); } SparselyPopulatedArrayAddInfo <CancellationCallbackInfo> registrationInfo = this.m_registeredCallbacksLists[num].Add(cancellationCallbackInfo); CancellationTokenRegistration result = new CancellationTokenRegistration(this, cancellationCallbackInfo, registrationInfo); if (!this.IsCancellationRequested) { return(result); } if (!result.TryDeregister()) { this.WaitForCallbackToComplete(cancellationCallbackInfo); return(default(CancellationTokenRegistration)); } } callback(stateForCallback); return(default(CancellationTokenRegistration)); }
internal void WaitForCallbackToComplete(CancellationCallbackInfo callbackInfo) { SpinWait spinWait = default(SpinWait); while (this.ExecutingCallback == callbackInfo) { spinWait.SpinOnce(); } }
internal void ExecuteCallback() { if (this.TargetExecutionContext != null) { ExecutionContext.Run(this.TargetExecutionContext, new ContextCallback(CancellationCallbackInfo.ExecutionContextCallback), this); return; } CancellationCallbackInfo.ExecutionContextCallback(this); }
private void CancellationCallbackCoreWork_OnSyncContext(object obj) { CancellationCallbackCoreWorkArguments cancellationCallbackCoreWorkArguments = (CancellationCallbackCoreWorkArguments)obj; CancellationCallbackInfo cancellationCallbackInfo = cancellationCallbackCoreWorkArguments.m_currArrayFragment.SafeAtomicRemove(cancellationCallbackCoreWorkArguments.m_currArrayIndex, this.m_executingCallback); if (cancellationCallbackInfo == this.m_executingCallback) { if (cancellationCallbackInfo.TargetExecutionContext != null) { cancellationCallbackInfo.CancellationTokenSource.ThreadIDExecutingCallbacks = Thread.CurrentThread.ManagedThreadId; } cancellationCallbackInfo.ExecuteCallback(); } }
internal CancellationTokenRegistration(CancellationTokenSource tokenSource, CancellationCallbackInfo callbackInfo, SparselyPopulatedArrayAddInfo <CancellationCallbackInfo> registrationInfo) { this.m_tokenSource = tokenSource; this.m_callbackInfo = callbackInfo; this.m_registrationInfo = registrationInfo; }
private static void ExecutionContextCallback(object obj) { CancellationCallbackInfo cancellationCallbackInfo = obj as CancellationCallbackInfo; cancellationCallbackInfo.Callback(cancellationCallbackInfo.StateForCallback); }