Arm 代码执行漏洞利用Cortex M4

Arm 代码执行漏洞利用Cortex M4,arm,exploit,cortex-m,Arm,Exploit,Cortex M,为了测试MPU和利用漏洞,我想从运行在STM32F4开发板上的本地缓冲区执行代码 int main(void) { uint16_t func[] = { 0x0301f103, 0x0301f103, 0x0301f103 }; MPU->CTRL = 0; unsigned int address = (void*)&func+1; asm volatile( "mov r4,%0\n" "ldr pc, [r4]\n" :

为了测试MPU和利用漏洞,我想从运行在STM32F4开发板上的本地缓冲区执行代码

int main(void)
{
  uint16_t func[] = { 0x0301f103, 0x0301f103, 0x0301f103 };
  MPU->CTRL = 0;
  unsigned int address = (void*)&func+1;
  asm volatile(
    "mov r4,%0\n"
    "ldr pc, [r4]\n"
    :    
    : "r"(address)    
  ); 
  while(1);
}
大体上,我是第一个转MPU的。我的指令存储在func中。在ASM部分中,我将thumb的地址0x2001ffe8+1加载到程序计数器寄存器中。当使用GDB单步执行代码时,在R4中存储正确的值,然后将其传输到PC寄存器。但我最终会在硬故障处理程序中结束

编辑: 堆栈如下所示:

0x2001ffe8: 0x0301f103  0x0301f103  0x0301f103  0x2001ffe9
内存中的说明是正确的。Cortex的最终指南说,区域0x20000000–0x3FFFFFFF是SRAM,该区域是可执行的,
因此,您可以在此处复制程序代码并执行它。

您正在为16位数组分配32位值

您的指令不会终止,它们会继续运行到ram中找到的任何内容中,因此会崩溃

您没有将数组的地址加载到程序计数器中您正在将数组中的第一项加载到程序计数器中,这将崩溃,您创建了一个间接级别

查看BX指令,而不是ldr pc

您没有将该数组声明为静态,因此可以将该数组优化为死的和未使用的,因此这可能会导致它崩溃

编译器还应该抱怨您将void*赋值给无符号变量,因此需要类型转换


作为一种习惯,我建议使用address |=1而不是+=1,在这种情况下,两者都将起作用。

建议使用stdint.h中的intptr\t作为一个整数类型,如果您使用>=C99,则可以保证能够保持指针,而实际上每个人都应该在2018年使用它!而不是无符号整数。