Click here to Skip to main content
15,881,281 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
I am starting my application by a Service. Now When I want to save a
file, I tried using CFileDialog. but when ever I select "desktop" it
prompts a message as "C:Windows\system32\config\systemprofile\desktop"
refers to location that iss unavailable. It could be hard drive on this
computer, or on a network... "

I checked that "C:Windows\system32\config\systemprofile" is available
but there is not desktop directory inside it.
Posted
Updated 5-Apr-15 20:03pm
v4

Now check your spelling:
"C:\document and setting\networkService"
Is not the same as
"C:\Documents and Settings\NetworkService"
And there is unlikely to be a "Desktop" folder in either of them!
So if you are trying to set the file dialog to the Desktop, you would be better off getting the actual desktop folder using SHGetSpecialFolderPath[^] and passing it CSIDL_DESKTOP
 
Share this answer
 
The Desktop directory is part of the user profile. Starting an application from a service means that it does not have a user profile and therefore no desktop.
 
Share this answer
 
I got the solution for my problem here
Launch your application in Vista under the local system account without the UAC popup[^]

any suggestions in the code are always welcome :)

Problem was, When I was launching my application through services, process was getting created in the context of system,
and wanted to launch the application for the logged in user,

my previous call for createProcessAsuser() was
BOOL CExecuteProcess::StartProcessWithToken(CString csProcessPath, CString csCommandLineParam,
C++
BOOL CExecuteProcess::StartProcessWithToken(CString csProcessPath, CString csCommandLineParam,CString csAccessProcessName, bool bWait)
{
	try
	{
		HANDLE				hToken = NULL;
		TOKEN_USER          oUser[16];
		DWORD               u32Needed;
		TCHAR               sUserName[256], domainName[256];
		DWORD               userNameSize, domainNameSize;
		SID_NAME_USE        sidType;

		ZeroMemory(oUser,sizeof(oUser));

		BOOL bRet = FALSE;

		do
		{
			bRet = OpenProcessToken(GetExplorerProcessHandle(csAccessProcessName), TOKEN_ALL_ACCESS, &hToken);
			if( !bRet )
			{
				//CString csError;
				//csError.Format(L"%d", GetLastError());
				//AddLogEntry(L"### Failed to OpenProcessToken %s", csError, 0, true, SECONDLEVEL);;
				//return FALSE;

				Sleep(1000);
			}
		} while (!bRet);


		if(hToken == NULL)
		{
			if(csAccessProcessName.CompareNoCase(L"explorer.exe") !=0)
			{
				if (!OpenProcessToken(GetExplorerProcessHandle(L"explorer.exe"), TOKEN_ALL_ACCESS, &hToken))
				{
					AddLogEntry(L"### Failed to GetExplorerProcessHandle", 0, 0, true, SECONDLEVEL);;
					return FALSE;
				}

				if(hToken == NULL)
				{
					AddLogEntry(L"### Failed to GetExplorerProcessHandle:: hToken", 0, 0, true, SECONDLEVEL);;
					return FALSE;
				}
			}
		}

		GetTokenInformation(hToken, TokenUser, &oUser[0], sizeof(oUser), &u32Needed);
		userNameSize		= _countof (sUserName) - 1;
		domainNameSize      = _countof (domainName) - 1;

		LookupAccountSid (NULL, oUser[0].User.Sid, sUserName, &userNameSize, domainName, &domainNameSize, &sidType);
		HDESK       hdesk = NULL;
		HWINSTA     hwinsta = NULL, hwinstaSave = NULL;
		PROCESS_INFORMATION pi;
		STARTUPINFO si;
		BOOL bResult = FALSE;
		// Save a handle to the caller's current window station.
		if((hwinstaSave = GetProcessWindowStation()) == NULL)
		{
			CloseHandle(hToken);
			AddLogEntry(L"### Failed to GetProcessWindowStation", 0, 0, true, SECONDLEVEL);;
			return FALSE;
		}

		// Get a handle to the interactive window station.
		hwinsta = OpenWindowStation(
			_T("winsta0"),                   // the interactive window station
			FALSE,							// handle is not inheritable
			READ_CONTROL | WRITE_DAC);		// rights to read/write the DACL

		if(hwinsta == NULL)
		{
			SetProcessWindowStation (hwinstaSave);
			CloseHandle(hToken);
			AddLogEntry(L"### Failed to GetProcessWindowStation:: OpenWindowStation::hwinsta", 0, 0, true, SECONDLEVEL);;
			return FALSE;
		}

		// To get the correct default desktop, set the caller's
		// window station to the interactive window station.
		if(!SetProcessWindowStation(hwinsta))
		{
			SetProcessWindowStation (hwinstaSave);
			CloseWindowStation(hwinsta);
			CloseHandle(hToken);
			AddLogEntry(L"### Failed to SetProcessWindowStation::After OpenWindowStation", 0, 0, true, SECONDLEVEL);;
			return FALSE;
		}

		// Get a handle to the interactive desktop.
		hdesk = OpenDesktop(
			_T("default"),     // the interactive window station
			0,             // no interaction with other desktop processes
			FALSE,         // handle is not inheritable
			READ_CONTROL | // request the rights to read and write the DACL
			WRITE_DAC |
			DESKTOP_WRITEOBJECTS |
			DESKTOP_READOBJECTS);

		if(hdesk == NULL)
		{
			SetProcessWindowStation(hwinstaSave);
			CloseWindowStation(hwinsta);
			CloseHandle(hToken);
			AddLogEntry(L"### Failed to OpenDesktop::hdesk", 0, 0, true, SECONDLEVEL);;
			return FALSE;
		}

		// Restore the caller's window station.
		if(!SetProcessWindowStation(hwinstaSave))
		{
			SetProcessWindowStation (hwinstaSave);
			CloseWindowStation(hwinsta);
			CloseDesktop(hdesk);
			CloseHandle(hToken);
			AddLogEntry(L"### Failed to SetProcessWindowStation after:: OpenDesktop", 0, 0, true, SECONDLEVEL);;
			return FALSE;
		}

		// Impersonate client to ensure access to executable file.
		if(!ImpersonateLoggedOnUser(hToken))
		{
			SetProcessWindowStation (hwinstaSave);
			CloseWindowStation(hwinsta);
			CloseDesktop(hdesk);
			CloseHandle(hToken);
			AddLogEntry(L"### Failed to ImpersonateLoggedOnUser ", 0, 0, true, SECONDLEVEL);;
			return FALSE;
		}

		// Initialize the STARTUPINFO structure.
		// Specify that the process runs in the interactive desktop.
		ZeroMemory(	&si, sizeof(STARTUPINFO));
		si.cb		=  sizeof(STARTUPINFO);
		si.lpDesktop =  _T("winsta0\\default");

		TCHAR   csCmdParam[MAX_PATH] = {0};
		wcscpy_s(csCmdParam, _countof(csCmdParam), csCommandLineParam);

		bResult = CreateProcessAsUser(
			hToken,            // client's access token
			csProcessPath,     // file to execute
			csCmdParam,		 // command line
			NULL,              // pointer to process SECURITY_ATTRIBUTES
			NULL,              // pointer to thread SECURITY_ATTRIBUTES
			FALSE,             // handles are not inheritable
			NORMAL_PRIORITY_CLASS | CREATE_NO_WINDOW,   // creation flags
			NULL,              // pointer to new environment block
			NULL,              // name of current directory
			&si,               // pointer to STARTUPINFO structure
			&pi                // receives information about new process
			);

		if(bResult && bWait && pi.hProcess)
		{
			::WaitForSingleObject(pi.hProcess, 1000 * 60 * 2);
			CloseHandle(pi.hThread);
			CloseHandle(pi.hProcess);
		}

		if(hwinstaSave)
			SetProcessWindowStation (hwinstaSave);
		if(hwinsta)
			CloseWindowStation(hwinsta);
		if(hdesk)
			CloseDesktop(hdesk);
		if(hToken)
			CloseHandle(hToken);
		// End impersonation of client.
		RevertToSelf();
		return bResult;
	}
	catch(...)
	{
		AddLogEntry(_T("Exception caught in KeyLoggerScannerDll.cpp StartProcess "));
	}
	return false;
}


then I changed it with

C++
BOOL CExecuteProcess::StartProcessWithToken(CString csProcessPath, CString csCommandLineParam,
	CString csAccessProcessName, bool bWait)
{
	PROCESS_INFORMATION		pi = { 0 };
	STARTUPINFO				si = { 0 };
	BOOL					bResult = FALSE;
	DWORD					dwSessionId = 0x00, winlogonPid = 0x00;
	HANDLE					hUserToken = NULL;
	HANDLE					hUserTokenDup = NULL;
	HANDLE					hPToken = NULL;
	HANDLE					hProcess = NULL;
	HANDLE					hToken = NULL;

	DWORD					dwCreationFlags = 0x00;
	DWORD					dwLastError = 0x00;

	// Log the client on to the local computer.

	dwSessionId = WTSGetActiveConsoleSessionId();

	//////////////////////////////////////////
	// Get the explorer process handle
	////////////////////////////////////////

	PROCESSENTRY32 procEntry;

	HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
	if (hSnap == INVALID_HANDLE_VALUE)
	{
		//return bResult;
		goto Cleanup;
	}

	procEntry.dwSize = sizeof(PROCESSENTRY32);

	if (!Process32First(hSnap, &procEntry))
	{
		//return bResult;
		goto Cleanup;
	}

	do
	{
		if (_wcsicmp(procEntry.szExeFile, csAccessProcessName) == 0)
		{
			// We found a explorer process...
			// make sure it's running in the console session
			DWORD winlogonSessId = 0;
			if (ProcessIdToSessionId(procEntry.th32ProcessID, &winlogonSessId)
				&& winlogonSessId == dwSessionId)
			{
				winlogonPid = procEntry.th32ProcessID;
				break;
			}
		}

	} while (Process32Next(hSnap, &procEntry));

	////////////////////////////////////////////////////////////////////////

	::WTSQueryUserToken(dwSessionId, &hUserToken);
	dwCreationFlags = NORMAL_PRIORITY_CLASS | CREATE_NEW_CONSOLE;
	ZeroMemory(&si, sizeof(STARTUPINFO));
	si.cb = sizeof(STARTUPINFO);
	si.lpDesktop = L"winsta0\\default";

	ZeroMemory(&pi, sizeof(pi));

	TOKEN_PRIVILEGES tp;
	LUID luid;

	hProcess = OpenProcess(MAXIMUM_ALLOWED, FALSE, winlogonPid);

	if (!::OpenProcessToken(hProcess, TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY
		| TOKEN_DUPLICATE | TOKEN_ASSIGN_PRIMARY | TOKEN_ADJUST_SESSIONID
		| TOKEN_READ | TOKEN_WRITE, &hPToken))
	{
		dwLastError = GetLastError();
		goto Cleanup;
		//return bResult;
	}

	if (!LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &luid))
	{
		//printf("Lookup Privilege value Error: %u\n", GetLastError());
		dwLastError = GetLastError();
		//return bResult;
		goto Cleanup;
	}

	tp.PrivilegeCount = 1;
	tp.Privileges[0].Luid = luid;
	tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

	DuplicateTokenEx(hPToken, MAXIMUM_ALLOWED, NULL,
		SecurityIdentification, TokenPrimary, &hUserTokenDup);

	dwLastError = GetLastError();

	//Adjust Token privilege
	SetTokenInformation(hUserTokenDup,
		TokenSessionId, (void*)dwSessionId, sizeof(DWORD));

	if (!AdjustTokenPrivileges(hUserTokenDup, FALSE, &tp, sizeof(TOKEN_PRIVILEGES),
		(PTOKEN_PRIVILEGES)NULL, NULL))
	{
		dwLastError = GetLastError();
		//return bResult;
		goto Cleanup;
	}

	//dwLastError = GetLastError();
	//if (dwLastError == ERROR_NOT_ALL_ASSIGNED)
	//{
	//	//return bResult;
	//	goto Cleanup;
	//}

	LPVOID	pEnv = NULL;

	if (::CreateEnvironmentBlock(&pEnv, hUserTokenDup, TRUE))
	{
		dwCreationFlags |= CREATE_UNICODE_ENVIRONMENT;
	}
	else
		pEnv = NULL;

	// Launch the process in the client's logon session.

	bResult = CreateProcessAsUser(
		hUserTokenDup,						// client's access token
		csProcessPath,						// file to execute
		csCommandLineParam.GetBuffer(csCommandLineParam.GetLength()),                 // command line
		NULL,				// pointer to process SECURITY_ATTRIBUTES
		NULL,               // pointer to thread SECURITY_ATTRIBUTES
		FALSE,              // handles are not inheritable
		dwCreationFlags,     // creation flags
		pEnv,               // pointer to new environment block
		NULL,               // name of current directory
		&si,               // pointer to STARTUPINFO structure
		&pi                // receives information about new process
		);
	csCommandLineParam.ReleaseBuffer();
	dwLastError = GetLastError();

	if (bResult)
		bResult = TRUE;
	//Perform All the Close Handles tasks

Cleanup:

	if (hProcess)
		CloseHandle(hProcess);

	if (hUserToken)
		CloseHandle(hUserToken);

	if (hUserTokenDup)
		CloseHandle(hUserTokenDup);

	if (hPToken)
		CloseHandle(hPToken);

	if (hToken)
		CloseHandle(hToken);

	return bResult;
}
 
Share this answer
 
v5

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900