当前位置:网站首页>[buuctf.reverse] 151_[FlareOn6]DnsChess

[buuctf.reverse] 151_[FlareOn6]DnsChess

2022-07-04 20:14:00 石氏是时试

这个题下来有三个附件 

ChessUI 这个应该是主程序,但逻辑不在这里头,因为后边还有链接库

ChessAI.so 这应该才是主要处理函数,里边函数很少,只有getNextMove有用

capture.pcap是与服务器的流量抓的包,先把抓的包复制出来就是这样

No.	Time	Source	Destination	Protocol	Length	Data	Info
1	0.000000	192.168.122.1	192.168.122.29	DNS	122		Standard query 0xabfd A rook-c3-c6.game-of-thrones.flare-on.com OPT
2	0.001078	192.168.122.29	192.168.122.1	DNS	188		Standard query response 0xabfd A rook-c3-c6.game-of-thrones.flare-on.com A 127.150.96.223 NS ns1.game-of-thrones.flare-on.com A 127.0.0.1 OPT
3	1.022791	192.168.122.1	192.168.122.29	DNS	124		Standard query 0x6dc5 A knight-g1-f3.game-of-thrones.flare-on.com OPT
4	1.023794	192.168.122.29	192.168.122.1	DNS	190		Standard query response 0x6dc5 A knight-g1-f3.game-of-thrones.flare-on.com A 127.252.212.90 NS ns1.game-of-thrones.flare-on.com A 127.0.0.1 OPT
5	2.046579	192.168.122.1	192.168.122.29	DNS	122		Standard query 0xa3e4 A pawn-c2-c4.game-of-thrones.flare-on.com OPT
6	2.048882	192.168.122.29	192.168.122.1	DNS	188		Standard query response 0xa3e4 A pawn-c2-c4.game-of-thrones.flare-on.com A 127.215.177.38 NS ns1.game-of-thrones.flare-on.com A 127.0.0.1 OPT

返回包里有请求的名字和IP地址

再看getNextMove()

__int64 __fastcall getNextMove(int a1, const char *a2, unsigned int a3, unsigned int a4, __int64 a5)
{
  struct hostent *v9; // [rsp+20h] [rbp-60h]
  char *v10; // [rsp+28h] [rbp-58h]
  char dest[72]; // [rsp+30h] [rbp-50h] BYREF
  unsigned __int64 v12; // [rsp+78h] [rbp-8h]

  v12 = __readfsqword(0x28u);
  strcpy(dest, a2);                             // 子
  get_place_name(dest, a3);                     // -c3
  get_place_name(dest, a4);                     // -c6
  strcat(dest, ".game-of-thrones.flare-on.com");// .xxxx
  v9 = gethostbyname(dest);                     // 返回信息
  if ( !v9 )
    return 2LL;
  v10 = *v9->h_addr_list;
  if ( *v10 != 127 || (v10[3] & 1) != 0 || a1 != (v10[2] & 0xF) )// IP地址末位为1的报错  3位低4位是序号
    return 2LL;
  sleep(1u);
  byte_4060[2 * a1] = v10[1] ^ qword_2020[2 * a1];// IP第2段是key异或,第3段为序号,每次两字节与byte_2020异或
  byte_4060[2 * a1 + 1] = v10[1] ^ qword_2020[2 * a1 + 1];
  *(_DWORD *)a5 = (unsigned __int8)v10[2] >> 4;
  *(_DWORD *)(a5 + 4) = (unsigned __int8)v10[3] >> 1;
  strcpy((char *)(a5 + 8), off_4120[a1]);
  return (unsigned __int8)v10[3] >> 7;
}

一开始将IP地址分段放到数组v10里,当第1段是不是127的返回,这应该是对数据包进行过滤的语句,跟flag无关的项在这里过滤掉

if ( *v10 != 127 || (v10[3] & 1) != 0 || a1 != (v10[2] & 0xF) )// IP地址末位为1的报错  3位低4位是序号
    return 2LL;

v10[3]&1 != 0 这也是一同过滤的,过滤后数据还剩15个包。

而a1是带入的参数,这里并不知道a1是多少,但是根据名字猜的话应该是包的序号。进函数后对包内容和序号进行核对。

而下边两句应该就是处理flag了,a1是序号的话,每次处理两字节,密文是bytes_2020,密钥是IP地址的第2个段

byte_4060[2 * a1] = v10[1] ^ qword_2020[2 * a1];// IP第2段是key异或,第3段为序号,每次两字节与byte_2020异或
  byte_4060[2 * a1 + 1] = v10[1] ^ qword_2020[2 * a1 + 1];

通过这个写程序处理

<?php
$str = file_get_contents("capture.txt");
preg_match_all("|response (0x[0-9a-f]{1,6}) A ([0-9a-z\-]{10,20}).game-of-thrones.flare-on.com A ([0-9]+)\.([0-9]+)\.([0-9]+)\.([0-9]+) NS ns1.game-of-thrones.flare-on.com|iUms", $str, $arg);
#print_r($arg);
$unk_2020 =[0x79,0x5A,0xB8,0xBC,0xEC,0xD3,0xDF,0xDD,0x99,0xA5,0xB6,0xAC,0x15,0x36,0x85,0x8D,0x09,0x08,0x77,0x52,0x4D,0x71,0x54,0x7D,0xA7,0xA7,0x08,0x16,0xFD,0xD7];

$b = [];
foreach($arg[1] as $i=>$v){
	if ($arg[3][$i] != 127 || $arg[6][$i]&1 !=0)continue;
	$a =  $arg[5][$i]&0xf;
	$key = $arg[4][$i];
	$b[$a] = chr($unk_2020[2*$a]^$key ).chr($unk_2020[2*$a+1]^$key);
	echo "$a,".$arg[2][$i]."\r\n";
}
ksort($b);
$flag = "";
foreach($b as $v)$flag .=$v;
print_r($b);
print($flag);
// LooksLikeYouLockedUpTheLookupZ
// flag{[email protected]}
?>

原网站

版权声明
本文为[石氏是时试]所创,转载请带上原文链接,感谢
https://blog.csdn.net/weixin_52640415/article/details/125596284