36.x86游戏实战-C++代码实现锁血

免责声明:内容仅供学习参考,请合法利用知识,禁止进行违法犯罪活动!

本次游戏没法给

内容参考于:微尘网络安全

工具下载:

链接:https://pan.baidu.com/s/1rEEJnt85npn7N38Ai0_F2Q?pwd=6tw3

提取码:6tw3

复制这段内容后打开百度网盘手机App,操作更方便哦

上一个内容:35.x86游戏实战-XXX自我秒杀call

上一个内容找到了游戏在哪修改了血量,本次就把涉及的东西(修改血量的函数地址、调用修改血量时的ecx)找一找

ecx的值如下图红框,通过被怪物打触发的断点,这个ecx现在猜测它是人物基址,我们玩家角色数据的基址之前找到了,接下来验证

经过验证,如下图,ecx的值确实是人物基址,0x1AB7CDC这个地址里存的是我们玩家角色的基址(这是之前找到的)

接下来看看eax的值变不变,eax的值没有变,写这次的内容的时候电脑已经关机重开过了,这样地址都没变它就不会变了,然后需要的东西就都找到了,所以接下来写到我们的C++项目里

c++代码

首先添加一个按钮,如下图

然后给按钮更改描述文字

如果工具箱和属性没有,看下图打开工具箱

鼠标右击按钮选属性,就能打开了

然后工具箱打开之后可能什么都没有,这时等待一会或鼠标右击工具箱,选择重置工具箱,就好了

准备工作就完了,然后双击下图红框的按钮

它就会自动创建这个按钮的点击事件处理函数,如下图红框

然后写锁血的代码

首先在下图中MyStrust.h文件里写下图红框的内容(void ChangeBlooad(int v);)

然后鼠标右击然后选择快速操作和重构

然后选择下图红框

然后就会创建好下图红框的代码

然后开始写代码,写下图红框里的内容

然后在MyStrust.cpp文件里修改一下InitMy函数,修改完之后,如下图

然后在更改血量的按钮的点击事件处理函数里写,下图红框的内容,mystruct.My.Blood是人物最大血量,通过把血量设置成最大血量来实现锁血

然后重新生成

重新生成完之后注入到游戏中进行测试,测试可以正常修改血量

MyStrust.h文件的内容:

#pragma once
struct Myself {
	DWORD Blood;// 血量
	FLOAT X; // x坐标
	FLOAT Y; // y坐标
	wchar_t* Name; // 名字
};
class MyStrust
{
public:
	Myself My;
	void InitMy();
	void UseObject(DWORD object);
	void ChangeBlooad(int v);
};

MyStrust.cpp文件的内容:

#include "pch.h"
#include "MyStrust.h"

void MyStrust::InitMy()
{
	//  [[0x1AB7CDC]+0x258] 名字
	/*
		*这个符号表示地址,在c++中被称为指针或指针类型
		int表示4字节数字
		int*就表示指针类型的int
		(int*)0x1AB7CDC;这样表示0x1AB7CDC地址里的内容是4字节的数字
	*/
	int* address = (int*)0x1AB7CDC;
	/*
		取出地址中的值,也就是取出0x1AB7CDC里的内容
		*address这样在左边只写一个*表示取内存地址里的值
		也就是取address它的值,address是0x1AB7CDC,也就是取0x1AB7CDC它的值

	*/
	int addressValue = *address;
	/*
		(*(int*)addressValue)意思是
		把addressValue转成int*,也就是把
		addressValue的值当成内存地址,addressValue的值现在是[0x1AB7CDC]+0x258这个
		现在这个地址里面的值是名字的地址,所以在左边加了一个*让把名字的地址去除了出来
		取出来之后就得到了名字,名字是UNICODE类型,UNICODE又被称为宽字节,宽字节的数据是用两个字节描述一个文字或字母
		在c++里wchar_t类型就是UNICODE
		然后在c++中名字这种数据被称为字符串,如果要用字符串必须用指针类型也就是wchar_t*
		右边加上*让wchar_t变成指针类型的wchar_t,才能在c++中使用字符串

	*/
	this->My.Name = (wchar_t*)(*(int*)(addressValue+0x258));
	// 一般函数名后面是W就表示有UNICODE,也就是要用宽字节
	OutputDebugStringW(this->My.Name);

	//  [[0x1AB7CDC]+0x18C]x坐标
	//  [[0x1AB7CDC]+0x190]y坐标
	/*
		取出地址中的值,也就是取出0x1AB7CDC里的内容
		*address这样在左边只写一个*表示取内存地址里的值
		也就是取address它的值,address是0x1AB7CDC,也就是取0x1AB7CDC它的值

	*/
 
	this->My.X= *(float*)(addressValue + 0x18C);
	this->My.Y = *(float*)(addressValue + 0x190);
	char buf[256] = { 0 };
	// 拼接文字,%f表示拼接一个小数(单浮点数)
	sprintf(buf, "x=%f;y=%f", this->My.X, this->My.Y);
	OutputDebugStringA(buf);

	// [[0x1AB7CDC]+0x36A0]血量
	this->My.Blood = *(int*)(addressValue + 0x36A0);
	// 拼接文字,%d表示拼接一个整数(32位的整数)
	sprintf(buf, "血量 = %d", this->My.Blood);
	OutputDebugStringA(buf);
}

void MyStrust::UseObject(DWORD object)
{
	object += 3; // 背包物品序号
	/*
	  try的作用
		如果
		__asm {
			pushad
			push object
			mov ecx, 0x1A5FB24 // 背包基址
			mov ecx, [ecx]
			mov eax, 0x7B9130 // 使用物品的函数地址
			call eax
			popad
		}
		这个代码运行过程中出现错误了,我不会让游戏崩溃,出现错误之后会执行
		catch (...) {
			OutputDebugStringA("MyStrust::UseObject error");
		}
		这个catch里面的代码,现在也就是执行OutputDebugStringA("MyStrust::UseObject error");这一行
	*/
	try { 
		__asm {
			pushad
			push object
			mov ecx, 0x1A5FB24 // 背包基址
			mov ecx, [ecx]
			mov eax, 0x7B9130 // 使用物品的函数地址
			call eax 
			popad
		}
	}
	catch (...) {
		OutputDebugStringA("MyStrust::UseObject error");
	}
}

void MyStrust::ChangeBlooad(int v)
{
	try {
		__asm {
			pushad
			push 0
			push 0
			push 0
			push v
			mov ecx, 0x1AB7CDC // 里面有我们玩家角色数据的基址
			mov ecx, [ecx]
			mov eax, 0x8174E0 // 使用物品的函数地址
			call eax
			popad
		}
	}
	catch (...) {
		OutputDebugStringA("MyStrust::ChangeBlooad error");
	}
}

DXXDlg.cpp文件的内容:

// DXXDlg.cpp: 实现文件
//

#include "pch.h"
#include "WCDXX.h"
#include "afxdialogex.h"
#include "DXXDlg.h"
#include "MyStrust.h"

// DXXDlg 对话框

IMPLEMENT_DYNAMIC(DXXDlg, CDialogEx)

DXXDlg::DXXDlg(CWnd* pParent /*=nullptr*/)
	: CDialogEx(IDD_DIALOG1, pParent)
{
	OutputDebugStringA("执行流程-执行DXXDlg构造函数流程1");
}

DXXDlg::~DXXDlg()
{
	OutputDebugStringA("执行流程-执行DXXDlg析构函数流程1");
}

void DXXDlg::DoDataExchange(CDataExchange* pDX)
{
	CDialogEx::DoDataExchange(pDX);
}


BEGIN_MESSAGE_MAP(DXXDlg, CDialogEx)
	ON_BN_CLICKED(IDC_BUTTON1, &DXXDlg::OnBnClickedButton1)
	ON_BN_CLICKED(IDC_BUTTON2, &DXXDlg::OnBnClickedButton2)
	ON_BN_CLICKED(IDC_BUTTON3, &DXXDlg::OnBnClickedButton3)
	ON_BN_CLICKED(IDC_BUTTON4, &DXXDlg::OnBnClickedButton4)
END_MESSAGE_MAP()


// DXXDlg 消息处理程序


void DXXDlg::OnBnClickedButton1()
{
	MyStrust mystruct;
	mystruct.InitMy();
}


void DXXDlg::OnBnClickedButton2()
{

}


void DXXDlg::OnBnClickedButton3()
{
	
}


void DXXDlg::OnBnClickedButton4()
{
	MyStrust mystruct;
	mystruct.InitMy(); // 初始化玩家角色数据
	mystruct.ChangeBlooad(mystruct.My.Blood/2); // 修改血量
	
	// TODO: 在此添加控件通知处理程序代码
}

上方的代码不全,只有手写的代码

完整代码:以 32.x86游戏实战-使用物品call 它的代码为基础进行修改

链接:https://pan.baidu.com/s/1W-JpUcGOWbSJmMdmtMzYZg?pwd=q9n5

提取码:q9n5

复制这段内容后打开百度网盘手机App,操作更方便哦


img

  • 24
    点赞
  • 10
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。 经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。 经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。 经导师精心指导并认可、获 98 分的毕业设计项目!【项目资源】:微信小程序。【项目说明】:聚焦计算机相关专业毕设及实战操练,可作课程设计与期末大作业,含全部源码,能直用于毕设,经严格调试,运行有保障!【项目服务】:有任何使用上的问题,欢迎随时与博主沟通,博主会及时解答。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值