網(wǎng)絡(luò)游戲外掛技術(shù)
網(wǎng)絡(luò)游戲外掛技術(shù)想必很多人都是聽(tīng)過(guò)或者使用過(guò),但是真正怎么取制作想必很多人都是不清楚的。所以學(xué)習(xí)啦小編今天就在這里給大家分享下網(wǎng)絡(luò)游戲外掛技術(shù)的知識(shí)。下面是具體內(nèi)容:
網(wǎng)絡(luò)游戲外掛技術(shù)引言
所謂游戲外掛,是一種游戲外部的輔助程序,它可以幫助玩家自動(dòng)生成游戲動(dòng)作、修改游戲的網(wǎng)絡(luò)數(shù)據(jù)封包等,使玩家以最少的時(shí)間和精力完成游戲中的各種任務(wù)。隨著網(wǎng)絡(luò)游戲的不斷升溫,游戲外掛作為其附屬品也得到了迅猛的發(fā)展。從最初的鼠標(biāo)鍵盤模擬和變速齒輪技術(shù)發(fā)展到擋截Sock、擋截API等高端技術(shù)的應(yīng)用。
事物都有兩面性,游戲外掛也不例外。一方面,它可以使玩家從機(jī)械的、重復(fù)的操作中解放出來(lái),使游戲更加人性化,娛樂(lè)化。另一方面,一些惡意外掛篡改游戲數(shù)據(jù),欺騙服務(wù)器,嚴(yán)重破壞了游戲的公平性,使玩家大量流失。因此,外掛的開(kāi)發(fā)應(yīng)僅限于研究和學(xué)習(xí)編程技術(shù)之用。
1 外掛技術(shù)綜述
外掛的種類紛繁復(fù)雜,功能也多種多樣。針對(duì)同一款網(wǎng)絡(luò)游戲的外掛甚至多達(dá)幾十種,功能相同的外掛實(shí)現(xiàn)起來(lái)也有若干種不同的技術(shù),例如本文下面要談到的某網(wǎng)絡(luò)斗地主游戲記牌器外掛的實(shí)現(xiàn)方式至少有三種,通過(guò)分析屏幕撲克牌的圖片、通過(guò)讀取游戲在本地機(jī)所使用的內(nèi)存空間、截獲并分析數(shù)據(jù)封包。因此對(duì)網(wǎng)游外掛做一個(gè)科學(xué)的分類顯得十分必要。按照外掛所針對(duì)的游戲類型,可以把其分為兩大類即,模擬玩家鼠標(biāo)、鍵盤操作的動(dòng)作模擬類外掛和截獲數(shù)據(jù)封包,提取或修改其中數(shù)據(jù)的封包類外掛。下面對(duì)兩類外掛所采用的技術(shù)進(jìn)行詳細(xì)說(shuō)明。
1.1 動(dòng)作模擬類外掛
動(dòng)作模擬類外掛可以在沒(méi)有人為干預(yù)的情況下,自動(dòng)控制游戲中的角色,使其四處行走或者發(fā)動(dòng)攻擊。此類外掛看似復(fù)雜,其實(shí)原理非常簡(jiǎn)單。游戲中角色的行動(dòng)是靠鼠標(biāo)與鍵盤控制,此類外掛就是調(diào)用相關(guān)的API函數(shù),來(lái)模擬玩家對(duì)鼠標(biāo)和鍵盤的操作,從而控制游戲中的角色。
1.1.1 鼠標(biāo)模擬技術(shù)
鼠標(biāo)的操作包含以下幾種,點(diǎn)擊左鍵、點(diǎn)擊右鍵、點(diǎn)擊中鍵、移動(dòng)鼠標(biāo)改變相應(yīng)窗體中指針的位置。下面介紹實(shí)現(xiàn)以上操作所需要的API函數(shù)。
1)mouse_event函數(shù),模擬鼠標(biāo)發(fā)出按下和放開(kāi)左右鍵的動(dòng)作,其格式如下:
VOID mouse_event(
DWORD dwFlags, // 鼠標(biāo)動(dòng)作標(biāo)識(shí)
DWORD dx, // 鼠標(biāo)橫坐標(biāo)位置
DWORD dy, // 鼠標(biāo)縱坐標(biāo)位置
DWORD dwData, // 鼠標(biāo)輪子轉(zhuǎn)動(dòng)的數(shù)量
DWORD dwExtraInfo // 其它信息
);
其中,dwFlags表示各種鼠標(biāo)動(dòng)作,如MOUSEEVENTF_LEFTDOWN 表示模擬按下鼠標(biāo)左鍵、MOUSEEVENTF_LEFTUP 表示模擬放開(kāi)鼠標(biāo)左鍵、MOUSEEVENTF_MOVE表示模擬鼠標(biāo)移動(dòng)事件等。
2)GetCursorPos函數(shù),獲取鼠標(biāo)當(dāng)前位置,其格式如下:
BOOL GetCursorPos(
LPPOINT lpPoint // 返回鼠標(biāo)的當(dāng)前位置
);
3)SetCursorPos函數(shù),設(shè)置當(dāng)前鼠標(biāo)位置,其格式如下:
BOOL SetCursorPos(
int X, // 鼠標(biāo)的橫坐標(biāo)
int Y //鼠標(biāo)的縱坐標(biāo)
);
游戲中角色的移動(dòng)一般是將鼠標(biāo)移動(dòng)到目的地,然后按下鼠標(biāo)左鍵來(lái)完成的。下面利用上面介紹的API函數(shù)來(lái)模擬角色的移動(dòng)。
CPoint oldPoint,newPoint; GetCursorPos(&oldPoint); //保存當(dāng)前鼠標(biāo)位置
newPoint=SetPoint(oldPoint);//SetPoint為自編的坐標(biāo)設(shè)置函數(shù)
SetCursorPos(newPoint.x,newPoint.y); //設(shè)置目的地位置
mouse_event(MOUSEEVENTF_LEFTDOWN,0,0,0,0);//模擬按下鼠標(biāo)左鍵
mouse_event(MOUSEEVENTF_LEFTUP,0,0,0,0);//模擬放開(kāi)鼠標(biāo)左鍵
1.1.2 鍵盤模擬技術(shù)
鍵盤的操作比較簡(jiǎn)單,只有按鍵的按下與放開(kāi)兩種。通過(guò)keydb_event函數(shù)模擬鍵盤動(dòng)作,其格式如下:
VOID keybd_event(
BYTE bVk, // 虛擬鍵值
BYTE bScan, // 硬件掃描碼
DWORD dwFlags, // 動(dòng)作標(biāo)識(shí)
DWORD dwExtraInfo //輔加信息
);
下面利用該函數(shù)來(lái)模擬按下Ctrl+C的操作。
keybd_event(VK_CONTROL,MapVirtualKey(VK_CONTROL,0),0,0); //按下CTRL鍵
keybd_event(0x43,MapVirtualKey(0x43,0),0,0);//鍵下C鍵
keybd_event(0x43,MapVirtualKey(0x43,0), KEYEVENTF_KEYUP,0);//放開(kāi)C鍵
keybd_event(VK_CONTROL,MapVirtualKey(VK_CONTROL,0),
KEYEVENTF_KEYUP,0);//放開(kāi)CTRL鍵
其中,MapVirtualKey函數(shù)功能是在虛擬鍵值與掃描碼之間進(jìn)行轉(zhuǎn)換。
1.2 封包類外掛
網(wǎng)絡(luò)游戲最大的特點(diǎn)在于分布在各地的玩家之間可以相互通信,實(shí)現(xiàn)這個(gè)功能的關(guān)鍵是玩家在游戲中所做的任何操作,都會(huì)以數(shù)據(jù)封包的形式發(fā)送至服務(wù)器,服務(wù)器經(jīng)過(guò)處理后再把數(shù)據(jù)封包反饋給游戲中的玩家們。
封包類外掛利用網(wǎng)絡(luò)游戲這個(gè)特點(diǎn),在客戶端攔截服務(wù)器發(fā)送來(lái)的數(shù)據(jù)封包,采用特定的方法對(duì)封包內(nèi)的數(shù)據(jù)進(jìn)行分析,最后按照需要修改封包內(nèi)的數(shù)據(jù)模擬客戶端發(fā)送至服務(wù)器。此類外掛實(shí)現(xiàn)的關(guān)鍵技術(shù)涉及兩個(gè)方面:封包截獲與封包數(shù)據(jù)的分析。
1.2.1 封包截獲
API Hook技術(shù)是封包截獲的核心,是指攔截API調(diào)用的過(guò)程。API Hook技術(shù)的應(yīng)用十分廣泛,如實(shí)時(shí)翻譯系統(tǒng)中屏幕取詞功能。API Hook一般由兩部分組成:Hook服務(wù)器和Hook驅(qū)動(dòng)器。Hook服務(wù)器一般以exe的形式出現(xiàn),主要負(fù)責(zé)把Hook驅(qū)動(dòng)器注入到目標(biāo)進(jìn)程或模塊中。Hook驅(qū)動(dòng)器一般以DLL的形式出現(xiàn),主要負(fù)責(zé)API的攔截工作。至此,又涉及到兩個(gè)核心技術(shù):DLL注入技術(shù)與API攔截技術(shù)。
1.3DLL注入技術(shù)
DLL的注入方法有很多種,由于篇幅有限,只介紹兩種比較常用的方法,即利用全局鉤子進(jìn)行DLL注入和利用遠(yuǎn)程線程進(jìn)行DLL注入。下面分別介紹。
全局鉤子必須在DLL中也就是Hook驅(qū)動(dòng)器中實(shí)現(xiàn),原理是當(dāng)待注入進(jìn)程在接收到某一消息時(shí),消息不會(huì)先到這個(gè)進(jìn)程,而是先到DLL中的鉤子函數(shù)中,由鉤子先處理這個(gè)消息后再傳遞到接收這個(gè)消息的進(jìn)程中。
也就是說(shuō),當(dāng)待注入進(jìn)程的消息被一個(gè)鉤子截獲時(shí),相當(dāng)于這個(gè)進(jìn)程調(diào)用了DLL中的鉤子函數(shù),系統(tǒng)便會(huì)強(qiáng)制把DLL文件映射到這個(gè)進(jìn)程的地址空間中,供這個(gè)進(jìn)程使用。以上是利用全局鉤子進(jìn)行DLL注入的全過(guò)程。可以通過(guò)SetWindowsHookEx函數(shù)在系統(tǒng)中安裝鉤子,通過(guò)UnHookWindowsHookEx卸載鉤子。
利用遠(yuǎn)程線程進(jìn)行DLL注入的步驟:
利用OpenProcess函數(shù)取得遠(yuǎn)程進(jìn)程的進(jìn)程ID;
利用VirtualAllocEx函數(shù)在遠(yuǎn)程進(jìn)程空間中分配一段內(nèi)存用來(lái)存放要注入的DLL完整路徑
;利用WriteProcessMemory函數(shù)將要注入的DLL的路徑寫到剛才分配的遠(yuǎn)程進(jìn)程空間;
利用GetProcAddress函數(shù)從Kernel32.dll中取得LoadLibray的地址
;利用CreateRemoteThread函數(shù)以從Kernel32.dll中取得的LoadLibrary函數(shù)的地址為線程函數(shù)的地址,以我們要注入的DLL文件名為參數(shù),創(chuàng)建遠(yuǎn)程線程。
1.4API攔截技術(shù)
API攔截的實(shí)現(xiàn)方法也有多種,本文重點(diǎn)介紹兩種最為常用的技術(shù),即擋截Winsock和擋截API函數(shù)。
Winsock是Windows網(wǎng)絡(luò)編程接口。在Windows系統(tǒng)中,使用Winsock接口為應(yīng)用程序提供基于TCP/IP協(xié)議的網(wǎng)絡(luò)訪問(wèn)服務(wù),而這些服務(wù)是由Wsock32.DLL提供的函數(shù)庫(kù)來(lái)完成的。因此,任何Windows基于TCP/IP的應(yīng)用程序都必須通過(guò)Winsock接口訪問(wèn)網(wǎng)絡(luò)。擋截Winsock的原理是由自己寫一個(gè)與原有進(jìn)程調(diào)用的Wsock32.DLL具有相同接口函數(shù)的DLL,再用重寫的DLL替換原有的DLL。在替換的過(guò)程中,可以對(duì)感興趣的函數(shù)進(jìn)行擋截,放入外掛控制代碼,而對(duì)其它不感興趣的函數(shù),則以函數(shù)轉(zhuǎn)發(fā)的形式調(diào)用原有Wsock32.DLL中的函數(shù)。
實(shí)現(xiàn)擋截API的常用方法是改寫執(zhí)行代碼,主要步驟是:利用GetProcAddress函數(shù)獲取所要擋截的API函數(shù)的地址;利用VirtualQuery函數(shù)查詢關(guān)于本進(jìn)程內(nèi)虛擬地址頁(yè)的信息,利用VirtualProtect函數(shù)改變本進(jìn)程內(nèi)虛擬地址頁(yè)的保護(hù)屬性;利用WriteProcessMemory函數(shù)修改原API函數(shù)執(zhí)行代碼的前8個(gè)字節(jié),使得對(duì)該API函數(shù)的調(diào)用能轉(zhuǎn)向自定義的函數(shù)調(diào)用。除此之外,還可以通過(guò)改寫PE文件的輸入地址表來(lái)實(shí)現(xiàn)擋截API的功能,有關(guān)此方法可以參見(jiàn)MSDN的相關(guān)內(nèi)容。 1.2.2 封包數(shù)據(jù)分析
封包數(shù)據(jù)分析的過(guò)程非常復(fù)雜,需要分析人員有極大的耐心和毅力。首先,封包內(nèi)數(shù)據(jù)的格式很復(fù)雜,需要經(jīng)過(guò)反復(fù)的試驗(yàn)與分析,才能得出數(shù)據(jù)中每個(gè)字節(jié)在游戲中所表示的含意。其次,絕大部分游戲?qū)Ψ獍鼉?nèi)的數(shù)據(jù)進(jìn)行了加密處理。在網(wǎng)絡(luò)游戲出現(xiàn)的初期,只要掌握幾種簡(jiǎn)單的加密解密算法,就可以通過(guò)對(duì)封包內(nèi)數(shù)據(jù)的分析得出封包的加密解密算法。但隨著機(jī)器性能的提高與網(wǎng)絡(luò)帶寬的提升,游戲開(kāi)發(fā)商對(duì)封包的加密與解密算法設(shè)計(jì)的越來(lái)越復(fù)雜,單純的通過(guò)封包內(nèi)數(shù)據(jù)的分析已經(jīng)很難推出加密解密算法。目前破解封包加密與解密算法的方法主要是通過(guò)動(dòng)態(tài)調(diào)試技術(shù)來(lái)實(shí)現(xiàn)的。
其原理是首先通過(guò)動(dòng)態(tài)調(diào)試跟蹤并取出加密與解密算法的代碼段,然后再通過(guò)分析這些代碼最終得出結(jié)論。動(dòng)態(tài)調(diào)試主要是跟蹤代碼的執(zhí)行,一般跟蹤的起點(diǎn)可以是windows消息、socket中的send與recv等函數(shù)。動(dòng)態(tài)調(diào)試工具一般采用OllyDbg,softice等工具。動(dòng)態(tài)調(diào)試工具所跟蹤的代碼都是以匯編語(yǔ)言的形式反饋給用戶,匯編語(yǔ)言相對(duì)高級(jí)語(yǔ)言難以讀懂,一般可以通過(guò)代碼反推導(dǎo)將匯編語(yǔ)言轉(zhuǎn)換為相應(yīng)的高級(jí)語(yǔ)言,
步驟如下:首先,可以將匯編碼寫成三元表達(dá)碼,其次,將代碼中的轉(zhuǎn)移指令轉(zhuǎn)換為條件語(yǔ)句或循環(huán)語(yǔ)句,再次,將代碼中的變量進(jìn)行迭代,最后,進(jìn)行變量形式轉(zhuǎn)換與語(yǔ)句形式轉(zhuǎn)換。當(dāng)然我們對(duì)代碼進(jìn)行動(dòng)態(tài)調(diào)試的目的是為了掌握封包的加密算法,進(jìn)而對(duì)封包中的數(shù)據(jù)進(jìn)行分析,通過(guò)大量的實(shí)驗(yàn),最終讀懂封包中重要數(shù)據(jù)的含意。為后面的編程工作做好準(zhǔn)備。
2 結(jié)束結(jié)
外掛程序?qū)W(wǎng)絡(luò)游戲的環(huán)境安全和健康發(fā)展有著極大的影響,防治外掛必然要對(duì)外掛的實(shí)現(xiàn)技術(shù)有所了解。但防治外掛僅靠技術(shù)手段是很難實(shí)現(xiàn)的,因?yàn)樵诰W(wǎng)絡(luò)世界沒(méi)有什么是絕對(duì)安全絕對(duì)保密的。技術(shù)手段只能是盡可能的加大外掛制作的難度,拖延外掛開(kāi)發(fā)的時(shí)間而已,并不可能完全杜絕外掛。因此外掛的防治必須要多管齊下,尤其是加強(qiáng)游戲信用體制的建設(shè),完善相應(yīng)的法律法規(guī),以促進(jìn)網(wǎng)絡(luò)游戲更好,更快的發(fā)展。