반응형

adm1nkyj (ㄱㅇㅈ) 님이 만드신 문젠데 어휴 어려웠다 ㄹㅇ


이 문제의 소스를 보자.


<?php
    error_reporting
(0);
    
    include(
"./config.php"); // hidden column name
    
include("../lib.php"); // auth_code function

    
mysql_connect("localhost","adm1nkyj","adm1nkyj_pz");
    
mysql_select_db("adm1nkyj");

    
/**********************************************************************************************************************/

    
function rand_string()
    {
        
$string "ABCDEFGHIJKLMNOPQRSTUVWXYZ1234567890abcdefghijklmnopqrstuvwxyz";
        return 
str_shuffle($string);
    }

    function 
reset_flag($count_column$flag_column)
    {
        
$flag rand_string();
        
$query mysql_fetch_array(mysql_query("SELECT $count_column$flag_column FROM findflag_2"));
        if(
$query[$count_column] == 150)
        {
            if(
mysql_query("UPDATE findflag_2 SET $flag_column='{$flag}';"))
            {
                
mysql_query("UPDATE findflag_2 SET $count_column=0;");
                echo 
"reset flag<hr>";
            }
            return 
$flag;
        }
        else
        {
            
mysql_query("UPDATE findflag_2 SET $count_column=($query[$count_column] + 1);");
        }
        return 
$query[$flag_column];
    }

    function 
get_pw($pw_column){
        
$query mysql_fetch_array(mysql_query("select $pw_column from findflag_2 limit 1"));
        return 
$query[$pw_column];
    }

    
/**********************************************************************************************************************/

    
$tmp_flag "";
    
$tmp_pw "";
    
$id $_GET['id'];
    
$pw $_GET['pw'];
    
$flags $_GET['flag'];
    if(isset(
$id))
    {
        if(
preg_match("/information|schema|user/i"$id) || substr_count($id,"(") > 1) exit("no hack");
        if(
preg_match("/information|schema|user/i"$pw) || substr_count($pw,"(") > 1) exit("no hack");
        
$tmp_flag reset_flag($count_column$flag_column);
        
$tmp_pw get_pw($pw_column);
        
$query mysql_fetch_array(mysql_query("SELECT * FROM findflag_2 WHERE $id_column='{$id}' and $pw_column='{$pw}';"));
        if(
$query[$id_column])
        {
            if(isset(
$pw) && isset($flags) && $pw === $tmp_pw && $flags === $tmp_flag)
            {
                echo 
"good job!!<br />FLAG : <b>".auth_code("adm1nkyj")."</b><hr>";
            }
            else
            {
                echo 
"Hello ".$query[$id_column]."<hr>";
            }
        }
    } else {
        
highlight_file(__FILE__);
    }
?>


보면 union 인젝션은 막혀있지 않다. 이걸 이용해서 인젝션을 해야한다고 추측을 했었다.


근데 기존의 union 인젝션은 컬럼명을 알아야지 데이터를 뽑아올 수 있었는데,


이 생각을 깨게 만들어준 문제기도 하다. 해결방법은 아래와 같다


mysql에는 서브쿼리라는 게 존재하고 from에다가 서브쿼리를 써주면 가상테이블이 생성된다.


가상테이블에서 이리저리 굴려서 alias를 해주면 아래와 같은 페이로드가 나오게 된다.


pw=' union select 1,b,3,4,5 from (select 1,2,3,4 b,5 from findflag_2 where 1=2 union select * from findflag_2)x%23


from쪽에 서브쿼리르 써주면 가상테이블의 컬럼명을 alias화 시킬 수 있으며


이 가상테이블을 alias해주고 최종적으로 union에서 뽑아준다. 이값은 플래그 값이고


패스워드는 id에다가 이리저리 굴려서 확인할 수 있으니 해보면 된다.

'Write up > Wargame' 카테고리의 다른 글

[Wargame.kr] All Clear  (0) 2016.09.13
[Wargame.kr] zairo  (0) 2016.09.08
[Wargame.kr] strcmp (550p)  (0) 2016.04.29
[Wargame.kr] Easy_CrackMe (500p)  (0) 2016.04.29
[Wargame.kr] md5 password  (0) 2016.04.29
블로그 이미지

KuroNeko_

KuroNeko

,