.NET 7 的 AOT 到底能不能杠反编译?

一:背景

1.讲故事

在B站,公众号上发了一篇 AOT 的文章后,没想到反响还是挺大的,都称赞这个东西能抗反编译,可以让破解难度极大提高,可能有很多朋友对逆向不了解,以为用 ILSpy,Reflector,DnSpy 这些工具打不开就觉得很安全,其实不然,在 OllyDbg,IDA,WinDBG 这些逆向工具面前一样是裸奔。

既然大家都很感兴趣,那这篇就和大家聊一聊。

二:几个例子

1. 动态修改程序数据

修改程序数据在逆向中再正常不过了,由于目前的 AOT 只能发布成 x64 ,这里就用 WinDbg 做下演示,首先看下例子。

internal class Program{static void Main(string[] args){while (true){Console.WriteLine("hello world!");Thread.Sleep(1000);}}}
6965caf284287d1046835b183011858f.png

程序在不断的输出,接下来我们将 hello world 中的 world 给去掉,操作手法非常简单,先内存搜索找到 hello world,然后修改 length=5 即可。

0:005> lm
start             end                 module name
00007ff7`95b70000 00007ff7`95e5d000   ConsoleApp1 C (private pdb symbols)  0:005> s-u 00007ff7`95b70000 L?0x00007ff7`95e5d000 hello
00007ff7`95e1c41c  0068 0065 006c 006c 006f 0020 0077 006f  h.e.l.l.o. .w.o.0:000> dp 00007ff795e1c41c-0x4 L1
00007ff7`95e1c418  00650068`0000000c0:000> eq 00007ff7`95e1c418 00650068`00000005
0:000> g
d5dcc3fa56d01075d340523285745223.png

2. 获取程序托管堆

AOT 再怎么牛,它终还是个托管程序,既然是托管程序自然就有托管堆,托管堆中就有所有的托管数据,玩过 SOS.dll 朋友应该知道,用 !eeheap -gc 就能把托管堆给显示出来,比如下面这样。

0:022> !eeheap -gc
Number of GC Heaps: 1
generation 0 starts at 0x000002414D891030
generation 1 starts at 0x000002414D891018
generation 2 starts at 0x000002414D891000
ephemeral segment allocation context: nonesegment             begin         allocated         committed    allocated size    committed size
000002414D890000  000002414D891000  000002414D8D1FE8  000002414D8D2000  0x40fe8(266216)  0x41000(266240)
Large object heap starts at 0x000002415D891000segment             begin         allocated         committed    allocated size    committed size
000002415D890000  000002415D891000  000002415D891018  000002415D892000  0x18(24)  0x1000(4096)
Pinned object heap starts at 0x0000024165891000
0000024165890000  0000024165891000  0000024165899C10  00000241658A2000  0x8c10(35856)  0x11000(69632)
Total Allocated Size:              Size: 0x49c10 (302096) bytes.
Total Committed Size:              Size: 0x42000 (270336) bytes.
------------------------------
GC Allocated Heap Size:    Size: 0x49c10 (302096) bytes.
GC Committed Heap Size:    Size: 0x42000 (270336) bytes.

虽然目前的 AOT 不支持 SOS 扩展,无法显示出托管堆,但一点关系都没有,SOS 是通过 DataAccess 去挖的,大不来我手工挖一下就好了哈,接下来就是怎么挖的问题了,熟悉 CLR 的朋友应该知道所谓的托管堆在内部用的是 generation_table[] 一维数据来维护的,以 的方式来划分,代的落地是用 heap_segment 来表示的, 参考代码如下:

generation gc_heap::generation_table [total_generation_count];enum gc_generation_num
{// small object heap includes generations [0-2], which are "generations" in the general sense.soh_gen0 = 0,soh_gen1 = 1,soh_gen2 = 2,max_generation = soh_gen2,// large object heap, technically not a generation, but it is convenient to represent it as suchloh_generation = 3,// pinned heap, a separate generation for the same reasons as lohpoh_generation = 4,uoh_start_generation = loh_generation,// number of ephemeral generationsephemeral_generation_count = max_generation,// number of all generationstotal_generation_count = poh_generation + 1
};

接下来用 x 命令看下数组内容,代码如下:

0:000> x ConsoleApp1!WKS::gc_heap::generation_table
00007ff7`95e25010 ConsoleApp1!WKS::gc_heap::generation_table = class WKS::generation [5]0:000> dx -r1 (*((ConsoleApp1!WKS::generation (*)[5])0x7ff795e25010))
(*((ConsoleApp1!WKS::generation (*)[5])0x7ff795e25010))                 [Type: WKS::generation [5]][0]              [Type: WKS::generation]...[4]              [Type: WKS::generation]0:000> dx -r1 (*((ConsoleApp1!WKS::generation *)0x7ff795e25010))
(*((ConsoleApp1!WKS::generation *)0x7ff795e25010))                 [Type: WKS::generation][+0x038] start_segment    : 0x25100000000 [Type: WKS::heap_segment *][+0x040] allocation_start : 0x25100001030 : 0x38 [Type: unsigned char *][+0x048] allocation_segment : 0x25100000000 [Type: WKS::heap_segment *][+0x0d0] allocation_size  : 0x0 [Type: unsigned __int64][+0x100] gen_num          : 0 [Type: int]...0:000> dx -r1 ((ConsoleApp1!WKS::heap_segment *)0x25100000000)
((ConsoleApp1!WKS::heap_segment *)0x25100000000)                 : 0x25100000000 [Type: WKS::heap_segment *][+0x000] allocated        : 0x25100001048 : 0x90 [Type: unsigned char *][+0x008] committed        : 0x25100012000 : Unable to read memory at Address 0x25100012000 [Type: unsigned char *][+0x010] reserved         : 0x25110000000 : 0x18 [Type: unsigned char *][+0x018] used             : 0x25100009fe0 : 0x0 [Type: unsigned char *][+0x020] mem              : 0x25100001000 : 0x38 [Type: unsigned char *][+0x028] flags            : 0x0 [Type: unsigned __int64][+0x030] next             : 0x0 [Type: WKS::heap_segment *]...

上面的这些字段就描述出了 !eeheap -gc 的结果,接下来想挖什么,提取什么我就不过多介绍了。

3. 提取托管线程列表

提取 托管线程 列表也是非常重要的, 它能指示出很多信息,一般用 !t 命令就能显示,输出如下:

0:022> !t
ThreadCount:      17
UnstartedThread:  0
BackgroundThread: 6
PendingThread:    0
DeadThread:       0
Hosted Runtime:   noLock  DBG   ID     OSID ThreadOBJ           State GC Mode     GC Alloc Context                  Domain           Count Apt Exception0    1     4128 000002414BDB8C70    2a020 Preemptive  000002414D8C6108:000002414D8C8000 000002414bdaf8f0 -00001 MTA 6    2     4458 000002414BDE5EB0    2b220 Preemptive  0000000000000000:0000000000000000 000002414bdaf8f0 -00001 MTA (Finalizer) 7    4     23e8 000002416DDB15C0  102b220 Preemptive  000002414D8C9250:000002414D8CA000 000002414bdaf8f0 -00001 MTA (Threadpool Worker) ...20   17     50a8 000002416DE43DD0  102b220 Preemptive  000002414D8BC2D0:000002414D8BDFD0 000002414bdaf8f0 -00001 MTA (Threadpool Worker) 21   18     57d4 000002416DE628E0  8029220 Preemptive  000002414D8CC2A8:000002414D8CE000 000002414bdaf8f0 -00001 MTA (Threadpool Completion Port)

既然目前的 SOS 不支持,同样可以手工到 CLR 中去挖,熟悉的朋友应该知道 !t 的数据源来自于 ThreadStore::s_pThreadStore 下的 m_ThreadList 集合,它以链表的形式串联了每个线程的 LinkPtr 字段,但可惜的是,在 AOT 中,这一块已经重写了,由 g_pTheRuntimeInstance 全局变量下的 m_ThreadList 来维护了。

为了方便观察,多生成几个 Thread。

static void Main(string[] args){Debugger.Break();var tasks = Enumerable.Range(0, 10).Select(m => new Thread(() =>{Console.WriteLine($"tid={Thread.CurrentThread.ManagedThreadId} 已执行!");Console.ReadLine();}));foreach (var item in tasks){item.Start();}Console.ReadLine();}

程序跑起来后,深挖 g_pTheRuntimeInstance 全局变量即可。

0:015> x ConsoleApp1!g_pTheRuntimeInstance
00007ff7`0155ee20 ConsoleApp1!g_pTheRuntimeInstance = 0x00000291`cb5b9300
0:015> dx -r1 ((ConsoleApp1!RuntimeInstance *)0x291cb5b9300)
((ConsoleApp1!RuntimeInstance *)0x291cb5b9300)                 : 0x291cb5b9300 [Type: RuntimeInstance *][+0x000] m_pThreadStore   : 0x291cb5b9390 [Type: ThreadStore *]...
0:015> dx -r1 ((ConsoleApp1!ThreadStore *)0x291cb5b9390)
((ConsoleApp1!ThreadStore *)0x291cb5b9390)                 : 0x291cb5b9390 [Type: ThreadStore *][+0x000] m_ThreadList     [Type: SList<Thread,DefaultSListTraits<Thread,DoNothingFailFastPolicy> >][+0x008] m_pRuntimeInstance : 0x291cb5b9300 [Type: RuntimeInstance *][+0x010] m_Lock           [Type: ReaderWriterLock]
0:015> dx -r1 (*((ConsoleApp1!SList<Thread,DefaultSListTraits<Thread,DoNothingFailFastPolicy> > *)0x291cb5b9390))
(*((ConsoleApp1!SList<Thread,DefaultSListTraits<Thread,DoNothingFailFastPolicy> > *)0x291cb5b9390))                 [Type: SList<Thread,DefaultSListTraits<Thread,DoNothingFailFastPolicy> >][+0x000] m_pHead          : 0x291ed366240 [Type: Thread *]
0:015> dx -r1 ((ConsoleApp1!Thread *)0x291ed366240)
((ConsoleApp1!Thread *)0x291ed366240)                 : 0x291ed366240 [Type: Thread *]...[+0x058] m_pNext          : 0x291cb6aeb60 [Type: Thread *][+0x060] m_hPalThread     : 0x204 [Type: void *][+0x068] m_ppvHijackedReturnAddressLocation : 0x0 [Type: void * *][+0x070] m_pvHijackedReturnAddress : 0x0 [Type: void *][+0x078] m_uHijackedReturnValueFlags : 0x0 [Type: unsigned __int64][+0x080] m_pExInfoStackHead : 0x0 [Type: ExInfo *][+0x088] m_threadAbortException : 0x0 [Type: Object *][+0x090] m_pThreadLocalModuleStatics : 0x291cb6aee90 [Type: void * *][+0x098] m_numThreadLocalModuleStatics : 0x1 [Type: unsigned int][+0x0a0] m_pGCFrameRegistrations : 0x0 [Type: GCFrameRegistration *][+0x0a8] m_pStackLow      : 0xf754100000 [Type: void *][+0x0b0] m_pStackHigh     : 0xf754200000 [Type: void *][+0x0b8] m_pTEB           : 0xf7533ba000 : 0x0 [Type: unsigned char *][+0x0c0] m_uPalThreadIdForLogging : 0x2044 [Type: unsigned __int64][+0x0c8] m_threadId       [Type: EEThreadId][+0x0d0] m_pThreadStressLog : 0x0 [Type: void *][+0x0d8] m_interruptedContext : 0x0 [Type: _CONTEXT *][+0x0e0] m_redirectionContextBuffer : 0x0 [Type: unsigned char *]
0:015> dx -r1 (*((ConsoleApp1!EEThreadId *)0x291ed366308))
(*((ConsoleApp1!EEThreadId *)0x291ed366308))                 [Type: EEThreadId][+0x000] m_uiId           : 0x2044 [Type: unsigned __int64]

从CLR 的 Thread 维护的信息来看,这个结构体已经很小了,也说明 AOT 在Thread信息维护上做了很多的精简。

三:总结

总的来说,AOT 确实能加速程序的初始启动,一体化的打包机制也非常方便部署,但怎么变终究还是一个托管程序,需要底层的 C++ 托着它,扛 反编译 无从谈起,所以防小人的话,该加壳的加壳,该混淆的混淆。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/281015.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

google hdr+_更好的隐私权控制使Google+死了

google hdrEarlier this year, Google started a project to review third-party developer access to Google accounts through the use of APIs. It found a security breach surrounding Google, and is now shutting the service down, at least for consumers. 今年年初&a…

新0-Day漏洞或将给Linux桌面发行版带来浩劫

Linux 的各个发行版都一直强调安全及其相关元素&#xff0c;比如防火墙、渗透测试、沙盒、无痕上网和隐私等等&#xff0c;但事实上可能并没有想象中的那么安全。安全研究员 Chris Evans 公开了其发现的针对 Linux 桌面发行版的 0day 漏洞&#xff0c;利用特制的音频文件入侵 L…

一份详尽的利用 Kubeadm部署 Kubernetes 1.13.1 集群指北

2019独角兽企业重金招聘Python工程师标准>>> 概 述 Kubernetes集群的搭建方法其实有多种&#xff0c;比如我在之前的文章《利用K8S技术栈打造个人私有云&#xff08;连载之&#xff1a;K8S集群搭建&#xff09;》中使用的就是二进制的安装方法。虽然这种方法有利于我…

.NET性能优化-使用内存+磁盘混合缓存

我们回顾一下上一篇文章中的内容&#xff0c;有一个朋友问我这样一个问题&#xff1a;我的业务依赖一些数据&#xff0c;因为数据库访问慢&#xff0c;我把它放在 Redis 里面&#xff0c;不过还是太慢了&#xff0c;有什么其它的方案吗&#xff1f;其实这个问题比较简单的是吧&…

最小生成树详解

注&#xff1a;本文算法使用链式前向星数据结构实现。学习链接&#xff1a;链式前向星-学习笔记 一、Prim算法 普通prim算法模板&#xff1a; //用前向星录数据的时候记得把head初始化为-1 fill(dist,distLEN,MAX); memset(vis,0,sizeof vis); int ans0; dist[1]0; //如…

dropbox文件_Dropbox即将发布的扩展程序更新将添加更多文件编辑支持,包括Pixlr照片...

dropbox文件Dropbox is perhaps the best-known cloud storage platform for consumers, but it’s hoping to become something more. With an upcoming overhaul to its user tools, Dropbox will add more complex editing tools, in addition to what it already provides …

黑客窃取思科、IBM与甲骨文认证管理系统内的敏感数据

目前一套被思科、F5、IBM以及甲骨文等企业所广泛使用的认证管理系统(即Credential Manager System)正面临着数据泄露风险&#xff0c;其中的敏感数据也许已经被黑客们所获取。 根据Pearson VUE(主营计算机测试方案开发与交付)发布的一项公告&#xff0c;某恶意软件已经藏身于该…

Spring下载地址

下载地址&#xff1a;https://repo.spring.io/libs-release-local/org/springframework/spring/ 进入后可选择下载版本&#xff0c;选择版本后&#xff0c;进入目录结构。其中dist是最终发布版本&#xff0c;包含开发所需lib和源码。docs是开发文档。schema是一些约束文件。 Do…

.NET7发布,一大批优秀.NET6项目没人看了吗...(都是好项目)

恍惚间都已经.NET7.0了&#xff0c;不能再呆在旧版本了&#xff01;这里分享一套Vue3 Axios TS Vite Element Plus .NET 6 WebAPI JWT SqlSugar的通用管理后台&#xff0c;各种最新框架组件&#xff0c;学习必备&#xff01;这里把源码、脚本以及专门录制的视频教程都打…

Python的日志记录-logging模块的使用

一、日志 1.1什么是日志 日志是跟踪软件运行时所发生的事件的一种方法&#xff0c;软件开发者在代码中调用日志函数&#xff0c;表明发生了特定的事件&#xff0c;事件由描述性消息描述&#xff0c;同时还包含事件的重要性&#xff0c;重要性也称为级别或严重性。 1.2何时使用日…

询问HTG:白噪声屏幕保护程序,有效的文件命名以及从密码泄露中恢复

Once a week we share three of the questions we’ve answered from the Ask HTG inbox with the greater readership; this week we’re looking at white noise screen savers, efficient file naming systems, and recovering from a password compromise. 每周一次&#…

专家预测第二波WannaCry勒索病毒攻击即将到来!

WannaCry的传播脚步今晨戛然而止 今天一大早&#xff0c;全网的WannaCry蠕虫病毒攻击突然减弱消退了!所有这一切功劳来自于英国研究人员malwaretech&#xff0c;他通过逆向发现WannaCry代码中有一个特殊域名地址&#xff1a; www.iuqerfsodp9ifjaposdfjhgosurijfaewrwergwea.co…

01.HTML基础命令笔记

目录 HTML结构 body内常用标签 常用 div与span img a标签 超链接标签 其他格式标签 列表 表格 表单 select标签 label标签 textarea多行文本 HTML结构 <!DOCTYPE html> <html lang"zh-CN"> <head><meta charset"UTF-8"&…

ios numlock_从“提示”框:默认情况下启用NumLock,无广告的iOS应用和立体声供电的派对灯...

ios numlockOnce a week we round up some of the great tips readers have sent into the tip box. This week we’re looking at how to enable the NumLock by default, stripping ads from iOS apps, and turning Christmas lights into audio-responsive party lights. 每…

Windows 7 自动更新失败导致无法进系统解决方案

故障现象&#xff1a;自动更新后&#xff0c;重启电脑&#xff0c;提示&#xff1a;&#xff08;配置Windows update 失败 还原更改 请勿关闭计算机&#xff09;&#xff0c; 而计算机一直停留该界面&#xff0c;如果半个小时以上都无反应。此时&#xff0c;就不要再继续等待了…

PaperWeekly 第28期 | 图像语义分割之特征整合和结构预测

“ 余昌黔 华中科技大学硕士 研究方向为图像语义分割 知乎专栏 https://zhuanlan.zhihu.com/semantic-segmentation 前言 近来阅读了 PASCAL VOC 2012 排行榜上前几的文章&#xff0c;包括 PSPNet 和林国省老师的几篇论文&#xff0c;觉得现在在 semantic segmentation 领域对于…

02.CSS基础笔记及导入

CSS是什么 CSS&#xff08;Cascading Style Sheet&#xff0c;层叠样式表)定义如何显示HTML元素。 当浏览器读到一个样式表&#xff0c;它就会按照这个样式表来对文档进行格式化&#xff08;渲染&#xff09;。 CSS样式 CSS引入HTML 内部样式与外部样式 <!DOCTYPE> …

如何还原桌面图标_如何为Windows 10桌面图标还原或更改文本的默认外观?

如何还原桌面图标For whatever reason, sooner or later we all have someone or something mess around with our keyboards and create ‘interesting’ results. With that in mind, today’s SuperUser Q&A post has a simple and elegant way to help a frustrated re…

「前端早读君007」css进阶之彻底理解视觉格式化模型

今日励志 不论你在什么时候开始&#xff0c;重要的是开始之后不要停止。 前言 对于部分前端工程师来讲&#xff0c;有时候CSS令他们很头疼&#xff0c;明明设置了某个样式&#xff0c;但是布局就是不起作用。 如果你也有这种问题&#xff0c;那么是时候学习下什么是css视觉格式…

.NET周报【11月第3期 2022-11-22】

国内文章.NET Conf China 2022 第一批讲师阵容大揭秘&#xff01;整个期待了&#xff01;https://mp.weixin.qq.com/s/4p89hhBPw6qv-0OB_T_TOg目光看过来 2022 年 12 月 3-4 日&#xff0c;一场社区性质的国内规模最大的 线上线下.NET Conf 2022 技术大会 即将盛大开幕。目前大…