服务中如何接受服务管理器传入的启动参数?
How to Get startup parameters via SCM in my Delphi program?
By Kingron, 2006
主要让大家看看我解决问题的思路!结果还是其次。
我第一反应是使用ImagePath,首先可以使用命令行,即服务在注册的时候,可以自己写注册表:
procedure TFleetDB . ServiceAfterInstall ( Sender : TService ); begin RegWriteString ( HKEY_LOCAL_MACHINE , CSRegServiceURL + Name , CSRegDescription , CSServiceDescription ); RegWriteString ( HKEY_LOCAL_MACHINE , CSRegServiceURL + Name , CSRegImagePath , ParamStr ( 0 ) + ' -svc' ); end ; procedure TFleetDB . ServiceBeforeInstall ( Sender : TService ); begin RegValueDelete ( HKEY_LOCAL_MACHINE , CSRegServiceURL + Name , CSRegDescription ); end ;
这样可以永久起作用!
但是我们使用服务管理器(Services.msc,SCM),可以打开某个服务的属性对话框,然后其中有一个startup parameters,可以输入,然后手动启动服务,传送这个参数给服务,Delphi中如何来实现呢?最开始我写了一个程序,以为可以从命令行获取,结果验证不行,后来怀疑Windows是否让这个起作用?于是用SCM带参数/testabcd123启动服务,用WinHex打开服务查看内存,发现内存中的确有/testabcd123这个参数,因此说明服务是可以传递并接受参数的。接着我查找了MSDN,发现其中有ServiceMain()这个过程,原来就在这里!打开Delphi的SvcMgr单元找到ServiceApplication的消息处理过程,一路追查,找到 TService(Components[i]).Main(Argc, Argv);继续追查,找到Main方法,发现原来Delphi已经处理过,收到的参数全部存储在ParamCount和Param[]数组中~。
可以用以下方法验证:
procedure TDemoService.ServiceStart(Sender: TService; var Started: Boolean);
var
i : Integer;
begin
for i := 0 to ParamCount - 1 do
WriteLog(ltInfo, Param[i]);
end;