Dreamhack

[Dreamhack] sql injection bypass WAF 풀이

minnggyuu 2024. 3. 2. 15:14

오랜만에 워게임을 풀어보았다. 

화이트햇 스쿨 준비한다고 전역하고도 마음껏 공부할 시간이 없었다(는 구라고 배그하느라 바빴음)

복학하면 꼭 공부에 올인하겠다는 다짐을 또 해본다. 

 

오늘의 문제는 웹해킹 - 서버 사이드 에 붙어있는 문제인 SQL injection bypass WAF이다. 

 

문제 화면

 

uid를 받고 쿼리에 집어넣고 결과를 출력해 주는 것 같다. 

 

1을 넣으면 1이 나오고, guest를 넣으면 guest가 나온다..(?)

 

소스코드를 보자. 

 

소스코드

 

GET으로 입력값을 받아서 check_WAF라는 함수에 넣어서 union, select 등의 키워드를 필터링한다. 

SQL 파일

 

SQL 파일을 열어보니 user라는 테이블에 여러 uid들이 있고, admin의 upw가 FLAG인 것을 알 수 있다. 

 

어떻게 페이로드를 짤 지 생각해보자

우선, 각종 키워드를 필터링해놨지만, SQL은 대소문자 구별을 하지 않기 때문에 select -> Select 로 하면 우회가 된다. 

SQL은 대소문자 구별 안함

 

공백도 필터링을 해놨는데, 이건 %09 (TAB) 으로 우회가 가능하다. 

 

'%09Union%09Select%09upw%09From%09user%09where%09uid='Admin'#

 

안됨

...

 

왜 500 에러가 났는가

 

UNION 앞의 구문에서 반환되는 column 수와 UNION 뒤의 구문에서 반환되는 column의 수가 달랐기 때문이다. (같아야함)

UNION의 특징 (반환되는 컬럼의 수가 같아야함)

컬럼 몇개?

user라는 테이블에는 idx, uid, upw 컬럼이 총 3개 있다.

 

수정 ㄱㄱ

%27Union%09Select%09null,(Select%09upw%09From%09user%09where%09uid='ADMIN'),null%23 (# -> %23)

 

Q : 왜 select null,(서브쿼리),null 로 함? null,null,서브쿼리 하면 안됨? 굳이 중간에 끼워넣어야 하나

A :

서브쿼리를 마지막에 넣으면 None이 반환됨

안됨.

app.py 코드

app.py 40번째 줄을 보면

result[1] (두번째 값) 을 반환을 반환하게 만들어졌기 때문이다.

 

1,2,3을 모두 select 해 보면 result[1]의 값인 2가 반환되는 모습을 볼 수 있다.

따라서 두 번째에 서브쿼리를 넣으면?