- 1,進程
現象:
游戲通過探測游戲客戶端進程是否已經存在來防止重復打開。
破解方法:
(1)隱藏進程。可以用工具 HideToolz,也可以自己寫驅動簡單的做個摘鏈隱藏。
(2)hook 游戲遍歷進程的 api。
CreateToolhelp32Snapshot()、Process32First()和Process32Next()
EnumProcesses()、EnumProcessModules()、GetModuleBaseName()
ZwQuerySystemInformation
WTSOpenServer()、WTSEnumerateProcess()
(3)修改進程名。拷貝一份游戲 exe 文件的副本,重命名即可。
- 2,窗口標題
現象:
游戲通過探測游戲客戶端的窗口是否已經存在來防止重復打開。
破解方法:
(1)使用 SetWindowText 修改窗口標題,可以自己調用或 hook 游戲的都可以。
(2)hook 游戲的 FindWindow ,不讓其獲取其他游戲的窗口句柄。
(3)hook 游戲的 EnumWindows ,不讓其遍歷窗口。
- 3,端口
現象:
游戲通過默認打開TCP或者UDP端口監聽。
破解方法:
端口隱藏(端口復用)
- 4,獨占文件、公共文件
現象(公共):游戲啟動后會以獨占方式打開某個文件的(lockfile)文件句柄,當第二次再有程序打開它時就會報錯。
現象(獨占):游戲啟動后用刀的所有文件(dll,ini 等)都使用獨占方式打開,當第二次再有程序打開它時就會報錯。
破解方法:
(1)hook 游戲的 OpenFileMapping,拷貝一份獨占文件副本並重命名,讓他獲取文件副本的句柄而不是原文件句柄。
(2)循環遍歷游戲的句柄表,刪除指定的 File 類型的句柄
- 5,多個操作系統賬號
現象:游戲通過限制一個用戶只能打開一個游戲來防止重復打開。
破解方法:
創建多個系統賬號后,Shift + 右鍵 ,以其他身份運行。
- 6,互斥體
現象:游戲只能單開,通過互斥對象/信號量/事件等線程同步對象來確定程序是否已經運行。
破解方法:
(1)Hook 對應創建互斥體的 API
(2)循環遍歷游戲句柄表,刪除對應的句柄
- 7,內存映射文件
現象:游戲只能開2個、3個等。而不是只能開1個,通過把程序實例信息放到跨進程的內存映射文件中,防止游戲多開。
破解方法:
(1)Hook CreateFileMapping 、OpenFileMapping
(2)循環遍歷游戲句柄表,刪除對應的句柄
- 8,DLL全局共享變量
現象:游戲只能開2個、3個等。而不是只能開1個 ,DLL全局共享區在映射到各個進程的地址空間時僅被初始化一次,且是在第一次被windows加載時,所以利用該區數據就能對程序進行多開限制。
破解方法:
(1)找到共享區段的位置,使用 PE 工具刪除這個區段。
(2)使用 ce 找到存放游戲實例的基地址,每當啟動一個實例后,使用 WriteProcessMemory 修改這個值。
- 9,Mac地址驗證
現象:游戲只能開2個、3個等。而不是只能開1個 ,登陸服務器時,獲取本機mac地址,發送至服務器端,服務端進行mac地址驗證,如果mac地址重復登陸,則不允許同服務器進行消息傳遞。
破解方法:
(1)hook 游戲獲取 mac 的 api ,讓每個游戲獲取不同的 mac 地址。注意游戲可能會多次獲取 mac ,所以不要將 mac 完全隨機,避免第一次獲取的 mac 和第二次獲取的 mac 不一樣,這就很尷尬。處理方法是 dll 注入時初始化一個隨機 mac ,之后 hook 時都使用這個 mac 來偽造。
(2)定時修改本機mac 。這種情況有一個缺陷,就是必須把時鍾設置的很小,因為游戲不一定只有登錄時才校驗 mac ,如果游戲對 mac 做循環校驗,就必須保證在打開的 n 個游戲的 n 個循環中 ,都修改一次 mac 。也就是說,打開的客戶端也多,修改本機mac 的時鍾就要設置的越小,且不能保證某一時刻客戶端 a 和 客戶端 b 獲取到的mac 是相同的 !
- 10,查看網絡連接
現象:獲取本機所有網絡連接,使用 GetTcpTable 獲取 TCP 連接,使用 GetUdpTable 獲取 UDP 連接,檢查是否有連接到服務器IP和端口號的連接,如果有,表示程序已經啟動,否則程序未啟動。
破解方法:
hook GetTcpTable 、GetUdpTable