• [极客大挑战 2019]BuyFlag 1(两种解法)


    题目环境:
    image.png
    image.png
    image.png

    FLAG NEED YOUR 100000000 MONEY
    flag需要你的100000000元

    F12瞅瞅源代码:
    image.png

    if (isset($_POST['password']))
     {   
    $password = $_POST['password'];   
    if (is_numeric($password)) 
    {   
    echo "password can't be number"
    }
    elseif ($password == 404)
     {  
     echo "Password Right!
      		} 
     	 } 
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12

    PHP代码审计:

    两个通过POST方式传参的参数password和money
    isset函数判断参数是否存在以及值是否为空,存在及不为空则返回TRUE
    is_numeric() 函数用于检测变量是否为数字或数字字符串;这里需要注意数字字符串的意思就是字面意思通过数字组成的字符串,比如:“123456789”
    如果是数字或者是数字字符串就会输出"password can’t be number"
    如果password是404则密码就是正确的

    当password是404的时候虽然满足了第二个elseif语句但是不满足第一个if语句
    因为404是数字和数字字符串
    想要满足第一个简单,让password成为普通字符串就可以,404a、404b、404c、404%10、404,%20、404%30等等
    这样第二个条件也顺便满足了,为什么呢?(在比较的时候把值转换成了数字字符串)
    "=="是PHP弱比较逻辑运算符

    PHP弱比较:

    PHP中的弱比较(Weak comparison)是一种比较两个值是否相等的方法,但它不会对两个值进行严格的全等比较。相反,它允许某些类型的值在比较时进行自动类型转换。
    弱比较使用以下规则:

    1. 如果两个值都是布尔值,则它们被认为是相等的,只要它们都是 true 或 false。
    2. 如果两个值都是整数或浮点数,则它们被认为是相等的,只要它们的值相等。
    3. 如果两个值都是字符串,则它们被认为是相等的,只要它们的长度和字符序列相同。
    4. 如果两个值是数组或对象,则它们被认为是相等的,只要它们具有相同的结构(键和值)和相同的顺序。
    5. 如果两个值是 null,则它们被认为是相等的。
    6. 对于其他类型的值,弱比较使用 PHP 的 == 操作符进行比较。

    传参并使用burpsuite进行抓包
    password=404a&money=100000000
    image.png

    先通过火狐浏览器插件Max HackBar进行POST传参,再抓包,这样数据包就是POST传参方式,如果直接在数据包里面把GET方式传参改为POST方式传参的话,可能依旧是GET方式传参,这点需要注意。

    image.png
    鼠标右键Repeater->Send进行重放
    image.png
    image.png

    仅学生用户可以购买FLAG
    注意Cookie:user=0
    user是用户,0通常代表flase(错误),1通常代表true(正确)
    咱们将user修改为1使后台程序可以正常运行

    修改user=1
    继续Send进行重放
    image.png

    用户和密码都绕过了
    Nember lenth is too long
    你的数字太长了
    到这里想到了使用科学计数法绕过
    1e9代表1的后面有9个0 => 1000000000 > 100000000 (要大于题目要求的money值!)
    既满足了条件,数字长度也不长

    使用科学计数法绕过money:
    password=404a&money=1e9
    image.png
    当money=1时
    image.png

    you have not enough money,loser
    你没有足够的钱

    经过给money参数分情况测试,有3种输出结果

    • 当 money => 100000000
      • 输出"Nember lenth is too long"
    • 当 money < 100000000
      • 输出"you have not enough money,loser"
    • 当 1e9 <= money <= 1e999999(说着当money变为数组时)
      • 输出"flag值"

    猜测用到了函数strcmp()用来比较两个字符串,同时还可以比较两个字符串的字符数

    strcmp(string1,string2)

    • 0 - 如果两个字符串相等
    • <0 - 如果 string1 小于 string2
    • 0 - 如果 string1 大于 string2

    所以当过滤不当不全时,可以通过将参数变为数组的方式进行绕过,这样的话就无法比较,直接返回true

    这里大胆猜测他的后台源码:

    
    $flag=100000000;
    $Flag='flag{0c531ed2-9c1e-479a-adcb-d975b1376ca6}'
    if (isset($_POST['money'])) {       
    	if (strcmp($_POST['money'],$flag) == 0)#比较money和flag的值和字符数,"=="PHP弱比较逻辑运算符           
    		echo $Flag;       
      elseif(strcmp($_POST['money'],$flag) < 0)           
    		print 'you have not enough money,loser';
      else
        print 'Nember lenth is too long';
    }
    ?>
    
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12

    通过数组绕过money:
    password=404a&mony[]=0
    image.png

    中途我2023版Burp里面的Repeater消失不见了,这里问下师傅们,现在不知道怎么回事,所以我又用2021版本Kali做题了,苦涩

    得到flag:
    flag{cb3acdc3-dcda-49d0-9597-b7247f9c6ff0}

  • 相关阅读:
    Linux检查Docker镜像,容器的磁盘空间
    RUST 每日一省:模式匹配
    滚珠螺杆的螺母朝向反了能用吗?
    Java 全栈体系(四)
    数字时代的新一代数据安全
    记阿里云mysql丢表丢数据的实践记录
    用户中心系统开发--表设计以及表说明
    鸿鹄工程项目管理系统 Spring Cloud+Spring Boot+Mybatis+Vue+ElementUI+前后端分离构建工程项目管理系统项目背景
    常用sql函数
    【王道】计算机组成原理第六章总线(六)
  • 原文地址:https://blog.csdn.net/m0_73734159/article/details/134339328