windows提权操作以及系统开机关机重启代码(用到了LookupPrivilegeValue和AdjustTokenPrivileges调整进程的Token权限)

对于UAC提权操作,一般在编译期间,如果程序有需求要提权,会在编译器里设置,vs2010比较简单,在工程属性里可以直接设置,vs2005稍微有点儿麻烦,参考这篇文章:

http://www.seanyxie.com/vs2005%E4%B8%8B%E7%A8%8B%E5%BA%8Fuac%E6%8F%90%E6%9D%83/

这里给出一段示例代码,用来提权操作,实现windows的开机,关机,重启等操作。

#include <Windows.h>  
#include <tchar.h>  
  
/*  
    系统特权提升 
    @lpName: 
    SE_SHUTDOWN_NAME 关机,重启权限 
 */  
BOOL PrivilegePromote(LPCTSTR lpName) {  
    HANDLE hToken = NULL;  
    TOKEN_PRIVILEGES tkp = {0};  
    // 打开进程令牌  
    if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY,&hToken))  
    {  
        return FALSE;  
    }  
  
    // 查找系统权限的特权值  
    if (!LookupPrivilegeValue(NULL,lpName,&tkp.Privileges[0].Luid))  
    {  
        CloseHandle(hToken);  
        return TRUE;  
    }  
  
    // 调整令牌特权  
    if(!AdjustTokenPrivileges(hToken,FALSE,&tkp,sizeof(TOKEN_PRIVILEGES),NULL,NULL)) {  
        CloseHandle(hToken);  
        return FALSE;  
    }  
  
    return TRUE;  
}  
  
  
/* 
  系统启动控制:注销,重启,关机 
  @dwFlags:EWX_LOGOFF | EWX_REBOOT | EWX_SHUTDOWN 
  @bForce:是否强制 
 */  
BOOL StartUpContrl(DWORD dwFlags,BOOL bForce) {  
    // 参数校验  
    if (dwFlags != EWX_LOGOFF && dwFlags != EWX_REBOOT && dwFlags != EWX_SHUTDOWN)  
    {  
        return FALSE;  
    }  
  
    // 获取系统版本,ExitWindowsEx 在NT平台上需要提升权限  
    OSVERSIONINFO osvi = {0};  
    osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);  
    // 版本信息获取  
    if ( !GetVersionEx(&osvi))  
    {  
        return FALSE;  
    }  
  
    // 是NT系统 需要进行权限提升  
    if (osvi.dwPlatformId == VER_PLATFORM_WIN32_NT)  
    {  
        PrivilegePromote(SE_SHUTDOWN_NAME);  
    }  
  
    dwFlags |= (bForce != FALSE)? EWX_FORCE : EWX_FORCEIFHUNG;  
  
    return ExitWindowsEx(dwFlags, 0);  
}  
  
int APIENTRY _tWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nShowCmd ) {  
    if (_tcscmp(lpCmdLine,_T("/r")) == 0){  
        StartUpContrl(EWX_REBOOT,TRUE);  
    } else if (_tcscmp(lpCmdLine,_T("/s")) == 0){  
        StartUpContrl(EWX_SHUTDOWN,TRUE);  
    } else if (_tcscmp(lpCmdLine,_T("/l")) == 0){  
        StartUpContrl(EWX_LOGOFF,TRUE);  
    }  
  
    return 0;  
}
BOOL ExitWindowsEx(
UINT uFlags, // 关闭参数
DWORD dwReserved // 系统保留,一般取0

);

参数介绍:

uFlags

指定关闭的类型。此参数必须有下列值的组合:
EWX_FORCE
强制终止进程。当此标志设置,Windows不会发送消息WM_QUERYENDSESSION和WM_ENDSESSION的消息给目前在系统中运行的程序。这可能会导致应用程序丢失数据。因此,你应该只在紧急情况下使用此标志。
EWX_LOGOFF
关闭所有进程,然后注销用户。
EWX_POWEROFF
关闭系统并关闭电源。该系统必须支持断电。
Windows要求:
Windows NT中调用进程必须有 SE_SHUTDOWN_NAME 特权。
Windows 9X中:可以直接调用。
EWX_REBOOT
关闭系统,然后重新启动系统。
Windows要求:
Windows NT中:调用进程必须有SE_SHUTDOWN_NAME特权。
Windows 9X中:可以直接调用。
EWX_SHUTDOWN
关闭系统,安全地关闭电源。所有文件缓冲区已经刷新到磁盘上,所有正在运行的进程已经停止。
Windows要求:
Windows NT中:调用进程必须有SE_SHUTDOWN_NAME特权。
Windows 9X中:可以直接调用。

dwReserved

系统保留,这参数被忽略。一般取0。
返回值
如果函数成功,返回值为非零。
如果函数失败,返回值是零。想获得更多错误信息,请调用GetLastError函数。
ExitWindowsEx函数返回后,启动了关闭。关闭或注销。
在关机或登录操作中,应用程序在允许关闭的时间具体数额内回应关机请求。如果时间到期时,Windows会显示一个对话框,允许用户强行关闭应用程序:关闭、重试,或取消关机要求。如果存在EWX_FORCE指定值,Windows会关闭应用程序而不显示该对话框。
Windows NT中:关闭或重新启动系统,调用进程必须使用AdjustTokenPrivileges函数使SE_SHUTDOWN_NAME特权。Windows 95中:安全特权,不支持或需要。

http://www.seanyxie.com/windows%E6%8F%90%E6%9D%83%E6%93%8D%E4%BD%9C%E4%BB%A5%E5%8F%8A%E7%B3%BB%E7%BB%9F%E5%BC%80%E6%9C%BA%E5%85%B3%E6%9C%BA%E9%87%8D%E5%90%AF%E4%BB%A3%E7%A0%81/

原文地址:https://www.cnblogs.com/findumars/p/5855126.html