none
OpenProcess失败 RRS feed

  • 问题

  • 操作系统:Windows 7

    IDE:Visual Studio 2010

    关键语句:

    HANDLE hProcess=OpenProcess(PROCESS_VM_READ|PROCESS_VM_WRITE|PROCESS_VM_OPERATION,false,pid);
    

    为了使用WriteProcessMemory,必须要用到ReadProcessMemory、VirtualProtectEx、OpenProcess等函数。但是发现WriteProcessMomory失败(返回0)。在cmd下调试,最后发现原来从OpenProcee开始已经失败了。后来发现如果直接在VS2010下调试,OpenProcess不会失败。(ReadProcessMemory、VirtualProtectEx在VS2010直接调试有时仍会失败)。

    于是用以下函数提权,

    void EnableDebugPriv() 
    { 
    	HANDLE hToken;
    	LUID sedebugnameValue; 
    	TOKEN_PRIVILEGES tkp; 
    
    	if ( ! OpenProcessToken( GetCurrentProcess(),TOKEN_ADJUST_PRIVILEGES | TOKEN_QUERY, &hToken ) ) 
    	{
    		cout<<"提权失败。"<<endl;
    		return; 
    	}
    
    	if ( ! LookupPrivilegeValue( NULL, SE_DEBUG_NAME, &sedebugnameValue ) ) 
    	{ 
    		CloseHandle( hToken ); 
    		cout<<"提权失败。"<<endl;
    		return; 
    	} 
    	tkp.PrivilegeCount = 1; 
    	tkp.Privileges[0].Luid = sedebugnameValue; 
    	tkp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED; 
    	if ( ! AdjustTokenPrivileges( hToken, FALSE, &tkp, sizeof tkp, NULL, NULL ) ) 
    	{
    		cout<<"提权失败。"<<endl;
    		CloseHandle( hToken );
    	}
    	else cout<<"提权成功!"<<endl;
    }
    

    然后再执行OpenProcess ,仍然失败,返回0。 


    操作系统:VirtualBox 虚拟机 Windows XP系统

    IDE:上述系统的Visual Studio 6

    关键语句:

    HANDLE hProcess=OpenProcess(PROCESS_VM_READ|PROCESS_VM_WRITE|PROCESS_VM_OPERATION,false,pid);
    

    几乎跟之前同样的代码,反而在XP下,VC++6中调式失败,直接XP下直接运行OpenProcess成功,并且不需要提权。

    win7下已经把cmd以管理员运行仍然失败,而XP下却不会。原因何在?

    补充相关测试代码如下:  

    // test4.cpp : Defines the entry point for the console application.
    //
    
    #include "stdafx.h"
    #include "test4.h"
    
    #ifdef _DEBUG
    #define new DEBUG_NEW
    #undef THIS_FILE
    static char THIS_FILE[] = __FILE__;
    #endif
    
    /////////////////////////////////////////////////////////////////////////////
    // The one and only application object
    
    CWinApp theApp;
    
    using namespace std;
    
    int _tmain(int argc, TCHAR* argv[], TCHAR* envp[])
    {
    	int nRetCode = 0;
    
    	// initialize MFC and print and error on failure
    	if (!AfxWinInit(::GetModuleHandle(NULL), NULL, ::GetCommandLine(), 0))
    	{
    		// TODO: change error code to suit your needs
    		cerr << _T("Fatal Error: MFC initialization failed") << endl;
    		nRetCode = 1;
    	}
    	else
    	{
    		// TODO: code your application's behavior here.
    		CString strHello;
    		strHello.LoadString(IDS_HELLO);
    		cout << (LPCTSTR)strHello << endl;
    		int pid = atoi(argv[1]);
    		printf("pid=%d\n",pid);
    		HANDLE hProcess=OpenProcess(PROCESS_VM_READ|PROCESS_VM_WRITE|PROCESS_VM_OPERATION,false,pid);
    		if(hProcess)
    			printf("打开进程成功!");
    		else
    			printf("打开进程失败!");
    		::CloseHandle(hProcess);
    		getchar();
    	}
    
    	return nRetCode;
    }
    2010年6月8日 8:46

答案

  • 我顺便说一句,我重新编辑帖子的时候,代码块内的行间距,都会比上一次多一行或两行。编辑两次,代码块的行间距会变为原来的2倍;估计,接下去是4倍、5倍了。这样,我不得不每次都重新插入代码块。这个算是bug吧?
    GetLastError试试
    2010年6月8日 9:31

全部回复

  • 我顺便说一句,我重新编辑帖子的时候,代码块内的行间距,都会比上一次多一行或两行。编辑两次,代码块的行间距会变为原来的2倍;估计,接下去是4倍、5倍了。这样,我不得不每次都重新插入代码块。这个算是bug吧?
    2010年6月8日 8:56
  • 我顺便说一句,我重新编辑帖子的时候,代码块内的行间距,都会比上一次多一行或两行。编辑两次,代码块的行间距会变为原来的2倍;估计,接下去是4倍、5倍了。这样,我不得不每次都重新插入代码块。这个算是bug吧?
    GetLastError试试
    2010年6月8日 9:31
  • 用GetlastError试了,错误代码是87(我还没分析,第一时间发了,我自己再想想看)。


    我又试了一下,发现时传参数时出错,这就就是为什么在VS中调试成功的原因,我在VS中对Pd函数的参数是强制赋值的来测试的。经测试发现

    通过主函数int _tmain(int argc, char* argv[], char* envp[]) 传入的参数,如果这样输入命令,

    test.exe 2000 10 11 + 回车

    结果printf出来,atol(argv[1])结果是2。同理如果是

    test.exe 676 10 11 + 回车

    结果printf出来,atol(argv[1])结果是6。

    这时用OpenProcess打开的句柄应该不存在,要么就是系统敏感句柄吧。

    但现在的问题是不知怎么传入这个参数了(貌似很低级的问题,很久没碰C++了,有些基础的东西忘了)。

    望解答(我自己继续看看怎么解决)。


    不知怎么,主函数怎么只能传入一个命令的第一个参数的第一个字符?难道还要我移动指针去读取第二个字符?
    2010年6月8日 12:17