본문 바로가기

WarGame & Conference/_Webhacking.kr

webhacking.kr 39번 문제

webhacking.kr 39번 문제를 클릭하면 다음과 같은 페이지가 뜬다.


아무글자나 입력해서 쿼리를 전송해보니까

Warning: mysql_fetch_array(): supplied argument is not a valid MySQL result resource in /www/webhacking_kr/challenge/bonus/bonus-10/index.php on line 18

위와 같은 경고가 뜬다. mysql_fetch_array()를 호출할때 사용한 쿼리가 틀려서

18번째 라인에서 에러가 났다는 뜻이다.

소스보기로 왜 에러가 발생했는지 살펴보자.


오류에 대한 원인은 없고 다만,

<!-- index.phps --> 라고 주석이 달려있다. 해당 주소로 이동해보자.
(http://webhacking.kr/challenge/bonus/bonus-10/index.phps)



다음과 같은 소스가 보여진다.

<html>
<head>
<title>Chellenge 39</title>
</head>
<body>

<?

$pw
="????"
;

if(
$_POST[id
])
{
$_POST[id]=str_replace("\\","",$_POST[id
]);
$_POST[id]=str_replace("'","''",$_POST[id
]);
$_POST[id]=substr($_POST[id],0,15
);
$q=mysql_fetch_array(mysql_query("select 'good' from zmail_member where id='$_POST[id]"
));

if(
$q[0]=="good") die("Password is $pw"
);

}

?>

<form method=post action=index.php>
<input type=text name=id maxlength=15 size=30>
<input type=submit>
</form>
</body>
</html>



소스를 분석해보자.

Warning: mysql_fetch_array(): 에러가 뜨는 mysql_fetch_array() 호출문인

$q=mysql_fetch_array(mysql_query("select 'good' from zmail_member where id='$_POST[id]"));

자세히 살펴보면 id = '$_POST[id]  에서 싱글쿼터가 닫혀 있지 않다.

따라서 에러가 발생하는 것이다.!!!


이제 에러 부분을 찾았고 $_POST[id] 에 대한걸 더 분석해보면

<input type=text name=id maxlength=15 size=30> // 15글자를 입력받는 id 라는 텍스트 폼을 만든다

이 폼에 입력을 하게되며


$_POST[id]=str_replace("\\","",$_POST[id]);
$_POST[id]=str_replace("'","''",$_POST[id
]);
$_POST[id]=substr($_POST[id],0,15
);

위의 세가지 과정을 거쳐 쿼리로 전송된다.


str_repleace 는 문자열에서 지정한 문자를 다른문자로 바꾸겠다는 뜻이다.

즉, 첫문장 $_POST[id]=str_replace("\\","",$_POST[id]); 에서

우리가 입력한 역슬래시(\) 가 없어지게 된다.

$_POST[id]=str_replace("'","''",$_POST[id]); 에서는

싱글쿼터( ' )가 더블쿼터( '' )로 바뀌게 된다.


substr() 함수는 입력한 지정된 문자열에서 지정한 부분만을 가져오는 함수이다.

따라서, $_POST[id]=substr($_POST[id],0,15);

위 두문장을 통해 변형된 $_POST[id] 값중에서 0번 인덱스부터 15개의 문자를 가져온다.


이제 어떻게 쿼리를 보내야 할지 생각을 해보자.

일단 아무값이나 입력한다 쳐도 마지막에 싱글쿼터로 꼭 닫아줘야 한다.

즉, admin'   이런식으로 쿼리가 전송되야 에러가 발생하지 않을것이다.

그런데 싱글쿼터(')를 입력해도 str_repleace 를 통하여 더블쿼터('')로 바뀌게 된다.

따라서 특문처리인 \' 이렇게 입력을 하려고 해도 \ 는 없어지기에 이방법도 실패한다.


해답은 substr에 의해 15글자만 가져온다는 것에 있다.

즉 홀수의 글자를 가져오기에 '' 에서 하나가 잘라져 나가 ' 로 보낼수 있는것이다.

14글자를 채운뒤 ' 쿼터를 입력하면 '' 쿼터로 변한다 16글자.

이중 0번 인덱스부터 15 문자를 가져오기에

마지막 쿼터 하나가 잘라져 나가 --------------' 이런식으로 완성이 될것이다.


따라서 admin         '  이렇게 쿼리를 전송한다면 admin         '' 으로 변한뒤

0번 인덱스부터 15글자를 가져와서 최종 쿼리는 admin'  이 될것이다.

문제가 풀려서 Password 값이 나오는 것을 확인할수 있다.

'WarGame & Conference > _Webhacking.kr' 카테고리의 다른 글

webhacking.kr 17번 문제  (1) 2010.07.17
webhacking.kr 16번 문제  (0) 2010.07.17
webhacking.kr 14번 문제  (0) 2010.07.05
webhacking.kr(Oldzombie) 가입문제  (9) 2010.03.12