攻防世界 Reverse高手进阶区 2分题 easyre-153

Posted 思源湖的鱼

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了攻防世界 Reverse高手进阶区 2分题 easyre-153相关的知识,希望对你有一定的参考价值。

前言

继续ctf的旅程
攻防世界Reverse高手进阶区的2分题
本篇是easyre-153的writeup

攻防世界的题目分数是动态的
就仅以做题时的分数为准了

解题过程

首先扔入exeinfope中查看信息,发现有upx壳:

扔进kali脱壳:

扔进IDA,F5,如下:

int __cdecl main(int argc, const char **argv, const char **envp)

  int pipedes[2]; // [esp+18h] [ebp-38h] BYREF
  __pid_t v5; // [esp+20h] [ebp-30h]
  int v6; // [esp+24h] [ebp-2Ch] BYREF
  char buf[30]; // [esp+2Eh] [ebp-22h] BYREF
  unsigned int v8; // [esp+4Ch] [ebp-4h]

  v8 = __readgsdword(0x14u);
  pipe(pipedes);
  v5 = fork();
  if ( !v5 )
  
    puts("\\nOMG!!!! I forgot kid's id");
    write(pipedes[1], "69800876143568214356928753", 0x1Du);
    puts("Ready to exit     ");
    exit(0);
  
  read(pipedes[0], buf, 0x1Du);
  __isoc99_scanf("%d", &v6);
  if ( v6 == v5 )
  
    if ( (unsigned __int8)*(_DWORD *)((char *)lol + 3) == 204 )
    
      puts(":D");
      exit(1);
    
    printf("\\nYou got the key\\n ");
    lol(buf);
  
  wait(0);
  return 0;

pipe函数的读元素和写元素如下:

fork函数:

  • 在父进程中返回新创建子进程的进程ID
  • 在子进程中返回0
  • 如果出现错误返回一个负值

然后对forkv5做个判断(是父还是子)

  • 子进程就给管道写入69800876143568214356928753
  • 父进程就读取并复制到缓存buf,然后进行两个判断,显然flag在lol

但是跟踪lol

emmmm
搁这搁这的
感觉不太对

去看了眼汇编

这不是有东西的嘛
看了看问题在于jnz short loc_80486D3永恒跳转了
jnz改为jz,即hex中75改成74

然后lol变为他原本的样子:


这显然是生成flag的逻辑
写成脚本就是了

key="69800876143568214356928753"
flag=""
flag+=chr(2*ord(key[1]))
flag+=chr(ord(key[4])+ord(key[5]))
flag+=chr(ord(key[8])+ord(key[9]))
flag+=chr(2*ord(key[12]))
flag+=chr(ord(key[18])+ord(key[17]))
flag+=chr(ord(key[10])+ord(key[21]))
flag+=chr(ord(key[9])+ord(key[25]))
print(flag)

得到flag:rhelheg
(提交的时候要加上RCTF

结语

汇编中有些小手脚

以上是关于攻防世界 Reverse高手进阶区 2分题 easyre-153的主要内容,如果未能解决你的问题,请参考以下文章

攻防世界 Reverse高手进阶区 2分题 easyre-153

攻防世界 Reverse高手进阶区 2分题 easyre-153

攻防世界 Reverse高手进阶区 2分题 easyre-153

攻防世界 Reverse高手进阶区 2分题 secret-galaxy-300

攻防世界 Reverse高手进阶区 3分题 crackme

攻防世界 Reverse高手进阶区 3分题 梅津美治郎