void IScheduledRunnable.SetConsumed() { // Optimization to avoid checking system clock again // after deadline has passed and task has been dequeued if (0ul >= (ulong)_periodNanos) { Debug.Assert(PreciseTime.NanoTime() >= _deadlineNanos); _deadlineNanos = 0L; } }
public virtual void Run() { Debug.Assert(Executor.InEventLoop); try { if ((ulong)DelayNanos > 0UL) // DelayNanos >= 0 { // Not yet expired, need to add or remove from queue if (Promise.IsCanceled) { _ = Executor._scheduledTaskQueue.TryRemove(this); } else { Executor.ScheduleFromEventLoop(this); } return; } if (0ul >= (ulong)_periodNanos) { if (TrySetUncancelable()) { Execute(); _ = Promise.TryComplete(); } } else { // check if is done as it may was cancelled if (!Promise.IsCanceled) { Execute(); if (!Executor.IsShutdown) { if (_periodNanos > 0) { _deadlineNanos += _periodNanos; } else { _deadlineNanos = PreciseTime.NanoTime() - _periodNanos; } if (!Promise.IsCanceled) { _ = Executor._scheduledTaskQueue.TryEnqueue(this); } } } } } catch (Exception exc) { _ = Promise.TrySetException(exc); } }
internal long RunScheduledTasks() { var time = PreciseTime.NanoTime(); while (true) { IRunnable task = PollScheduledTask(time); if (task is null) { return(NextScheduledTaskNanos()); } task.Run(); } }
/// <summary> /// Return <c>true</c> if at least one scheduled task was executed. /// </summary> private bool ExecuteExpiredScheduledTasks() { if (_scheduledTaskQueue.IsEmpty) { return(false); } var nanoTime = PreciseTime.NanoTime(); var scheduledTask = PollScheduledTask(nanoTime); if (scheduledTask is null) { return(false); } do { SafeExecute(scheduledTask); } while ((scheduledTask = PollScheduledTask(nanoTime)) is object); return(true); }
private bool FetchFromScheduledTaskQueue() { if (_scheduledTaskQueue.IsEmpty) { return(true); } var nanoTime = PreciseTime.NanoTime(); IScheduledRunnable scheduledTask = PollScheduledTask(nanoTime); while (scheduledTask is object) { if (!_taskQueue.TryEnqueue(scheduledTask)) { // No space left in the task queue add it back to the scheduledTaskQueue so we pick it up again. _ = _scheduledTaskQueue.TryEnqueue(scheduledTask); return(false); } scheduledTask = PollScheduledTask(nanoTime); } return(true); }
public void TestGracefulShutdownQuietPeriod() { _loopA.ShutdownGracefullyAsync(TimeSpan.FromSeconds(1), TimeSpan.FromDays(1)); // Keep Scheduling tasks for another 2 seconds. for (int i = 0; i < 20; i++) { Thread.Sleep(100); _loopA.Execute(NOOP.Instance); } long startTime = PreciseTime.NanoTime(); Assert.True(_loopA.IsShuttingDown); Assert.False(_loopA.IsShutdown); while (!_loopA.IsTerminated) { _loopA.WaitTermination(TimeSpan.FromDays(1)); } Assert.True(PreciseTime.NanoTime() - startTime >= PreciseTime.ToDelayNanos(TimeSpan.FromSeconds(1))); }
protected bool FetchFromScheduledTaskQueue() { if (ScheduledTaskQueue.IsEmpty) { return(true); } var nanoTime = PreciseTime.NanoTime(); var scheduledTask = PollScheduledTask(nanoTime); var taskQueue = _taskQueue; while (scheduledTask is object) { if (!taskQueue.TryEnqueue(scheduledTask)) { // No space left in the task queue add it back to the scheduledTaskQueue so we pick it up again. _ = ScheduledTaskQueue.TryEnqueue(scheduledTask); return(false); } scheduledTask = PollScheduledTask(nanoTime); } return(true); }
public void GracefulShutdownQuietPeriod() { Task task = this.eventLoop.ShutdownGracefullyAsync(TimeSpan.FromSeconds(1), TimeSpan.MaxValue); // Keep Scheduling tasks for another 2 seconds. for (int i = 0; i < 20; i++) { Thread.Sleep(100); this.eventLoop.Execute(new NoOp()); } long startTime = PreciseTime.NanoTime(); Assert.True(this.eventLoop.IsShuttingDown); Assert.False(this.eventLoop.IsShutdown); Assert.True(task.Wait(DefaultTimeout), "Loop shutdown timed out"); Assert.True(this.eventLoop.IsShuttingDown); Assert.True(this.eventLoop.IsShutdown); long duration = (long)PreciseTime.ToTimeSpan(PreciseTime.NanoTime() - startTime).TotalMilliseconds; Assert.True(duration >= 1000, $"Expecting shutdown quite period >= 1000 milliseconds, but was {duration}"); }
protected static long NanoTime() => PreciseTime.NanoTime();
/// <summary> /// Returns <c>true</c> if a scheduled task is ready for processing. /// </summary> protected bool HasScheduledTasks() { return(ScheduledTaskQueue.TryPeek(out IScheduledRunnable scheduledTask) && scheduledTask.DeadlineNanos <= PreciseTime.NanoTime()); }
protected virtual long GetTimeFromStart() { return(PreciseTime.NanoTime()); }
public static PreciseTimeSpan Deadline(TimeSpan deadline) => new PreciseTimeSpan(PreciseTime.NanoTime() + PreciseTime.TicksToPreciseTicks(deadline.Ticks));