如何判断一个进程是否是自身进程的一个实例?
比如说做了一个程序叫a.exe, 然后将它拷贝成(文件名不一定一样)b.exe,c.exe,....xxx.exe,然后分别运行,它得到进程快照,然后遍历进程句柄,
但它怎样判断得到的一个进程句柄是否是自己的一个实例呢?
ReadProcessMemory(?)?
请大家具体点好吗

解决方案 »

  1.   

    通常是用GetModuleFileName判断模块的文件路径是否是指定的文件路径
      

  2.   

    进程快照不是可以得到进程ID呀
    然后自己再调用GetCurrentProcessID() == 进程快照得到的ID
    就可以了。
      

  3.   

    我想,可以建立一个共享的数据段,里面保留足够的空间。程序启动后,要把自身的ProcessId放到该段中。其它实例启动的时候,扫描该段,就可以知道哪些进程是本程序的实例之一了。
      

  4.   

    楼上的可行!!直接使用ProcessId!!!!!!!!!!!!!!
      

  5.   

    回lianglp() ,你可能没太明白我的意思,用GetCurrentProcessID只能判断一个进程ID是不是自身进程, 不能判断进程快照中有自己多个实例它门分别的进程ID。我想楼上halk(天涯海角)和 force_eagle(战鹰)想法不错, 但比较空洞,没有进一步说明如何建立一个共享的数据段,和读写该数据段。还望诸位高见!
      

  6.   

    20分,少了点……算了,助人为乐嘛!
    看懂就结贴,最好能提交一下FAQ看能不能给俺加点信誉分,嘿嘿……小于100已经很久了。
      

  7.   

    // 建立一个数据段
    #pragma data_seg("new_data_sec")
    DWORD dwProcessIds[1024]={0}; // 保留1024个位置,用于存储ProcessId
    #pragma data_seg()
    // 将这个数据段设置为共享段……
    #pragma comment(linker, "/section:new_data_sec,RWS")……
    ……int APIENTRY WinMain(HINSTANCE hInstance,
                         HINSTANCE hPrevInstance,
                         LPSTR     lpCmdLine,
                         int       nCmdShow)
    {
    ……
    for(int i=0;i<1024;i++)
    {
      if(dwProcessIds[i] != 0)// 打印出已有的id
      {
        printf("Instance No.%d:0x%08x", i, dwProcessIds[i]);
      }
      else // 找到一个空白,把自己的ID加入到共享段中……
      {
          dwProcessIds[i] = GetCurrentProcessId();
          break;
      }
    }
    // 继续其它语句
    }
      

  8.   

    既然楼主否认了jiangsheng(蒋晟.MSMVP2004Jan)的方法。我想搂住的意思是
    假如有文件c:\a.exe; 与文件d:\test\b.exe是同一个可执行文件的拷贝, 同时运行这两个exe文件, 如何判断他们本质上是属于同一个文件的拷贝。
    是不是这样啊?如果是的话,  halk(天涯海角)的方法就行不通了。共享段只能在同一个exe文件的多个实列实现共享变量,而不能在多个不同名的exe文件共享。我想可以用内存映射文件来实现, 每个exe或同一个exe文件的多个实例启动时,在共享的内存映射文件里登记注册一下它的进程ID,这样访问这个内存映射文件就可以知道有多少个"实例"(你所谓的实例)在运行了。
      

  9.   

    正是 jruv(~~~一叶落而知天下秋~~~) 所说的意思,我用 halk(天涯海角)的方法试过了,但总运行另一个实例后共享数据被初始化了(可能也是jruv所说的;"共享段只能在同一个exe文件的多个实列实现共享变量,而不能在多个不同名的exe文件共享。"
    )
    分数确实给少了,确实不好意思(因为我的分不多了)。内存映射文件我一直没用过,我还不知道该怎么用.
      

  10.   

    所谓内存映射,就是一块可以被所有的进程都访问到的物理存储区域。MSDN上有详细描述,
    参考CreateFileMapping, MapViewofFile等函数的用法。
      

  11.   

    建立楼主首先得到exe的modulename
    然后直接对文件进行字节比较
    或者进行md5抽样比较
    如果相同则认为是同一exe
    感觉楼主的问题似乎没有多大意义?
    或者说楼主的说法有问题
    什么叫一个进程是自身进程的一个实例?
      

  12.   

    在你的程序里创建一个命名Mutex对象——CreateMutex( 0, 0, "Name" );
    如果你的程序在创建这个名字的Mutex之前,已经有这个Mutex存在,说明已经有一个实例在运行了。用OpenMutex( 0, "Name" )来判断Mutex是否已经创建了。
    我意思是说,利用命名Mutex对象在系统中的唯一性来判断你的程序是否已经实例在运行。
    这个名字一定要确保不与其他的对象的名字冲突。
      

  13.   

    同意 msdn_user(蓝天) 的观点1. 先取得该进程的exe文件名
    2. 再取得自己进程的exe文件名然后比较这两个文件的二进制数据是否相同
      

  14.   

    来电怪异的,上面有人说比较文件数据
    我看还不如将EXE文件的头部DOS HEADER部分修改一下,比如:This is my file!,只比较这个字符串就知道了
    只要比较进程头部的字符串和上面的字符串就知道是不是自身的多个实例或者其他相同代码EXE的实例
      

  15.   

    我觉得 msdn_user(蓝天) 的方法有问题:在进程中用GetModuleFileName( )能够取到这个进程的其他实例的exe文件路径吗?baojian88888() 
    1. 先取得该进程的exe文件名
    2. 再取得自己进程的exe文件名-------------“该进程”是指哪个进程?在“自己进程”里如何取得“该进程”的信息。
      

  16.   

    HANDLE hmutex=CreateMutex(NULL,true,"这里写上一个有唯一性的标记符号");
    if(GetLastError()==ERROR_ALREADY_EXISTS){ExitProcess(0);}只要在你的程序开始的地方加入上面的两行,就能保证你的程序只有一个实例在内存中运行了,不管你的.exe被复制成几份,从几个不同的路径运行。
    如:
    WinMain()
    {
               HANDLE hmutex=CreateMutex(NULL,true,"set_app_id");
               if(GetLastError()==ERROR_ALREADY_EXISTS){ExitProcess(0);}
     
    }
      

  17.   

    footway(靠边行走) 
    >> 我觉得 msdn_user(蓝天) 的方法有问题:在进程中用GetModuleFileName( )能够取到这个进程的其他实例的exe文件路径吗?baojian88888() 
    1. 先取得该进程的exe文件名
    2. 再取得自己进程的exe文件名-------------“该进程”是指哪个进程?在“自己进程”里如何取得“该进程”的信息。
    ----------------------------------------人家有说是用GetModuleFileName( )函数来取得其他实例的exe文件路径吗?“该进程”也就是楼主标题“如何判断一个进程是否是自身进程的一个实例? ”中所说的“一个进程”。不好意思,没有描述清楚