事情是这样的,公司的产品有个守护进程(windows Service)需要启动产品的主程序exe,让主程序它运行为管理员权限(因为主程序会加载一个插件,插件中有列出端口监听的功能,需要由端口查找到进程PID,由进程PID查找进程名或进程镜像路径,这些对于一些特殊进程例如svchost需要有管理员权限才能查到进程名和路径)。windows下的程序是不能在运行时获得管理员权限的,只能在创建进程的时候提升为管理员权限。如果是普通进程运行一个管理员权限程序,可以调用ShellExcute API。双击鼠标运行exe,可以在manifest文件中加入invoker admin,UAC 会提示用户以管理员权限运行。但是,特殊就在这里了!!守护进程是windows service,service不能调用ShellExcute来创建进程,如果这样,就会会失败。需要调用CreateProcessAsUser API来创建进程,这个API的普通用法,不能创建带有管理员权限的程序,需要一丁点特殊用法,如下:

 bool createProcessWithAdmin(const std::string & process_name, LPPROCESS_INFORMATION process)
{
HANDLE hToken = NULL;
HANDLE hTokenDup = NULL; if (process_name.empty()) {
return false;
} if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &hToken))
{
return false;
} if (!DuplicateTokenEx(hToken, TOKEN_ALL_ACCESS, NULL, SecurityAnonymous, TokenPrimary, &hTokenDup))
{
CloseHandle(hToken);
return false;
} STARTUPINFO si;
LPVOID pEnv = NULL;
DWORD dwSessionId = WTSGetActiveConsoleSessionId(); ZeroMemory(&si, sizeof(STARTUPINFO)); if (!SetTokenInformation(hTokenDup, TokenSessionId, &dwSessionId, sizeof(DWORD)))
{
CloseHandle(hToken);
CloseHandle(hTokenDup);
return false;
} si.cb = sizeof(STARTUPINFO);
si.lpDesktop = "WinSta0\\Default";
si.wShowWindow = SW_SHOW;
si.dwFlags = STARTF_USESHOWWINDOW; if (!CreateEnvironmentBlock(&pEnv, hTokenDup, FALSE))
{
CloseHandle(hToken);
CloseHandle(hTokenDup);
return false;
} if (!CreateProcessAsUser(hTokenDup, process_name.c_str(), NULL, NULL, NULL, FALSE,
NORMAL_PRIORITY_CLASS | CREATE_NEW_CONSOLE | CREATE_UNICODE_ENVIRONMENT,
pEnv, NULL, &si, process))
{
CloseHandle(hToken);
CloseHandle(hTokenDup);
return false;
} if (pEnv)
{
DestroyEnvironmentBlock(pEnv);
} CloseHandle(hToken);
CloseHandle(hTokenDup);
return true;
}

用法:

 PROCESS_INFORMATION pi;
createProcessWithAdmin("D:/absolute-path-exe", &pi);

用以上的代码就能用windows服务进程创建带有管理员权限的主GUI程序了。

另外windows service推荐用Qt的解决方案,编写windows service更简单了: https://github.com/qtproject/qt-solutions

references:

http://stackoverflow.com/questions/6418791/requesting-administrator-privileges-at-run-time

http://blog.csdn.net/woshinia/article/details/7850295

http://stackoverflow.com/questions/6261427/how-to-run-a-process-as-an-administrator-from-win32-c

http://blog.csdn.net/breeze_vickie/article/details/4334257

https://stackoverflow.com/questions/267838/how-can-a-windows-service-execute-a-gui-application

windows Service启动带有管理员权限的GUI进程的更多相关文章

  1. Windows 无法启动MongoDB服务 错误1067:进程意外终止

    1:Windows 无法启动MongoDB服务 错误1067:进程意外终止 2:解决方法: 进入MongoDB安装目录\data\将此文件夹下的mongod.lock删除(网友提供解决方案,实验之后貌 ...

  2. [Windows]VS2010如何以管理员权限启动?(转)

    在某些项目进行开发的时候,需要提升应用程序本身的权限,这个是很容易的.但是如何让VS2010启动的时候就已管理员权限运行程序呢?为这个问题苦恼了好久,终于找到了办法. 找到VS2010的快捷方式:右击 ...

  3. WIN8,开机启动 需要管理员权限的程序

    1. 用WPF开发,需要管理员权限并开机启动,以写注册表的方式实现.仅写注册表只能启动一般权限的程序. 2. 考虑这样实现: 程序以一般权限启动,启动以后申请管理员权限. 实现: App类中重写OnS ...

  4. window 10 删除带有管理员权限的Oracle文件夹

    因为文件已经被删除就不附图解释了 因为文件安装的方式错误,所以本是按照正常步骤卸载Oracle,前面的禁用Orace服务与删除Oracle注册表都没有出错,但到最后一步---------Oracle文 ...

  5. Windows Service 访问远程共享权限设置

    最近为实现共享目录之间的文件同步,开发了一个Windows Service. 考虑到在拷贝过程中,如果网络忽然抽风访问不了,导致文件拷贝不完整的情况,果断抛弃.Net 自带的 COPY 方法,而使用D ...

  6. Windows 8提升普通管理员权限为超级管理员权限以及激活超级管理员Administrator

    在Windows 8下运行某些操作时(比如删除一些文件或者更改某些系统设置时)系统会提示我们权限不够.须要Administrator账户的权限. 相信很多其它的使用者都会觉得自己当前使用的账户已经是系 ...

  7. windows Service 之调试过程(附加到进程里调试,而且启动时间不能超过30秒)

    最近第一次用C#写了一个windows service ,其实实现的内容比较简单.就是启动remoting 连接,但是调试相对初次写windws service 的我来说,比较烦.没有经验,而且没办法 ...

  8. MySQL的安装(比较详细的安装步骤,包括客户端和服务端的安装,还有环境变量的配置以及使用Windows service启动MySQL)

    1.MySQL官网下载操作系统对应的MySQL安装包,解压之后就可以直接使用(免安装). MySQL安装包,一种是MySQL Enterprise Edition (commercial)企业版,还有 ...

  9. 使用程序控制windows service启动/停止

    1.首先加入引用: using System.ServiceProcess; 2.控制启动服务: public void Start() { var timeout = TimeSpan.FromSe ...

随机推荐

  1. 诺基亚S40手机联系人导入安卓手机

    电话号码较少的话比较简单,拷贝到SIM卡中通过SIM卡中转,只是一般SIM卡只能存储200个左右,联系人比较多的情况就麻烦一点,今天帮导师把诺基亚5220中的800个电话转到三星S4中,综合下来还是使 ...

  2. ASP.NET Razor C# 和 VB 代码语法

    ylbtech-.NET: ASP.NET Razor  C# 和 VB 代码语法 Razor 不是一种编程语言.它是服务器端的标记语言. 1. C# 和 VB 代码语法返回顶部 Razor 同时支持 ...

  3. 奇怪吸引子---ChenLee

    奇怪吸引子是混沌学的重要组成理论,用于演化过程的终极状态,具有如下特征:终极性.稳定性.吸引性.吸引子是一个数学概念,描写运动的收敛类型.它是指这样的一个集合,当时间趋于无穷大时,在任何一个有界集上出 ...

  4. @Autowired用法详解

    @Autowired 注释,它可以对类成员变量.方法及构造函数进行标注,完成自动装配的工作. 通过 @Autowired的使用来消除 set ,get方法.在使用@Autowired之前,我们对一个b ...

  5. 第二章 TypeScript 开发环境搭建

    Mac OS X 下 TypeScript 开发环境搭建 一.集成开发环境 WebStrom VSCode 二.安装 TypeScript Homebrew(macOS 缺失的软件包管理器) ruby ...

  6. CodeFirst体验之且行且珍惜

    CodeFirst作为一种新的开发理念和方式,EF  Code-First相对于MVC中的DataFirst,ModelFirst确实开发效率确实高点,至少数据库建表这一块,直接用类映射到数据中,标记 ...

  7. OpenFeign封装为springboot starter

    OpenFeign是什么 随着业务的增多,我们的单体应用越来越复杂,单机已经难以满足性能的需求,这时候出现了分布式.分布式通讯除了RPC, REST HTTP请求是最简单的一种方式.OpenFeign ...

  8. 如何配置官方peerDroid,使其运行起来

    一.Peer Droid是JXME协议到android平台的移植,开发者可以利用它来实现android设备以及传统PC机通讯的应用程序,peerDroid的官方demo主要是实现PC端peer和and ...

  9. Centos下配置单元测试工具gtest

    gtest是google提供的一个非常强大的单元测试工具,下载地址:https://code.google.com/p/googletest 我下载的是gtest-1.6.0.拷贝到Centos系统上 ...

  10. 从 bootup.js 学习加载脚本等资源

    本文内容 如何使用 示例 参考资料 本文的目的在于,通过 bootup.js 的源代码,认识如何从客户端加载服务器的文件,特别是 JavaScript 文件,注入到页面,并存储在本地缓存,以扩展对 J ...