[Solved in under 1 hour 7 minutes]
오늘 굉장히 충격 먹은 사실을 알았다.
리얼월드에서는 오라클의 SQL DB가 가장 많다는 사실..
본인 MySQL밖에 할 줄 몰라서 우울해서 풀러왔다.
일단 가보자..

<?php
include "./config.php";
login_chk();
$db = dbconnect();
if(preg_match('/prob|_|\.|\(\)/i', $_GET[id])) exit("No Hack ~_~");
if(preg_match('/prob|_|\.|\(\)/i', $_GET[pw])) exit("No Hack ~_~");
if(preg_match('/\'/',$_GET[id])) exit("HeHe");
if(preg_match('/\'/',$_GET[pw])) exit("HeHe");
$query = "select id from prob_succubus where id='{$_GET[id]}' and pw='{$_GET[pw]}'";
echo "<hr>query : <strong>{$query}</strong><hr><br>";
$result = @mysqli_fetch_array(mysqli_query($db,$query));
if($result['id']) solve("succubus");
highlight_file(__FILE__);
?>
일단 코드를 간단하게 정리하자면 인자는 id,pw 두개 다 받고 DB에 있는 아무거나 로그인만 하면 풀리는 문제다.
되게 필터링 걸려있는게 없다.
근데. 싱글쿼터(')가 필터링에 걸려있다.
정말 별에 별거 다 해봤다 진짜로 그런데 포인트를 알아야한다
뭐든 상관없다 그냥 로그인만해라 = true 로만 만들어라.
query : select id from prob_succubus where id='' and pw=''
이거를 자세히 보자.
아직 잘 안보이나
' and pw='
이렇게 하면 뭔가 많이 본 듯한 느낌이 들지 않나요
백슬레이스(\)를 이용하면 바로뒤의 싱글쿼터가 이스케이프 처리 돼서 저게 SQL에서 문자열로 처리 된다.
즉,id='(\' and pw=)'' 이렇게 되는거다.
그리고 pw값에 한칸 띄어주고 or 1=true' 이렇게 될거고 이거를 주석 처리하면
쿼리에는
id='(\' and pw=)' or 1=true#'
이렇게 들어 갈 것이다 해보자

ㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡ 답 ㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡ
?\&pw= or 1=true%23
ㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡㅡ
문제가 풀린다.
와 진짜 이 문제 전혀 생각하지 못했다.
진짜 싱글쿼터 우회하려고 별에 별거 다 해봤는데 어처구니 없지도 않다 단지 정말 놀라워서 감탄했다 ㅋㅎㅋㅎㅎㅋ
그래도 새로운거 배워서 기분은 좋다!!
LoS(Lord of SQL Injection) Succubus Write-up
이상 보고 끝!