VC程序在win7系统上运行,自动获取管理员权限 .
2012-08-15 22:22
344 查看
本文转载至: /article/8126346.html
在win7 上运行程序,经常需要管理员权限,如何让自己编写的程序启动的时候获取管理员权限呢?方法如下:
1: 在VS2010中,可以参考《VS2010与Win7共舞:UAC与数据重定向》这篇文章,为了方便,这里复制过来:
<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
禁用UAC Virtualization
凡事都没有绝对。如果因为一些特殊的要求(众所周知,客户的要求千奇百怪,无奇不有),我们一定要向“Program Files”目录写入数据,这时该怎么办呢?面对这种极其特殊的情况,我们可以在应用程序的Manifest禁用UAC Virtualization,取消其对数据写操作的重定向。在项目属性中,我们设置启用UAC(Enable User Account Control),并且在UAC Execution Level中设置请求管理员权限。这样,应用程序在启动的时候,就会向用户请求管理员权限,当应用程序获得管理员执行权限后,当然可以向任意目录写入数据,UAC
Virtualization也就不会起作用了。
图2 通过Manifest禁用UAC Virtualization
对于64位应用程序,本身是不具备UAC Virtualization机制的,所以根本不存在禁用的问题。当我们在64位应用程序中尝试向“Program Files”等敏感目录写入数据时,就会遇到一个“拒绝访问”的错误:
<!--
Code highlighting produced by Actipro CodeHighlighter (freeware)
http://www.CodeHighlighter.com/
-->// 测试文件夹是否存在
BOOL IsDirectoryExists(TCHAR *dirName)
{
WIN32_FILE_ATTRIBUTE_DATA dataDirAttrData;
if (!::GetFileAttributesEx(dirName, GetFileExInfoStandard,
&dataDirAttrData))
{
DWORD lastError = ::GetLastError();
if (lastError
== ERROR_PATH_NOT_FOUND
|| lastError
== ERROR_FILE_NOT_FOUND
|| lastError
== ERROR_NOT_READY)
return FALSE;
}
return (dataDirAttrData.dwFileAttributes
& FILE_ATTRIBUTE_DIRECTORY)
!= 0;
}
// …
// 获取文件夹路径
//if (FAILED(SHGetKnownFolderPath(FOLDERID_ProgramData,
// 0, NULL, &pszPath)))
// 错误的做法:
if (FAILED(SHGetKnownFolderPath(FOLDERID_ProgramFiles,
0, NULL,
&pszPath)))
{
// 提示错误
MessageBox(hwndDlg, _T("SHGetKnownFolderPath无法获取文件路径"),
_T("Error"), MB_OK
| MB_ICONERROR);
return FALSE;
}
//…
// 检查文件夹是否存在
if (::IsDirectoryExists(dataFilePath))
{
// 如果文件夹不存在,则创建文件夹
if (!::CreateDirectory(dataFilePath, NULL))
{
DWORD dwErrorCode = ::GetLastError();
LPCWSTR lpBuffer;
// 获取错误信息
FormatMessage ( FORMAT_MESSAGE_ALLOCATE_BUFFER
|
FORMAT_MESSAGE_IGNORE_INSERTS |
FORMAT_MESSAGE_FROM_SYSTEM,
NULL,
dwErrorCode, // 错误代码
LANG_NEUTRAL,
(LPTSTR)&lpBuffer,
0 ,
NULL );
// 显示错误对话框
MessageBox(hwndDlg, lpBuffer, _T("创建文件夹错误"), MB_OK
| MB_ICONERROR);
LocalFree((HLOCAL)lpBuffer);
return FALSE;
}
}
当这段代码执行到创建文件夹的时候,会遇到一个“拒绝访问”错误:
图3 创建文件夹的“拒绝访问”错误
为了避免这个错误,同样的,我们可以通过在项目属性中设置,使得Manifest中嵌入UAC相关的信息,在应用程序启动的时候请求管理员权限,就像我们在运行其他大多数需要管理器权限的应用程序一样。当应用程序获得管理员权限后,这个错误就不存在了。但是这里必须要指出,这种做法是不太安全的,能够避免尽量避免。
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
按照上述文章,VS2010编写的程序可以运行时获取管理员权限;
但是如果是VS2010以前的程序呢?
方法1:当然是移植到VS2010上了;
方法2:(这才是要说的):
(1)按照《VS2010与Win7共舞:UAC与数据重定向》上述方法,随便写一个VS2010工程,编译,在这个工程的Debug目录下会有两个文件: *.exe.embed.manifest 和 *.exe.intermediate.manifest ;
(2)随便复制一个 .manifest 文件到你现在的工程目录的资源文件夹(res)下,然后在工程的资源中Import这个文件;
(3)资源文件夹设置为“24”,资源ID设置为“1”;
现在ok了,你编译的程序,可以获取管理员权限了。
用一下这个函数就可以启动其他程序以管理员权限,当然可以自己启动自己
BOOL ElevateCurrentProcess(CString sCmdLine)
{
TCHAR szPath[MAX_PATH] = {0};
if (::GetModuleFileName(NULL, szPath, MAX_PATH))
{
// Launch itself as administrator.
SHELLEXECUTEINFO sei = { sizeof(SHELLEXECUTEINFO) };
sei.lpVerb = _T("runas");
sei.lpFile = szPath;
sei.lpParameters = (LPCTSTR)sCmdLine;
// sei.hwnd = hWnd;
sei.nShow = SW_SHOWNORMAL;
if (!ShellExecuteEx(&sei))
{
DWORD dwStatus = GetLastError();
if (dwStatus == ERROR_CANCELLED)
{
// The user refused to allow privileges elevation.
return FALSE;
}
else
if (dwStatus == ERROR_FILE_NOT_FOUND)
{
// The file defined by lpFile was not found and
// an error message popped up.
return FALSE;
}
return FALSE;
}
return TRUE;
}
return FALSE;
}
。
在win7 上运行程序,经常需要管理员权限,如何让自己编写的程序启动的时候获取管理员权限呢?方法如下:
1: 在VS2010中,可以参考《VS2010与Win7共舞:UAC与数据重定向》这篇文章,为了方便,这里复制过来:
<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<
禁用UAC Virtualization
凡事都没有绝对。如果因为一些特殊的要求(众所周知,客户的要求千奇百怪,无奇不有),我们一定要向“Program Files”目录写入数据,这时该怎么办呢?面对这种极其特殊的情况,我们可以在应用程序的Manifest禁用UAC Virtualization,取消其对数据写操作的重定向。在项目属性中,我们设置启用UAC(Enable User Account Control),并且在UAC Execution Level中设置请求管理员权限。这样,应用程序在启动的时候,就会向用户请求管理员权限,当应用程序获得管理员执行权限后,当然可以向任意目录写入数据,UAC
Virtualization也就不会起作用了。
图2 通过Manifest禁用UAC Virtualization
对于64位应用程序,本身是不具备UAC Virtualization机制的,所以根本不存在禁用的问题。当我们在64位应用程序中尝试向“Program Files”等敏感目录写入数据时,就会遇到一个“拒绝访问”的错误:
<!--
Code highlighting produced by Actipro CodeHighlighter (freeware)
http://www.CodeHighlighter.com/
-->// 测试文件夹是否存在
BOOL IsDirectoryExists(TCHAR *dirName)
{
WIN32_FILE_ATTRIBUTE_DATA dataDirAttrData;
if (!::GetFileAttributesEx(dirName, GetFileExInfoStandard,
&dataDirAttrData))
{
DWORD lastError = ::GetLastError();
if (lastError
== ERROR_PATH_NOT_FOUND
|| lastError
== ERROR_FILE_NOT_FOUND
|| lastError
== ERROR_NOT_READY)
return FALSE;
}
return (dataDirAttrData.dwFileAttributes
& FILE_ATTRIBUTE_DIRECTORY)
!= 0;
}
// …
// 获取文件夹路径
//if (FAILED(SHGetKnownFolderPath(FOLDERID_ProgramData,
// 0, NULL, &pszPath)))
// 错误的做法:
if (FAILED(SHGetKnownFolderPath(FOLDERID_ProgramFiles,
0, NULL,
&pszPath)))
{
// 提示错误
MessageBox(hwndDlg, _T("SHGetKnownFolderPath无法获取文件路径"),
_T("Error"), MB_OK
| MB_ICONERROR);
return FALSE;
}
//…
// 检查文件夹是否存在
if (::IsDirectoryExists(dataFilePath))
{
// 如果文件夹不存在,则创建文件夹
if (!::CreateDirectory(dataFilePath, NULL))
{
DWORD dwErrorCode = ::GetLastError();
LPCWSTR lpBuffer;
// 获取错误信息
FormatMessage ( FORMAT_MESSAGE_ALLOCATE_BUFFER
|
FORMAT_MESSAGE_IGNORE_INSERTS |
FORMAT_MESSAGE_FROM_SYSTEM,
NULL,
dwErrorCode, // 错误代码
LANG_NEUTRAL,
(LPTSTR)&lpBuffer,
0 ,
NULL );
// 显示错误对话框
MessageBox(hwndDlg, lpBuffer, _T("创建文件夹错误"), MB_OK
| MB_ICONERROR);
LocalFree((HLOCAL)lpBuffer);
return FALSE;
}
}
当这段代码执行到创建文件夹的时候,会遇到一个“拒绝访问”错误:
图3 创建文件夹的“拒绝访问”错误
为了避免这个错误,同样的,我们可以通过在项目属性中设置,使得Manifest中嵌入UAC相关的信息,在应用程序启动的时候请求管理员权限,就像我们在运行其他大多数需要管理器权限的应用程序一样。当应用程序获得管理员权限后,这个错误就不存在了。但是这里必须要指出,这种做法是不太安全的,能够避免尽量避免。
>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
按照上述文章,VS2010编写的程序可以运行时获取管理员权限;
但是如果是VS2010以前的程序呢?
方法1:当然是移植到VS2010上了;
方法2:(这才是要说的):
(1)按照《VS2010与Win7共舞:UAC与数据重定向》上述方法,随便写一个VS2010工程,编译,在这个工程的Debug目录下会有两个文件: *.exe.embed.manifest 和 *.exe.intermediate.manifest ;
(2)随便复制一个 .manifest 文件到你现在的工程目录的资源文件夹(res)下,然后在工程的资源中Import这个文件;
(3)资源文件夹设置为“24”,资源ID设置为“1”;
现在ok了,你编译的程序,可以获取管理员权限了。
用一下这个函数就可以启动其他程序以管理员权限,当然可以自己启动自己
BOOL ElevateCurrentProcess(CString sCmdLine)
{
TCHAR szPath[MAX_PATH] = {0};
if (::GetModuleFileName(NULL, szPath, MAX_PATH))
{
// Launch itself as administrator.
SHELLEXECUTEINFO sei = { sizeof(SHELLEXECUTEINFO) };
sei.lpVerb = _T("runas");
sei.lpFile = szPath;
sei.lpParameters = (LPCTSTR)sCmdLine;
// sei.hwnd = hWnd;
sei.nShow = SW_SHOWNORMAL;
if (!ShellExecuteEx(&sei))
{
DWORD dwStatus = GetLastError();
if (dwStatus == ERROR_CANCELLED)
{
// The user refused to allow privileges elevation.
return FALSE;
}
else
if (dwStatus == ERROR_FILE_NOT_FOUND)
{
// The file defined by lpFile was not found and
// an error message popped up.
return FALSE;
}
return FALSE;
}
return TRUE;
}
return FALSE;
}
。
相关文章推荐
- VC程序在win7系统上运行,自动获取管理员权限
- VC程序在win7系统上运行,自动获取管理员权限
- VC程序在win7系统上运行,自动获取管理员权限
- VC程序自动获取windows7/vista系统管理员权限(vs2008)
- VC程序自动获取windows7/vista系统管理员权限(vs2008)
- VC程序自动获取windows7/vista系统管理员权限(vs2008)
- vc++MCF/C++/C中怎样让应用程序获得或以管理员权限运行 ,ShellExecuteEX编程 --- 获取管理员权限
- 2012-11-22 11:23 vc编写以管理员权限运行的程序
- 让.net程序自动运行在管理员权限下
- VC编写在windows7下以管理员权限运行的程序(转)
- VC编写在windows7下以管理员权限运行的程序(转)
- Vista、Win7上.net程序如何自动使用管理员权限运行
- 在Windows 7 下使用Visual Studio 2010 编写自动申请管理员权限运行的程序
- vc程序以管理员权限运行方法
- VC程序获取管理员权限
- VC程序获取管理员权限
- Win7如何提升为管理员权限,如何开机启动需要管理员权限的程序,解决win7开机不能自动运行的问题等
- 让.net程序自动运行在管理员权限下
- VC,在win7下让程序获取管理员权限
- .bat文件注册.ocx+win8开机获得管理员权限+运行程序自动注册.ocx