首页
课程
问答
CTF
社区
招聘
峰会
发现
排行榜
知识库
工具下载
看雪20年
看雪商城
证书查询
登录
注册
首页
社区
课程
招聘
发现
问答
CTF
排行榜
知识库
工具下载
峰会
看雪商城
证书查询
社区
逆向工程
发新帖
3
33
[原创]带你走进我的世界 热注入黑客(一)
发表于: 2026-1-22 23:37
4890
[原创]带你走进我的世界 热注入黑客(一)
略地
2026-1-22 23:37
4890
# 原理 做我的世界这类的外挂其实是最好做的一类 毕竟没有客户端的反作弊 而且源码还全部能看到 所以想做一个好外挂的正真难点其实还是功能的实现 但在这里我就主要讲讲底层一点的内容。 写我的世界外挂和其他外挂的最大不同其实就是系统 我的世界是运行在jvm上的软件 而其他游戏是运行在windows上的 因此我们先要了解几个工具 - JVMTI - JNI JVMTI的作用更多的是JVM的底层调试比如像字节码修改(后续用来hook) JNI的功能就是调用java里面的类 这两个工具的功能是互补的 所以都很重要 ## DLL注入 注入我的世界和注入其他的程序一样 就是写一个dllmain文件具体咋写可以去看微软的文档 这里要注意 在dllmain里面要创建一个新线程去跑我们自己的代码不然会有问题 ```C++ BOOL APIENTRY DllMain(HMODULE hModule, DWORD ul_reason_for_call, LPVOID lpReserved) { lclt::windows::g_hModule = hModule; CloseHandle(CreateThread(nullptr, 0, main, nullptr, 0, nullptr)); return TRUE; } ``` 大概就是这么写 ## 初始化JNI和JVMTI 因为这两个工具是由JVM提供的 因此如果我们想要获取并初始化这两个工具 我们要先获取jvm.dll 这一步很简单 因为我们注入的就是一个jvm所以这个进程里天生就加载了jvm.dll 我们只要获取一下就行了 ```C++ auto jvm_handle = GetModuleHandleA("jvm.dll"); ``` 但是获取到jvm.dll还不够 因为一个程序可以有很多jvm的实例 虽然大多数只有一个jvm 但我们还要获取我们需要的那个jvm 因此在这里我们还要使用到一个函数 JNI_GetCreatedJavaVMs 他的功能就是帮我们做这件事的 ```C++ typedef jint(*t_JNI_GetCreatedJavaVMs)(JavaVM** vmBuf, jsize bufLen, jsize* nVMs); auto o_JNI_GetCreatedJavaVMs = reinterpret_cast<t_JNI_GetCreatedJavaVMs(GetProcAddress(jvm_handle,"JNI_GetCreatedJavaVMs")); o_JNI_GetCreatedJavaVMs(&g_Jvm, 1, nullptr); ``` 然后就能获取到我的世界的jvm了 获取到jvm后就能获取到jni ```C++ g_Jvm->AttachCurrentThread(reinterpret_cast<void**>(&jvmEnv), nullptr) ``` 这段代码就是把之前创建的那个线程也变成jvm的一部分 同时我们也获得了使用jni的权利 也就是我上面的jvmEnv变量 获取jvmti也差不多 ```C++ if (g_Jvm->GetEnv((void**)&jvm::jvmtiEnv, JVMTI_VERSION_1) == JNI_OK) { LOG_INFO("[init] JVMTI environment obtained successfully"); jvmtiCapabilities capabilities{}; capabilities.can_get_bytecodes = 1; if (jvm::jvmtiEnv->AddCapabilities(&capabilities)!=jvmtiError::JVMTI_ERROR_NONE) { LOG_ERROR("[init] add jvmti capabilities failed"); } } ``` 和获取jni最大的不同就是 jvmti要设置它的能力 因为我们要做的我的世界的外挂所以就添加了一个获取字节码的能力 也可以加其他的能力 ## 使用IMGUI(可选) 这里顺带提一嘴怎么使用imgui 我的世界底层使用的opengl渲染所以我们只要使用minhook之类的库hook一下SwapBuffers然后就可以在里面写imgui的代码了 # 步入我的世界和JVM 先给不熟悉java的同学科普一下java里的classloader classloader顾名思义就是类加载器 功能就是用来加载类 这个东西非常重要 你大致可以把它看成C++里的namespace 但还是有很多不同的 具体可以去网上搜 接下来我们会大量的使用jni和我的世界的类交互 没有classloader我们就没办法获取到我的世界定义的class ## JNI简单入门 先看一段代码 ```C++ jclass c_Thread = jvmEnv->FindClass("java/lang/Thread"); jmethodID m_Thread_getAllStackTraces = jvmEnv->GetStaticMethodID(c_Thread, "getAllStackTraces","()Ljava/util/Map;"); jobject obj_stackTracesMap = jvm::jvmEnv->CallStaticObjectMethod(c_Thread, m_Thread_getAllStackTraces); jvm::jvmEnv->DeleteLocalRef(threads); ``` 看懂这四行代码基本上就可以入门JNI了 想要在C++里调用java里的函数 我们首先要找获取要调用的类 也就是第一行干的事 然后我们要在class里获取我们要获取要调用的函数 也就是第二行(注意:通过jvmEnv->FindClass获取的class是一个定义 而不是实例 所以使用这个方法获取的class只能调用其静态函数) 有人可能会问 ()Ljava/util/Map; 是什么意思 这个就是用来描述一个java函数定义的表达式 具体规则可以直接问AI非常方便 第三行就是调用我们刚刚获取的函数 最后就是释放我们刚刚获取的class 接下来放一段使用我的世界classloader获取类的函数(网上找来的) ```C++ jclass findclass(const char* clsName, JNIEnv* env) { jclass thread_clazz = env->FindClass("java/lang/Thread"); static jmethodID curthread_mid = env->GetStaticMethodID(thread_clazz, "currentThread", "()Ljava/lang/Thread;"); jobject thread = env->CallStaticObjectMethod(thread_clazz, curthread_mid); jmethodID threadgroup_mid = env->GetMethodID(thread_clazz, "getThreadGroup", "()Ljava/lang/ThreadGroup;"); jclass threadgroup_clazz = env->FindClass("java/lang/ThreadGroup"); jobject threadgroup_obj = env->CallObjectMethod(thread, threadgroup_mid); jmethodID groupactivecount_mid = env->GetMethodID(threadgroup_clazz, "activeCount", "()I"); jfieldID count_fid = env->GetFieldID(threadgroup_clazz, "nthreads", "I"); jint activeCount = env->GetIntField(threadgroup_obj, count_fid); jobjectArray arrayD = env->NewObjectArray(activeCount, thread_clazz, NULL); jmethodID enumerate_mid = env->GetMethodID(threadgroup_clazz, "enumerate", "([Ljava/lang/Thread;)I"); jint enumerate = env->CallIntMethod(threadgroup_obj, enumerate_mid, arrayD); jmethodID mid_getname = env->GetMethodID(thread_clazz, "getName", "()Ljava/lang/String;"); jobject array_elements = env->GetObjectArrayElement(arrayD, 0); jmethodID threadclassloader = env->GetMethodID(thread_clazz, "getContextClassLoader", "()Ljava/lang/ClassLoader;"); if (threadclassloader != 0) { auto class_loader = env->CallObjectMethod(array_elements, threadclassloader); jclass launch_clazz = env->FindClass("net/minecraft/launchwrapper/Launch"); jclass class_loader_class = env->GetObjectClass(class_loader); jmethodID find_class_id = env->GetMethodID(class_loader_class, "findClass", "(Ljava/lang/String;)Ljava/lang/Class;"); env->DeleteLocalRef(launch_clazz); jstring name = env->NewStringUTF(clsName); jclass res = (jclass)env->CallObjectMethod(class_loader, find_class_id, name); env->DeleteLocalRef(name); env->DeleteLocalRef(class_loader_class); env->DeleteLocalRef(array_elements); env->DeleteLocalRef(thread_clazz); env->DeleteLocalRef(thread); env->DeleteLocalRef(threadgroup_clazz); env->DeleteLocalRef(threadgroup_obj); env->DeleteLocalRef(arrayD); return res; } env->DeleteLocalRef(array_elements); env->DeleteLocalRef(thread_clazz); env->DeleteLocalRef(thread); env->DeleteLocalRef(threadgroup_clazz); env->DeleteLocalRef(arrayD); env->DeleteLocalRef(threadgroup_obj); return env->FindClass(clsName); } ``` 这段代码的作用就是通过我的世界的classloader来找我的世界游戏的class 不难看出这段复杂的代码就是翻来覆去的使用我上面那四行代码 ## 混淆和模组加载器 首先我要明确一下 接下来以及上面提到的的classloader都是模组加载器提供的 如果是纯原版是不会有定制的classloader(应该吧?) 上面那个用classloader获取class的函数如果你直接放到程序里用 大概率是可以编译但是运行的时候会出问题 因为我的世界是被混淆过的 虽然我的世界过段时间要取消混淆 但目前绝大多数的版本都是被混淆过的 所以反混淆就诞生了 比较出名的反混淆有yarn和MCP 而上面那段代码的运行就必须在1.7.10FORGE的环境下才能执行 主要是由于这段代码 ```C++ jclass launch_clazz = env->FindClass("net/minecraft/launchwrapper/Launch"); ``` 上面那整一段代码的具体逻辑我就不细讲了 这一行代码在试着用当前线程的classloader寻找net/minecraft/launchwrapper/Launch这个游戏中的类 但这个类只存在于我的世界1.7.10FORGE里面 在往后更新一点的版本里由于FORGE引入了SRG(中间名)因此无法直接寻找到net/minecraft/launchwrapper/Launch这个类 此外Fabric和Forge使用的反混淆也是截然不同 所以上面这个classloader查询class的函数还有改进的空间 接下来的开发想要使用到我的世界的源码 可以是fabric的也可以是forge的 关键看你是给哪个版本写的 # 结尾 写到这里有点累了 还有很多没讲 等到哪天心情不错了再继续写(如果大家喜欢看的话我就尽快更新) 以上的内容都是自己的经验之谈 如果有错误或者更好的方案一定要告诉我
回复或点赞可查看完整内容
传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!!
#系统底层
#其他内容
收藏
・
3
点赞
・
33
打赏
分享
分享到微信
分享到QQ
分享到微博
赞赏记录
参与人
雪币
留言
时间
git_51951meggadf3df
非常支持你的观点!
2026-9-11 06:11
Reverser07
你的分享对大家帮助很大,非常感谢!
2026-9-7 13:27
mb_lthgjpwj
为你点赞!
2026-8-21 08:12
mb_wsoacceo
为你点赞!
2026-8-11 01:27
mb_aimiyfrp
为你点赞!
2026-8-7 07:56
音混不散
感谢你的贡献,论坛因你而更加精彩!
2026-8-3 23:24
hyz111
为你点赞!
2026-7-19 14:10
wx_晨梦
谢谢你的细致分析,受益匪浅!
2026-7-16 05:26
git_43837featherL
感谢你的贡献,论坛因你而更加精彩!
2026-7-9 10:40
智童
感谢你的积极参与,期待更多精彩内容!
2026-6-30 23:50
git_29219delmarocks
你的分享对大家帮助很大,非常感谢!
2026-6-30 21:06
Henglie
你的帖子非常有用,感谢分享!
2026-6-11 19:08
ReGenesis
非常支持你的观点!
2026-5-28 19:15
梧桐生
期待更多优质内容的分享,论坛有你更精彩!
2026-5-25 18:42
DEADC0DE
你的帖子非常有用,感谢分享!
2026-5-25 10:36
wjdidi
你的帖子非常有用,感谢分享!
2026-5-17 23:22
DawnDawnDawn
感谢你的贡献,论坛因你而更加精彩!
2026-5-8 22:15
梦里看花
感谢你分享这么好的资源!
2026-4-29 20:05
PPTV
你的分享对大家帮助很大,非常感谢!
2026-4-27 08:16
mb_kjiivjoh
你的帖子非常有用,感谢分享!
2026-4-27 01:40
npc0vo
这个讨论对我很有帮助,谢谢!
2026-4-25 21:50
Helmet5260
非常支持你的观点!
2026-4-8 20:37
150149
谢谢你的细致分析,受益匪浅!
2026-4-7 22:47
mb_fzxqyeiu
这个讨论对我很有帮助,谢谢!
2026-3-1 19:07
LingMo0412
感谢你分享这么好的资源!
2026-2-8 02:41
mb_xwjfepcv
感谢你的贡献,论坛因你而更加精彩!
2026-2-6 19:58
wx_U_439
你的帖子非常有用,感谢分享!
2026-2-5 13:30
mb_pyiykezf
感谢你的贡献,论坛因你而更加精彩!
2026-2-1 17:48
我的小拇指啊
感谢你的积极参与,期待更多精彩内容!
2026-1-25 16:46
huangyalei
这个讨论对我很有帮助,谢谢!
2026-1-23 21:35
jjjo
感谢你的贡献,论坛因你而更加精彩!
2026-1-23 11:20
fogSea
这个讨论对我很有帮助,谢谢!
2026-1-23 11:02
P_Hac
期待更多优质内容的分享,论坛有你更精彩!
2026-1-23 00:10
查看更多
赞赏
×
1 雪花
5 雪花
10 雪花
20 雪花
50 雪花
80 雪花
100 雪花
150 雪花
200 雪花
支付方式:
微信支付
赞赏留言:
快捷留言
感谢分享~
精品文章~
原创内容~
精彩转帖~
助人为乐~
感谢分享~
最新回复
(
7
)
啊你好哇123
雪 币:
723
能力值:
( LV1,RANK:0 )
在线值:
发帖
0
回帖
362
粉丝
0
关注
私信
啊你好哇123
2
楼
这个只能在本地玩吧? 玩别人服务器都是在服务器上面验证的,功能啥的没效果吧,好像用处不大只能玩单人吧
2026-2-1 22:09
0
小迷糊ddd
雪 币:
268
能力值:
( LV1,RANK:0 )
在线值:
发帖
0
回帖
152
粉丝
0
关注
私信
小迷糊ddd
3
楼
感谢分享,学习一下。
2026-4-6 22:59
0
略地
雪 币:
70
活跃值:
(453)
能力值:
( LV2,RANK:10 )
在线值:
发帖
3
回帖
6
粉丝
1
关注
私信
略地
4
楼
啊你好哇123
这个只能在本地玩吧? 玩别人服务器都是在服务器上面验证的,功能啥的没效果吧,好像用处不大只能玩单人吧
你可以看一下vape的效果 底层都一样
2026-4-8 20:28
0
mb_kjiivjoh
雪 币:
228
能力值:
( LV1,RANK:0 )
在线值:
发帖
0
回帖
1
粉丝
0
关注
私信
mb_kjiivjoh
5
楼
注入布吉岛的话要改一下jnienv的获取方式 可以用inlinehook去hook jvm.dll的JVM_NanoTime
2026-4-27 01:42
0
mb_llakvlta
雪 币:
25
能力值:
( LV1,RANK:0 )
在线值:
发帖
0
回帖
45
粉丝
0
关注
私信
mb_llakvlta
6
楼
666
2026-5-21 13:29
0
温泉划水鱼
雪 币:
84
能力值:
( LV1,RANK:0 )
在线值:
发帖
6
回帖
224
粉丝
28
关注
私信
温泉划水鱼
7
楼
kk
2026-6-11 12:35
0
mb_slilvodq
雪 币:
208
能力值:
( LV1,RANK:0 )
在线值:
发帖
0
回帖
10
粉丝
0
关注
私信
mb_slilvodq
8
楼
1111
2026-6-11 16:28
0
游客
登录
|
注册
方可回帖
回帖
表情
雪币赚取及消费
高级回复
返回
略地
3
发帖
6
回帖
10
RANK
关注
私信
他的文章
[原创]带你走进我的世界 热注入黑客(一)
4890
[原创]金盾播放器研究
1829
[求助] 逆向遇到错误怎么解决
1350
关于我们
联系我们
企业服务
看雪公众号
专注于PC、移动、智能设备安全研究及逆向工程的开发者社区
看原图
赞赏
×
雪币:
+
留言:
快捷留言
为你点赞!
返回
顶部