美文网首页
腾讯管家攻防驱动分析-TsDefenseBt

腾讯管家攻防驱动分析-TsDefenseBt

作者: 超哥__ | 来源:发表于2018-01-23 07:26 被阅读0次

    layout: wiki
    title: 腾讯管家攻防驱动分析-TsDefenseBt
    categories: WindowsDriver
    description: 腾讯管家攻防驱动分析-TsDefenseBt
    keywords:
    url: https://lichao890427.github.io/ https://github.com/lichao890427/


    TsDefenseBt分析

      该驱动主要用于和各类竞品做对抗用,本文为2015.7.23版本的Tsdefensebt.sys的分析。该驱动使用TsFltMgr和TsSysKit提供的接口,和另外几个驱动一样存在验签名机制。

    入口点

    1.设置ZwQueryValueKey的PrevFilter为ZwQueryValueKeyHooker
      ZwQueryValueKeyHooker中拦截Service.exe对qqpcrtp服务的查询
    2.检查HookPort, 360SelfProtection若存在则设置360存在标志位,baidu标志位默认设置为存在
      若baidu存在,则解除baidu驱动进程创建、映像加载、线程创建回调
    若360存在,则对TsDefensebt本身做ObOpenObjectByName的IAT hook,并记录iat信息(防止360 hook),初始化360tray.exe, zhudongfangyu.exe, 360se.exe, 360chrome.exe, wscript.exe到进程id监视表
    3.获取系统api真实地址
    4.获取关机回调队列头
    5.获取TsSyskit接口
    6.设置UnloadDispatch,CreateDispatch,CloseDispatch,IoCtlDispatch,ShutdownDispatch
    7.挂钩进程创建为NtCreateProcessNotifyHooker1
      若360存在则挂钩NtSetValueKey为NtSetValueKeyHooker,挂钩ZwRequestWaitReplyPort为ZwRequestWaitReplyPortHooker,挂钩ZwAlpcSendWaitReceivePort为ZwAlpcSendWaitReceivePortHooker,挂钩ZwWriteVirtualMemory为ZwWriteVirtualMemoryHooker,挂钩ZwCreateThread为ZwCreateThreadHooker,挂钩ObReferenceObjectByHandle为FakeObReferenceObjectByHandle
    8.注册注册表回调CmCallback
    9.创建TSDFStategy设备,作为穿透驱动第二通道
    10.保存TsDefenseBt映像起始地址处4096字节
      若ShutdownTime被修改,若360存在则从SysOpt.ini删除指定的启动项,若baidu存在则删除服务项BDMWrench,BDArKit,BDSGRTP,BDMiniDlUpdate,bd0001,bd0002,bd0003,bd0004,BDDefense,BDEnhanceBoost,BDFileDefend,BDMNetMon,BDSafeBrower,BDSandBox,Bprotect,Bhbase,Bfmon,Bfilter
    11.加密TsDefenseBt->DriverObject->DriverSection中存储的驱动路径

    Ntfs创建回调NtfsFsdCreateHooker

    若当前进程为360Tray.exe, Zhudongfangyu.exe, 360se.exe, 360chrome.exe, rundll32.exe, 360tray.exe,目标目录为
    appdata\roaming\microsoft\windows\start menu\programs\startup, 
        \「开始」菜单\程序\启动, 
        \local settings\defend, 
        \local\defend, 
        且目标文件为.lnk后缀则拒绝
    若当前进程为svchost.exe,目标目录为\360safe\则拒绝
    若当前进程为explorer.exe或runonce.exe,目标路径为\360safe\且目标文件为.lnk .slnk .flnk .plnk .zlnk .xlnk .qlnk .qqlnk则拒绝
    若当前进程为360tray.exe或zhudongfangyu.exe,目标路径为\360safe\且目标文件为.lnk .slnk .flnk .plnk .zlnk .xlnk .qlnk .qqlnk则拒绝;目标匹配
        \*\WINDOWS\TEMP\*.EXE, 
        \*\LOCAL SETTINGS\TEMP\*.EXE,
        \*\LOCAL\TEMP\*.EXE, 
        \*\LOCAL*\F9\*.EXE,
        \*\APPDATA\SAFERUN\*.EXE\*\APPDATA\*\*.EXE*\PROGRAMDATA\*\*.EXE
        则拒绝
    若当前进程为cmd.exe 360se.exe wscript.exe 360chrome.exe,且目标文件为360tray.exe zhudongfangyu.exe则拒绝
    

    RegisterShutdown

    重置TsDefenseBt关机回调
    若发现ShutdownTime被修改则执行ClearThread
    将\Driver\WMIxWDM,\Driver\mountmgr,\FileSystem\RAW,\Driver\volmgr,\Driver\ksecdd,\Driver\BDArKit关机回调置无效
    设置注册表\\Registry\\Machine\\System\\CurrentControlSet\\Control\\Windows键回调为RegisterShutdown
    

    ClearThread

    若360存在则清除SysOpt.ini指定的启动项
    删除baidu注册表项
    

    ShutdownDispatch

    打开360文件
    \safemon\safeloader.exe, 
    \safemon\BAK_safeloader.exe, 
    \safemon\ok_safeloader.exe, 
    \safemon\zz_safeloader.exe, 
    \safemon\agesafe.exe, 
    \safemon\sssafefix.exe,
    \safemon\safe505.exe并存储句柄
    创建ClearThread线程
    删除360注册表项
    删除360快捷方式(文件和注册表)
    删除360服务项
    删除baidu注册表项
    

    UnloadDispatch

    删除ZwQueryValueKey的PrevFilter
    

    CreateDispatch

    检查进程是否处于监视列表
    检查进程是否为Ts文件,并加入监视列表
    

    CloseDispatch

    IoCtlDispatch

    IoCtlCode= 0x222044 TSDFStategy 记录文件注册表(加密)数据用于增删查改
    IoCtlCode= 0x222048 文件、注册表穿透操作新通道
    IoCtlCode= 0x222054|0x222058    穿透加载驱动新通道
    IoCtlCode= 0x222014 设置开自保
    IoCtlCode= 0x222004 用于同步
    IoCtlCode= 0x222028| 0x22202C   设置注册表服务项标识位
    IoCtlCode= 0x222030 设置关自保
    

    删除360注册表项

    删除
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Run
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\RunOnce
    \Registry\Machine\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\Explorer\Run
    \Registry\Machine\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\Explorer\RunOnce
    和\Registry\User下每个用户的
        \Software\Microsoft\Windows\CurrentVersion\Run
        \Software\Microsoft\Windows\CurrentVersion\RunOnce
        \SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\Explorer\Run
        \SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\Explorer\RunOnce
    下的键:
    Fix360Safe
    "{7B03EE23-306B-47a7-B9A5-4B4783FBB2A6}"
    "{7A03EE23-306B-47a7-B9A5-4B4783FBB2A6}"
    Repair360Safe
    360安全卫士应急修复
    360Safe安全卫士应急修复
    360应急修复程序
    360SafeEmergencyRepair
    Safe安全卫士应急修复
    360卫士自我修复程序
    应急修复360卫士程序
    360卫士用户应急自修复程序
    360卫士应急自修复程序
    360卫士应急自修复程序7896
    360安全卫士应急修复工具
    360安全卫士异常修复工具
    360卫士异常修复工具
    360卫士异常应急修复工具
    360卫士异常应急修复程序
    360卫士异常应急修复服务程序
    360卫士应急修复服务程序
    360卫士应急修复服务工具
    360安全卫士应急修复服务工具
    360安全卫士异常应急修复服务工具
    360安全卫士异常应急修复服务程序
    360安全卫士修复服务工具
    360安全卫士修复服务工具7787
    3-6-0安全卫士-异常应急修复-Fix2
    3-6-0-F-i-x-3
    360卫士异常应急修复服务程序7xi
    360卫士异常应急修复服务程序Ok
    360卫士-异常应急修复服务程序
    卫士-修复程序
    360-卫士-修复程序
    卫士-360-修复
    360-Tray-修复
    tray-360-修复
    修复-tray-360
    卫士安全修复应急
    卫士修复安全应急
    修复安全卫士应急
    异常安全卫士应急修复
    360安全卫士应急修复异常组件程序
    "My360Helper"
    "MyDefend360"
    "36ORepair"
    "Safe360Tray"
    "360Safe360TrayFix"
    "360SafeTrayFix"
    "360SafeTrayFix123"
    "360SafeTrayFix1"
    "360SafeTrayFix2"
    "Rep36O"
    "Rep36Osafes"
    "Rep36OFixsafe"
    "360SafeTrayFix3"
    "Defend360TrayFix"
    "360Safe_TrayFix"
    "36OFix_360safe"
    "36OFix_360safe1"
    "36OFix_safe"
    "3 6 0 F i x"
    "3 6 O F i x"
    "3-6-O-F-i-x"
    "3-6-0 F-i-x"
    "36 0 Fi x"
    "36 0 F i-x"
    "360-Fi-x"
    "-360Fix-"
    "-3 6-0 F-i x-"
    "-3-6-0 F-i x-"
    "-3-6-0F-i x-"
    "3-6-0-Fix-0"
    "360fiix_69"
    "360fiix_419"
    "fixfixfixfix"
    "QFiPCTray"
    "QFiPCTray_1"
    "PCTray360"
    "PCFTray360"
    "OKJPCTray"
    "sdCFTrayJHSDSDF"
    "TrayFixSVC"
    "Traydsfsdffs"
    "FTrayPCsss"
    "120FTray"
    "361FTray"
    "361FTrayFix"
    "GFFsFTray"
    "s1aGFFsFTray"
    "31aGFFsFTray"
    "31FixQFTray"
    "FwwwixQFTray"
    "DdFFdOTA"
    "AlchemistFAA"
    "BearFixAW"
    "DestroyerUHSFSS"
    "AxeWUDIZHAN"
    "spiderManSAD"
    "BaneZhiYuan"
    "ursaXiongZi"
    "BMShouWangZ"
    "gondarSanJin"
    "KunkkaChuanZhang"
    "Azwraithnver"
    和项:
    "360_FIX*"
    "360FIX*"
    "3-60FIX*"
    "360FIIX*"
    "QFIPCTRAY*"
    删除\REGISTRY\MACHINE\SOFTWARE\Classes\CLSID\{FC6354A7-BACD-47C3-A989-312F7FADA3E2}\LocalServer32
    删除TSDFStategy指定的键值
    

    解除baidu驱动回调

    分别对\Driver\BDMWrench,\Driver\BDArKit,\Driver\bd0001,\Driver\bd0002,\FileSystem\bd0003,
    \Driver\bd0004,\Driver\BdSandBox,\Driver\BDMNetMon几个驱动,从映像起始地址处4096字节范围内,以1为步长的4096个地址,做摘除进程回调、映像加载回调、线程回调操作
    

    删除360快捷方式

    删除\REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders, Common Startup键,以及\Registry\User下每个用户\Software\Microsoft\Windows\CurrentVersion\Explorer\ShellFolders, Startup键 (lnk文件及注册表):
    \safe505.lnk
    \safeFY.lnk
    \FYFY.lnk
    \OKFOU.lnk
    \OKFix.lnk
    \OKZFix.lnk
    \OKAgeFix.lnk
    \sssafeFix.lnk
    \SafeFix360.lnk
    \ss360safeFix.lnk
    \yy360safeFix.lnk
    \Fixs360safeFix.lnk
    \FixMy360safe.lnk
    \MyFix360safe.lnk
    \ProFixSafe.lnk
    \DoFix360Safe.lnk
    \RunHelper60safe.lnk
    \360
    \360safe.lnk
    \360trayfix.lnk
    \360
    \360safe505Fixs.lnk
    \360safe110Fixs.lnk
    \safe505110Fixs.lnk
    

    删除360服务项

    360FixSvc
    3600FixSvc
    360SFixSvc
    Fix360SafeService
    SafeFix
    360XFixSvc
    Fix360Service
    360FixService
    360FixSafe
    FixSafeService
    RepairSafezage
    360csvcsFix
    360Fixcsvcs
    360ServiceFixs
    360SafeFixService
    360SafeFixOk
    360Fix360Safe
    360Fix360tray
    Fix360trayService
    360Fix360trayService
    360Fix360trayServices
    360Fix360trayServicess
    360Fix360trayFix
    360trayFixService
    360trayFixsSvc
    360trayFixsSvcx
    360trayRunFix
    360trayRunFixs
    360traysRunFix
    360sRunFix
    360ssxxaRunFix
    360stxaFix
    FixSafe360
    FixsvcSafe360
    FixsvcServiceSafe360
    FixServiceSafe360tary
    FixSafe360taryServices
    505Fix360Safe
    505360Safe
    repair505
    505repair
    saferepair
    repairtray
    repair360
    startrep
    SoS360Safe
    S0S360Safe
    360Sos
    36OSosSafe
    36OOKS0SSafe
    360OKS0SSafe
    3600KSOSSafe
    36O0OKSOSafe
    36000KSOSSafe
    36000OKSOSSafe
    36O00OKSOSSafe
    36O00OsKSOSSafe
    36O0OOKSOSSafe
    36O00OsKSOSSafe
    3605050Safe
    36OSOSFixSafe
    

    删除baidu注册表项

    "BDMWrench"
    "BDArKit"
    "BDSGRTP"
    "BDMiniDlUpdate"
    "bd0001"
    "bd0002"
    "bd0003"
    "bd0004"
    "BDDefense"
    "BDEnhanceBoost"
    "BDFileDefend"
    "BDMNetMon"
    "BDSafeBrower"
    "BDSandBox"
    "Bprotect"
    "Bhbase"
    "Bfmon"
    "Bfilter"
    

    NtCreateProcessNotifyHooker1

    若当前进程为360tray.exe, zhudongfangyu.exe, 360se.exe, 360chrome.exe, wscript.exe则添加到进程id监视表safemonfilehandle
    若360存在,且目标进程为\SystemRoot\system32\sc.exe或\SystemRoot\system32\rundll32.exe则添加到监视列表
    若目标进程为explorer.exe且当前进程为Userinit.exe或Taskmgr.exe则删除进程id监视表safemonfilehandle
    若目标文件为Userinit.exe,则打开360文件\safemon\safeloader.exe, \safemon\BAK_safeloader.exe, \safemon\ok_safeloader.exe, \safemon\zz_safeloader.exe, \safemon\agesafe.exe, \safemon\sssafefix.exe, \safemon\safe505.exe并存储句柄
    若目标进程为baiduprotect.exe
    若   当前进程为explorer.exe或svchost.exe且目标进程为safe505.exe:
        当前进程为runonce.exe且目标进程为360tray.exe
        当前进程为360se.exe或360chrome.exe且目标进程为360tray.exe, zhudongfangyu.exe, safe505.exe, liveupdate360.exe:
        目标进程为safe505.exe, safefix.exe, safeloader.exe, 360xfix505.exe:
        若目标进程为
        \360safe\softmgr\softmanager.exe
    \360safe\safemon\360realpro.exe 
    \360safe\uninst.exe
    \360safe\utils\filesmasher.exe
    \360safe\utils\360fileunlock.exe
    \360safe\360shellpro.exe
    \360safe\360safe.exe
    \360safe\mobilemgr\360mobilemgr.exe
    \360safe\360apploader.exe
    \360safe\deepscan\dsmain.exe
    \360safe\safemon\360tray.exe
    则强制结束进程
    若创建目标进程为explorer.exe或winlogon.exe,则
    若baidu存在则解除baidu驱动回调
    若360存在则删除360启动项和快捷方式
    若结束目标进程为explorer.exe或winlogon.exe,则
    若baidu存在则解除baidu驱动回调
    若360存在则:执行FuckCompeete1,删除360启动项和快捷方式;清除SysOpt.ini指定的启动项;删除\Registry\User下每个用户\Software\Microsoft\Windows\CurrentVersion\Run和\Software\Microsoft\Windows\CurrentVersion\RunOnce的360safetray和360sd项;删除360服务项;删除baidu服务项^_^
    
    FuckCompete1:将\\FileSystem\\360boost的关机回调设置为无效;挂钩Ntfs创建例程;重置自身关机回调;创建随机名驱动及设备执行并设置其关机回调为ShutdownDispatch
    

    NtSetValueKeyHooker

    若系统关机/注销,且ValueName存在360或当前进程为zhudongfangyu.exe,且目标注册表路径为:
        \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Svchost
    \REGISTRY\*\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN*
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Run
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\RunOnce
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\360
    \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\CONTROL\SESSION MANAGER
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\Explorer
    \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\*
    \REGISTRY\*\SOFTWARE\CLASSES\CLSID\*\LOCALSERVER32*
    则拒绝
    

    ZwRequestWaitReplyPortHooker/ZwAlpcSendWaitReceivePortHooker

    若当前进程为360se.exe或360chrome.exe,目标进程为360tray.exe或zhudongfangyu.exe则拒绝
    若当前进程为zhudongfangyu.exe或wmiprvse.exe系统正在关机,或当前进程为360tray.exe,且目标操作存在关键字Win32_Service, Create, :\\WINDOWS\\system32\\svchost.exe –k, Win32_Process, Defend360, Fix360, FixRundll, \SoftMgr\, 360Safe, .dll, .dat, .exe, .cp, DllGetClassObject, 360csvcs, RERDVGYBHNJ, REPA, REPAIR则拒绝
    

    NtWriteVirtualMemoryHooker/NtCreateThreadHooker

    若当前进程为360se.exe或360chrome.exe且目标进程为explorer.exe,则拒绝(explorer.exe被注入)
    

    FakeObReferenceObjectByHandle

    若当前进程为zhudongfangyu.exe且目标对象路径为
    \*\WINDOWS\CURRENTVERSION\RUN
    \*\WINDOWS\CURRENTVERSION\RUN\*
    \*\WINDOWS\CURRENTVERSION\RUNONCE
    \*\WINDOWS\CURRENTVERSION\RUNONCE\*
    \*\CURRENTVERSION\SVCHOST
    \*\SYSTEM\CONTROLSET*\SERVICES\QQ*
    \*\SYSTEM\CONTROLSET*\SERVICES\TS*
    则拒绝
    若当前进程为zhudongfangyu.exe, 360tray.exe, svchost.exe,且目标对象位于监视链表中则拒绝
    若系统正在关机或注销:
        若当前进程为services.exe, svchost.exe且目标路径为
    \\REGISTRY\\MACHINE\\SYSTEM\\*CONTROLSET*\\SERVICES\\*FIX*SERV*
    \\REGISTRY\\MACHINE\\SYSTEM\\*CONTROLSET*\\SERVICES\\*FIX*SAFE*
    \\REGISTRY\\*\\SOFTWARE\\CLASSES\\CLSID\\*\\LOCALSERVER32*
    则拒绝
    若当前进程为zhudongfangyu.exe, 360tray.exe,且目标对象路径为
        \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Svchost
    \REGISTRY\*\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN*
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Run
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\RunOnce
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Explorer\Shell Folders
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\App Paths
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Uninstall\360
    \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\CONTROL\SESSION MANAGER
    \REGISTRY\MACHINE\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\Explorer
    \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\*
    \REGISTRY\*\SOFTWARE\CLASSES\CLSID\*\LOCALSERVER32*
    则拒绝
    

    CmCallback

    若存在修改ShutdownTime的行为,则执行FuckCompete1:
    将\FileSystem\360boost关机回调置无效
    挂钩NtfsFsdCreate或NtfsCreateDispatch为NtfsFsdCreateHooker
    设置监视\Registry\Machine\System\CurrentControlSet\Control\Windows,回调设置为RegisterShutdown
        创建随机名驱动及设备执行并设置其关机回调为ShutdownDispatch
    

    Tsksp分析

      该驱动为qq管家函数过滤驱动,跟TsFltMgr.sys搭配,TsFltMgr主要完成KiFastCallEntry的挂钩和提供设置过滤函数的接口,而该驱动主要用于配置拦截规则,用前者提供的接口设置真正的过滤函数,并在过滤函数中进行规则匹配以决定拦截行为。并提供一系列接口函数和控制码用于控制规则和内部数据。设备名\Device\TSKSP,符号链接名\DosDevices\TSKSP ,加密手段:Rabbit算法、MD5算法。通过InlineHook KifastCallEntry实现挂钩。

    一、驱动入口DriverEntry

    • 获取TsFltMgr接口,初始化注册表信息、规则、操作系统版本等信息
    • 创建\Device\TSSysKit设备和\DosDevices\TSSysKit符号链接
    • 初始化接口
    • 注册IRP_MJ_CREATE、IRP_MJ_CLOSE、IRP_MJ_DEVICE_CONTROL、IRP_MJ_SHUTDOWN派遣例程
    • 保存Ntfs和Fastfat派遣函数
    • 设置保护关键目录和注册表项
    • 挂钩各个过滤函数
    • 挂钩KeUserModeCallback和重要回调
    • 开自保

    1.1 监控模型

    [图片上传失败...(image-14a21c-1516663530040)]

    1.2 派遣例程

    • IRP_MJ_CREATE
        检查驱动加载者是否有Ts签名
    • IRP_MJ_SHUTDOWN
        设置\REGISTRY\MACHINE\SYSTEM\CurrentControlSet\Services\TSCPM\目录的LastShutdownFlag和LastShutdownTime
      清空\REGISTRY\MACHINE\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN\QQDisabled下的值

    1.3 监控函数

      Ts进程:位于Q管目录或签名为Q管文件签名的进程,按规则判断:上抛给主防主防进程判断;默认情况下若发起者为Ts进程的都放过,使用AddPrevFilter接口设置的过滤函数有:

    Ts进程:位于Q管目录或签名为Q管文件签名的进程,按规则判断:上抛给主防主防进程判断;默认情况下若发起者为Ts进程的都放过
    使用AddPrevFilter接口设置的过滤函数有:
    NtAllocateVirtualMemory
        若发起者为非TS进程而目标为TS进程,则设置PostFilter
        若发起者为非TS进程而目标为非TS进程,则放行
        若发起者为非TS进程而目标为未知进程,则查询虚拟内存监视链表,对比进程路径,按是否Ts进程分别处理
    在PostFilter中记录得到的地址信息
    
    NtAlpcCreatePort
        若发起者为非Ts进程,且不是csrss, services, smss, svchost, lsass, lsm,且操作为修改DNS解析器,则上抛主防根据规则判断
    
    NtAlpcSendWaitReceivePort
        若发起者为非lsass非csrss非Ts进程,修改SAM信息,则上抛主防根据规则判断
        若发起者为非Ts进程,触发csrss进程结束/winlogon关机,则上抛主防根据规则判断
        若发起者为非Ts进程,操作驱动服务端口ntsvcs,则按服务号处理:
    RcloseServiceHandle 执行功能,并将服务从监视列表中移除
    RdeleteService, RsetServiceObjectSecurity, RchangeServiceConfigW,RchangeServiceConfigA,RChangeServiceConfig2A,
    RChangeServiceConfig2W, RcontrolService,RcontrolServiceExA,RcontrolServiceExW   如果目标服务为QQPCRTP, TSKSP, TsFltMgr, QQSysMon, TSSysKit, TSSysFix则拒绝,否则执行功能
    RopenServiceW,RopenServiceA 执行功能并上报主防
    RcreateServiceW,RCreateServiceA 查注册表匹配树并根据结果选择执行功能且加入监控列表或上抛主防根据规则判断
    RstartServiceW,RStartServiceA   查注册表匹配树,上抛主防加载驱动事件,并根据结果放行或不执行,从监控列表中删除
    
    NtAssignProcessToJobObject
        若发起者为非TS进程而目标为TS进程,则拒绝
    
    NtCreateFile
        穿透实现NtCreateFile
    
    NtCreateMutant
        添加PostFilter,在PostFilter中,若发起这为非Ts进程且目标Object处于g_StorageList[14]中则上抛主防判断
    
    NtCreateKey
        若发起者为非主防进程,则在注册表键值匹配ACL树(RegMonTree)中查找,并根据结果上抛主防根据规则判断
    
    NtCreateProcessEx
        添加PostFilter,在PostFilter中,将进程添加到进程监控链表并上报给主防
    
    NtCreatePort
    若发起者为非Ts进程,且不是csrss, services, smss, svchost, lsass, lsm,且操作为修改DNS解析器,则上抛主防根据规则判断
    
    NtCreateSection
        满足DesiredAccess=SECTION_ALL_ACCESS,SectionPageProtection=PAGE_EXECUTE,AllocationAttributes=SEC_IMAGE时:
            设置PostFilter;若目标文件为Ts文件,则检查应用层回溯栈,如果存在CreateProcessInternalW,则在启动参数增加CREATE_PRESERVE_CODE_AUTHZ_LEVEL位
    
    
    NtCreateThread 
        若发起者为非主防进程,且该线程不是进程第一个线程,且目标进程为Ts进程,则拒绝
    若发起者为非主防进程,且该线程不是进程第一个线程,且目标进程为非Ts进程,则上抛主防根据规则判断
    
    NtCreateThreadEx
        若发起者为非主防进程,且该线程不是进程第一个线程,且目标进程为Ts进程,则拒绝
    若发起者为非主防进程,且该线程不是进程第一个线程,且目标进程为非Ts进程,则上抛主防根据规则判断
    
    NtCreateSymbolicLinkObject
        若目标对象为\Device\PhysicalMemory则拒绝
        否则查询ACL表,若不符合则记录最近创建的4个符号名,若符合则上抛主防根据规则判断
    
    NtCreateUserProcess
        若目标文件为Ts文件,则检查应用层回溯栈,如果存在CreateProcessInternalW,则在启动参数增加CREATE_PRESERVE_CODE_AUTHZ_LEVEL位
    
    NtDeleteKey
        若目标在g_StorageList[9]中则拒绝
        若目标在注册表监控树中,若符合则上抛主防根据规则判断
    
    NtDeleteValueKey
        若目标在g_StorageList[9]中则拒绝
        若目标在注册表监控树中,若符合则上抛主防根据规则判断
    
    NtDeviceIoControlFile
        IoControlCode=0x8FFF23C8或0x8FFF23CC,目标驱动为\Driver\NDProxy,则上抛主防根据规则判断    IoControlCode=0x2A0000(IOCTL_SWENUM_INSTALL_INTERFACE)则将该服务项添加到监视
        IoControlCode=0x980C8(FSCTL_SET_ZERO_DATA)
        IoControlCode=0x2D1400(IOCTL_STORAGE_QUERY_PROPERTY), 0x700A0(IOCTL_DISK_GET_DRIVE_GEOMETRY_EX), 0x170002(IOCTL_NDIS_QUERY_GLOBAL_STATS), 0x4D008(IOCTL_SCSI_MINIPORT), 0x900c0(FSCTL_CREATE_OR_GET_OBJECT_ID), 0x90073(FSCTL_GET_RETRIEVAL_POINTERS), 0x7c088(SMART_RCV_DRIVE_DATA), 0x74080(SMART_GET_VERSION) 则上抛主防根据规则判断
        IoControlCode=0xA8730154, 0xA8730010 则采用不同解密密钥解密出PEPROCESS地址,若对应进程路径文件在内存操作监视链表中则拒绝
    
    NtDuplicateObject (发起者,源进程,目标进程互不相同)
        若源进程和目标进程为本进程,且Options=DUPLICATE_SAME_ACCESS则放行
        若发起者为TS, csrss, services, smss, svchost, lsass, lsm进程则放行
        源进程为Ts进程,且”发起进程-源进程”对处于监视列表中则拦截,否则放行
        源进程为非Ts进程,目标进程为Ts进程,且非QQPCSoftGame, QQPCSoftMgr, QQPCClinic, QQPCExternal,则检查”发起进程-目标进程”对是否处于监视列表中,若存在则拦截,否则放行
        源进程为非Ts进程,目标进程为普通进程或QQPCSoftGame, QQPCSoftMgr, QQPCClinic, QQPCExternal:
            源进程和目标进程不同,或Options=DUPLICATE_SAME_ACCESS:
                源进程为发起进程,且源句柄类型为Process/Thread则拦截
                源进程不同于发起进程,则用本进程作为目标进程执行函数得到目标句柄:
                    若执行成功且目标句柄类型为Process/Thread则拦截
                    若执行返回STATUS_INSUFFICIENT_RESOURCES且获取进程句柄数无效则拦截
        其余情况放行
    
    NtEnumerateValueKey
        执行函数,若KeyValueInformationClass=KeyValueFullInformation且发起进程为explorer:
            则只能枚举出子项\REGISTRY\MACHINE\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN\QQDISABLED
    
    NtFreeVirtualMemory
        若发起进程为非Ts进程且目标进程为Ts进程则设置PostFilter,在PostFilter中吧释放的内存从监视数据中去除
    
    NtFsControlFile
        若发起进程为非Ts进程,非lsass, csrss,则监视FsControlCode=0x11C017决定是否上抛主防
    
    NtGetNextThread
        若发起进程为非主防进程且目标进程为Ts进程则拒绝执行
        若发起进程为非主防进程且目标进程为非Ts进程则将访问权限限制为SYNCHRONIZE|THREAD_QUERY_INFORMATION|THREAD_GET_CONTEXT
    
    NtGetNextProcess
        设置PostFilter
    
    NtLoadDriver
        若发起进程为非Ts进程,则将驱动文件信息上抛主防判断
    
    NtMakeTemporaryObject
        若目标对象为Section类型,且对象名路径在\knowndlls\下则拒绝,否则放行
    
    NtOpenFile
        穿透实现NtOpenFile
    
    NtOpenProcess
        若全局开关“监视打开进程”开启,则设置PostFilter,重置AccessMask参数并执行函数,在PostFilter中将发起线程加入监控链表中
        若全局开关“监视打开进程”关闭:
    若发起进程为非Ts进程:
                若目标进程为QQPCFileSafe.exe, QQPCSoftGame.exe, QQPCSoftMgr.exe, QQPCExternal.exe, QQPCClinic.exe则上抛主防判断
                若发起进程为svchost且目标进程为QQPCRtp.exe则上抛主防判断,若不符合条件则修改AccessMask标志位
                若发起进程为lsass且目标进程为QQPCTray.exe则上抛主防判断,若不符合条件则修改AccessMask标志位
                若发起进程为service且目标进程为Ts进程则上抛主防判断,若不符合条件则修改AccessMask标志位
                若不满足上述条件,且不在g_StorageList[15]中,则上抛主防判断,否则修改AccessMask
            若发起进程为Ts进程,或发起进程与目标进程相同,则修改AccessMask
    
    NtOpenThread
        若全局开关“监控打开线程”开启,则设置PostFilter,重置AccessMask参数并执行函数,在PostFilter中将发起线程加入监控链表中
        若全局开关“监视打开进程”关闭:
            若发起进程为非Ts进程,且目标进程为Ts进程,则根据发起进程权限判断是否修改AccessMask
    
    NtOpenSection
        若发起进程为非主防进程,且DesiredAccess有写权限,且目标对象为\device\physicalmemory则上抛主防根据规则判断
    
    NtProtectVirtualMemory
        若发起者为非TS进程而目标为TS进程,则上抛主防根据规则进行判断
    
    NtQueueApcThread
        若发起者为非TS进程而目标为TS进程,则拒绝
        若发起者为非TS进程而目标为非TS进程,则查询ACL表上抛主防根据规则判断
    
    NtQueueApcThreadEx
        若发起者为非TS进程而目标为TS进程,则拒绝
        若发起者为非TS进程而目标为非TS进程,则查询ACL表上抛主防根据规则判断
    
    NtReplaceKey
        若发起者为非Ts进程:
    目标注册表键路径匹配g_StorageList[9],则拒绝
            目标注册表键路径匹配SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN,则拒绝
            其他情况由注册表监控树获取权限并上抛主防根据规则判断
    
    NtRequestWaitReplyPort
        若发起者为非lsass非csrss非Ts进程,修改SAM信息,则上抛主防根据规则判断
        若发起者为非Ts进程,触发csrss进程结束/winlogon关机,则上抛主防根据规则判断
        若发起者为非Ts进程,操作驱动服务端口ntsvcs,则按服务号处理:
    RcloseServiceHandle 执行功能,并将服务从监视列表中移除
    RdeleteService, RsetServiceObjectSecurity, RchangeServiceConfigW,RchangeServiceConfigA,RChangeServiceConfig2A,
    RChangeServiceConfig2W, RcontrolService,RcontrolServiceExA,RcontrolServiceExW   如果目标服务为QQPCRTP, TSKSP, TsFltMgr, QQSysMon, TSSysKit, TSSysFix则拒绝,否则执行功能
    RopenServiceW,RopenServiceA 执行功能并上报主防
    RcreateServiceW,RCreateServiceA 查注册表匹配树并根据结果选择执行功能且加入监控列表或上抛主防根据规则判断
    RstartServiceW,RStartServiceA   查注册表匹配树,上抛主防加载驱动事件,并根据结果放行或不执行,从监控列表中删除
    
    NtRestoreKey
        若发起者为非Ts进程:
    目标注册表键路径匹配g_StorageList[9],则拒绝
            目标注册表键路径匹配SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN,则拒绝
            其他情况由注册表监控树获取权限并上抛主防根据规则判断
    
    NtSetContextThread
        若发起者为非TS进程而目标为TS进程,则查询ACL表并上抛主防根据规则进行判断
    
    NtSetInformationFile
        若发起者为主防进程则放过
        若FileInformationClass=FileDispositionInformation:
            检查目标文件权限并上抛主防根据规则判断
        若FileInformationClass= FileRenameInformation:
            检查源文件和目标文件权限并上抛主防根据规则判断
        若FileInformationClass= FileLinkInformation:
            检查目标文件权限并上抛主防根据规则判断
    若FileInformationClass= FileEndOfFileInformation:
            检查目标文件权限并上抛主防根据规则判断
    若FileInformationClass= FileAllocationInformation:
            检查目标文件权限并上抛主防根据规则判断
        其他FileInformationClass放行
    
    NtSetSecurityObject
        若发起者为非Ts进程,目标对象为以下之一则拒绝,否则放过:
            \REGISTRY\MACHINE\SYSTEM\ControlSet001\services\TSSysKit
            \REGISTRY\MACHINE\SYSTEM\ControlSet002\services\TSSysKit
            \REGISTRY\MACHINE\SYSTEM\CurrentControlSet\services\TSSysKit
            \REGISTRY\MACHINE\SYSTEM\ControlSet001\services\TSKSP
            \REGISTRY\MACHINE\SYSTEM\ControlSet002\services\TSKSP
            \REGISTRY\MACHINE\SYSTEM\CurrentControlSet\services\TSKSP
            \REGISTRY\MACHINE\SYSTEM\ControlSet001\services\QQPCRTP
            \REGISTRY\MACHINE\SYSTEM\ControlSet002\services\QQPCRTP
            \REGISTRY\MACHINE\SYSTEM\CurrentControlSet\services\QQPCRTP
    
    NtSetSystemInformation
        若SystemInformationClass=SystemExtendServiceTableInformation:
            若发起者为非Ts进程且驱动文件存在则上抛主防根据规则进行判断
        若SystemInformationClass= SystemRegistryAppendStringInformation:
            若发起者为非Ts进程且目标注册表路径匹配g_StorageList[9],若键值路径匹配\REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\CONTROL\SESSION MANAGER下的PendingFileRenameOperations,或PendingFileRenameOperations2,则根据文件监控树中的重命名前文件和重命名后文件的访问权限上抛主防判断,否则根据注册表监控树上抛主防判断
    
    NtSetValueKey
        若发起者为非Ts进程,且目标对象路径匹配\REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSKSP*或\REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\QQPCRTP,且目标注册表键名为Start(服务启动类型),则上抛主防根据规则进行判断,根据结果选择是否执行
        若发起者为非Ts进程,且目标进程不是service,若匹配g_StorageList[9]则根据注册表监控树的访问权限上抛主防判断
        若键值路径匹配\REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\CONTROL\SESSION MANAGER下的PendingFileRenameOperations,或PendingFileRenameOperations2,则根据文件监控树中的重命名前文件和重命名后文件的访问权限上抛主防判断,否则根据注册表监控树上抛主防判断
    
        上抛判断前,会做清理以下键值以反调试:
        \Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\QQPCTray.exe
    \Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\QQPCRTP.EXE
    \Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\QQPCUPDATE.EXE
    \Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\QQPCAddWidget.exe
    \Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\QQPCMgr_tz_Setup.exe
    \Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\QQPCMgr.exe
    \Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\QQPConfig.exe
    
    NtSuspendThread
        若发起者为非Ts进程且目标进程为Ts进程则上抛主防根据规则判断
        若发起者为非Ts进程且目标进程为非Ts进程则放过
    
    NtSystemDebugControl
        若Command=SysDbgWriteVirtual或SysDbgWritePhysical则上抛主防根据规则判断
    
    NtTerminateProcess
        若发起者为非Ts进程且目标进程为Ts进程:
            若目标进程权限不足则放过
            若发起进程在g_StorageList[11]中则上抛主防根据规则判断
        若发起者为非Ts进程且目标进程为非Ts进程:
            若目标进程id在g_StorageList[1]中或权限不足则上抛主防根据规则判断
            若目标进程不是taskmgr则放过,否则上抛主防根据规则判断
    
    NtTerminateThread
        若发起者为非TS进程而目标为TS进程,则拒绝
        若发起者为非TS进程而目标为非TS进程,则查询ACL表上抛主防根据规则判断
    
    NtUnmapViewOfSection
        若发起者为非主防进程,且目标进程为Ts进程,则拒绝
        若发起者为非主防进程,且目标进程为非Ts进程,则上抛主防根据规则判断
    
    NtUserClipCursor
        若发起者为非主防进程,且激活窗口属于Ts进程,则匹配预设进程名,若匹配则跳过执行,否则放行
    
    NtUserGetAsyncKeyState
        若发起者为普通进程,执行功能,若键’0’-‘9’,’A’-‘Z’, 数字键盘’0’~’9’被按下,则上抛主防根据规则重置结果
    
    NtUserGetKeyboardState
        若发起者为普通进程,执行功能,若键’0’-‘9’,’A’-‘Z’, 数字键盘’0’~’9’被按下,则上抛主防根据规则重置结果
    
    NtUserGetKeyState
        若发起者为普通进程,执行功能,若键’0’-‘9’,’A’-‘Z’, 数字键盘’0’~’9’被按下,则上抛主防根据规则重置结果
    
    NtUserGetRawInputBuffer
        若发起者为普通进程,执行功能,若键’0’-‘9’,’A’-‘Z’, 数字键盘’0’~’9’被按下,则上抛主防根据规则重置结果
    
    NtUserGetRawInputData
        若发起者为普通进程,执行功能,若键’0’-‘9’,’A’-‘Z’, 数字键盘’0’~’9’被按下,则上抛主防根据规则重置结果
    
    NtUserMessageCall
        若dwType=FNID_SENDMESSAGECALLPROC, FNID_SENDMESSAGE, FNID_SENDNOTIFYMESSAGE, FNID_SENDMESSAGECALLBACK则跳过执行
        若发起进程为普通进程,且uMsg=WM_GETTEXT或WM_SETTEXT则执行函数,若获取的字符串在列表中则上报主防
    
    NtUserPostMessage
        若发起进程不属于smss, lsass, lsm则上报主防进程
        捕获uMsg= WM_KEYFIRST, WM_KEYUP, WM_SYSKEYDOWN, WM_SYSKEYUP, WM_LBUTTONDBLCLK, WM_LBUTTONDOWN, WM_LBUTTONUP, WM_MBUTTONDBLCLK, WM_MBUTTONDOWN, WM_MBUTTONUP, WM_RBUTTONDBLCLK, WM_RBUTTONDOWN, WM_RBUTTONUP, BM_CLICK, WM_COMMAND, WM_NOTIFY 
        若uMsg=WM_COMMAND,则监视指定控件通知码
        若发起进程不同于目标窗口所属进程则决定是否上报主防
        若发起进程为非主防进程,且目标线程不同于发起线程,则关注uMsg=WM_KEYDOWN, WM_LBUTTONDOWN, BM_CLICK, WM_CLOSE, WM_SYSCOMMAND, SC_CLOSE, WM_SETREDRAW, WM_SHOWWINDOW, WM_NCDESTROY, WM_DESTROY, WM_SETTEXT, IE_DOCOMMAND, IE_GETCOMMAND, IE_GETCOUNT, WM_COMMAND
        若uMsg=WM_SYSCOMMAND或SC_CLOSE且发起者为explorer则放行,否则跳过执行
    
    NtUserPostThreadMessage
        若发起进程不属于smss, lsass, lsm则上报主防进程
        捕获uMsg= WM_KEYFIRST, WM_KEYUP, WM_SYSKEYDOWN, WM_SYSKEYUP, WM_LBUTTONDBLCLK, WM_LBUTTONDOWN, WM_LBUTTONUP, WM_MBUTTONDBLCLK, WM_MBUTTONDOWN, WM_MBUTTONUP, WM_RBUTTONDBLCLK, WM_RBUTTONDOWN, WM_RBUTTONUP, BM_CLICK, WM_COMMAND, WM_NOTIFY 
        若uMsg=WM_COMMAND,则监视指定控件通知码
        若发起进程不同于目标窗口所属进程则决定是否上报主防
        若发起进程为非主防进程,且目标线程不同于发起线程,则关注uMsg=WM_KEYDOWN, WM_LBUTTONDOWN, BM_CLICK, WM_CLOSE, WM_SYSCOMMAND, SC_CLOSE, WM_SETREDRAW, WM_SHOWWINDOW, WM_NCDESTROY, WM_DESTROY, WM_SETTEXT, IE_DOCOMMAND, IE_GETCOMMAND, IE_GETCOUNT, WM_COMMAND,若匹配则根据情况跳过执行
    
    NtUserSendInput
        若发起进程不属于smss, lsass, lsm则上报主防进程
        若发起进程为非主防进程则跳过执行
    
    NtUserSetImeInfoEx
        先执行函数以获取文件名
        若输入法序号不存在于\Registry\Machine\SYSTEM\CurrentControlSet\Control\Keyboard Layouts\或子项为空,且发起进程为非Ts进程,则根据注册表监控树上抛主防根据规则决定是否放行
        若输入法文件不为msctfime.ime/ msctf.dll,则根据注册表监控树上抛主防根据规则决定是否放行,否则放行
    执行KeUserModeCallback前对该函数做还原inline hook处理
    
    NtUserSetWindowsHookEx
        若发起者为非Ts进程,ThreadId不为NULL,且目标进程为Ts进程,则拒绝
        若发起者为非Ts进程,ThreadId不为NULL,且目标进程为System进程,若ModuleName为shell32.dll, msctf.dll, ieframe.dll, mshtml.dll, dinput8.dll, browseui.dll则放过,否则上抛主防根据规则判断
        若发起者为非Ts进程,ThreadId为NULL,且目标进程为Ts进程,则按全局键盘钩子上抛主防根据规则判断
    放行WH_KEYBOARD_LL类hook
    
    NtUserSetWindowLong
        若nCmdShow为SW_SHOWMINNOACTIVE或SW_FORCEMINIMIZE且目标窗口属于QQ.exe则上报给主防
        若发起进程为主防进程则放过
    若目标窗口属于Ts进程则跳过执行
    
    NtUserSetWindowPos
        若nCmdShow为SW_SHOWMINNOACTIVE或SW_FORCEMINIMIZE且目标窗口属于QQ.exe则上报给主防
        若发起进程为主防进程则放过
    若目标窗口属于Ts进程则跳过执行
    
    NtUserSetWinEventHook
        若发起进程为Ts进程则放过
        若dwflags不包含WINEVENT_INCONTEXT则放过
        若发起进程等同目标进程则放过
        若目标进程为Ts进程,则上抛主防根据规则判断
    
    NtUserShowWindow
        若nCmdShow为SW_SHOWMINNOACTIVE或SW_FORCEMINIMIZE且目标窗口属于QQ.exe则上报给主防
        若发起进程为主防进程则放过
        若nCmdShow不为SW_HIDE, SW_SHOWMINIMIZED, SW_MINIMIZE, SW_SHOWMINNOACTIVE, SW_FORCEMINIMIZE则放过
    若目标窗口属于Ts进程则跳过执行
    
    NtUserShowWindowAsync
        若发起进程为主防进程则放过
        若nCmdShow不为SW_HIDE, SW_SHOWMINIMIZED, SW_MINIMIZE, SW_SHOWMINNOACTIVE, SW_FORCEMINIMIZE则放过
    若目标窗口属于Ts进程则跳过执行
    
    NtWriteVirtualMemory
        若发起者为普通进程,若目标进程为Ts进程,则拒绝;若目标进程为普通进程,则在用户态回溯栈中判定是否由CreateProcess发起 ,并根据ACL表上抛主防根据规则决定是否放行
        
    KeUserModeCallback
        若ApiNumber=__ClientLoadLibrary:
    若发起者为主防进程,跳过执行
    若目标文件和事先传入(IoCtlCode=0x22E0E8)的Ts dll文件匹配则跳过执行
    若目标文件在g_StorageList[13]中则跳过执行
    若开启白名单且目标文件不在g_StorageList[16]中则跳过执行
    若目标文件在g_StorageList[5]中且发起进程为Ts进程则跳过执行,否则放过
        若ApiNumber== __fnHkINLPKBDLLHOOKSTRUCT:
    若发起者为普通进程,执行功能,若键’0’-‘9’,’A’-‘Z’, 数字键盘’0’~’9’被按下,则上抛主防根据规则重置结果
        若ApiNumber== __ClientImmLoadLayout
            先执行函数以获取文件名
            若输入法序号不存在于\Registry\Machine\SYSTEM\CurrentControlSet\Control\Keyboard Layouts\或子项为空,且发起进程为非Ts进程,则根据注册表监控树上抛主防根据规则决定是否放行
            若输入法文件不为msctfime.ime/ msctf.dll,则根据注册表监控树上抛主防根据规则决定是否放行,否则放行
    执行KeUserModeCallback前对该函数做还原inline hook处理
    

    1.4重要回调的挂钩

    PsSetCreateProcessNotifyRoutine
        将新增加的进程信息加入(ProcInfoList)链表
        若为创建进程:
    清除关键Ts文件映像劫持,即\Registry\Machine\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options下的QQPCTray.exe, QQPCRTP.EXE, QQPCUPDATE.EXE, QQPCAddWidget.exe, QQPCMgr_tz_Setup.exe, QQPCMgr.exe, QQPConfig.exe
    若为删除进程:
    清除进程相关信息
    若进程为主防进程,则清除和关闭消息通信,进行清理工作
    上报进程退出
    PsSetCreateProcessNotifyRoutineEx
        若CreateInfo为空则获取父进程id后交给CreateProcessNotify处理
        将新增加的进程信息加入(ProcExInfoList)链表
    PsSetLoadImageNotifyRoutine
        若为系统模块,若为TesSafe.sys则记录该模块信息
        若为普通模块,加载进程为若为Ts进程,且和目标模块exe相同,则清空PEB结构中的ShimData数据
    

    1.5 一些用到的数据

    BuildNumber[21] => UNKNOWN, 2195, 2600, 3790, 6000, 6001, 6002, 7000|7600, 7601, 8102, 8250, 8400, 8432|8441, 8520, 9200, 9600, 9841, 9860, 9926, 10041, 10049
    ApiName[15] => NtUserFindWindowEx, NtUserBuildHwndList, NtUserQueryWindow, NtUserGetForegroundWindow, NtUserSetParent, NtUserSetWindowLong, NtUserMoveWindow, NtUserSetWindowPos, NtUserSetWindowPlaceMent, NtUserShowWindow, NtUserShowWindowAsync, NtUserSendInput, NtUserMessageCall, NtUserPostMessage, NtUserPostThreadMessage
    Index[BuildNumber][ApiName]=
    0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,0x000,
    0x170,0x12e,0x1d2,0x189,0x1fe,0x20d,0x1c1,0x20f,0x20e,0x218,0x219,0x1e1,0x1bc,0x1cb,0x1cc,
    0x17a,0x138,0x1e3,0x194,0x211,0x220,0x1d1,0x222,0x221,0x22b,0x22c,0x1f6,0x1cc,0x1db,0x1dc,
    0x179,0x137,0x1e1,0x193,0x20e,0x21c,0x1d0,0x21e,0x21d,0x227,0x228,0x1f4,0x1cb,0x1da,0x1db,
    0x187,0x142,0x1f8,0x1a2,0x226,0x236,0x1e4,0x238,0x237,0x243,0x244,0x20d,0x1df,0x1f1,0x1f2,
    0x187,0x142,0x1f8,0x1a2,0x226,0x236,0x1e4,0x238,0x237,0x243,0x244,0x20d,0x1df,0x1f1,0x1f2,
    0x187,0x142,0x1f8,0x1a2,0x226,0x236,0x1e4,0x238,0x237,0x243,0x244,0x20d,0x1df,0x1f1,0x1f2,
    0x18c,0x143,0x203,0x1a7,0x230,0x242,0x1ef,0x244,0x243,0x24f,0x250,0x218,0x1ea,0x1fc,0x1fd,
    0x18c,0x143,0x203,0x1a7,0x230,0x242,0x1ef,0x244,0x243,0x24f,0x250,0x218,0x1ea,0x1fc,0x1fd,
    0x1c7,0x166,0x1de,0x1aa,0x246,0x230,0x1f3,0x22e,0x22f,0x223,0x222,0x25e,0x1f8,0x1e6,0x1e5,
    0x1c9,0x167,0x1e0,0x1ac,0x249,0x232,0x1f5,0x230,0x231,0x225,0x224,0x261,0x1fa,0x1e8,0x1e7,
    0x1ca,0x168,0x1e1,0x1ad,0x24b,0x234,0x1f6,0x232,0x233,0x227,0x226,0x263,0x1fb,0x1e9,0x1e8,
    0x1cb,0x168,0x1e2,0x1ae,0x24d,0x236,0x1f7,0x234,0x235,0x229,0x228,0x265,0x1fc,0x1ea,0x1e9,
    0x1cc,0x168,0x1e3,0x1ae,0x24f,0x237,0x1f8,0x235,0x236,0x22a,0x229,0x267,0x1fd,0x1eb,0x1ea,
    0x1cb,0x168,0x1e2,0x1ad,0x24e,0x236,0x1f7,0x234,0x235,0x229,0x228,0x266,0x1fc,0x1ea,0x1e9,
    0x1cc,0x16a,0x1e3,0x1ae,0x251,0x239,0x1f9,0x237,0x238,0x22c,0x22b,0x269,0x1fe,0x1ec,0x1eb,
    0x1ce,0x16b,0x1e5,0x1af,0x253,0x23b,0x1fb,0x239,0x23a,0x22e,0x22d,0x26b,0x200,0x1ee,0x1ed,
    0x1d2,0x16f,0x1e9,0x1b3,0x259,0x23f,0x1ff,0x23d,0x23e,0x232,0x231,0x271,0x204,0x1f2,0x1f1,
    0x1d2,0x16f,0x1e9,0x1b3,0x25a,0x240,0x1ff,0x23e,0x23f,0x233,0x232,0x272,0x204,0x1f2,0x1f1,
    0x1d2,0x16f,0x1e9,0x1b3,0x25b,0x240,0x1ff,0x23e,0x23f,0x233,0x232,0x273,0x204,0x1f2,0x1f1,
    0x1d3,0x16f,0x1ea,0x1b3,0x25c,0x241,0x200,0x23f,0x240,0x234,0x233,0x274,0x205,0x1f3,0x1f2,
        __ClientLoadLibrary在KeUserModeCallBack中的ApiNumber   ImmLoadLayoutIndex[BuildNumber] =
    -1, -1, 84, -1, -1, -1, -1, 82, 82, -1, -1, -1, -1, -1, 84, 88, -1, -1, -1, -1, -1
        KeyboardLL在KeUserModeCallBack中的ApiNumber  HookKeyboardLLIndex[BuildNumber] =
    -1, -1, 45, -1, -1, -1, -1, 45, 45, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1
    对象例程相对于对象类型结构偏移 ObjectProcedureOffset [BuildNumber] =
    -1, -1, 140, 140, 88, 88, 88, 88, 88, -1, -1, -1, -1, -1, 88, 88, 88, 88, 88, 88, -1
        ShimData成员相对PEB结构偏移 
    -1, -1, 488, -1, -1, -1, -1, 488, 488, -1, 488, 488, -1, -1, 488, 488, -1, -1, 0, 0, 0
        KeUserModeCallBack的ImmLoadLayout功能号中模块路径相对InputBuffer偏移 ClientLoadLibraryNameOffset[BuildNumber] =0, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 28, 48, 28, 0
    

    1.6 OBJECT_TYPE_INITIALIZER 挂钩

      和TsSyskit中类似,只不过Tsksp中,采用的是Proxy~Hooker的方式,将Proxy替换OpenProcedure,为每种Procedure预留5个函数槽用于存放过滤函数,只要有一个失败则返回失败。Proxy结构数组我在IDA中标记为ObjectProceduresProxy,依次为Event, File, Process, Thread, Mutant, Section的Proxy结构:

    Struct ObjectProcedureStruct
    {
        ULONG ObType;//标识对象类型
    /*
    0 ExEventObjectType
    1 PsProcessType
    2 PsThreadType
    3 IoFileObjectType
    4 ExMutantObjectType
    5 MmSectionObjectType
    */
        ULONG ProcIndex;//标识函数类型
    /*
    0 DumpProcedure
    1 OpenProcedure
    2 CloseProcedure
    3 DeleteProcedure
    4 ParseProcedure
    5 SecurityProcedure
    6 QueryNameProcedure
    7 OkayToCloseProcedure
    */
        ULONG Proxy[21];//存放代理函数地址,分21个操作系统版本
    }
    

      再用一个数组存储对应的过滤函数:ULONG ObjectProceduresD(ynamic)Filter[6][8][5], 6对应ObType,8对应ProcIndex,5为函数槽个数,数组中的数据,是从静态结构模板中导入的,该静态模板结构沿用了ObjectProcedureStruct结构。TsKsp中最终只对6种对象类型的OpenProcedure做了挂钩。代理函数逻辑:

    NTSTATUS __stdcall ProcedureProxy(OB_OPEN_REASON OpenReason, PEPROCESS Process, PVOID Object, ACCESS_MASK GrantedAccess, ULONG HandleCount)
    {
        NTSTATUS status = STATUS_SUCCESS;
        For(int i=0;i<5;i++)
        {
            If(ObjectProceduresDFilter[ObType][ProcType][i])
                Status = ObjectProceduresDFilter[ObType][ProcType][i](OpenReason,Process,Object,GrantedAccess,HandleCount);
            If(!NT_SUCCESS(status))
                Break;
    }
    Return status;
    }
    

    1.7 PROCINFO结构

    Struct PROCINFO
    {
        HANDLE ProcessId;
        ULONG ProcDir;//标志目录属性
        ULONG ProcType;//标志进程类型
        ULONG Access;//标志访问权限
        WCHAR Path[260];
        ULONG IsSignMatch;
        ULONG Index;
    }
    
    ProcDir域:
    “System”, “Idle”        4
    Ts进程                2
    普通进程            1
    
    ProcType域:
    “System”                -3
    “Idle”              -2
    普通进程            -1
    “csrss”             0
    “services”          1
    “smss”              2
    “explorer”          3
    “winlogon”          4
    “svchost”               5
    “lsass”             6
    “lsm”               7
    “taskmgr”           8
    
    Access域:(访问权限)
    0x1 通信
    0x2 进程线程创建打开,驱动加载,内存操作
    0x4 结束进程
    0x8 注册表创建打开设置
    0x10    设置文件属性
    0x100   窗口交互类
    
    “System”,”Idle”,Ts进程        0x1FF
    “svchost”,”csrss”,“lsm”,”lsass” 0x107
    “smss”                      0x10
    “services”                  0x8
    普通进程                    0x0
    
    对重要进程访问控制权限的设定:
    PROCINFO信息是在进程创建时构造的,对于重要系统进程会单独进行初始化(InitCriticalProcessList)
    name=csrss.exe,access=0x107,index=0
    name=services.exe,access=0x8,index=1
    name=smss.exe,access=0x10,index=2
    name=Explorer.exe,access=0x0,index=3
    name=winlogon.exe,access=0x0,index=4
    name=svchost.exe,access=0x107,index=5
    name=lsass.exe,access=0x107,index=6
    name=lsm.exe,access=0x107,index=7
    name=taskmgr.exe,access=0x2,index=8
    

    二、控制信息

    2.1 ACL访问控制列表

    struct ACLTable     进程相关ProcessAclTable
    +00h    BYTE* arr   BYTE AclTable [dimen3][dimen2][dimen1]
    +04h    int dimen1  源进程类型相关    PROCINFO->ProcDir
        普通        1
        同目录      2
        "Idle"      4
        "System"    4
    +08h    int dimen2  目标进程类型相关    PROCINFO->ProcDir
        普通        1
        同目录      2
        "Idle"      4
        "System"    4
    +0Ch    int dimen3  
    进程相关:
        ZwTerminateProcess      3
        ZwCreateThread          6
        ZwCreateThreadEx            6
        ZwTerminateThread       7
        ZwQueueApcThread        9
        ZwQueueApcThreadEx      9
        ZwSetContextThread      10
        ZwAllocateVirtualMemory 11
        ZwFreeVirtualMemory     11  
    ZwWriteVirtualMemory        11
    +10h    bool inited
    

    文件也有类似的访问控制表

    2.2 匹配树

      TsKsp中存在注册表权限匹配树,和文件权限匹配树,结构为树+链表:

    struct TreeData
    {
        PWCHAR MatchString;
        BOOLEAN HasVal;
        ULONG* Val1;
        ULONG Val2;
        TreeData* Next;
    };
    
    struct MatchTree
    {
        PWCHAR MatchString;
        MatchTree* Left;
        MatchTree* Right;
        TreeData* Data;
        BOOLEAN HasVal;
    };
    
    void TranverseData(TreeData* data,int depth)
    {
        while(data)
        {
            for(int i=0;i<depth;i++)
                DbgPrint("\t");
            DbgPrint("access=%x %x\n",*(ULONG*)data->Val1,data->Val2);  
            if(data->MatchString)
            {
                for(int i=0;i<depth;i++)
                    DbgPrint("\t");
                DbgPrint("-%ws",data->MatchString);
            }
            data=data->Next;
        }
    }
    
    void TranverseTree(MatchTree* node,int depth)
    {
        if(node)
        {
            if(node->MatchString)
            {
                for(int i=0;i<depth;i++)
                    DbgPrint("\t");
                DbgPrint("+%ws\n",node->MatchString);
            }
            TranverseData(node->Data,depth+1);
            TranverseTree(node->Left,depth+1);
            TranverseTree(node->Right,depth);
        }
    }
    Main()
    {
                MatchTree* node=*(MatchTree**)(Base+0x2C908);
                TranverseTree(node,0);
    }
    

    2.3 全局开关DriverSwitch

      全局监视开关,共有128bit,预留128个开关,具体标志位如下:

    DriverSwitch[0] & 1         监视消息和Section
    DriverSwitch[0] & 2         监视窗口控件消息
    DriverSwitch[0] & 4         监视硬件IOCTL
    DriverSwitch[0] & 8         是否在创建/打开文件时将读权限设置为读|删除
    DriverSwitch[0] & 0x100     拦截LPC某消息
    DriverSwitch[0] & 0x200     在进程操作中通过文件号打开NTFS分区文件
    DriverSwitch[1] & 4         是否允许任务管理器结束进程
    DriverSwitch[1] & 8         监视键盘状态
    DriverSwitch[1] & 0x40      监视加载输入法文件
    DriverSwitch[1] & 0x80      监视访问系统文件保护 sfc 
    DriverSwitch[2] & 0x100     监视Ole LPC
    DriverSwitch[1] & 0x200     打开进程和注册表时是否允许发起者为普通进程
    DriverSwitch[1] & 0x400     监视csrss process shutdown
    DriverSwitch[1] & 0x1000    监视服务操作的进程是否为敏感进程
    DriverSwitch[2] & 0x2000    监视操作虚拟内存目标进程为系统线程
    DriverSwitch[1] & 0x4000    是否使用回调式进程虚拟内存记录监视虚拟内存;是否监视创建非系统线程
    DriverSwitch[1] & 0x8000    监视对象操作的总开关,已包括Process, Thread, Mutant, Section, File, Event对象
    DriverSwitch[1] & 0x20000   是否启用创建进程监视链表MonCreateProcessList
    DriverSwitch[1] & 0x80000   监视内存映射
    DriverSwitch[1] & 0x100000  监视窗口消息
    DriverSwitch[1] & 0x200000  监视打开文件对象
    DriverSwitch[1] & 0x800000  监视打开进程
    DriverSwitch[1] & 0x1000000 监视NDIS 0Day Attack
    DriverSwitch[1] & 0x2000000 是否打开监视注册表、进程、线程、文件等函数的总开关,包括
    ZwCreateKey,ZwDeleteKey,ZwDeleteValueKey,ZwCreateThread,
    ZwDeviceIoControlFile,ZwQueueApcThread,ZwSetInformationFile,ZwSetSecurityObject,ZwSetSystemInformation,
    ZwCreateFile,ZwOpenFile,ZwSetValueKey,ZwSuspendThread,ZwSystemDebugControl,ZwTerminateProcess,
    ZwTerminateThread,ZwDuplicateObject,ZwEnumerateValueKey,ZwOpenProcess,ZwOpenSection,ZwQueueApcThreadEx
    DriverSwitch[1] & 0x8000000 设置打开进程的PostFilter
    DriverSwitch[1] & 0x10000000    监视打开线程对象
    DriverSwitch[1] & 0x20000000    允许从存储的进程链表获取签名信息
    
    DriverSwitch[2] & 0x10      监视打开Event, Mutant对象
    DriverSwitch[2] & 0x80      是否检查权限时使用PROCESSINFO的签名位IsSignMatch
    DriverSwitch[2] & 0x100     检测Ole LPC通信
    DriverSwitch[2] & 0x200     检测父进程创建时间逻辑
    DriverSwitch[2] & 0x400     监视虚拟内存的创建、写入和释放
    DriverSwitch[2] & 0x800         监视winlogon shutdown
    DriverSwitch[2] & 0x1000        监视打开Mutant对象
    DriverSwitch[2] & 0x2000        是否允许操作System进程虚拟内存
    DriverSwitch[2] & 0x80000       监视操作SAM
    DriverSwitch[2] & 0x8000000 监视操作栈区虚拟内存
    DriverSwitch[2] & 0x40000000    监视用户态模块加载
    
    MaskForDriverSwitch[14] 用于生成特定组合的DriverSwitch,见IoCtlCode == 0x22E410,数据:
    0,0x22b8
    1,0x21fc
    2,0x2199
    3,0x26b8
    4,0x22b7
    5,0x22b5
    6,0x22b6
    7,0x26b9
    8,0x219a
    9,0x22b3
    10,0x26ba
    11,0x26bd
    12,0x26bb
    13,0x26be
    
    0xx22E410控制码接收4字节数据mask,根据mask生成对应DriverSwitch
    
    BOOL SwitchControl(ULONG mask)
    {
        int bit;
        int val;
        int index;
        BOOL set = FALSE;
        switch((mask >> 28) & 7)// 28~30 bit
        {
        case 0:
            for(bit=0;bit<14;bit++)
            {
                if(MaskForDriverSwitch[bit] == mask & 0xFFFFFFF)
                    break;
            }
            if(bit<14)
            {
                set = TRUE;
                if((mask & 0x80000000) == 0)
                    DriverSwitch[0] &= ~(1<<bit);
                else
                    DriverSwitch[0] |= 1<<bit;
            }
        case 2:
            val = mask & 0xFFFFFFF;
            if(val <= 0x65)
            {
                set = TRUE;
                index = val >> 5;
                bit = val & 0x1F;
                if((mask & 0x80000000) == 0)
                    DriverSwitch[index] &= ~(1<<bit);
                else
                    DriverSwitch[index] |= 1<<bit;
            }
        }
    }
    
    

    2.4 自保开关影响的函数和功能

    在DriverEntry中,将\REGISTRY\MACHINE\SYSTEM\CurrentControlSet\Services\QQSysMon\spvalue的值若为0或1,则开启自保。另外可以在Q管界面常规设置选择自保护以手动方式开关自保,对应的程序QQPConfig.exe每次启动时会从TsKsp读取自保位(控制码0x22E0A0),设置完毕时发送给TsKsp(控制码0x22E070)
    NtSetInformationFile    
    影响Class=FileDispositionInformation, FileRenameInformation, FileLinkInformation, FileEndOfFileInformation, FileAllocationInformation的判断
    NtCreateSymbolicLinkObject
    NtDeviceIoControlFile
        影响IoCtlCode=FSCTL_SET_ZERO_DATA的判断
    NtSetSystemInformation  
        影响Class=SystemRegistryAppendStringInformation重启替换/删除注册表键的判断
        影响Class=SystemExtendServiceTableInformation 加载可执行映像的判断
    NtSetValueKey   
    影响重启替换/删除注册表键的判断
    NtRestoreKey
    NtOpenProcess
    NtOpenThread
    NtUser*
    NtRequestWaitReplyPort/NtAlpcSendWaitReceivePort
        影响RChangeServiceConfig, RDeleteService, RSetServiceObjectSecurity, 
    NtAssignProcessToJobObject
    NtCreateMutant
    NtCreateThread\NtCreateThreadEx
    NtDeleteKey
    NtDeleteValueKey
    NtSetValueKey
    NtDuplicateObject
    NtGetNextProcess
    NtOpenProcess
    NtOpenThread
    NtProtectVirtualMemory
    NtQueueApcThread\NtQueueApcThreadEx
    NtSetContextThread
    NtSetSecurityObject
    NtSuspendThread
    NtTerminateProcess
    NtUnmapViewOfSection
    NtWriteVirtualMemory
    KeUserModeCallback
        影响ApiNumber=ClientLoadLibrary,若加载Ts文件的判断
    CreateProcessNofity/ CreateProcessNotifyEx
        影响每次创建进程是否清除注册表调试键
        影响每次创建进程是否清除注册表调试键
    LoadImageNotify
        影响加载用户态映像的判断
    Object-OpenProcedure
    影响Event, File, Mutant, Process, Thread 对象的过滤
    LPC通信中访问\RPC Control\IcaApi
    

    2.5 规则判断

    1.获取规则组号
    int __stdcall GetRuleGroup(int mIndex, int nIndex, wchar_t *chname, wchar_t *enname)  根据传递的中英文字符串(说明,路径等)参数匹配出组号
    mIndex 一级序号
     0 进程线程
     1 文件
     3 其他
    nIndex 二级序号  通过FuncTypeToNum转换
      mIndex=0时,为进程/线程操作
    3  TerminateProcess
    4  CreateProcess
    5  QueryProcess
    6  CreateThread
    7  TerminateThread
    8  SuspendThread
    9  QueueApcThread
    10 SetContextThread
      mIndex=2时,为注册表操作
    0  NtCreateKey  
    2  NtSetValueKey    
    3  NtDeleteValueKey 
    4  NtDeleteKey  
        5  NtRestoreKey 
        6  默认   
    mIndex=3时,为文件操作
        0  FileEndOfFileInformation/FileAllocationInformation 
        1  FileDispositionInformation
    2  FileLinkInformation 
        3  FileRenameInformation 
        5  重启删除/重命名文件   
        6  默认   
      mIndex=4  
    取消进程钩子
      mIndex=5
    1  QueueApcThread 
    2  RChangeServiceConfig
    3  RDeleteService
    7  NtUserSendInput
    8  HardwareIoctl
    10 Ole LPC
    chname 中文类型说明
    enname 英文类型说明
    2.将规则id, 源进程id, 目标进程id, 源进程路径, 目标进程路径等信息序列化(SerialData)到上抛消息结构中
    3.设置事件等待主防读取并取得判断结果
    实例:
    kd> dd tsksp+29960
    b2cbd960  00000012 8149b648 00000140 8149c000
    b2cbd970  00000000 00000000 0000001d 81487508
    见TsKsp Log.txt 规则判断
    

    2.6 黑白名单g_StorageList

    • 共有17个,!list -t _LIST_ENTRY.Flink -x "dd @$extret+8 " tsksp+252A8+index*0x30
    • 每种类型的链表对应不同Index,都用同样的数据结构存储
    Struct MonitorDataHead
    {
        ULONG Index;//功能序号
        SPIN_LOCK Lock;//用于同步
        PVOID PData;//存储下面17种继承于LIST_ENTRY的数据结构
        ULONG OffsetToHead;//每种结构List成员相对于PData的偏移
        ULONG DataSize;//每种结构数据大小
        ULONG InsertRoutine;//插入元素例程
        ULONG DeleteRoutine;//删除元素例程
        ULONG FindRoutine;//查找元素例程
        ULONG FindWrapperRoutine;//互斥查找元素例程
        ULONG DeleteAllRoutine;//清空数据例程
        ULONG CompareRoutine;//比较元素例程
    }
    
    Index=0  sizeof=528     结束进程名黑名单    关自保或进程文件为普通文件生效
        +00 LIST_ENTRY List
        +08 WCHAR ProcessName[260]
    
    Index=1  sizeof=12      结束进程ID黑名单   关自保或进程文件为普通文件生效
        +00 LIST_ENTRY List
        +08 HANDLE ProcessId            进程Id
    
    Index=2 sizeof=528      未知
        +00 LIST_ENTRY List
        +08 WCHAR ProcessName[260]  进程名
    
    Index=3 sizeof=12       未知
        +00 LIST_ENTRY List
        +08 HANDLE ProcessId            进程Id
    
    Index=4  sizeof=536     未知
        +00 LIST_ENTRY List
        +08     WCHAR ProcessName[260]      进程名
        +210 IsWild//是否为通配符
    
    Index=5 sizeof=528      ClientLoadLibrary加载模块白名单            SelfProcInjectAllow
        +00 LIST_ENTRY List
        +08 WCHAR ImagePath[260]        映像路径
    
    C:\Program Files\Tencent\QQPCMgr\11.1.16892.209\QMForbiddenWinKey.dll
    C:\WINDOWS\system32\mshtml.dll
    C:\WINDOWS\system32\IEUI.dll
    C:\WINDOWS\system32\ieframe.dll
    C:\WINDOWS\system32\uxtheme.dll
    C:\WINDOWS\system32\browseui.dll
    
    Index=6 sizeof=528          未知
        +00 LIST_ENTRY List
        +08 WCHAR [260]
    
    Index=7 sizeof=1048             未知
        +00 LIST_ENTRY List
        +08 WCHAR [260]
        +210 WCHAR [260]
    
    Index=8 sizeof=528          操作虚拟内存,创建进程,创建内存映射文件 目标黑名单 
        +00 LIST_ENTRY List
        +08 WCHAR  FileName[260]    文件名
    
    Index=9 sizeof=12           注册表操作黑名单    
    LIST_ENTRY
    WCHAR[260]  KeyPathPattern      键路径模式
    WCHAR[260]  ValueNamePattern        键值模式
    
    \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSKSP*, *
    \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\QQPCRTP*, *
    \REGISTRY\MACHINE\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN, QQPCTRAY
    \REGISTRY\MACHINE\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN\QQDISABLED, *
    \REGISTRY\USER\S-*\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\RUN\QQDISABLED, *
        \REGISTRY\MACHINE\SOFTWARE\TENCENT\QQPCMGR\SYSTEMOPTIMIZE\DISABLED, *
        \REGISTRY\MACHINE\SOFTWARE\TENCENT\QQPCMGR\SYSTEMOPTIMIZE\DISABLEDSVC, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSDEFENSEBT*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\QQSYSMON*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TFSFLT*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSSYSKIT*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSFLTMGR*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSSK*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSNETMON*, *
        \REGISTRY\USER\QMCONFIG*, *
        \REGISTRY\MACHINE\SOFTWARE\MICROSOFT\WINDOWS\CURRENTVERSION\UNINSTALL\QQPCMGR*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\TSSYSFIX*, *
        \REGISTRY\MACHINE\SYSTEM\*CONTROLSET*\SERVICES\ANTIRK*, *
    
    Index=10    sizeof=536              文件
        +00 LIST_ENTRY List
        +08 WCHAR  FileName[260]    文件/路径名
        +210 BOOL IsDir
        +214
        
    Index=11    sizeof=528  结束进程查询名单        CTSKspWrap::AddSelfProcTeminateQuery
        +00 LIST_ENTRY List
        +08 WCHAR FilePath [260]    文件名
    
        C:\Program Files\Tencent\QQPCMgr\11.1.16892.209
    
    Index=12    sizeof=528      未知
        +00 LIST_ENTRY List
        +08 WCHAR [260]
    
    Index=13    sizeof=528      __ClientLoadLibrary   __ClientLoadLibrary发起进程黑名单
        +00 LIST_ENTRY List
        +08 FileName [260]      文件名
    
    TASLogin.exe
    Client.exe
    SoapUI_4_6_4.exe
    QQPCLeakScan.exe
    navicat.exe
    NativeWeb.exe
    phpstorm.exe
    ugraf.exe
    League of Legends.exe
    dnf.exe
    tgp_daemon.exe
    my.exe
    pycharm.exe
    bugreport.exe
    QQPetBear.exe
    TXPlatform.exe
    xmind.exe
    tencentdl.exe
    _INS5576._MP
    
    Index=14    sizeof=536          打开对象目标黑名单               SyncObjProtect
    LIST_ENTRY  List
    POBJECT_NAME_INFORMATION ObjInfo        对象路径
     WCHAR ObjectPath[260]
    
    04CE0CB6-CDF3-4a4b-8B9D-292A455FAF5B
    04CE0CB6-CDF3-4a4b-8B9D-292A455F
    AF5B
    QDOCTOR_2
    QDOCTOR_1
    QDOCTOR_0
    qpcmgr\10002_0_80
    ENCENT_QMTAV_TSCAN_HANG
    
    Index=15    sizeof=1072         打开进程/复制句柄发起进程白名单            SelfProcAllow
    LIST_ENTRY  List
    ULONG   Enable??
    ULONG       SourceFilePathLen           
    WCHAR[261] SourceProcessFilePath        源进程路径
    ULONG   Target FilePathLen
    WCHAR[261]  TargetProcessFilePath   目标进程路径
     ACCESS_MASK GrantedAccess
    
    Index=16    528 ImageName    __ClientLoadLibrary发起进程白名单
        +00 LIST_ENTRY List
        +08 FileName [260]      模块文件名
    
    wuauclt.exe
    MiniThunderPlatform.exe
    RtxLite.exe
    DriveTheLife.exe
    115chrome.exe
    adownloader.exe
    2345Explorer.exe
    MyIE9.exe
    krbrowser.exe
    Ruiying.exe
    csbrowser.exe
    114Web.exe
    114IE.exe
    WebGamegt.exe
    Coral.exe
    TangoWeb.exe
    tango3.exe
    TaoBrowser.exe
    YY.exe
    Android PC Suite.exe
    wandoujia2.exe
    DriverGenius.exe
    DTLSoftManage.exe
    sdDown.exe
    VDisk.exe
    klive.exe
    Kanbox.exe
    sedown.exe
    Alibrowser.exe
    BaiduHi.exe
    LiveUpdate360.exe
    flashgetmini.exe
    flashget3.exe
    idman.exe
    Explorer.exe
    QQBrowserExtHost.exe
    QBDownloader.exe
    FoxMail.exe
    ieuser.exe
    TTraveler.exe
    rtx.exe
    tm.exe
    fetion.exe
    msnmsgr.exe
    outlook.exe
    UDownSrv.exe
    UDown.exe
    WebThunder.exe
    MiniThunder.exe
    Thunder5.exe
    ThunderMini.exe
    DUTool.exe
    RaySource.exe
    peer.exe
    Thunder.exe
    ThunderService.exe
    thunderplatform.exe
    minimule.exe
    emule.exe
    QQDownload.exe
    baidubrowser.exe
    liebao.exe
    QQBrowser.exe
    360chrome.exe
    360se.exe
    webkit2webprocess.exe
    safari.exe
    huaer.exe
    saayaa.exe
    twchrome.exe
    firefox.exe
    thooe.exe
    theworld.exe
    myiq.exe
    greenbrowser.exe
    ybrowser.exe
    115br.exe
    opera.exe
    chrome.exe
    maxthon.exe
    sogouexplorer.exe
    

    2.7 上抛消息结构

    Type            Id
    ProcessId       0       进程Id
    ChildProcessId  1       子进程Id
    SrcFilePath     4       源文件路径
    ChildFilePath   5       子进程路径
    RegPathName 6       注册表路径
    RegKeyName  7       注册表键
    RegData     8       注册表数据
    ObjFilePath 9       目标文件路径
    RuleId      10      规则id
    ChName      11      中文描述
    EnName      12      英文描述
    ??          13
    ProcessData 14
    ChildData       15
    ProcessIndex    17      进程序号
    RegKeyType  18      注册表数据类型
    RegDataSize 19      注册表数据大小
    

      过滤函数中,根据条件进行筛选以后,遇到符合条件的消息,先根据特征获取消息序号,然后在GroupAccessList中查找进程对应该消息号的权限,之后根据捕获类型构造消息结构, SerialData函数将必要的数据按上述类型序列化到缓冲区,之后将消息添加进消息队列中,并设置写信号,等待主防进程读取,上抛过程可以是同步或者异步方式。

    SENDMSG     sizeof=0x1000
    +000        ULONG Size//0x1000
    +004        SENDMSG* self
    +008        struct  REPLYMSG*   sizeof=0x1000
            +000        
            +004        SENDMSG* notifymsg;
            +00C        UCHAR[6] MsgTypeString;//”REPLY”
            +018        PKEVENT Event
            +01C        HANDLE ThreadId
    +00C        UCHAR[7]    MsgTypeString;//”NOTIFY”
    +01C        ULONG nIndex//事件类型标识
    +020        ULONG pIndex//事件类型标识
    +024        PKEVENT Event
    +028        HANDLE ThreadId//待检测线程id
    +02C        ULONG 请求结果类型//=0 不请求
    +030        BOOL 主防是否需要给出结果
    +034        ULONG MsgSize//串行化后总长度
    +038        PBYTE data[0xFC8] 串行化数据  格式“类型-大小-数据[]”
    

    2.8 其他

    读取ini文件
    标记为和应用层api的名字相同(GetPrivateProfile*)的函数,函数调用类型基本相同
    GetPrivateProfileInt, 从Ini文件中获取整型值
    GetPrivateProfileIntEncrypt从Ini文件中解密并获取整型值
    GetPrivateProfileString从Ini文件中获取字符串
    GetPrivateProfileStringEncrypt 从Ini文件中解密并获取字符串
    
    主防QMHIPSService通信日志
        可以打印出QMHIPSService与Tsksp.sys进行DeviceIoControl通信日志
        在HKEY_LOCAL_MACHINE\Software\Tencent\QQPCMgr下新建EnableLogToView的Dword键,设置为0xFFFFFFFF,即可打开Magic debuge,xp下主防的日志在\Documents and Settings\All Users\Application Data\Tencent\QQPCMgr\TrojanLog\qqpcrtp_qmhipsservice.log
    
    对Q管签名的破解
        Q管签名验证,存在于除TsFltMgr之外的所有驱动中(boot start),代码已经在TsSysKit分析文中给出,过程如下:
        1.读取PE,以IMAGE_DOS_HEADER->e_res2[0-1] 的DWORD值作为文件偏移,取该处128字节,通常在文件尾
        2.用这128字节密文解密出24字节信息:
        +00 被加密数据的文件偏移,通常是代码段起始
        +04 被加密数据的信息长度,通常到加密前的文件结束位置
        +08 BYTE[16]      文件内容经过MD5变种算法加密出的16字节密钥
        3.对被加密数据重新MD5校验,将结果和16字节密钥对比
        由于算法可逆性未知,128字节密文不易从自己构造的24字节原始信息恢复,因此我的破解方法是取最小的具有Ts签名的文件尾项数据,插在PE开头,原先PE段相应移位,这样便可以通过Ts签名校验。代码为SignAsTsFile.cpp
    
    影响到PROCINFO的IsSignMatch成员,该标志为Ts文件签名通过标志,由DriverSwitch开关控制,访问权限没有“Q管目录文件”级别高,影响到的函数有:
    NtDuplicateObject 放行执行者
    虚拟内存操作 保护目标
    允许输入法注入
    NtCreateThreadEx放行执行者
    NtSuspendThread放行执行者
    NtGetNextThread放行执行者
    NtTerminateProcess 放行执行者
    NtTerminateThread 放行执行者
    NtQueueApcThread放行执行者
    NtQueueApcThreadEx放行执行者
    NtUserSetWinEventHook放行执行者
    NtUserSetWinEventHookEx放行执行者 保护目标
    SetSystemInformation 放行执行者
    NtSetContextThread放行执行者
    NRestoreKey放行执行者
    NtSetValueKey 放行执行者
    NtCreateThread保护目标
    NtUnmapViewOfSection放行执行者
    NtCreateSymbolicLinkObject放行执行者
    OpenObject放行执行者
    NtSetSecurityObject放行执行者
    NtAlpcCreatePort 放行执行者
    NtCreatePort 放行执行者
    NtAssignProcessToJobObject放行执行者
    NtLoadDriver放行执行者
    

    三、接口和控制码

    3.1 导出接口

    ULONG_PTR __stdcall Interface(int Index)
    {
        Swtich(index)
    {
        Case 1:
            Return GetProcInfoById;// 函数指针,用于通过进程Id拷贝PROCINFO结构,如前所述
        Case 2:
            Return &EnableUpThrow;//用于控制是否将驱动事件上抛给主防消息并按规则处理,影响大部分过滤函数
        Case 3:
                Return &SelfProtectSwitch;//自保开关,影响的过滤函数见“自保开关影响的函数和功能”一节
        Case 4:
            Return &MonitorSwitch;
    /*
    ULONG[0]:进程,线程,钩子操作开关,影响的过滤函数有:NtTerminateProcess, NtCreateThread, NtTerminateThread, NtSetContextThread, NtCreateThreadEx, NtQueueApcThread, NtQueueApcThreadEx, NtUserSetWinEventHook, NtUserSetWindowsHookEx
    ULONG[1]: 注册表操作开关,影响的过滤函数有:NtRestoreKey, NtSetValueKey, NtCreateKey, NtDeleteKey, NtDeleteValueKey, NtLoadDriver, NtSystemDebugControl, NtSetSystemInformation
    ULONG[2]: 文件,设备操作,影响的过滤函数有:NtSetInformationFile, NtCreateSymbolinkObject, NtDeviceIoControlFile
    */
        Case 5:
            Return &SetFileSwitch;//文件操作开关,若关闭则用Tsksp内置规则,否则交给文件过滤驱动分析逻辑
        Case 6:
            Return GetProcDir;//函数指针,用于通过进程Id获取ProcDir属性,如前所述
        Default:
            Return NULL;
    }
    }
    

    3.2 控制码

    0x22E004        挂钩KeUserModeCallBack并返回结果
        Buffer=     sizeof=4
        +00 BOOL ret
    
    0x22E008        未实现
    
    0x22E010        增加结束进程名黑名单元素 g_StorageList[0]
        Buffer=     sizeof=0x208
        +00 WCHAR ProcessName[260]
    
    0x22E014        删除结束进程名黑名单元素 g_StorageList[0]
        Buffer=     sizeof=0x208
        +00 WCHAR ProcessName[260]
    
    0x22E01C        设置进程线程钩子操作开关MonitorSwitch       如前所述
        Buffer=     sizeof=0xC
        +00 ULONG Data[3]
    
    0x22E020        未知
    
    0x22E028        添加结束进程ID黑名单元素
        Buffer=     sizeof=4
        +00 HANDLE ProcessId
    
    0x22E02C        删除结束进程ID黑名单元素
        Buffer=     sizeof=4
        +00 HANDLE ProcessId
    
    0x22E030        添加g_StorageList[2]元素
    
    0x22E034        删除g_StorageList[2]元素
    
    0x22E038        增加允许自注入名单g_StorageList[5]       CTSKspWrap::AddSelfProcInjectAllow
        Buffer=     sizeof=0x208
        +00 WCHAR ImagePath[260]
    
    0x22E03C        删除ClientLoadLibrary加载模块白名单元素    
        Buffer=     sizeof=0x208
        +00 WCHAR  FilePath[260]    
    
    0x22E040        挂钩KeUserModeCallback
    
    0x22E044        添加g_StorageList[4]元素
    
    0x22E048        删除g_StorageList[4]元素
    
    0x22E04C    添加g_StorageList[6]元素
    
    0x22E064        DriverEntry中若KeUserModeCallback挂钩失败,则IRP_MJ_ DEVICE_CONTROL派遣例程只接受该控制码,用于获取挂钩信息
        Buffer=     sizeof=4
        +00 ULONG //0挂钩成功       2挂钩失败
    
    0x22E050        删除g_StorageList[6]元素
    
    0x22E054        添加g_StorageList[7]元素
    
    0x22E058        删除g_StorageList[7]元素
    
    0x22E05C        重置关闭自保状态
        Buffer=     sizeof=4
        +00 ULONG  1重置  2关闭 
    
    0x22E060        设置检测发送消息开关SendInputSwitch   CTSKspWrap::SetSendInputSwitch
        Buffer=     sizeof=4
        +00 ULONG => SendInputSwitch        
        该标志位影响的过滤函数有:NtUserSendInput, NtUserMessageCall, NtUserPostmessage, NtUserPostThreadMessage
    
    0x22E064
        Buffer=     sizeof=4
        +00 ULONG status;// KeUserModeCallback挂钩结果
    
    0x22E06C        添加g_StorageList[12]元素
    
    0x22E070        设置自保开关SelfProtectSwitch CTSKspWrap::SetSelfProtectState
        Buffer=     sizeof=4
        +00 ULONG => SelfProtectSwitch  
    
    0x22E074        传入%SystemRoot%\system32\advapi32.dll        CreateServiceA地址        CTSKspWrap::AddApiAddress
        Buffer=     sizeof=4
        +00 ULONG   Addr
    
    0x22E078        传入%SystemRoot%\system32\advapi32.dll        CreateServiceW地址        CTSKspWrap::AddApiAddress
        Buffer=     sizeof=4
        +00 ULONG   Addr
    
    0x22E07C        传入%SystemRoot%\system32\rpcrt4.dll      NdrClientCall2地址        CTSKspWrap::AddApiAddress
        Buffer=     sizeof=4
        +00 ULONG   Addr
    
    0x22E080        增加自结束进程查询名单     CTSKspWrap::AddSelfProcTeminateQuery
        Buffer=     sizeof=0x208
        +00 WCHAR  FilePath[260]    
    
    0x22E084        增加注册表监控项    CTSKspWrap::AddRegMonitor       
        Buffer=     sizeof=0x418
    +000h   WCHAR       RegPath[260]
    +208h   WCHAR       KeyName[260]         
    +410h   HANDLE  ProcessHandle
    +414h   DWORD   Access
    
    0x22E08C        根据id设置PROCINFO的ProcDir域
        Buffer=     sizeof=8
        +0  HANDLE ProcessId
        +4  ULONG ProcDir
    
    0x22E090            CTSKspWrap::AddFileGroup
        Buffer=     sizeof=0x212
        +00 ULONG Access
        +08 WCHAR [260] 匹配路径
    
    0x22E094                CTSKspWrap::AddProcPrivilege
        
    0x22E09C        初始化驱动同步     CTSKspWrap::InitDriverSync
        Buffer=     sizeof=4
        +00 ULONG =>  InitDriverSync
    
    0x22E0A0        获取自保开关状态            CTSKspWrap::GetSelfProtectState
        Buffer=     sizeof=4
        +00 ULONG Data <= SelfProtectSwitch
    
    0x22E0C4        和驱动建立连接的过程中,发给驱动的用于通知主防驱动已经写完消息等待读取的同步信号
        Buffer=     sizeof=4
        +00 PKSEMAPHORE MsgWriteLock
    
    0x22E0C8        主防向驱动索取消息结构     CTSKspWrap::DriverGetMessage
        Buffer=     sizeof=0x1000
    
    0x22E0CC        驱动返回消息  CTSKspWrap::DriverReplyMessage
    
    0x22E0D0        通知驱动主防进程退出,做清理工作        CTSKspWrap::CloseDriverEvent
        
    0x22E0D8           穿透创建服务加载驱动
        buffer=     sizeof=0x91C
        +000    WCHAR ImagePath[260] 驱动文件路径
        +208    DWORD Type  驱动注册表Type项
        +20C    DWORD Start 驱动注册表项Start类型
        +210    DWORD flag  (决定是否设置注册表Tag和Group信息)
        +214    ???
        +468    DWORD Tag 驱动注册表Tag项
        +46C    WCHAR DisplayName[300] 驱动注册表项DisplayName
        +6C4    WCHAR ServiceName[300] 驱动服务名
    
    0x22E0DC        下发要监控的线程Id给驱动,存储于ThreadIdSlot,该结构在创建/打开文件操作中生效
        Buffer=     sizeof=4
        +00 HANDLE ThreadId 
    
    0x22E0E0        取消要监控的线程Id,修改ThreadIdSlot
        Buffer=     sizeof=4
        +00 HANDLE ThreadId
    
    0x22E0E4    重置全局访问控制表ACL =>AclTable  三维数组,详述见全局访问控制表章节
        Buffer=     sizeof=0x10
        +00 ULONG dimen1//第一维大小
        +04 ULONG dimen2//第二维大小
        +08 ULONG dimen3//第三维大小
        +0C PBYTE data//数据基址
    
    0x22E0E8        添加__ClientLoadLibrary发起进程黑名单元素 g_StorageList[13]        CTSKspWrap::SetIoControl
        Buffer=     sizeof=0x208
    +00 FileName [260]      模块文件名
    
    0x22E0EC        删除__ClientLoadLibrary发起进程黑名单元素 g_StorageList[13]
        Buffer=     sizeof=0x208
    +00 FileName [260]      模块文件名
    
    0x22E0F0        设置要监控的模块路径      CTSKspWrap::SetIoControl
        Buffer=     sizeof=0x208
    +00 DllPath [260]       模块文件名
    
    0x22E100        设置进程信息
        Buffer=     sizeof=0xC
        +00 HANDLE ProcessId    in
        +04 ULONG ProcDir       out
        +08 ULONG           out
    
    0x22E104        是否开启验证父进程和子进程创建时间逻辑
        Buffer=     sizeof=4
        +00 BOOLEAN VerifyTime//0不开启    1开启
    
    0x22E108        添加__ClientLoadLibrary发起进程白名单项g_StorageList[16]      CTSKspWrap::SetIoControl
        Buffer=     sizeof=0x208
    +00 FileName [260]      模块文件名
    
    0x22E10C        开启__ClientLoadLibrary发起进程白名单项g_StorageList[16]的验证
    
    0x22E110        删除__ClientLoadLibrary发起进程白名单项g_StorageList[16]      CTSKspWrap::SetIoControl
        Buffer=     sizeof=0x208
    +00 FileName [260]      模块文件名
    
    0x22E114        关闭__ClientLoadLibrary发起进程白名单项g_StorageList[16]的验证
    
    0x22E400        增加监控条目      信息添加到数组,做第一次规则匹配        CTSKspWrap::AddMonitorItem
        Buffer=     sizeof>0x10
        +00 USHORT  cbSize
        +02 USHORT  0/1
        +04 USHORT  2   
        +06 USHORT  GroupInfoSize//组信息结构大小
        +08 USHORT  Type    //组类型   0进程线程   1文件 2??     3其他
        +10 UBYTE[] 组信息
    
    0x22E404    增加”规则组进程访问权限”信息 信息添加到二级链表,做第二次规则匹配
        Buffer=     sizeof>0x10
        +00 USHORT  cbSize
        +02 USHORT  0/1
        +04 USHORT  2   
        +06 USHORT  GroupInfoSize//进程相关的权限信息结构大小
        +10 UBYTE[] 组信息
    
        内部存储结构:
        +00  LIST_ENTRY ListEntry
        +08  LIST_ENTRY ChildListEntry
            +00 LIST_ENTRY ListEntry
                +08     ULONG   uMinRuleNum
                +0C ULONG   uMaxruleNum
                +10 ULONG   Access;//0放过   非0拦截
        +10  HANDLE ProcessId
        
        保存在内存中的结构为RuleGroupInfo[4]  每个结构由成员个数(=n)和基地址2个ULONG组成,每个基地址存放着n个下列子结构:
    00  ULONG ruleid          
    04  ULONG mid            
    08  ULONG subid          
    0C  ULONG val4           
    10  WCHAR* matchfirst      
    14  WCHAR* matchsecond  
        详细情况后面有详述
    
    0x22E410        设置全局开关DriverSwitch      DriverSwitch见全局开关章节     CTSKspWrap::SetDriverSwitch
        Buffer=     sizeof=4
        +00 ULONG mask
        
    0x22E414        监视操作窗口标题,将新标题字符串加入监视列表白名单
    Buffer=     sizeof>0
    +00 WCHAR[??]   窗口标题
        
    0x22E418        获取在NtRequestWaitReplyPort和NtAlpcSendWaitReceivePort通信中使用IWbemInterface通信的进程
        Bufer=      sizeof=8
        +00 HANDLE ProcessId
        +04 0
    
    0x22E41C        增加打开对象目标黑名单项g_StorageList[14],见“黑白名单”一节     CTSKspWrap::AddSyncObjProtect
        Buffer=     sizeof=0x208
        +00 WCHAR ObjectPath[260]
    
    0x22E420        增加打开进程/复制句柄发起进程白名单项 g_StorageList[15] ,见“黑白名单”一节        CTSKspWrap::AddSelfProcAllow
        Buffer=     sizeof=0x430
        +000    LIST_ENTRY  List
        +008    ULONG   Enable??
        +00C    ULONG   SourceFilePathLen           
        +010    WCHAR   SourceProcessFilePath[261]
        +21C    ULONG   TargetFilePathLen
        +220    WCHAR   TargetProcessFilePat[261]
        +42C    ACCESS_MASK GrantedAccess
    
    0x22E420        由进程Id获取进程加载序号,PROCESSINFO的Index域
        Buffer=     sizeof=8
        +0  HANDLE ProcessId  <=>   ULONG Index
    
    0x22E424        由进程Id获取进程文件全路径
        Buffer=     sizeof= in 4    out 0x104
        +0  HANDLE ProcessId    <=> 
    

    四、基础库

    4.1 由进程Id获取文件对象

    BOOLEAN GetSectionObjectOffset()
    {
        UCHAR Inst1[]={0x8B, 0xFF, 0x55, 0x8B, 0xEC, 0x8B, 0x45, 0x08, 0x8B, 0x80};
        UCHAR Inst2[]={0x8B, 0x44, 0x24, 0x04, 0x8B, 0x80};
        BOOLEAN result = FALSE;
        ULONG_PTR SectionBaseOffset = 0;
        PsGetProcessSectionBaseAddress = MmGetSystemRoutineAddress(&uName);
        if(PsGetProcessSectionBaseAddress && MmIsAddressValid(PsGetProcessSectionBaseAddress))
        {
            if(MmIsAddressValid((PVOID)((char*)PsGetProcessSectionBaseAddress + 14)) &&
                RtlCompareMemory((PVOID)Inst1, PsGetProcessSectionBaseAddress, sizeof(Inst1)) == sizeof(Inst1))
            {
                /*
                    nt!PsGetProcessSectionBaseAddress:
                    805287da 8bff            mov     edi,edi
                    805287dc 55              push    ebp
                    805287dd 8bec            mov     ebp,esp
                    805287df 8b4508          mov     eax,dword ptr [ebp+8]
                    805287e2 8b803c010000    mov     eax,dword ptr [eax+13Ch]
                    805287e8 5d              pop     ebp
                */
                SectionBaseOffset = *(ULONG*)((char*)PsGetProcessSectionBaseAddress + 10);
            }
            else if(MmIsAddressValid((PVOID)((char*)PsGetProcessSectionBaseAddress + 10)) &&
                RtlCompareMemory((PVOID)Inst2, PsGetProcessSectionBaseAddress, sizeof(Inst2)) == sizeof(Inst2))
                //and BuildNumber==2600
            {
                SectionObjectOffset = *(ULONG*)((char*)PsGetProcessSectionBaseAddress + 6);
            }
            if(SectionBaseOffset >= 276)
            {
                SectionObjectOffset = SectionBaseOffset - 4;
                result = TRUE;
            }
        }
        return result;
    }
    
    NTSTATUS GetFileObjectByProcessId(HANDLE ProcessId, PFILE_OBJECT* pFileObject)
    {//法一 借助PEPROCESS结构
        NTSTATUS status = STATUS_UNSUCCESSFUL;
        PEPROCESS Process = NULL;
        if(!pFileObject)
            return status;
        if(NT_SUCCESS(PsLookupProcessByProcessId(ProcessId,&Process)))
        {
            if(MajorVersion == 1 || MajorVersion == 2)
            {
                PSECTION Section = *(PSECTION*)((char*)Process + SectionObjectOffset);
                if(Section && MmIsAddressValid(Section) && Section->Segment && MmIsAddressValid(Section->Segment) &&
                    Section->Segment->ControlArea && MmIsAddressValid(Section->Segment->ControlArea))
                {
                    *pFileObject = Section->Segment->ControlArea->FilePointer;
                    if(*pFileObject)
                    {
                        ObReferenceObject(*pFileObject);
                        status = STATUS_SUCCESS;
                    }
                }
            }
            else if(MajorVersion == 5)
            {
                if(!PsReferenceProcessFilePointer)
                    PsReferenceProcessFilePointer = (ULONG)MmGetSystemRoutineAddress(&uName);
                if(PsReferenceProcessFilePointer)
                    status = ((NTSTATUS (__stdcall*)(PEPROCESS,PFILE_OBJECT*))PsReferenceProcessFilePointer)(Process,pFileObject);
            }
        }
        if(Process)
            ObDereferenceObject(Process);
        return status;
    }
    
    NTSTATUS GetPebBaseByProcessObject(PEPROCESS Process, PVOID *PebBaseAddr)
    {
        NTSTATUS status = STATUS_UNSUCCESSFUL;
        HANDLE ProcessHandle = NULL;
        PROCESS_BASIC_INFORMATION ProcessInformation;
        if(NT_SUCCESS(ObOpenObjectByPointer(Process, OBJ_KERNEL_HANDLE, NULL,0, NULL, KernelMode, &ProcessHandle)) &&
            ZwQueryInformationProcess(ProcessHandle, ProcessBasicInformation, &ProcessInformation, sizeof(ProcessInformation), NULL) &&
            ProcessInformation.PebBaseAddress)
        {
            *PebBaseAddr = ProcessInformation.PebBaseAddress;
            status = STATUS_SUCCESS;
        }
        if(ProcessHandle)
            ZwClose(ProcessHandle);
        return status;
    }
    
    PFILE_OBJECT GetFileObjectByProcessId(HANDLE ProcessId)
    {//法二 借助PEB命令行
        PEPROCESS Process = NULL;
        PPEB PebBaseAddr = NULL;
        BOOLEAN Attached = FALSE;
        HANDLE FileHandle = NULL;
        PVOID Buffer = NULL;
        PFILE_OBJECT FileObject = NULL;
        UNICODE_STRING ImagePathName;
        UNICODE_STRING FullPath;
        OBJECT_ATTRIBUTES Oa;
        UNICODE_STRING Prefix = RTL_CONST_STRING(L"\??\");
        IO_STATUS_BLOCK IoStatus;
        if(KeGetCurrentIrql() == PASSIVE_LEVEL && 
            NT_SUCCESS(PsLookupProcessByProcessId(ProcessId, &Process)) &&
            NT_SUCCESS(GetPebBaseByProcessObject(Process, (PVOID*)&PebBaseAddr)))
        {
            KeAttachProcess(Process);
            Attached = TRUE;
            __try
            {
                ProbeForRead(PebBaseAddr,0x1D8,1);
                ProbeForRead(PebBaseAddr->ProcessParameters,0x90,1);
                ImagePathName = PebBaseAddr->ProcessParameters->ImagePathName;
                if(ImagePathName.Length != 0 && ImagePathName.Length < 0xFFF8)
                {
                    if((char*)ImagePathName.Buffer < (char*)PebBaseAddr->ProcessParameters)// 如果该成员是偏移而不是指针
                        ImagePathName.Buffer = (PWSTR)((ULONG)ImagePathName.Buffer + PebBaseAddr->ProcessParameters);
                    ProbeForRead(ImagePathName.Buffer,ImagePathName.Length,1);
                    ULONG FullLen = ImagePathName.Length;
                    if(!RtlPrefixUnicodeString(&Prefix, &ImagePathName, TRUE))
                        FullLen += 8;
                    Buffer = ExAllocatePool(NonPagedPool, FullLen);
                    if(Buffer)
                    {
                        RtlZeroMemory(Buffer,FullLen);
                        FullPath.Buffer = (PWCH)Buffer;
                        FullPath.MaximumLength = FullLen;
                        if(FullLen != ImagePathName.Length)
                            RtlAppendUnicodeStringToString(&FullPath,&Prefix);
                        RtlAppendUnicodeStringToString(&FullPath,&ImagePathName);
                    }
                }
            }
            __except(0)
            {
                Attached = FALSE;
            }
            InitializeObjectAttributes(&Oa,&FullPath,OBJ_KERNEL_HANDLE,NULL,NULL);
            if(NT_SUCCESS(ZwOpenFile(&FileHandle, SYNCHRONIZE | FILE_READ_ATTRIBUTES, &Oa, &Ios,
                FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE, FILE_SYNCHRONOUS_IO_NONALERT | FILE_NON_DIRECTORY_FILE)))
                ObReferenceObjectByHandle(FileHandle, 0, *IoFileObjectType, KernelMode, (PVOID*)&FileObject, NULL);
        }
        if(Attached)
            KeDetachProcess();
        if(FileHandle)
        {
            ZwClose(FileHandle);
            FileHandle = NULL;
        }
        if(Process)
        {
            ObDereferenceObject(Process);
            Process = NULL;
        }
        if(Buffer)
            ExFreePool(Buffer);
        return FileObject;
    }
    

    4.2 由线程句柄获取进程对象

    PEPROCESS GetProcessObjectFromThreadHandle(HANDLE ThreadHandle)
    {
        PETHREAD Thread = NULL;
        PEPROCESS Process = NULL;
        if(ThreadHandle)
        {
            if(NT_SUCCESS(ObReferenceObjectByHandle(ThreadHandle, 0, *PsThreadType, 
                IsKernelHandle(ThreadHandle)?KernelMode:UserMode, (PVOID*)&Thread, NULL)))
            {
                Process = IoThreadToProcess(Thread);
                ObDereferenceObject(Thread);
            }
        }
        return Process;
    }
    

    4.3 由线程对象获取进程Id

    NTSTATUS GetProcIdFromProcessObject(PEPROCESS Process,PHANDLE pProcessId)
    {
        NTSTATUS status = STATUS_UNSUCCESSFUL;
        HANDLE ProcessHandle = NULL;
        PROCESS_BASIC_INFORMATION ProcessInformation;
        if(NT_SUCCESS(ObOpenObjectByPointer(Process, OBJ_KERNEL_HANDLE, NULL,0, NULL, KernelMode, &ProcessHandle)) &&
            ZwQueryInformationProcess(ProcessHandle, ProcessBasicInformation, &ProcessInformation, sizeof(ProcessInformation), NULL))
        {
            *pProcessId = ProcessInformation.UniqueProcessId;
            status = STATUS_SUCCESS;
        }
        if(ProcessHandle)
            ZwClose(ProcessHandle);
        return status;
    }
    
    NTSTATUS GetThreadProcessId(PETHREAD Thread,PHANDLE pProcessId)
    {
        NTSTATUS status = STATUS_UNSUCCESSFUL;
        PVOID PsGetThreadProcessId = NULL;
        ULONG OffsetEprocessToThreadObject = 0x22C;
        if(MmIsAddressValid(Thread))
        {
            PsGetThreadProcessId = MmGetSystemRoutineAddress(&uName);
            if(PsGetThreadProcessId)
            {
                *pProcessId = ((HANDLE (__stdcall*)(PETHREAD))PsGetThreadProcessId)(Thread);
                status = STATUS_SUCCESS;
            }
            if(!NT_SUCCESS(status))
            {
                ULONG Addr = (ULONG)Thread + OffsetEprocessToThreadObject;
                if(Addr && MmIsAddressValid((PVOID)Addr))
                {
                    PEPROCESS Process = *(PEPROCESS*)Addr;
                    if(Process && MmIsAddressValid(Process))
                    {
                        if(NT_SUCCESS(GetProcIdFromProcessObject(Process, pProcessId)))
                        {
                            status = STATUS_SUCCESS;
                        }
                    }
                }
            }
        }
        return status;
    }
    

    4.4 由Ntfs文件索引号获取文件对象

    PFILE_OBJECT GetRealFileObject(HANDLE ProcessId,PFILE_OBJECT FileObject)
    {
        UNICODE_STRING uNtfs = RTL_CONSTANT_STRING(L"\\Ntfs");
        PDRIVER_OBJECT NtfsDrvObj = NULL;
        PDEVICE_OBJECT NtfsDevObj = NULL,fsDevObj = NULL;
        PFILE_OBJECT NtfsFileObj = NULL,ObjFileObj = NULL,RealFileObj = NULL;
        NTSTATUS status;
        PFILE_OBJECT Ntfs;
        BOOLEAN Real=FALSE;
    
        //检查是否文件属于NTFS文件系统
        status = IoGetDeviceObjectPointer(&uNtfs,0,&NtfsFileObj,&NtfsDevObj);
        if(NT_SUCCESS(status) && NtfsFileObj && MmIsAddressValid(NtfsFileObj) && MmIsAddressValid(NtfsFileObj->DeviceObject))
            NtfsDrvObj = NtfsFileObj->DeviceObject->DriverObject;
        fsDevObj = IoGetBaseFileSystemDeviceObject(FileObject);//FileSystem\Ntfs
        if(fsDevObj && MmIsAddressValid(fsDevObj) && fsDevObj->DriverObject == NtfsDevObj)
        {
            FILE_STANDARD_INFORMATION StandardInfo;
            ULONG RetLen;
            status = IoQueryFileInformation(FileObject,FileStandardInformation,sizeof(StandardInfo),&StandardInfo,&RetLen);
            if(NT_SUCCESS(status))
            {
                if(StandardInfo.NumberOfLinks > 1)
                {
                    ObjFileObj = GetFileObjectByProcessId(ProcessId);
                    if(ObjFileObj && ObjFileObj->FsContext != FileObj->FsContext)
                    {
                        //2种方式的FsContext不同,说明可能被拦截,下面采用Ntfs文件号获取
                        Real = TRUE;
                        ObDereferenceObject(ObjFileObj);
                    }
                }
            }
        }
        if(!Real)
        {
            //获取该文件Ntfs文件号
            FILE_INTERNAL_INFORMATION InternalInfo;
            ULONG RetLen;
            PVOID Buf = ExAllocatePool(PagedPool,1024);
            status = IoQueryFileInformation(FileObj,FileInternalInformation,sizeof(InternalInfo),&InternalInfo,&RetLen);
            if(NT_SUCCESS(status) && Buf)
            {
                //获取父目录信息
                RtlZeroMemory(Buf,1024);
                POBJECT_NAME_INFORMATION DeviceName = (POBJECT_NAME_INFORMATION)Buf;
                OBJECT_ATTRIBUTES Oa;
                IO_STATUS_BLOCK IoStatus;
                HANDLE DeviceHandle = NULL;
                HANDLE FileHandle = NULL;
                status = ObQueryNameString(FileObj->DeviceObject,Buf,1024,RetLen);
                if(NT_SUCCESS(status) && DeviceName->Name.Buffer)
                {
                    InitializeObjectAttributes(&Oa,&DeviceName->Name,OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, NULL, NULL);
                    status = ZwOpenFile(&DeviceHandle , 0, &Oa, &IoStatus, 0, FILE_NON_DIRECTORY_FILE);
                    if(NT_SUCCESS(status))
                    {
                        UNICODE_STRING InnerFileName = {sizeof(InternalInfo), sizeof(InternalInfo), &InternalInfo};
                        InitializeObjectAttributes(&Oa, &InnerFileName, OBJ_CASE_INSENSITIVE | OBJ_KERNEL_HANDLE, DeviceHandle, NULL);
                        status = ZwOpenFile(FileHandle, SYNCHRONIZE | FILE_READ_ATTRIBUTES, &Oa, &IoStatus, 
                            FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE, FILE_OPEN_BY_FILE_ID | FILE_NON_DIRECTORY_FILE | FILE_SYNCHRONOUS_IO_NONALERT);
                        if(NT_SUCCESS(status))
                        {
                            //用文件索引号打开文件成功
                            ObReferenceObjectByHandle(FileHandle, 0, *IoFileObjectType, KernelMode, &RealFileObj);
                        }
                    }
                }
                if(FileHandle)
                    ZwClose(FileHandle);
                if(DeviceHandle)
                    ZwClose(DeviceHandle);
            }
            if(Buf)
                ExFreePool(Buf);
        }
        return RealFileObj;
    }
    

    4.5 长度反汇编引擎

      用于根据前几个机器码获取汇编指令长度

    int DisasmLen(unsigned char* bytecode)
    {
        unsigned long decode1[256][7]=
        {
            {0x00,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x01,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x02,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x03,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x04,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x05,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x06,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x07,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x08,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x09,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x0a,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x0b,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x0c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x0d,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x0e,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x0f,0x03,0x03,0x02,0x00,0x00,0x00,},
            {0x10,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x11,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x12,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x13,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x14,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x15,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x16,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x17,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x18,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x19,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x1a,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x1b,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x1c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x1d,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x1e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x1f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x20,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x21,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x22,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x23,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x24,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x25,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x26,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x27,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x28,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x29,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2c,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2d,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2e,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2f,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x30,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x31,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x32,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x33,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x34,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x35,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x36,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x37,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x38,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x39,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x3a,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x3b,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x3c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x3d,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x3e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x3f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x40,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x41,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x42,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x43,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x44,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x45,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x46,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x47,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x48,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x49,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x4a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x4b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x4c,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x4d,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x4e,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x4f,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x50,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x51,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x52,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x53,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x54,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x55,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x56,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x57,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x58,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x59,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x5a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x5b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x5c,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x5d,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x5e,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x5f,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x60,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x61,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x62,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x63,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x64,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x65,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x66,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x67,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x68,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x69,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x6a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x6b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x6c,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x6d,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x6e,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x6f,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x70,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0x71,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0x72,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0x73,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0x74,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x75,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x76,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x77,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x78,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x79,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x7a,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x7b,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x7c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x7d,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x7e,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x7f,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x80,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x81,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x82,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x83,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x84,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x85,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x86,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x87,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x88,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x89,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x8a,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x8b,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x8c,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x8d,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x8e,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x8f,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0x90,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x91,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x92,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x93,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x94,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x95,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x96,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x97,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x98,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x99,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x9a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x9b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x9c,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x9d,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x9e,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x9f,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xa0,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xa1,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xa2,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xa3,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xa4,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xa5,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xa6,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xa7,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xa8,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xa9,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xaa,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xab,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xac,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xad,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xae,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xaf,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb0,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb1,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb2,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb3,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb4,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb5,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb6,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb7,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xb8,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xb9,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xba,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xbb,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xbc,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xbd,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xbe,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xbf,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc0,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc1,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc2,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc3,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc4,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xc5,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xc6,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xc7,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc8,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xc9,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xca,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xcb,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xcc,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xcd,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xce,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xcf,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xd0,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xd1,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd2,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd3,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd4,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd5,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd6,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd7,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd8,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd9,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xda,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdb,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdc,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdd,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xde,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdf,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe0,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe1,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe2,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe3,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe4,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe5,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe6,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe7,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe8,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe9,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xea,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xeb,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xec,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xed,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xee,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xef,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf0,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf1,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf2,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf3,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf4,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf5,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf6,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf7,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf8,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xf9,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xfa,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xfb,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xfc,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xfd,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xfe,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xff,0x01,0x01,0x00,0x00,0x00,0x00,},
        };
    
        unsigned long decode2[256][7]=
        {
            {0x00,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x01,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x02,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x03,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x04,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x05,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x06,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x07,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x08,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x09,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x0a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x0b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x0c,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x0d,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x0e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x0f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x10,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x11,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x12,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x13,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x14,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x15,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x16,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x17,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x18,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x19,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x1a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x1b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x1c,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x1d,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x1e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x1f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x20,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x21,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x22,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x23,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x24,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x25,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x26,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x27,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x28,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x29,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x2c,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x2d,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x2e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x2f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x30,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x31,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x32,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x33,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x34,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x35,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x36,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x37,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x38,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x39,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x3a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x3b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x3c,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x3d,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x3e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x3f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x40,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x41,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x42,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x43,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x44,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x45,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x46,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x47,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x48,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x49,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x4a,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x4b,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x4c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x4d,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x4e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x4f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x50,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x51,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x52,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x53,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x54,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x55,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x56,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x57,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x58,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x59,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x5a,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x5b,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x5c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x5d,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x5e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x5f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x60,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x61,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x62,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x63,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x64,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x65,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x66,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x67,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x68,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0x69,0x06,0x04,0x01,0x00,0x04,0x00,},
            {0x6a,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x6b,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0x6c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x6d,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x6e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x6f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x70,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x71,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x72,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x73,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x74,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x75,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x76,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x77,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x78,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x79,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x7a,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x7b,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x7c,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x7d,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x7e,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x7f,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0x80,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0x81,0x06,0x04,0x01,0x00,0x04,0x00,},
            {0x82,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0x83,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0x84,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x85,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x86,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x87,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x88,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x89,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x8a,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x8b,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x8c,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x8d,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x8e,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x8f,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0x90,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x91,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x92,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x93,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x94,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x95,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x96,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x97,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x98,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x99,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x9a,0x07,0x05,0x00,0x00,0x00,0x01,},
            {0x9b,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x9c,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x9d,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x9e,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0x9f,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xa0,0x05,0x03,0x00,0x00,0x00,0x02,},
            {0xa1,0x05,0x03,0x00,0x00,0x00,0x02,},
            {0xa2,0x05,0x03,0x00,0x00,0x00,0x02,},
            {0xa3,0x05,0x03,0x00,0x00,0x00,0x02,},
            {0xa4,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xa5,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xa6,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xa7,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xa8,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xa9,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xaa,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xab,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xac,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xad,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xae,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xaf,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xb0,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb1,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb2,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb3,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb4,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb5,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb6,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb7,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xb8,0x05,0x03,0x00,0x00,0x00,0x08,},
            {0xb9,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xba,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xbb,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xbc,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xbd,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xbe,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xbf,0x05,0x03,0x00,0x00,0x00,0x00,},
            {0xc0,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xc1,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xc2,0x03,0x03,0x00,0x00,0x00,0x00,},
            {0xc3,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xc4,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc5,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xc6,0x03,0x03,0x01,0x00,0x01,0x00,},
            {0xc7,0x06,0x04,0x01,0x00,0x04,0x00,},
            {0xc8,0x04,0x04,0x00,0x00,0x00,0x00,},
            {0xc9,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xca,0x03,0x03,0x00,0x00,0x00,0x01,},
            {0xcb,0x01,0x01,0x00,0x00,0x00,0x01,},
            {0xcc,0x01,0x01,0x00,0x00,0x00,0x01,},
            {0xcd,0x02,0x02,0x00,0x00,0x00,0x01,},
            {0xce,0x01,0x01,0x00,0x00,0x00,0x01,},
            {0xcf,0x01,0x01,0x00,0x00,0x00,0x01,},
            {0xd0,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd1,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd2,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd3,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd4,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xd5,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xd6,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xd7,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xd8,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xd9,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xda,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdb,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdc,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdd,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xde,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xdf,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xe0,0x02,0x02,0x00,0x01,0x00,0x04,},
            {0xe1,0x02,0x02,0x00,0x01,0x00,0x04,},
            {0xe2,0x02,0x02,0x00,0x01,0x00,0x04,},
            {0xe3,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0xe4,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xe5,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xe6,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xe7,0x02,0x02,0x00,0x00,0x00,0x00,},
            {0xe8,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0xe9,0x05,0x03,0x00,0x01,0x00,0x00,},
            {0xea,0x07,0x05,0x00,0x00,0x00,0x01,},
            {0xeb,0x02,0x02,0x00,0x01,0x00,0x00,},
            {0xec,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xed,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xee,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xef,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf0,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf1,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf2,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf3,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf4,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf5,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf6,0x00,0x00,0x00,0x00,0x00,0x00,},
            {0xf7,0x00,0x00,0x00,0x00,0x00,0x00,},
            {0xf8,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xf9,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xfa,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xfb,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xfc,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xfd,0x01,0x01,0x00,0x00,0x00,0x00,},
            {0xfe,0x02,0x02,0x01,0x00,0x00,0x00,},
            {0xff,0x02,0x02,0x01,0x00,0x00,0x00,},
        };
    
        unsigned char decode3[256]=
        {
            0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,
            0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,
            0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,
            0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,0x00,0x00,0x00,0x00,0x11,0x24,0x00,0x00,
            0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,
            0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,
            0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,
            0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,0x01,0x01,0x01,0x01,0x02,0x01,0x01,0x01,
            0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,
            0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,
            0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,
            0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,0x04,0x04,0x04,0x04,0x05,0x04,0x04,0x04,
            0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
            0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
            0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
            0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,0x00,
        };
    
        unsigned char* ptr = bytecode;
        unsigned long len = 0,var2 = 0,var3 = 0, decodel[7]={0};
        unsigned long* pdecode = 0;
    
        switch(*ptr)
        {
        case 0xF:
            ptr++;
            len = 1;
            pdecode = &decode1[*ptr][0];
            break;
        case 0x26:
        case 0x2E:
        case 0x36:
        case 0x3E:
        case 0x64:
        case 0x65:
            len = 1;
            ptr++;
            break;
        case 0x66:
            len = 1;
            var3 = 1;
            ptr++;
            break;
        case 0x67:
            len = 1;
            var2 = 1;
            ptr++;
            break;
        case 0xF0:
        case 0xF2:
        case 0xF3:
            len = 1;
            ptr++;
            break;
        case 0xF6:
            decodel[0] = 0xF6;
            if(*(ptr+1) & 0x38)
            {
                decodel[1] = 2;
                decodel[2] = 2;
                decodel[3] = 1;
                decodel[5] = 0;
            }
            else
            {
                decodel[1] = 3;
                decodel[2] = 3;
                decodel[3] = 1;
                decodel[5] = 1;
            }
            pdecode = decodel;
            break;
        case 0xF7:
            decodel[0] = 0xF6;
            decodel[3] = 1;
            if(*(ptr+1) & 0x38)
            {
                decodel[1] = 6;
                decodel[2] = 4;
                decodel[5] = 4;
            }
            else
            {
                decodel[1] = 2;
                decodel[2] = 2;
                decodel[5] = 0;
            }
            pdecode = decodel;
            break;
        default:
            break;
        }
        if(!pdecode)
            pdecode = decode2[*ptr];
        if(pdecode[6] & 2)
        {
            if(var2 == 0)
                len += pdecode[1];
            else
                len += pdecode[2];
        }
        else
        {
            if(var3 == 0)
                len += pdecode[1];
            else
                len += pdecode[2];
        }
    
        if(pdecode[3])
        {
            unsigned char var4 = ptr[pdecode[3]];
            len += decode3[var4] & 0xF;
            if((decode3[var4] & 0x10) && (ptr[pdecode[3] + 1] & 7) == 5)
            {
                switch(var4 & 0xC0)
                {
                case 0x40:
                    len++;
                    break;
                case 0x00:
                case 0x80:
                    len += 4;
                    break;
                default:
                    break;
                }
            }
        }
        return len;
    }
    

    相关文章

      网友评论

          本文标题:腾讯管家攻防驱动分析-TsDefenseBt

          本文链接:https://www.haomeiwen.com/subject/uolzoxtx.html