[Code audit] PHP Weak Type Summary

0x01 Foreword

php is the world's best language, php own security issues are also web security aspect. Due to its weak built-in functions and characteristics of the type of language for loose handle incoming parameters, it will bring a lot of problems here will be brief.

Weakly typed language does not limit the data type of the variable, the variable assignment can be adapted to other types of variables gives the people, while variable can be converted into any other type of data.

0x02 Basics

php There are two symbols compared with == ===

=== 在进行比较的时候,会先判断两种字符串的类型是否相等,再比较
== 在进行比较的时候,会先将字符串类型转化成相同,再比较

If the comparison string or a numeric string comparison and relate to the digital content, the string is converted into a numerical value according to the comparison and

<?php
var_dump("admin"==0);  //true
var_dump("1admin"==1); //true
var_dump("admin1"==1) //false
var_dump("admin1"==0) //true
var_dump("0e123456"=="0e4456789"); //true 
?>  //上述代码可自行测试
1 观察上述代码,"admin"==0 比较的时候,会将admin转化成数值,强制转化,由于admin是字符串,转化的结果是0自然和0相等
2 "1admin"==1 比较的时候会将1admin转化成数值,结果为1,而“admin1“==1 却等于错误,也就是"admin1"被转化成了0,为什么呢??
3 "0e123456"=="0e456789"相互比较的时候,会将0e这类字符串识别为科学技术法的数字,0的无论多少次方都是零,所以相等
<?php
$test=1 + "10.5"; // $test=11.5(float)
$test=1+"-1.3e3"; //$test=-1299(float)
$test=1+"bob-1.3e3";//$test=1(int)
$test=1+"2admin";//$test=3(int)
$test=1+"admin2";//$test=1(int)
?>

So it explains why "admin1" == 1 => False The

0x03 few of the more common functions

3.1 md5 bypass (Hash relatively defect)

<?php
if (isset($_GET['Username']) && isset($_GET['password'])) {
    $logined = true;
    $Username = $_GET['Username'];
    $password = $_GET['password'];

     if (!ctype_alpha($Username)) {$logined = false;}
     if (!is_numeric($password) ) {$logined = false;}
     if (md5($Username) != md5($password)) {$logined = false;}
     if ($logined){
    echo "successful";
      }else{
           echo "login failed!";
        }
    }
?>

Subject to the effect that you want to enter a string and numeric types, and their md5 values ​​are equal, we can successfully execute the next statement

Introduced a number of md5 is the beginning of a string 0e mentioned above, 0e when comparing it will be regarded as scientific notation, so no matter what is behind 0e, 0, 0, or how much power. md5 ( '240610708') == md5 ( 'QNKCDZO') successfully bypassed!
Examples:

QNKCDZO
0e830400451993494058024219903391

s878926199a
0e545993274517709034328855841020
  
s155964671a
0e342768416822451524974117254469

3.2 json bypass

<?php
if (isset($_POST['message'])) {
    $message = json_decode($_POST['message']);
    $key ="*********";
    if ($message->key == $key) {
        echo "flag";
    } 
    else {
        echo "fail";
    }
 }
 else{
     echo "~~~~";
 }
?>

Json enter a string type, the function of json_decode decrypted into an array, the array is determined whether the key value is equal to a value of $ key, but the value of the $ key we do not know, may be utilized 0 == "admin" about this form live

The final payload message = { "key": 0}

3.3 array_search bypass

<?php
if(!is_array($_GET['test'])){exit();}
$test=$_GET['test'];
for($i=0;$i<count($test);$i++){
    if($test[$i]==="admin"){
        echo "error";
        exit();
    }
    $test[$i]=intval($test[$i]);
}
if(array_search("admin",$test)===0){
    echo "flag";
}
else{
    echo "false";
}
?>

The above is to write a first incoming judgment is not array, then loops through each value in the array, and each value in the array and admin not equal, and each value is converted to type int, then judge whether the incoming array has admin, there are flag is returned

payload test [] = 0 can be bypassed

Here is the official manual of introduction to array_search

mixed array_search ( mixed $needle , array $haystack [, bool $strict = false ] )

$ Needle, $ haystack required, $ strict optional function to determine the value of $ haystack exist $ needle, the presence of the key value of the third argument is returned defaults to false, it will be set to true if strict filtering

<?php
$a=array(0,1);
var_dump(array_search("admin",$a)); // int(0) => 返回键值0
var_dump(array_seach("1admin",$a));  // int(1) ==>返回键值1
?>

array_search function is similar == $ a == "admin" $ a = 0, of course, of course, if the third parameter is true can not be bypassed

3.4 strcmp loopholes to bypass php -v <5.3

<?php
    $password="***************"
     if(isset($_POST['password'])){

        if (strcmp($_POST['password'], $password) == 0) {
            echo "Right!!!login success";n
            exit();
        } else {
            echo "Wrong password..";
        }
?>

strcmp compares two strings, if str1 <str2 Returns <0 if str1 is greater than str2 returns> 0 returns 0 if both are equal

We do not know the value of $ password, the subject of the request strcmp judge accepted value and $ password required equal, strcmp passed the expected type is a string type, if the incoming array is what will happen

We pass password [] = xxx can be bypassed because the function receives the type does not match, an error will occur, but still judged equal

payload: password[]=xxx

3.5 switch bypass

<?php
$a="4admin";
switch ($a) {
    case 1:
        echo "fail1";
        break;
    case 2:
        echo "fail2";
        break;
    case 3:
        echo "fail3";
        break;
    case 4:
        echo "sucess";  //结果输出success;
        break;
    default:
        echo "failall";
        break;
}
?>

This principle is similar to the previous, it not explained in detail

0x04 Reference Links

https://www.jianshu.com/p/90d235d4f745
https://www.cnblogs.com/Mrsm1th/p/6745532.html

Guess you like

Origin www.cnblogs.com/-mo-/p/11646006.html