When configuring a Windows Service, the startup parameters passed to the ServiceBase.Run()
method play a crucial role in service initialization. A common concern among developers is whether these parameters persist after system reboots when the service startup type is set to "Automatic".
Windows Services configured with Automatic startup type do not preserve command-line parameters across reboots by default. The service control manager (SCM) starts automatic services without any parameters.
// This is how you typically start a service with parameters
static void Main()
{
ServiceBase[] ServicesToRun;
ServicesToRun = new ServiceBase[]
{
new MyService(args) // Parameters passed here
};
ServiceBase.Run(ServicesToRun);
}
To maintain parameters between restarts, consider these approaches:
1. Registry Storage
Store parameters in the Windows Registry during service operation:
// Saving parameters to registry
Microsoft.Win32.RegistryKey key = Microsoft.Win32.Registry.LocalMachine.CreateSubKey(@"SOFTWARE\MyService");
key.SetValue("StartParams", string.Join("|", args));
key.Close();
// Retrieving during service start
string[] savedParams = ((string)key.GetValue("StartParams", "")).Split('|');
2. Configuration Files
Use application configuration files (app.config/web.config) or custom config files:
<configuration>
<appSettings>
<add key="ServiceParam1" value="value1"/>
<add key="ServiceParam2" value="value2"/>
</appSettings>
</configuration>
3. Service Recovery Options
Configure recovery actions to restart with parameters:
sc failure "MyService" reset= 0 actions= restart/60000/restart/60000/restart/60000
For robust parameter handling, implement a hybrid approach combining configuration files with registry fallback:
public string[] GetStartupParameters()
{
// Try config file first
var configParams = ConfigurationManager.AppSettings["ServiceParams"];
if (!string.IsNullOrEmpty(configParams))
return configParams.Split('|');
// Fallback to registry
using (var key = Registry.LocalMachine.OpenSubKey(@"SOFTWARE\MyService"))
{
if (key != null)
{
var regParams = key.GetValue("StartParams") as string;
if (!string.IsNullOrEmpty(regParams))
return regParams.Split('|');
}
}
return new string[0]; // Default empty parameters
}
- Security: Always validate and sanitize stored parameters
- Encryption: Consider encrypting sensitive parameters in storage
- Change Detection: Implement mechanisms to detect parameter changes
- Logging: Maintain logs of parameter changes and service startups
When configuring a Windows Service, developers often need to pass startup parameters to control service behavior. These parameters are typically specified when manually starting the service using the sc start
command or the Service Control Manager. However, the persistence of these parameters becomes particularly important when dealing with services configured for automatic startup.
For services with StartupType = Automatic
, Windows does not preserve start parameters across system reboots. This is by design - automatic startup initiates the service without any parameters, using only the configuration stored in the registry.
// Example of setting parameters during manual start
sc start MyService param1 param2
The proper way to persist startup parameters is through the service's registry configuration. The parameters should be stored in the ImagePath
value under the service's registry key:
HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\MyService
Here are two common methods to implement persistent parameters:
1. Direct Registry Modification
// C# example of modifying registry
using Microsoft.Win32;
RegistryKey key = Registry.LocalMachine.OpenSubKey(
@"SYSTEM\CurrentControlSet\Services\MyService", true);
if (key != null)
{
string imagePath = key.GetValue("ImagePath").ToString();
key.SetValue("ImagePath", imagePath + " -param1 -param2");
key.Close();
}
2. Using SC Command
sc config MyService binPath= "\"C:\Path\To\Service.exe\" -param1 -param2"
For complex scenarios, consider using external configuration files:
// In service code:
var config = ConfigurationManager.AppSettings["ServiceParam"];
When storing parameters in registry or configuration files:
- Use appropriate registry permissions
- Consider encrypting sensitive parameters
- Validate all input parameters
To confirm your parameters are properly set:
sc qc MyService