Rust编写Windows服务
编写Windows服务可选语言很多, 其中C#最简单。本着练手Rust语言,尝试用Rust编写一个服务。
一:Windows服务程序大致原理
参考官网C/C++创建服务流程
https://learn.microsoft.com/zh-cn/windows/win32/services/service-program-tasks
- 编写服务程序的main函数
- main函数中,填充数据结构
DispatchTable
: [[服务名,ServiceMain函数], [NULL, NULL]] - 调用
StartServiceCtrlDispatcher( DispatchTable )
- main函数中,填充数据结构
int __cdecl _tmain(int argc, TCHAR *argv[])
{
SERVICE_TABLE_ENTRY DispatchTable[] =
{
{
SVCNAME, (LPSERVICE_MAIN_FUNCTION) SvcMain },
{
NULL, NULL }
};
if (!StartServiceCtrlDispatcher( DispatchTable ))
{
SvcReportEvent(TEXT("StartServiceCtrlDispatcher"));
}
}
- 编写 ServiceMain 函数
- 注册控制处理函数
RegisterServiceCtrlHandler(SvcCtrlHandler )
- 设置服务状态,SERVICE_START_PENDING
- 做一些预备工作,比如初始化日志/注册事件等
- 设置服务状态,SERVICE_START_RUNNING
- 开始loop处理我们自己的代码(loop循环中可以接受3中注册的事件,当通知停止时退出循环)
- 注册控制处理函数
- 编写控件处理程序函数
- 接受事件管理器发送的消息并处理,比如收到
SERVICE_CONTROL_STOP
时,使用3中注册的事件句柄发送停止事件
- 接受事件管理器发送的消息并处理,比如收到
二:Rust中编写windows服务
借用第三方库
windows-service = "0.7.0"
https://crates.io/crates/windows-service
参考windows-service
中ping-service示例提取了一个模板,只有替换编写两处/* */代码
use std::{
ffi::OsString,
sync::mpsc,
time::Duration,
};
use windows_service::{
define_windows_service,
service::{
ServiceControl, ServiceControlAccept, ServiceExitCode, ServiceState, ServiceStatus,
ServiceType,
},
service_control_handler::{
self, ServiceControlHandlerResult},
service_dispatcher,
};
static SERVICE_NAME: &str = "Rust Demo Service";
fn main() -> Result<(), windows_service::Error> {
service_dispatcher::start(SERVICE_NAME, ffi_service_main)?;
Ok(())
}
define_windows_service!(ffi_service_main, my_service_main);
fn my_service_main(arguments: Vec<OsString>) {
let _ = arguments;
/*
这里服务还没开始, 可以填写初始化日志文件等操作
*/
let (shutdown_tx, shutdown_rx) = mpsc::channel();
// 对应SvcCtrlHandler
let _event_handler = move |control_event| -> ServiceControlHandlerResult {
match control_event {
ServiceControl