函数简介:

DmGuard的加强接口,用于获取一些额外信息. 具体看下面参数介绍

函数原型:

string DmGuardParams(cmd,subcmd,param)

参数定义:

cmd 字符串: 盾类型. 这里取值为"gr"或者"th"(以后可能会有扩充). 这里要注意的是,如果要获取指定的盾类型信息,必须先成功用DmGuard开启此盾.比如这里的"gr"必须dm.DmGuard 1,"gr"开启成功才可以

subcmd 字符串: 针对具体的盾类型,需要获取的具体信息.

           如果cmd"gr",那么subcmd取值如下定义:
                      "enum" :
枚举指定进程的所有句柄.
                      "get"  :
获取指定进程的指定句柄信息.(类型,名字,权限值)
                      "set"  :
设置指定进程的指定句柄的权限值.
                      "close":
关闭指定进程的指定句柄.

           如果cmd"th",那么subcmd取值如下定义:
                      "enum" :    
枚举指定进程的所有线程.
                      "get"  :    
获取指定线程的详细信息.(句柄值,优先级,ETHREAD,TEB,win32StartAddresss,线程地址所在的模块名,交换次数,线程状态,挂起次数)
                      "resume"  :
恢复指定的线程.不可操作本线程. suspend_count大于0,每调用一次resume,都会让suspend_count1,直到0为止才会真正的恢复线程.
                      "suspend": 
挂起指定线程.不可操作本线程.
                     
"terminate":结束指定线程.不可操作本线程.

param 字符串: 参数信息,这里具体的含义取决于cmdsubcmd.

           如果cmd"gr",subcmd取值为如下时,具体的参数含义:
                      "enum" : param
"pid", pid为进程pid,10进制形式.
                      "get"  : param
"pid handle",pid为进程pid,10进制形式,handle为句柄值,10进制形式.
                      "set"  : param
"pid handle access",pid为进程pid,10进制形式,handle为句柄值,10进制形式,access为权限值,10进制形式.
                      "close": param
"pid handle", pid为进程pid,10进制形式,handle为句柄值,10进制形式.

           如果cmd"th",subcmd取值为如下时,具体的参数含义:
                      "enum" :     param
"pid", pid为进程pid,10进制形式.
                      "get"  :     param
"tid", tid为线程tid,10进制形式.
                      "resume"  :  param
"tid", tid为线程tid,10进制形式.
                      "suspend"  : param
"tid", tid为线程tid,10进制形式.
                      "terminate": param
"tid", tid为线程tid,10进制形式.

返回值:

字符串: 根据不同的cmdsubcmd,返回值不同.

           如果cmd"gr",subcmd取值为如下时,具体的返回值:
                      "enum" : "handle1|handle2|.....|handlen",
每个handle都是10进制长整数. 如果失败返回空字符串
                      "get"  : "type|name|access". type
表示句柄的类型,比如"Event","File"等之类的. name表示句柄的名字,有些句柄的名字可能是空的. access10进制整数,表示此句柄的权限值. 如果失败返回空字符串
                      "set"  :
成功返回"ok",否则为空字符串.
                      "close":
成功返回"ok",否则为空字符串.

           如果cmd"th",subcmd取值为如下时,具体的返回值:
                      "enum" : "tid1|tid2|.....|tidn",
每个tid都是10进制整数. 如果失败返回空字符串
                      "get"  : "tid|prority|ethread|teb|win32StartAddress|module_name|switch_count|state|suspend_count".
如果失败返回空字符串.
                                tid :
线程tid,10进制整数
                                prority :
线程优先级, 10进制整数
                                ethread :
线程内核对象ETHREAD指针. 6416进制整数.
                                teb :
线程内核对象TEB指针. 6416进制整数
                                win32StartAddress :
线程起始地址. 6416进制整数
                                module_name :
线程起始地址所在的模块名.
                                switch_count :
线程切换次数. 10进制整数
                                state :
线程状态. 10进制整数. 0 : 初始化 1 : 准备 2 : 运行 3 : 待机 4 : 结束 5 : 等待 6 : 转换. 这个地方其实只需要关心是不是4就行了. 如果是4表示线程结束了. 其它的状态都可以认为是运行状态. 不用太关心.
                                suspend_count :
线程挂起次数. 10进制整数. 线程挂起次数,当此值大于0,表示线程处于挂起状态. 等于0表示处于运行状态.
                      "resume"  :
成功返回"ok",否则为空字符串.
                      "suspend":
成功返回"ok",否则为空字符串.
                      "terminate":
成功返回"ok",否则为空字符串.

示例:

// 枚举进程的所有句柄,并获取此句柄的信息,并打印出来
dm_ret = dm.DmGuard(1,"gr")
dm_ret = dm.DmGuardParams("gr","enum","1024")

If len(dm_ret) > 0 Then
   ss = split(dm_ret,"|")
   index = 0
   count = UBound(ss) + 1
   Do While index < count
      dm_ret = dm.DmGuardParams("gr","get","1024 " & ss(index))
      TracePrint dm_ret
      index = index +1
   Loop
End If

// 关闭指定进程的句柄
dm_ret = dm.DmGuard(1,"gr")
dm_ret = dm.DmGuardParams("gr","close","1024 240")
TracePrint dm_ret

// 修改指定进程的句柄的权限
dm_ret = dm.DmGuard(1,"gr")
dm_ret = dm.DmGuardParams("gr","set","1024 240 12345")
TracePrint dm_ret

//
枚举进程的所有线程,并把线程的信息都打印出来
dm_ret = dm.DmGuard(1,"th")
dm_ret = dm.DmGuardParams("th","enum","1024")

If len(dm_ret) > 0 Then
   ss = split(dm_ret,"|")
   index = 0
   count = UBound(ss) + 1
   Do While index < count
      dm_ret = dm.DmGuardParams("th","get",ss(index))
      TracePrint dm_ret
      index = index +1
   Loop
End If

// 结束指定线程. 注意后面的338是线程tid. 不是进程pid
dm_ret = dm.DmGuardParams("th","terminate","338")
//
挂起指定线程
dm_ret = dm.DmGuardParams("th","suspend","338")
//
恢复指定线程
dm_ret = dm.DmGuardParams("th","resume","338")

 

: gr盾对应的这些subcmd,其实最主要的目的是"set", 设置句柄权限.
比如场景1:
     
我们需要打开进程,或者打开线程,文件等等,如果在打开进程的权限里写了最高权限,那么由于一些保护措施,往往会失败. 但是如果你降低一些权限,比如用最低权限,反而会成功. 所以我们可以先用低权限打开对应的句柄,然后用"set"来提权,这样就相当于用间接的方式用最高权限打开了句柄.

再比如场景2:
     
某些时候,有坏人打开我们自己的进程来做一些非法的事情,这时候我们可以通过扫描("enum"功能),来检查是否有关我们进程的句柄,如果有的话,我们可以考虑直接关闭句柄("close"),或者给他降低权限("set").

其它场景,请自行脑补. 可能又有人会问,我怎么知道设定的权限值到底是多少呢? 这个很简单。 每种句柄都对应不同的权限,我们可以自己创建一个最高权限的句柄,来获取("get")这个句柄的信息,就知道最高权限对应的权限到底是多少. 同样最低权限也一样。 这里一定要注意,不同类型的句柄,权限定义是不同的. 比如"Event""File"就是完全不同的权限值.

这里对进程句柄举个例子. 比如我们想获取最高权限的进程句柄权限值,那么操作如下
// 我们打开进程id1024的句柄, 1024只是一个例子,必须换成真实存在的pid
handle = dm.OpenProcess(1024)
dm_ret = dm.DmGuard(1,"gr")
my_pid = GetCurrentProcessId() //
这个GetCurrentProcessId是调用系统API,获取当前进程ID,因为打开的句柄在本进程里
info = dm.DmGuardParams("gr","get",cstr(my_pid)& " " & cstr(handle))
ss = split(info,"|")
access = clng(ss(2))
//
那么这里的access就是最高权限的值了.

一般来说,每种句柄权限在不同系统里的定义都是相同的. 所以你可以在一个系统里获取到后,在其它系统里也是通用的.

ps : 上次有人问我,如何把一个别人正在读写的文件给强行打开读写,其实也是一个权限的事,增加一个SHARE_READSHARE_WRITEOK. 具体方法和上面这个进程句柄大同小异.