Discussion:
CreateProcessAsUser fails with error code 2 (file not found)
(too old to reply)
e***@gmail.com
2008-12-03 00:32:17 UTC
Permalink
I have code that works on XP and Vista, on about 20 different test
PCs, except on one XP system CreateProcessAsUser fails sometimes.
Here is the code, without error checking:

OpenProcessToken(GetCurrentProcess(),TOKEN_ALL_ACCESS,&t);

DuplicateTokenEx
(t,TOKEN_ALL_ACCESS,NULL,SecurityImpersonation,TokenPrimary,&dt);

DWORD sid = WTSGetActiveConsoleSessionId();
SetTokenInformation(dt,TokenSessionId,&sid,sizeof(sid));

STARTUPINFO si;
memset(&si,0,sizeof(si));
si.cb = sizeof(si);
si.lpDesktop = "winsta0\\default";

CreateProcessAsUser(dt,NULL,"c:\myfile.exe",
NULL,NULL,FALSE,NORMAL_PRIORITY_CLASS|CREATE_NEW_CONSOLE,
NULL,NULL,&si,&UserModeProcessInfo);

The code runs in a service running as LocalSystem. I want the process
to run as LocalSystem also (I know the security risks).

If the active console session ID is 0, the code always works. If non-
zero (1, 2, 3, etc), only one on XP system the CreateProcessAsUser
fails and GetLastError() returns 2 (file not found). I can add a
check right before that call to see if the file exists, and it does.
I can change form myfile.exe to notepad.exe or some other system EXE,
and get the same results. If I force to code to always use session ID
0 then it also works, but of course the app runs on the wrong session
(I want it on the active console session).

So obviously there is some issue related to a service (running in
session 0, since this is XP), starting a process under another
session. Weird that the error is 2, and not something like 5 (access
denied).

Or is there a better method to have a service that runs apps under the
current console session, and runs those apps as LocalSystem? All of
the examples I've found on MSDN use LogonUser or WTSQueryUserToken to
"display UI from a service", but in my case I really need/want the
process to run as LocalSystem, not as the active user.
Boris
2008-12-04 12:46:53 UTC
Permalink
Line:

CreateProcessAsUser(dt,NULL,"c:\myfile.exe",...

- has a typo. You should use double backslash inside quoted string.

Boris
Post by e***@gmail.com
I have code that works on XP and Vista, on about 20 different test
PCs, except on one XP system CreateProcessAsUser fails sometimes.
OpenProcessToken(GetCurrentProcess(),TOKEN_ALL_ACCESS,&t);
DuplicateTokenEx
(t,TOKEN_ALL_ACCESS,NULL,SecurityImpersonation,TokenPrimary,&dt);
DWORD sid = WTSGetActiveConsoleSessionId();
SetTokenInformation(dt,TokenSessionId,&sid,sizeof(sid));
STARTUPINFO si;
memset(&si,0,sizeof(si));
si.cb = sizeof(si);
si.lpDesktop = "winsta0\\default";
CreateProcessAsUser(dt,NULL,"c:\myfile.exe",
NULL,NULL,FALSE,NORMAL_PRIORITY_CLASS|CREATE_NEW_CONSOLE,
NULL,NULL,&si,&UserModeProcessInfo);
The code runs in a service running as LocalSystem. I want the process
to run as LocalSystem also (I know the security risks).
If the active console session ID is 0, the code always works. If non-
zero (1, 2, 3, etc), only one on XP system the CreateProcessAsUser
fails and GetLastError() returns 2 (file not found). I can add a
check right before that call to see if the file exists, and it does.
I can change form myfile.exe to notepad.exe or some other system EXE,
and get the same results. If I force to code to always use session ID
0 then it also works, but of course the app runs on the wrong session
(I want it on the active console session).
So obviously there is some issue related to a service (running in
session 0, since this is XP), starting a process under another
session. Weird that the error is 2, and not something like 5 (access
denied).
Or is there a better method to have a service that runs apps under the
current console session, and runs those apps as LocalSystem? All of
the examples I've found on MSDN use LogonUser or WTSQueryUserToken to
"display UI from a service", but in my case I really need/want the
process to run as LocalSystem, not as the active user.
e***@gmail.com
2008-12-18 20:35:08 UTC
Permalink
Post by Boris
CreateProcessAsUser(dt,NULL,"c:\myfile.exe",...
- has a typo. You should use double backslash inside quoted string.
Sorry, I just typed that wrong when posting, but in my actual code it
is typed correctly. If it wasn't, then my code wouldn't work on any
platform. Anyway, since I didn't get any other answers, I'm guessing
no one else has seen this issue and doesn't have any ideas of how to
fix it. So far we've tested on about 100 PCs, and only found 1 with
the issue, so obviously it isn't very common.
lzx
2009-01-15 03:14:34 UTC
Permalink
oh, I also encountered the same problem,
when Users use mstsc.exe (with /console switch) to connect to the
console session of their server, WTSGetActiveConsoleSessionId returns
none-zero, In this case, my ServiceApp can not create process into the
physical console session, untill Users Logoff the Terminal Services
session ,
have u solved it?
n***@nickcwilson.co.uk
2012-08-02 17:04:29 UTC
Permalink
Very late reply, but "for the record", after a long time bashing my head:

CreateProcessAsUser returns code 2 (ERROR_FILE_NOT_FOUND) if the token is for an invalid session.

It's not necessarily saying that the exe file couldn't be found; instead, it munges the session id associated with the token to create the path of a named pipe. csrss.exe listens on a load of named pipes, one for each session; CreateProcessAsUser serialised its arguments and sends them to csrss to do the actual launching for you. If the token has a session id in it which doesn't exist, CPAU will try and open a connection on a named pipe which hasn't been created: the file it tried to open was not found, hence the error.

Took me long time to realise why I was getting that error message!

Nicholas
Post by e***@gmail.com
Post by Boris
CreateProcessAsUser(dt,NULL,"c:\myfile.exe",...
- has a typo. You should use double backslash inside quoted string.
Sorry, I just typed that wrong when posting, but in my actual code it
is typed correctly. If it wasn't, then my code wouldn't work on any
platform. Anyway, since I didn't get any other answers, I'm guessing
no one else has seen this issue and doesn't have any ideas of how to
fix it. So far we've tested on about 100 PCs, and only found 1 with
the issue, so obviously it isn't very common.
f***@gmail.com
2016-03-17 21:22:41 UTC
Permalink
Just for the record. CreateProcessAsUser calls SearchPath internally. SearchPath uses the File System Redirector https://msdn.microsoft.com/en-us/library/windows/desktop/aa384187%28v=vs.85%29.aspx

So, if you are running a 32 bit app under WOW64 and you ask for a process using an exe in system32 dir e.g. "c:\windows\system32\myapp.exe", CreateProcessAsUser will look in syswow64 instead e.g."c:\windows\syswow64\myapp.exe". If your exe is not there you'll get a "file not found error".
Loading...