首页
社区
课程
招聘
[原创]win10 1909逆向(APIC中断和实验--1、初始化)
发表于: 2022-8-21 20:23 13733

[原创]win10 1909逆向(APIC中断和实验--1、初始化)

2022-8-21 20:23
13733

         

          逆它纯粹就是无聊,后面想想以后中断虚拟化应该能用到,由于工作项目时间很紧,勉强断断续续逆向了一部分加自己做些实验来验证,目前先将这部分分享出来,带和我一样的新手入个门,建议先看下面推荐的三本书里的APIC章节,文章下面关于基础知识的介绍,来自网络各个大佬的笔墨,小弟就搬抄过来,省去自己写的麻烦事,建议先看书,文章纯粹是辅助(王者荣耀里的孙膑,顶多给你加加速),以下的步骤就是APIC的初始化流程,对了,AMD和INTEL内部实现会有部分区别,我的是INTEL的,AMD就将就看看吧,区别不大。


         参考书籍:《Intel手册》、《x86/x64体系探索及编程》、《一个64位操作系统的设计与实现》

          



       APIC (Advanced Programmable Interrupt Controller)是90年代Intel为了应对将来的多核趋势提出的一整套中断处理方案,用于取代老旧的8259A PIC。这套方案适用于多核(Multi-Processor)机器,每个CPU拥有一个Local APIC,整个机器拥有一个或多个IOAPIC,设备的中断信号先经由IOAPIC汇总,再分发给一个或多个CPU的Local APIC。为了配合APIC,还推出了MPSpec (Multiprocessor Specification),为BIOS向OS提供中断配置信息的方式提供了规范。

       自90年代以来,PCI总线发展出了MSI (Message Signalled Interrupt),目前的机器中是以MSI为主要的中断机制,IOAPIC作为辅助,但CPU处仍使用Local APIC接收和处理中断。当时提出的MPSpec经过演化目前已成为了ACPI规范的一部分,BIOS可以通过ACPI表向OS报告中断配置情况(e.g. IOAPIC的引脚连接到哪个设备)。

       初代奔腾(Pentium)上初次引入Local APIC时,它是外置的Intel 82489DX芯片。在一些奔腾型号以及P6 family(即从奔腾Pro到奔腾3)上则将其改为了内置,但功能保持不变。自奔腾4及至强(Xeon)开始取消了APIC Bus以及一部分相关设置,于是改称xAPIC,目前Intel CPU的默认模式就是xAPIC。后来又增加了x2APIC模式作为xAPIC的扩展。

       通过上面【BIOS可以通过ACPI表向OS报告中断配置情况】这段话,我们知道windows内核是通过ACPI表知道中断硬件的配置情况。

       没办法,简单介绍一下啥是ACPI,简单来说:就是固件(BIOS/UEFI)向系统传递硬件架构信息的机制。

       那传递哪些硬件架构信息了?


      MADT/"APIC":每个处理器的Local APIC信息(包括ID以及NMI等信息)以及系统的I/O APIC信息(包括与8259A相比的板载基础设备的中断重定向信息)

     "HPET":系统的HPET信息

     "MCFG":系统的PCIe的MCFG信息

     "DSDT"、"SSDT":其它信息,包括板载基础设备的配置信息(包括内存、I/O、中断等信息),PCI/PCIe设备在8259A和APIC状态下的中断路由信息,以及 ACPI的一些特定的电源配置信息等

     


      好了,正主来了,MADT(多APIC描述表),它描述了APIC的工作原理,windows通过以下API来得到,内部实现并不复杂,就是通过关键字去查找你需要的是那个硬件配置信息,有兴趣可以自行逆向研究,当然整个ACPI机制还是较为复杂的,有兴趣可以带小弟一起学习。     

      


     pMapic=HalSocGetAcpiTable('CIPA')



不同的版本,有不同的结构体,APICTABLES内部不同,为了方便,我们通过RW来查看

内部各个结构字段的意义,还请各位看官自己动动手BAIDU/GOOGLE吧!


前面的基础介绍里面,介绍了APIC->xAPIC->x2APIC的由来,知道从Apic总线变成了SystemBus,当然变化的不只这一点,CPU的个数变了,更重要的是访问方式也改变了,LAPIC的寄存器是通过MMIO访问的(即xAPIC模式),后来添加的x2APIC模式则通过MSR来访问其寄存器(可以向前兼容),windows需要根据你是哪个模式,采用哪种方式访问,所以用了下面这个API。


status = HalpApicSetupRegisterAccess();


主要实现了


如果是xAPIC:

HalpApicRead=HalpApic1ReadRegister

HalpApicWrite=HalpApic1WriteRegister

HalpApicWriteCommand=HalpApic1WriteIcr

HalpApicWaitForCommand=HalpApic1WaitForIcr

HalpApicEndOfInterrupt=HalpApic1EndOfInterrupt


如果是x2APIC

HalpApicRead=HalpApicX2ReadRegister

HalpApicWrite=HalpApicX2WriteRegister

HalpApicWriteCommand=HalpApicX2WriteCommand

HalpApicWaitForCommand=HalAcquireDisplayOwnership

HalpApicEndOfInterrupt==HalpApicX2EndOfInterrupt




实际上就是生成一个中断控制器对象,然后放进HalpRegisteredInterruptControllers链表里,(不好理解?你就理解类似EPROCESS的创建,后续只要调用APIC的函数,就需要这个对象)


HalpApicRegisterIoUnit(__int64 IoapicPhyAddr, int IoApicId, int GsiBase)


至于这个GsiBase是啥,百度吧,简单介绍一下就是:GSI是ACPI引入的概念,它为系统中每个中断源指定一个唯一的中断号,如果你只是想简单的在windows上了解APIC的工作机制,这个可以不用去深究,如果你想了解windows上APIC的管理,这个你得去深究了,windows把LocalApi和IoApic的引脚弄了一套中断线(INTERRUPT_LINE)的概念,一个Interrupt Line可以管理对应1/多个引脚,对中断控制器进行抽象 ,类似于对象管理器(object/object_header等等),Apic / Gic / Bcm2836ic / pic就是实例,实现很复杂,目前我没有逆完,就不在这里误人子弟了。 



[注意]传递专业知识、拓宽行业人脉——看雪讲师团队等你加入!

最后于 2022-8-21 23:12 被学技术打豆豆编辑 ,原因:
收藏
免费 16
支持
分享
最新回复 (8)
雪    币: 62
活跃值: (662)
能力值: ( LV2,RANK:10 )
在线值:
发帖
回帖
粉丝
2
抛开内容不谈,吃饭的事什么时候安排下。
2022-8-21 20:35
0
雪    币: 1420
活跃值: (2171)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
3
抛开内容不谈,吃饭的事什么时候安排下。
2022-8-21 21:27
0
雪    币: 3738
活跃值: (3872)
能力值: ( LV4,RANK:50 )
在线值:
发帖
回帖
粉丝
4
豆总6b!
2022-8-21 22:15
0
雪    币: 12848
活跃值: (9147)
能力值: ( LV9,RANK:280 )
在线值:
发帖
回帖
粉丝
5
6
2022-8-22 07:21
0
雪    币: 889
活跃值: (4118)
能力值: ( LV6,RANK:98 )
在线值:
发帖
回帖
粉丝
6
dz默契 抛开内容不谈,吃饭的事什么时候安排下。
豆豆说你回来才请我吃饭,所以你啥时候回来
2022-8-22 10:14
0
雪    币: 198
活跃值: (8558)
能力值: ( LV9,RANK:180 )
在线值:
发帖
回帖
粉丝
7
还我六千雪币 豆豆说你回来才请我吃饭,所以你啥时候回来
周六
2022-8-22 13:40
0
雪    币: 1129
活跃值: (2756)
能力值: ( LV3,RANK:20 )
在线值:
发帖
回帖
粉丝
8
感谢分享
2022-8-22 23:14
0
雪    币: 8203
活跃值: (2738)
能力值: ( LV5,RANK:65 )
在线值:
发帖
回帖
粉丝
9
哇咔咔,这不得精华安排
2022-9-1 18:43
0
游客
登录 | 注册 方可回帖
返回
//