I have a C# Windows service running with elevated privileges. One of the service's jobs is to create a new local user account and perform some setup tasks with that account (set some registry settings, et cetera). The service is running under the "Local System" account.
Privileges in manifest
<requestedExecutionLevel level="requireAdministrator" uiAccess="false" />
Code that spawns the process
using (var proc = new Process())
using (var password = new SecureString())
{
foreach (var c in accountPassword)
{
password.AppendChar(c);
}
proc.StartInfo = new ProcessStartInfo(
pathToExecutable,
arguments)
{
LoadUserProfile = true,
UseShellExecute = false,
CreateNoWindow = true,
RedirectStandardError = true,
RedirectStandardInput = true,
RedirectStandardOutput = true,
Domain = accountDomain,
UserName = accountName,
Password = password
};
StringWriter outWriter = new StringWriter(), errWriter = new StringWriter();
proc.OutputDataReceived += (o, e) => outWriter.Write(e.Data);
proc.ErrorDataReceived += (o, e) => errWriter.Write(e.Data);
proc.EnableRaisingEvents = true;
proc.Start(); // <-- exception thrown here
...
Resulting exception
System.ComponentModel.Win32Exception (0x80004005): Access is denied at System.Diagnostics.Process.StartWithCreateProcess(ProcessStartInfo startInfo) at ...
Experiments
If I go to the local services control panel, I can change the service so it runs as the administrator's account (i.e. "JoeAdmin", not "administrator"), and the program is successful. Here is the part that gets frustrating: I tried running whoami.exe /priv
from the service to see what privileges I had as "JoeAdmin" that I didn't have as "Local System" that would cause the program to fail. Spoiler: according to whoami, "Local System" has all of the privileges that "JoeAdmin" has, with one exception (SeRemoteShutdownPrivilege, and I hope that's not important).
Priviliges for Local System
(As a reminder, the operation failed with these privileges.)
PRIVILEGES INFORMATION ---------------------- Privilege Name Description State =============================== ========================================= ======== SeAssignPrimaryTokenPrivilege Replace a process level token Disabled SeLockMemoryPrivilege Lock pages in memory Enabled SeIncreaseQuotaPrivilege Adjust memory quotas for a process Disabled SeTcbPrivilege Act as part of the operating system Enabled SeSecurityPrivilege Manage auditing and security log Disabled SeTakeOwnershipPrivilege Take ownership of files or other objects Disabled SeLoadDriverPrivilege Load and unload device drivers Disabled SeSystemProfilePrivilege Profile system performance Enabled SeSystemtimePrivilege Change the system time Disabled SeProfileSingleProcessPrivilege Profile single process Enabled SeIncreaseBasePriorityPrivilege Increase scheduling priority Enabled SeCreatePagefilePrivilege Create a pagefile Enabled SeCreatePermanentPrivilege Create permanent shared objects Enabled SeBackupPrivilege Back up files and directories Disabled SeRestorePrivilege Restore files and directories Disabled SeShutdownPrivilege Shut down the system Disabled SeDebugPrivilege Debug programs Enabled SeAuditPrivilege Generate security audits Enabled SeSystemEnvironmentPrivilege Modify firmware environment values Disabled SeChangeNotifyPrivilege Bypass traverse checking Enabled SeUndockPrivilege Remove computer from docking station Disabled SeManageVolumePrivilege Perform volume maintenance tasks Disabled SeImpersonatePrivilege Impersonate a client after authentication Enabled SeCreateGlobalPrivilege Create global objects Enabled SeIncreaseWorkingSetPrivilege Increase a process working set Enabled SeTimeZonePrivilege Change the time zone Enabled SeCreateSymbolicLinkPrivilege Create symbolic links Enabled
Privileges for JoeAdmin
(The operation succeeded with these privileges.)
PRIVILEGES INFORMATION ---------------------- Privilege Name Description State =============================== ========================================= ======== SeIncreaseQuotaPrivilege Adjust memory quotas for a process Disabled SeSecurityPrivilege Manage auditing and security log Disabled SeTakeOwnershipPrivilege Take ownership of files or other objects Disabled SeLoadDriverPrivilege Load and unload device drivers Disabled SeSystemProfilePrivilege Profile system performance Disabled SeSystemtimePrivilege Change the system time Disabled SeProfileSingleProcessPrivilege Profile single process Disabled SeIncreaseBasePriorityPrivilege Increase scheduling priority Disabled SeCreatePagefilePrivilege Create a pagefile Disabled SeBackupPrivilege Back up files and directories Disabled SeRestorePrivilege Restore files and directories Disabled SeShutdownPrivilege Shut down the system Disabled SeDebugPrivilege Debug programs Disabled SeSystemEnvironmentPrivilege Modify firmware environment values Disabled SeChangeNotifyPrivilege Bypass traverse checking Enabled SeRemoteShutdownPrivilege Force shutdown from a remote system Disabled SeUndockPrivilege Remove computer from docking station Disabled SeManageVolumePrivilege Perform volume maintenance tasks Disabled SeImpersonatePrivilege Impersonate a client after authentication Enabled SeCreateGlobalPrivilege Create global objects Enabled SeIncreaseWorkingSetPrivilege Increase a process working set Disabled SeTimeZonePrivilege Change the time zone Disabled SeCreateSymbolicLinkPrivilege Create symbolic links Disabled
The question
Can I spawn the process from the Local System account? Or,
The service is installed by a WiX installer, is there a way I can give the service the correct privileges from the installer?
<ServiceInstall
Id="ServiceInstaller"
Type="ownProcess"
Name="MyCoolService"
DisplayName="My Cool Service"
Description="My Cool Service Component"
Start="auto"
ErrorControl="normal" />