/*
* Process Hacker -
* timer
*
* Copyright (C) 2009 wj32
*
* This file is part of Process Hacker.
*
* Process Hacker is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* Process Hacker is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with Process Hacker. If not, see .
*/
using System;
using ProcessHacker.Native.Api;
using ProcessHacker.Native.Objects;
using ProcessHacker.Native.Security;
namespace ProcessHacker.Native.Threading
{
///
/// Represents a callback to be called when a timer is signaled.
///
/// The context passed when the timer was set.
public delegate void TimerCallback(IntPtr context);
///
/// Represents a timer.
///
public sealed class Timer : NativeObject
{
private TimerCallback _callback;
///
/// Creates a timer.
///
public Timer()
: this(null)
{ }
///
/// Creates a timer.
///
///
/// Whether the timer should automatically reset to a
/// non-signaled state after waiters have been released.
///
public Timer(bool autoReset)
: this(null, autoReset)
{ }
///
/// Creates or opens a timer.
///
///
/// The name of the new timer, or the name of an existing timer.
///
public Timer(string name)
: this(name, false)
{ }
///
/// Creates a timer.
///
/// The name of the new timer.
///
/// Whether the timer should automatically reset to a
/// non-signaled state after waiters have been released.
///
public Timer(string name, bool autoReset)
{
this.Handle = TimerHandle.Create(
TimerAccess.All,
name,
ObjectFlags.OpenIf,
null,
autoReset ? TimerType.SynchronizationTimer : TimerType.NotificationTimer
);
}
///
/// Gets the remaining time before the timer is signaled.
///
public TimeSpan RemainingTime
{
get { return new TimeSpan(this.Handle.GetBasicInformation().RemainingTime); }
}
///
/// Gets whether the timer is signaled.
///
public bool Signaled
{
get { return this.Handle.GetBasicInformation().TimerState; }
}
///
/// Cancels the timer, preventing it from being signaled.
///
public void Cancel()
{
this.Handle.Cancel();
}
///
/// Starts the timer.
///
/// The due time, in milliseconds.
public void Set(int dueTime)
{
this.Set(dueTime, 0);
}
///
/// Starts the timer.
///
/// The due time, in milliseconds.
/// The interval to use for periodic signaling, in milliseconds.
public void Set(int dueTime, int period)
{
this.Set(null, dueTime, period);
}
///
/// Starts the timer.
///
/// A function to be called when the timer is signaled.
/// The due time, in milliseconds.
/// The interval to use for periodic signaling, in milliseconds.
public void Set(TimerCallback callback, int dueTime, int period)
{
this.Set(callback, dueTime, period, IntPtr.Zero);
}
///
/// Starts the timer.
///
/// A function to be called when the timer is signaled.
/// The due time, in milliseconds.
/// The interval to use for periodic signaling, in milliseconds.
/// A value to pass to the callback function.
public void Set(TimerCallback callback, int dueTime, int period, IntPtr context)
{
TimerApcRoutine apcRoutine = (context_, lowPart, highPart) => callback(context_);
_callback = callback;
this.Handle.Set(
dueTime * Win32.TimeMsTo100Ns,
true,
callback != null ? apcRoutine : null,
context,
period
);
}
///
/// Starts the timer.
///
/// The time at which the timer will be signaled.
public void Set(DateTime dueTime)
{
this.Set(dueTime, 0);
}
///
/// Starts the timer.
///
/// The time at which the timer will be signaled.
/// The interval to use for periodic signaling, in milliseconds.
public void Set(DateTime dueTime, int period)
{
this.Set(null, dueTime, period);
}
///
/// Starts the timer.
///
/// A function to be called when the timer is signaled.
/// The time at which the timer will be signaled.
/// The interval to use for periodic signaling, in milliseconds.
public void Set(TimerCallback callback, DateTime dueTime, int period)
{
this.Set(callback, dueTime, period, IntPtr.Zero);
}
///
/// Starts the timer.
///
/// A function to be called when the timer is signaled.
/// The time at which the timer will be signaled.
/// The interval to use for periodic signaling, in milliseconds.
/// A value to pass to the callback function.
public void Set(TimerCallback callback, DateTime dueTime, int period, IntPtr context)
{
TimerApcRoutine apcRoutine = (context_, lowPart, highPart) => callback(context_);
_callback = callback;
this.Handle.Set(
dueTime.ToFileTime(),
false,
callback != null ? apcRoutine : null,
context,
period
);
}
}
}