首页 » 技术分享 » 植物大战僵尸v1.2---外挂源码

植物大战僵尸v1.2---外挂源码

 

 

 

 

/*************************************/
//wnd.h
//
/***********************************/
#pragma once

#define WM_GRAYCONTROLES WM_USER+100 

#define APP_NAME L"植物大战僵尸修改器 v1.2"


#define WND_W 360
#define WND_H 230

#define IMG_H 55

#define ID_TIMER 1
#define TIMER_SLEEP_TIME 1000

#include <windows.h>
#include <tchar.h>
#include <Commctrl.h> 
#include <psapi.h>
#include <process.h>
 

#pragma comment(lib, "psapi")
#pragma comment(lib, "comctl32.lib")   
  
#pragma comment(linker,"/manifestdependency:\"type='win32'\
	name='Microsoft.Windows.Common-Controls' "\
	"version='6.0.0.0' \
	processorArchitecture='*'\
	publicKeyToken='6595b64144ccf1df' \
    language='*'\"")  

BOOL	CALLBACK DlgProc(HWND,UINT,WPARAM,LPARAM);
LRESULT CALLBACK WndProc(HWND,UINT,WPARAM,LPARAM);

BOOL	EnableDebugPrivilege(HANDLE hProcess);
HWND	FindDestWnd();
DWORD	GetPIDFromeWnd();
HANDLE	OpenProcessWithDbg(DWORD PID);


DWORD	GetPIDFromeProcesses(LPCTSTR lpWndName);

 

/*************************************/
//wnd.cpp
//
/***********************************/


#include "Wnd.h"
#include "resource.h"
#include "InjectCode.h"

BOOL g_bWndActive = false;

BOOL EnableDebugPrivilege(HANDLE hProcess)
{
	HANDLE hToken;
	LUID luid;
	TOKEN_PRIVILEGES tp;

	//打开令牌环
	BOOL bOK = OpenProcessToken(hProcess,TOKEN_ADJUST_PRIVILEGES|TOKEN_QUERY,&hToken);
	if(!bOK)
		return FALSE;

	bOK = LookupPrivilegeValue(NULL,SE_SECURITY_NAME,&luid);
	if(!bOK)
		return FALSE;

	tp.PrivilegeCount = 1;
	tp.Privileges[0].Luid = luid;
	tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;

	//调整权限
	bOK = AdjustTokenPrivileges(hToken, FALSE, &tp, sizeof(TOKEN_PRIVILEGES),NULL,NULL);

	if(!bOK)
		return FALSE;
	CloseHandle(hToken);
	return TRUE;
}


int WINAPI WinMain(HINSTANCE hInst, HINSTANCE, LPSTR lpCmdLine, int nShowCmd)
{
	InitCommonControls();

	HWND	hWnd;
	MSG		msg;
	TCHAR	szClsName[] = L"MainWnd";
	WNDCLASSEX	wcex;

	wcex.cbSize = sizeof(WNDCLASSEX);
	wcex.hInstance = hInst;
	wcex.lpfnWndProc = WndProc;
	wcex.cbClsExtra = 0;
	wcex.cbWndExtra = 0;
	wcex.hCursor = LoadCursor(NULL, IDC_ARROW);
	
	wcex.hbrBackground = (HBRUSH)(COLOR_MENUBAR+1);
	wcex.lpszClassName = szClsName;
	wcex.lpszMenuName = NULL;
	wcex.style = 0;
	wcex.hIconSm = LoadIcon(hInst, MAKEINTRESOURCE(IDI_ICON1));
	wcex.hIcon = LoadIcon(hInst, MAKEINTRESOURCE(IDI_ICON2));

	if(!RegisterClassEx(&wcex))
		return 0;

	hWnd = CreateWindowEx(
		WS_EX_CONTROLPARENT, 
		szClsName, 
		APP_NAME, 
		(WS_CLIPCHILDREN 
		|WS_CLIPSIBLINGS 
		|WS_MINIMIZEBOX 
		|WS_SYSMENU 
		|WS_CAPTION 
		|WS_TABSTOP) 
		&(~WS_MAXIMIZEBOX ),
		GetSystemMetrics(SM_CXFULLSCREEN)/2-WND_W/2,
		GetSystemMetrics(SM_CYFULLSCREEN)/2-WND_H/2,
		WND_W,
		WND_H,
		NULL,
		NULL,
		hInst,NULL);
	if(!hWnd)
		return 0;

	ShowWindow(hWnd, nShowCmd);
	UpdateWindow(hWnd);

	while(GetMessage(&msg, NULL, 0, 0))
	{
		TranslateMessage(&msg);
		DispatchMessage(&msg);
	}
	return msg.wParam;
}



LRESULT CALLBACK WndProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
	static HWND	hDlg;
	static RECT rectWnd;
	RECT rectDlg;
	static HANDLE hBmp;
	HDC hdcWnd, hdcMem;
	PAINTSTRUCT ps;
	int ID;


	switch(uMsg)
	{
	case WM_KEYDOWN:
		{		
			switch(wParam)
			{
			case VK_F1:		ID = IDC_CHECK1; break;
			case VK_F2:		ID = IDC_CHECK2; break;
			case VK_F3:		ID = IDC_CHECK3; break;
			case VK_F4:		ID = IDC_CHECK4; break;
			case VK_F5:		ID = IDC_CHECK5; break;
			case VK_F6:		ID = IDC_CHECK6; break;
			case VK_F7:		ID = IDC_CHECK7; break;
			case VK_F8:		ID = IDC_CHECK8; break;
			default:
				return DefWindowProc(hWnd, uMsg, wParam, lParam);;
			}
			PostMessage(hDlg, WM_COMMAND, (WPARAM)ID, NULL);
			return 1;
		}

	case WM_PAINT:
		{
			hdcWnd = BeginPaint(hWnd, &ps);
			hdcMem = CreateCompatibleDC (hdcWnd);
			SelectObject(hdcMem,hBmp);
			BitBlt(hdcWnd,0,0,WND_W,WND_H,hdcMem,0,0,SRCCOPY);
			DeleteDC(hdcMem);
			EndPaint(hWnd, &ps);
			return 1;
		}

	case WM_TIMER:
		{
			if( FindDestWnd() == NULL)
				g_bWndActive = FALSE;
			else
				g_bWndActive = TRUE;
			PostMessage(hDlg, WM_GRAYCONTROLES,0,g_bWndActive);
			SetTimer(hWnd, ID_TIMER, TIMER_SLEEP_TIME, NULL);
			return 1;
		}
	case WM_DESTROY:
		KillTimer(hWnd, ID_TIMER);
		EndDialog(hDlg, 0);
		PostQuitMessage(0);
		return 0;
	case WM_CREATE:
		{
			if( FindDestWnd() == NULL)
				g_bWndActive = FALSE;
			else
				g_bWndActive = TRUE;

			hBmp = LoadImage(
				(HINSTANCE)GetModuleHandle(0),
				MAKEINTRESOURCE(IDB_BITMAP1),
				IMAGE_BITMAP,
				0,0,
				LR_DEFAULTSIZE);

			hDlg = CreateDialogParam(
				(HINSTANCE)GetModuleHandle(0),
				MAKEINTRESOURCE(IDD_FORMVIEW),
				hWnd,
				DlgProc,
				NULL);    

			GetWindowRect(hDlg,&rectDlg);
			GetClientRect(hWnd, &rectWnd);
			MoveWindow(hDlg,
				(rectWnd.right-rectWnd.left)/2 - (rectDlg.right-rectDlg.left)/2,
				IMG_H+1,rectDlg.right-rectDlg.left,rectDlg.bottom-rectDlg.top,NULL);
			ShowWindow(hDlg,SW_SHOW);
			SetFocus(GetParent(hDlg));
			SetTimer(hWnd, ID_TIMER, TIMER_SLEEP_TIME, NULL);
		}
		return 1;
	}
	return DefWindowProc(hWnd, uMsg, wParam, lParam);
}

BOOL CALLBACK DlgProc(HWND hDlg, UINT uMsg, WPARAM wParam, LPARAM lParam)
{
	BOOL bSetState;
	int  ctrlID;
	DWORD PID;
	HANDLE hProcess = NULL;
	BOOL bSuccess = FALSE;

	static INJECT_BLOCK 
		AutoCollect,
		Nondecrease,
		DoubleSun_1,
		DoubleSun_2,
		DoubleMoney,
		SecKill_1,
		SecKill_2,
		UnlockSlot_1,
		UnlockSlot_2;

	static GOODS_BACKUP goodsBackup[GOODS_COUNT];

	PINJECT_BLOCK pInjectes[3] = {NULL,NULL,NULL};

	switch(uMsg)
	{
	case WM_COMMAND:
		{
			if(g_bWndActive == FALSE)
				return FALSE;
			ctrlID = LOWORD(wParam);
			if(IsDlgButtonChecked(hDlg, ctrlID) == BST_CHECKED)
				bSetState = FALSE;
			else
				bSetState = TRUE;

			switch(ctrlID)
			{

			case IDC_CHECK1:
				pInjectes[0] = &AutoCollect;
				break;

			case IDC_CHECK2:
				pInjectes[0] = &Nondecrease;
				break;

			case IDC_CHECK3:
				pInjectes[0] = &DoubleSun_1;
				pInjectes[1] = &DoubleSun_2;
				break;

			case IDC_CHECK4:
				pInjectes[0] = &DoubleMoney;
				break;

			case IDC_CHECK5:
			case IDC_CHECK6:
				{
					PID = GetPIDFromeWnd();
					if(PID <= 0)
						return FALSE;
					hProcess = OpenProcessWithDbg(PID);
					if(hProcess == NULL)
						return FALSE;
					bSuccess = WriteGoodsAttrToMem(hProcess,
						(ctrlID==IDC_CHECK5)?GOODS_ATTR_PRICE:GOODS_ATTR_TIME,
						goodsBackup,
						bSetState);

					goto hereleave;
				}

			case IDC_CHECK7:
				pInjectes[0] = &SecKill_1;
				pInjectes[1] = &SecKill_2;
				break;

			case IDC_CHECK8:	
				pInjectes[0] = &UnlockSlot_2;
				pInjectes[1] = &UnlockSlot_1;
				break;

			default:
				return FALSE;
			}

			PID = GetPIDFromeWnd();
			if(PID <= 0)
				return FALSE;
			hProcess = OpenProcessWithDbg(PID);
			if(hProcess == NULL)
				return FALSE;

			for(int i=0; i<3; i++)
			{
				if(pInjectes[i] != NULL)
					bSuccess = WriteCodeToMem(hProcess,
					pInjectes[i],
					bSetState);
				else
					break;
			}
hereleave:
			SetFocus(GetParent(hDlg));
			if(bSuccess)
				CheckDlgButton(hDlg, ctrlID, bSetState);
			return TRUE;
		}
	case WM_GRAYCONTROLES:
		{
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK1), lParam);
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK2), lParam);
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK3), lParam);
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK4), lParam);
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK5), lParam);
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK6), lParam);
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK7), lParam);
			EnableWindow(GetDlgItem(hDlg,IDC_CHECK8), lParam);
			if(lParam == FALSE)
			{
				CheckDlgButton(hDlg, IDC_CHECK1, BST_UNCHECKED);
				CheckDlgButton(hDlg, IDC_CHECK2, BST_UNCHECKED);
				CheckDlgButton(hDlg, IDC_CHECK3, BST_UNCHECKED);
				CheckDlgButton(hDlg, IDC_CHECK4, BST_UNCHECKED);
				CheckDlgButton(hDlg, IDC_CHECK5, BST_UNCHECKED);
				CheckDlgButton(hDlg, IDC_CHECK6, BST_UNCHECKED);
				CheckDlgButton(hDlg, IDC_CHECK7, BST_UNCHECKED);
				CheckDlgButton(hDlg, IDC_CHECK8, BST_UNCHECKED);
			}
			return TRUE;
		}
	case WM_INITDIALOG:
		{
			AutoCollect.dwBaseAddr = 0x44c5f1;
			AutoCollect.dwSize = 1;
			AutoCollect.sbNewCode[0] = 0x1;

			Nondecrease.dwBaseAddr = 0x433f86;
			Nondecrease.dwSize = 6;
			memset(&Nondecrease.sbNewCode, 0x90, 6);

			DoubleSun_1.dwBaseAddr = 0x44ba22;
			DoubleSun_1.dwSize = 1;
			DoubleSun_1.sbNewCode[0] = 0x32;

			DoubleSun_2.dwBaseAddr = 0x44ba2e;
			DoubleSun_2.dwSize = 1;
			DoubleSun_2.sbNewCode[0] = 0x19;

			DoubleMoney.dwBaseAddr = 0x44ba92;
			DoubleMoney.dwSize = 1;
			DoubleMoney.sbNewCode[0] = 0x2;

			SecKill_1.dwBaseAddr = 0x5671f9;
			SecKill_1.dwSize = 2;
			SecKill_1.sbNewCode[0] = 0xeb;
			SecKill_1.sbNewCode[1] = 0x16;

			SecKill_2.dwBaseAddr = 0x566d07;
			SecKill_2.dwSize = 3;
			SecKill_2.sbNewCode[0] = 0xf6;
			SecKill_2.sbNewCode[1] = 0x90;
			SecKill_2.sbNewCode[2] = 0x90;

			UnlockSlot_1.dwBaseAddr = 0x43470f;
			UnlockSlot_1.dwSize = 2;
			UnlockSlot_1.sbNewCode[0] = 0xEB;
			UnlockSlot_1.sbNewCode[1] = 0x15;

			UnlockSlot_2.dwBaseAddr = 0x434726;
			UnlockSlot_2.dwSize = 8;
			*(LONGLONG*)UnlockSlot_2.sbNewCode = 0xE9EB0AB0027C0A3C;

			SendMessage(hDlg, WM_GRAYCONTROLES,0,(LPARAM)g_bWndActive?TRUE:FALSE);
			return TRUE;
		}



	}
	return FALSE;
}


HWND FindDestWnd()
{
	HWND h = NULL;
	TCHAR* szDestWndNames[] = 
	{
		{L"Plants vs. Zombies 1.2.0.1073 RELEASE"},
		{L"植物大战僵尸中文版"},
		{L"植物大战僵尸"},
		{L"PlantsVsZombies"}
	};

	for(int i=0; i<sizeof(szDestWndNames)/sizeof(TCHAR*); i++)
	{
		h = FindWindow(NULL, szDestWndNames[i]);
		if(NULL != h)
			break;
	}
	return h;
}

DWORD GetPIDFromeWnd()
{
	DWORD id = -1;
	HWND hWnd;
	if( (hWnd = FindDestWnd()) == NULL)
		return -1;
	GetWindowThreadProcessId(hWnd,&id);
	return id;
}



HANDLE OpenProcessWithDbg(DWORD PID)
{
	HANDLE hProcess;
	hProcess = OpenProcess(PROCESS_ALL_ACCESS,FALSE,PID);
	if(hProcess == NULL)
		return NULL;
	if(!EnableDebugPrivilege(hProcess))
	{
		MessageBox(0, L"提升权限失败!", L"错误提示", 0);
		CloseHandle(hProcess);
		return NULL;
	}
	return hProcess;
}


/***********************************
************************************
************************************/
BOOL IsDestPID(DWORD PID)
{
	TCHAR szProcessName[MAX_PATH];
	TCHAR szDestName[] = L"PlantsVsZombies.exe";
	HANDLE hProc = OpenProcess(PROCESS_QUERY_INFORMATION |PROCESS_VM_READ,FALSE,PID);
	if(hProc == NULL)
		return FALSE;

	HMODULE hMod;
	DWORD cbNeeded;

	if ( !EnumProcessModules( hProc, &hMod, sizeof(hMod),&cbNeeded ))
		goto Exit;


	if(GetModuleBaseName( hProc, hMod, szProcessName,sizeof(szProcessName)/sizeof(TCHAR)) ==0)
		goto Exit;


	if(_wcsicmp(szProcessName, szDestName) == 0)
	{
		CloseHandle(hProc);
		return TRUE;
	}

Exit:
	CloseHandle(hProc);
	return FALSE;
}


DWORD GetPIDFromeProcesses(LPCTSTR lpWndName)
{
	DWORD aProcesses[1024],cbNeeded, cProcesses;
	UINT  i;
	DWORD pid;

	EnumProcesses(aProcesses, sizeof(aProcesses),&cbNeeded);

	cProcesses = cbNeeded / sizeof(DWORD);
	for ( i = 0; i < cProcesses; i++ )
	{
		if( aProcesses[i] != 0 )
		{
			if(IsDestPID(aProcesses[i]))
			{
				pid = aProcesses[i];
				return pid;
			}
		}
	}
	return -1;
}

 

/*************************************/
//InjectCode.cpp
//
/***********************************/
#pragma once

#define BUF_LEN 20  //缓存大小

#define GOODS_COUNT 53   //物品的数目

#define GOODS_ATTR_PRICE 1 //物品价格属性标记
#define GOODS_ATTR_TIME 2  //物品冷却时间属性标记

#include <windows.h>

//物品属性
typedef struct _GOODS_ATTRIBUTE
{
	DWORD type;  //物品种类
	DWORD unknown2;
	DWORD unknown3;
	DWORD unknown4;
	DWORD price;   //价格
	DWORD coolingTime;  //冷却时间
	DWORD unknown7;
	DWORD unknown8;
	DWORD unknown9;
}GOODS_ATTRIBUTE,*PGOODS_ATTRIBUTE;

//保存物品属性
typedef struct _GOODS_BACKUP
{
	DWORD price;
	DWORD time;
}GOODS_BACKUP,*PGOODS_BACKUP;


typedef struct _tagINJECT_BLOCK
{
	DWORD	dwBaseAddr;  //注入基址
	DWORD   dwSize;      //注入字节数
	DWORD   dwOldProtect;  
	BYTE	sbNewCode[BUF_LEN];  //要注入的代码
	BYTE	sbOldCode[BUF_LEN];  //保存原来的代码
}INJECT_BLOCK,*PINJECT_BLOCK;


BOOL WriteCodeToMem(HANDLE hProcess,
					PINJECT_BLOCK pInjectBlock, 
					BOOL writeNew);

BOOL WriteGoodsAttrToMem(HANDLE hProcess,
						 DWORD AttrBitMark, 
						 PGOODS_BACKUP pBackup,
						 BOOL writeNew);

 

/*************************************/
//InjectCode.cpp
//
/***********************************/

#include "InjectCode.h"


BOOL WriteCodeToMem(HANDLE hProcess,
					PINJECT_BLOCK pInjectBlock,
					BOOL writeNew)
{
	BOOL bRtn = FALSE;

	bRtn = VirtualProtectEx(hProcess,
		(void*)pInjectBlock->dwBaseAddr,
		pInjectBlock->dwSize,
		PAGE_READWRITE,
		&pInjectBlock->dwOldProtect);

	if(!bRtn)
		return FALSE;

	if(writeNew)
	{
		bRtn = ReadProcessMemory(hProcess,
			(void*)pInjectBlock->dwBaseAddr,
			pInjectBlock->sbOldCode,
			pInjectBlock->dwSize,
			0);
		if(!bRtn)
			return FALSE;

		bRtn = WriteProcessMemory(hProcess,
			(void*)pInjectBlock->dwBaseAddr,
			pInjectBlock->sbNewCode,
			pInjectBlock->dwSize,
			0);
		if(!bRtn)
			return FALSE;
	}
	else
	{
		bRtn = WriteProcessMemory(hProcess,
			(void*)pInjectBlock->dwBaseAddr,
			pInjectBlock->sbOldCode,
			pInjectBlock->dwSize,
			NULL);
		if(!bRtn)
			return FALSE;
	}

	bRtn = VirtualProtectEx(hProcess,
		(void*)pInjectBlock->dwBaseAddr,
		pInjectBlock->dwSize,
		pInjectBlock->dwOldProtect,
		&pInjectBlock->dwOldProtect);
	if(!bRtn)
		return FALSE;
	return bRtn;
}


BOOL WriteGoodsAttrToMem(HANDLE hProcess,
						 DWORD AttrBitMark, 
						 PGOODS_BACKUP pBackup,
						 BOOL writeNew)
{
	const DWORD dwGoodsBase = 0x76c600;

	BOOL  bRtn = FALSE;
	DWORD dwInject = 0;
	DWORD dwProtect;
	DWORD dwPriceAddr, dwTimeAddr; 
	DWORD dwGoodsAddr = dwGoodsBase;
	

	bRtn = VirtualProtectEx(hProcess,
		(void*)dwGoodsAddr,
		sizeof(GOODS_ATTRIBUTE)*GOODS_COUNT,
		PAGE_READWRITE,
		&dwProtect);

	if(!bRtn)
		return FALSE;
	for(int i=0; i<GOODS_COUNT; i++)
	{
		dwPriceAddr = dwGoodsAddr+ 16;
		dwTimeAddr = dwGoodsAddr +20;

		if(writeNew)
		{
			if(GOODS_ATTR_PRICE ==(AttrBitMark & GOODS_ATTR_PRICE))
			{
				bRtn = ReadProcessMemory(hProcess,
					(void*)dwPriceAddr,
					(LPVOID)&pBackup->price,
					4,0);
				if(!bRtn)
					return FALSE;

				bRtn = WriteProcessMemory(hProcess,
					(void*)dwPriceAddr,
					(void*)&dwInject,
					4,0);
				if(!bRtn)
					return FALSE;
			}

			if(GOODS_ATTR_TIME ==(AttrBitMark & GOODS_ATTR_TIME))
			{
				bRtn = ReadProcessMemory(hProcess,
					(void*)dwTimeAddr,
					(LPVOID)&pBackup->time,
					4,0);
				if(!bRtn)
					return FALSE;
				bRtn = WriteProcessMemory(hProcess,
					(void*)dwTimeAddr,
					(void*)&dwInject,
					4,0);
				if(!bRtn)
					return FALSE;
			}

		}
		else
		{
			if(GOODS_ATTR_PRICE ==(AttrBitMark & GOODS_ATTR_PRICE))
			{
				bRtn = WriteProcessMemory(hProcess,
					(void*)dwPriceAddr,
					(void*)&pBackup->price,
					4,0);
				if(!bRtn)
					return FALSE;
			}

			if(GOODS_ATTR_TIME ==(AttrBitMark & GOODS_ATTR_TIME))
			{
				bRtn = WriteProcessMemory(hProcess,
					(void*)dwTimeAddr,
					(void*)&pBackup->time,
					4,0);
				if(!bRtn)
					return FALSE;
			}
		}


		dwGoodsAddr += sizeof(GOODS_ATTRIBUTE);
		++pBackup;
	}

	bRtn = VirtualProtectEx(hProcess,
		(void*)dwGoodsBase,
		sizeof(GOODS_ATTRIBUTE),
		dwProtect,
		&dwProtect);
	if(!bRtn)
		return FALSE;

	return bRtn;
}

 

 

转载自原文链接, 如需删除请联系管理员。

原文链接:植物大战僵尸v1.2---外挂源码,转载请注明来源!

0