Service本质就是一个驻留Process,驻留Prcess至少有一个驻留线程,这个线程处在waiting的状态(相对于Runable),控制流停在某个点上,等待外部事件驱动,或者是自己的timer驱动。
Windows Service
是一个exe,要有Main方法,Main方法要把一个继承了ServiceBase、实现了OnStart(), OnStop()等生命周期回调方法的Service类的实例注册给SCM。
当在Control Panel里启动一个Service, SCM其实就是运行程序调用Main方法,进而SCM会调用OnStart()方法。void Main() { DataGeneratorService service = new DataGeneratorService(args); System.ServiceProcess.ServiceBase.Run(service); }
安装Service就是把exe注册给控制面板,然后可以通过控制面板启动停止程序。Windows Service就是提供了一个帮助你管理驻留程序的界面。也可以不用,自己启动程序,自己发送消息结束process。
所有驻留Process都是一个模板: 一个循环,退出条件就是是否退出的一个flag, 然后要么阻塞在一个消息队列上,等待输入;要么就是一个timer,等待一段时间执行一次循环体。
OnStart的工作就是创建你的service Process的 驻留线程,在Mediaroom的Service里,有2个驻留线程,一个是heartbeat thread, 一个是workerMethod thread,
protected override void OnStart(String[] args)
{
tracer.Write(TracerLevel.Default, "{0} is starting", this.ServiceName);
// First, reset the event
serviceStoppedEvent = new ManualResetEvent(false);
// Kick off the pinging thread if it is active
pingingThread = new Thread(new ParameterizedThreadStart(PingingThreadMethod));
pingingThread.Name = "Pinging Thread";
pingingThread.Start(this);
// Kick off the worker thread.
workerThread = new Thread(new ParameterizedThreadStart(WorkerThreadMethod));
workerThread.Name = "Worker Thread";
workerThread.Start(this);
}
2个典型的驻留线程的模板
void WorkerThreadMethod () {
do {
//non-blocking logic
...
//if stopEvent set, exit, or wait intervalTime before next run
} while (stopEvent.WaitOne(intervalTime) == false)
}
void workerThreadMethod() {
do {
input = readInput(); // blocking call
...
} while (stopEvent.WaitOne(0) == false)
}
第一个是timer类型的驻留线程,第二个是等待IO型的驻留线程。
每个线程(控制流)就像一列火车,要么运行,要么停止,决定它停止或运行的是信号,也就是说一个线程必然依赖一些信号,所谓的blocking call底层就是wait到一个信号,当IO准备好数据,信号变为”可通行“,线程才接着运行。至于临界区是指那些线程之间的交叉点,十字路口,必须确保火车不相撞。
Service,即驻留process就是,等在信号上的线程。对象之间的交互是直接调用服务、相互发消息,线程之间交互式是通过信号,一个对象可以接受很多消息,但一个线程一般不会有很多依赖的信号,一般就一个,所以考虑线程的时候一定要考虑线程依赖的信号。
调用一个线程的服务,放置输入数据 + 发送信号,