Impersonate as SYSTEM

I want to access files stored under "X:\System Volume Information" but I cannot do so even with Admin provoleges. I have seen virus scanners (McAfee to be specific) scan that folder even when a "User" is loggen on. I bet the process runs with SYSTEM privileges - a bit higher than Admin. How can I impersonate the SYSTEM account?

the actual goal is to read file information from that folder. so if there is a way to access that info without impersonation that would be much better from security standpoint. I am looking for a solution in .NET but C/C++ would work.
Who is Participating?

[Product update] Infrastructure Analysis Tool is now available with Business Accounts.Learn More

I wear a lot of hats...

"The solutions and answers provided on Experts Exchange have been extremely helpful to me over the last few years. I wear a lot of hats - Developer, Database Administrator, Help Desk, etc., so I know a lot of things but not a lot about one thing. Experts Exchange gives me answers from people who do know a lot about one thing, in a easy to use platform." -Todd S.

>>How can I impersonate the SYSTEM account?

The easiest way would IMO be a small service that - by default - runs as 'LocalSystem' to gather that information. Youcould also obtain a token from a process that is running under that account(services.exe or svchost.exe is a good choice <s>). You'll need the PID to call 'OpenProcess()', then 'OpenProcessToken()' with 'TOKEN_IMPERSONATE' access. See;EN-US;q175030 ("HOWTO: Enumerate Applications Using Win32 APIs (Q175030)") on how to get that PID - it comes with sample code. Then, once you have the token, you have to call 'ImpersonateLoggedOnUser()', et voilà, you are there.
jhshuklaAuthor Commented:
ok that makes sense. is there a way to impersonate the SYSTEM without getting a list of processes?
jhshuklaAuthor Commented:
I got to the point where i can get process handles from PID but OpenProcessToken fails with GetLastError = 5 (Access denied). here is relevant code (C#):
            private void Impersonate()
                  int pid = GetSystemPID();

                  const int TOKEN_IMPERSONATE = 0x0004; // copied from WinNT.h
                  const int READ_CONTROL = 0x00020000; // copied from WinNT.h
                  const int PROCESS_QUERY_INFORMATION = 0x0040; // copied from WinNT.h
                  int tokenHandle = 0;
                  int proc = OpenProcess(READ_CONTROL | PROCESS_QUERY_INFORMATION, false, pid);
                  bool returnValue = OpenProcessToken(proc, TOKEN_IMPERSONATE, ref tokenHandle);
                  if ( returnValue == true )
                        MessageBox.Show("Token Obtained");
                        MessageBox.Show(String.Format("Error {0}", GetLastError()));

            private int GetSystemPID()
                  System.Diagnostics.Process[] procs = System.Diagnostics.Process.GetProcesses(); // lists ALL running processes, even those that don't appear in TaskMgr
                  for ( int i=0; i<procs.Length; i++ )
                        if ( procs[i].ProcessName.CompareTo("System") == 0) // THE system process other than SysIdleProc. PID = 4
                              return procs[i].Id;
                  return -1;
Exploring SQL Server 2016: Fundamentals

Learn the fundamentals of Microsoft SQL Server, a relational database management system that stores and retrieves data when requested by other software applications.

jhshuklaAuthor Commented:
one more piece of info. gives me the same error even if i try to get the token from the current process.
Hm, what account are you running that under?

Also, would be using a service too much effort?
jhshuklaAuthor Commented:
Admin account, and where did i say i run a service? it is just a regular .NET application.
>>and where did i say i run a service?

Nowhere, I brought that up earlier, since services run under 'LocalSystem' natively and therefore can access that directory.
jhshuklaAuthor Commented:
yes it would be too much effort. this program just reads and reports disk usage for all folders on given drive. too much effort to run the program. not too much to change the settings to make a service.
another thing that is noticed was that mcconsol.exe (GUI to McAfee) ran as admin and was still able to access SysVolInfo. I wonder if it was using a service to get raw data.
jhshuklaAuthor Commented:
I had to combine TOKEN_IMPERSONATE | TOKEN_QUERY to get the token for a process. I can impersonate as admin through any other process started by admin but I am still unable to impersonate as the localsystem.
Bad news here, too. I did some experiments (even though I did not mention that here, sorry) and checked some earlier projects, but the security set on that process does not seem to allow to get an impersonation token even from a process that runs as admin. What I did in the past to overcome that all ends up with having a service running and communicate with that one, so that ends up in a circle...
jhshuklaAuthor Commented:
okay, I do not plan to release the prog to anyone else. it will be running only on my machine and i know that i will have certain services running all the time. is it possible to impersonate the system using token from any other process? i haven't had luck so far. I have been requesting minimal privileges:

      retVal = OpenProcessToken(hProc, TOKEN_IMPERSONATE | TOKEN_QUERY | STANDARD_RIGHTS_READ, &hToken);
jhshuklaAuthor Commented:
another thought. what if i create an on-demand service? will that service run with localsystem privileges? what i plan to do is create a launcher application that will start the service and the service will do whatever my original application was supposed to do.
Easiest way to impersonate system is with the built-in scheduler service.

Just run at (current time + 2 minutes) /interactive cmd.exe

Then you'll have a command prompt running as SYSTEM, you can do pretty much anything.

Of course you may eventually need to automate your tasks as a standalone service, but this works great for testing.

Note that running taskmgr as SYSTEM lets you "end process" on protected system services.

Experts Exchange Solution brought to you by

Your issues matter to us.

Facing a tech roadblock? Get the help and guidance you need from experienced professionals who care. Ask your question anytime, anywhere, with no hassle.

Start your 7-day free trial
>>what if i create an on-demand service? will that service run with localsystem privileges?

Yes, that's what I am having in mind and currently am working on... it's just not non-trivial, and I am quite busy, so bear with me.
jhshuklaAuthor Commented:
>> Easiest way to impersonate system is with the built-in scheduler service.
>> Just run at (current time + 2 minutes) /interactive cmd.exe
how? where?

>> it's just not non-trivial
do two negations mean it is trivial?
The command called "at"....

The AT command schedules commands and programs to run on a computer at
a specified time and date. The Schedule service must be running to use
the AT command.

AT [\\computername] [ [id] [/DELETE] | /DELETE [/YES]]
AT [\\computername] time [/INTERACTIVE]
    [ /EVERY:date[,...] | /NEXT:date[,...]] "command"

\\computername     Specifies a remote computer. Commands are scheduled on the
                   local computer if this parameter is omitted.
id                 Is an identification number assigned to a scheduled
/delete            Cancels a scheduled command. If id is omitted, all the
                   scheduled commands on the computer are canceled.
/yes               Used with cancel all jobs command when no further
                   confirmation is desired.
time               Specifies the time when command is to run.
/interactive       Allows the job to interact with the desktop of the user
                   who is logged on at the time the job runs.
/every:date[,...]  Runs the command on each specified day(s) of the week or
                   month. If date is omitted, the current day of the month
                   is assumed.
/next:date[,...]   Runs the specified command on the next occurrence of the
                   day (for example, next Thursday).  If date is omitted, the
                   current day of the month is assumed.
"command"          Is the Windows NT command, or batch program to be run.
jhshuklaAuthor Commented:
isn't it equivalent to "scheduled task"?
jhshuklaAuthor Commented:
thanks both of you guys.
The "at" command and scheduled tasks both use the scheduler service, but they give you different options.  I don't know any way using at to schedule for startup, shutdown, or idle, which you can do with the scheduled tasks property page.  At does let you run as SYSTEM and interact with the program graphically, which Scheduled Tasks doesn't/
It's more than this solution.Get answers and train to solve all your tech problems - anytime, anywhere.Try it for free Edge Out The Competitionfor your dream job with proven skills and certifications.Get started today Stand Outas the employee with proven skills.Start learning today for free Move Your Career Forwardwith certification training in the latest technologies.Start your trial today
Microsoft Development

From novice to tech pro — start learning today.