前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >服务进程里面去创建带窗口的进程(备忘)

服务进程里面去创建带窗口的进程(备忘)

作者头像
大菊观
发布2021-09-26 11:00:56
6900
发布2021-09-26 11:00:56
举报
代码语言:javascript
复制
DWORD WINAPI GetActiveSessionId()
{
	HMODULE hInstKernel32 = LoadLibrary (L"Kernel32.dll" );
	if (!hInstKernel32 )
	{
		return 0;
	}
	HMODULE hInstWtsapi32 = LoadLibrary (L"Wtsapi32.dll" );
	if (!hInstWtsapi32)
	{
		return 0;
	}

	typedef DWORD (WINAPI *__pfnWTSGetActiveConsoleSessionId)();  
	__pfnWTSGetActiveConsoleSessionId pfnWTSGetActiveConsoleSessionId =  (__pfnWTSGetActiveConsoleSessionId)GetProcAddress(hInstKernel32, "WTSGetActiveConsoleSessionId");  
	if(pfnWTSGetActiveConsoleSessionId == NULL)  
	{  
		//WriteLog("Not found api: WTSGetActiveConsoleSessionId\n");  
		return 0;  
	}

	typedef BOOL (WINAPI *__pfnWTSEnumerateSessions)(HANDLE hServer, DWORD Reserved, DWORD Version, PWTS_SESSION_INFO *ppSessionInfo, DWORD *pCount);
	__pfnWTSEnumerateSessions pfnWTSEnumerateSessions = (__pfnWTSEnumerateSessions)GetProcAddress(hInstWtsapi32, "WTSEnumerateSessionsW");  
	if(pfnWTSEnumerateSessions == NULL)
	{
		return 0;
	}

	typedef void (WINAPI *__pfnWTSFreeMemory)(PVOID pMemory);
	__pfnWTSFreeMemory pfnWTSFreeMemory = (__pfnWTSFreeMemory)GetProcAddress(hInstWtsapi32, "WTSFreeMemory");  
	if(pfnWTSFreeMemory == NULL)
	{
		return 0;
	}

	DWORD dwActive = pfnWTSGetActiveConsoleSessionId();

	PWTS_SESSION_INFO pSessionInfo = 0;
	DWORD dwCount = 0;
	pfnWTSEnumerateSessions(WTS_CURRENT_SERVER_HANDLE, 0, 1, &pSessionInfo, &dwCount);
	for (DWORD i = 0; i < dwCount; ++i)
	{
		WTS_SESSION_INFO si = pSessionInfo[i];
		if (WTSActive == si.State)
		{ 
			dwActive = si.SessionId;
			break;
		}
	}     
	pfnWTSFreeMemory(pSessionInfo);
	return dwActive;
}

DWORD CreateXPProcessInSession0( LPCWSTR lpCommand )
{
	system show dlg
	HDESK hdeskCurrent ;
	HDESK hdesk ;
	HWINSTA hwinstaCurrent ;
	HWINSTA hwinsta ;
	hwinstaCurrent = GetProcessWindowStation();
	if (hwinstaCurrent == NULL)
	{
		return FALSE ;
	}
	hdeskCurrent = GetThreadDesktop (GetCurrentThreadId());
	if (hdeskCurrent == NULL){
		return FALSE ;
	}
	//打开winsta0
	//打开winsta0
	hwinsta = OpenWindowStation (L"Winsta0" , FALSE, WINSTA_ALL_ACCESS);
	// WINSTA_ACCESSCLIPBOARD|
	// WINSTA_ACCESSGLOBALATOMS |
	// WINSTA_ENUMDESKTOPS |
	// WINSTA_CREATEDESKTOP |
	// WINSTA_CREATEDESKTOP |
	// WINSTA_ENUMERATE |
	// WINSTA_EXITWINDOWS |
	// WINSTA_READATTRIBUTES |
	// WINSTA_READSCREEN |
	// WINSTA_WRITEATTRIBUTES);
	if (hwinsta == NULL){
		return FALSE ;
	}
	if (!SetProcessWindowStation (hwinsta))
	{
		return FALSE ;
	}
	//打开desktop
	hdesk = OpenDesktop (L"default" , 0, FALSE,
		DESKTOP_CREATEMENU |
		DESKTOP_CREATEWINDOW |
		DESKTOP_ENUMERATE|
		DESKTOP_HOOKCONTROL|
		DESKTOP_JOURNALPLAYBACK |
		DESKTOP_JOURNALRECORD |
		DESKTOP_READOBJECTS |
		DESKTOP_SWITCHDESKTOP |
		DESKTOP_WRITEOBJECTS);
	if (hdesk == NULL){
		return FALSE ;
	}
	SetThreadDesktop(hdesk );
	end of system show dlg
	STARTUPINFO si = { sizeof( si) };
	SECURITY_ATTRIBUTES saProcess , saThread;
	PROCESS_INFORMATION piProcessB;// , piProcessC;


	// Prepare to spawn Process B from Process A.
	// The handle identifying the new process
	// object should be inheritable.
	saProcess.nLength = sizeof( saProcess);
	saProcess.lpSecurityDescriptor = NULL;
	saProcess.bInheritHandle = TRUE;

	// The handle identifying the new thread
	// object should NOT be inheritable.
	saThread.nLength = sizeof( saThread);
	saThread.lpSecurityDescriptor = NULL;
	saThread.bInheritHandle = FALSE;

	TCHAR szCmd[1024] = {0};
	_sntprintf_s(szCmd,_countof(szCmd),_TRUNCATE,_T("%s"),lpCommand);
	CreateProcess(NULL , 
		szCmd, 
		&saProcess, 
		&saThread ,
		FALSE, 
		0,
		NULL,
		NULL, 
		&si, 
		&piProcessB );

	if (!SetProcessWindowStation (hwinstaCurrent))
		return FALSE ;
	if (!SetThreadDesktop (hdeskCurrent))
		return FALSE ;
	if (!CloseWindowStation (hwinsta))
		return FALSE ;
	if (!CloseDesktop (hdesk))
		return FALSE ;
	return TRUE ;
}

DWORD CreateProcessInSession0( LPCWSTR lpCommand )
{
	DWORD dwRet = 0;
	PROCESS_INFORMATION pi ;
	STARTUPINFO si ;
	DWORD dwSessionId ;
	HANDLE hUserToken = NULL;
	HANDLE hUserTokenDup = NULL;
	HANDLE hPToken = NULL;
	HANDLE hProcess = NULL;
	DWORD dwCreationFlags ;

	dwSessionId = GetActiveSessionId();
	do
	{
		//pfnWTSQueryUserToken( 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 ;

		if( !::OpenProcessToken ( GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY
			| TOKEN_DUPLICATE | TOKEN_ASSIGN_PRIMARY | TOKEN_ADJUST_SESSIONID
			| TOKEN_READ | TOKEN_WRITE , &hPToken ) )
		{
			dwRet = GetLastError ();
			break;
		}

		if ( !LookupPrivilegeValue ( NULL, SE_DEBUG_NAME, &luid ) )
		{
			dwRet = GetLastError ();
			break;
		}

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

		if( !DuplicateTokenEx ( hPToken, MAXIMUM_ALLOWED, NULL , SecurityIdentification , TokenPrimary, & hUserTokenDup ) )
		{
			dwRet = GetLastError ();
			break;
		}

		//Adjust Token privilege
		if( !SetTokenInformation ( hUserTokenDup,TokenSessionId ,(void*)& dwSessionId,sizeof (DWORD) ) )
		{
			dwRet = GetLastError ();
			break;
		}

		if( !AdjustTokenPrivileges ( hUserTokenDup, FALSE, &tp , sizeof(TOKEN_PRIVILEGES ), (PTOKEN_PRIVILEGES) NULL, NULL ) )
		{
			dwRet = GetLastError ();
			break;
		}

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

		// Launch the process in the client's logon session.
		TCHAR szCmd[1024] = {0};
		_sntprintf_s(szCmd,_countof(szCmd),_TRUNCATE,_T("%s"),lpCommand);
		if( CreateProcessAsUser ( hUserTokenDup, // client's access token
			NULL, // file to execute
			szCmd, // 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
			) )
		{
		}
		else
		{
			dwRet = GetLastError ();
			break;
		}
	}
	while( 0 );

	//Perform All the Close Handles task
	if( NULL != hUserToken )
	{
		CloseHandle( hUserToken );
	}

	if( NULL != hUserTokenDup)
	{
		CloseHandle( hUserTokenDup );
	}

	if( NULL != hPToken )
	{
		CloseHandle( hPToken );
	}

	return dwRet ;
}

win系统环境。这里只是做个备忘,代码写的比较糙,请自行测试美化优化。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2021-09-17 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
相关产品与服务
腾讯云服务器利旧
云服务器(Cloud Virtual Machine,CVM)提供安全可靠的弹性计算服务。 您可以实时扩展或缩减计算资源,适应变化的业务需求,并只需按实际使用的资源计费。使用 CVM 可以极大降低您的软硬件采购成本,简化 IT 运维工作。
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档