Skip to content
KitploitKITPLOIT
उपकरणब्लॉग
जमा करें
उपकरणब्लॉग
जमा करें

हैकिंग, पेनटेस्ट और साइबर सुरक्षा उपकरण आपके सुरक्षा शस्त्रागार के लिए!

Kitploit हैकिंग, साइबर सुरक्षा और पेंटेस्टिंग टूल्स की एक निर्देशिका है। कमजोरियों को खोजने, सिस्टम का विश्लेषण करने, परीक्षण को स्वचालित करने और अपनी सुरक्षा को मजबूत करने के लिए नवीनतम प्रोजेक्ट अपडेट खोजें।

··फ़ीड·संपर्क·गोपनीयता·© 2026 Kitploit

टूल निर्देशिका

श्रेणियाँ

सभी श्रेणियाँ देखें
Loading categories
CVE-2021-35042 — CVE-2021-35942 के बारे में एक बुनियादी विश्लेषण। Django में SQL इंजेक्शन। | Kitploit
उपकरण/GitHubGitHub/zer0qs/cve-2021-35042
भेद्यता विश्लेषणशोषणवेब सुरक्षापेपर और शोधलर्निंग और शिक्षा
GitHubzer0qs/cve-2021-35042

CVE-2021-35042

CVE-2021-35942 के बारे में एक बुनियादी विश्लेषण। Django में SQL इंजेक्शन।

रिपॉजिटरी देखें
24 साल पहलेअभी तक समीक्षित नहीं

सबसे लोकप्रिय

सभी देखें →

हमारे समुदाय द्वारा सबसे अधिक उपयोग किए जाने वाले उपकरण खोजें।

सभी उपकरण खोजें

हमारे उपकरणों का संग्रह ब्राउज़ करें

सभी उपकरण देखें →
साझा करें

CVE-2021-35042: Django SQL इंजेक्शन भेद्यता

I. अवलोकन

Django एक ओपन-सोर्स वेब एप्लिकेशन फ्रेमवर्क है, जिसे Python में लिखा गया है और MVC (Model - View - Controller) मॉडल के आधार पर बनाया गया है। प्रारंभ में इसे Lawrence प्रकाशन समूह के स्वामित्व वाली समाचार सामग्री वेबसाइटों, CMS (सामग्री प्रबंधन प्रणाली) सॉफ़्टवेयर के प्रबंधन के लिए बनाया गया था।

Django संस्करण 3.1.x -> 3.1.13 और संस्करण 3.2.x -> 3.2.5 में SQL इंजेक्शन भेद्यता मौजूद है।

इस भेद्यता का कारण यह है कि QuerySet.order_by() पर उपयोगकर्ता-नियंत्रित इनपुट डेटा को फ़िल्टर करने का कार्य SQL इंजेक्शन हमलों से बचाव के लिए पर्याप्त नहीं है। इस भेद्यता का फायदा उठाकर हमलावर अनधिकृत कार्य कर सकते हैं, जिससे संवेदनशील डेटा का रिसाव हो सकता है।

CVE - IDCVE-2021-35042
गंभीरता9.8 - CRITICAL
CWE - IDCWE-89: SQL कमांड में विशेष तत्वों का अनुचित निष्प्रभावीकरण ('SQL इंजेक्शन')
भेद्यता प्रकाशन तिथि1/7/2021
प्रभावित सॉफ़्टवेयर3.1.x < 3.1.13, 3.2.x < 3.2.5
प्रमाणीकरण आवश्यकआवश्यक नहीं

II. विस्तृत अवलोकन

0x01. Django का Model

Django में, डेटाबेस में तालिका बनाना और फ़ील्ड परिभाषित करना models.py फ़ाइल में एक model क्लास घोषित करके किया जाता है। इस उदाहरण में, हम Wolf नामक एक तालिका और name नामक एक फ़ील्ड घोषित करते हैं।

0x02. Django में QuerySet और Order_by()

Django में निर्मित ORM फ्रेमवर्क का उपयोग डेटाबेस के साथ संचालन के लिए किया जाता है, और क्वेरी का परिणाम एक संग्रह होता है, यह संग्रह एक QuerySet है।

order_by(fields) डिफ़ॉल्ट रूप से, order_by() एक QuerySet लौटाता है जिसे Model के Meta में ordering विकल्प में निर्दिष्ट क्रम के अनुसार क्रमबद्ध किया जाता है। हम order_by() विधि का उपयोग करके प्रत्येक क्वेरी में order_by की स्थिति को ओवरराइड कर सकते हैं।

उदाहरण

wolves = Wolf.objects.order_by('-name', 'id')

उपरोक्त क्वेरी का परिणाम name फ़ील्ड के अनुसार घटते क्रम में, फिर id के अनुसार बढ़ते क्रम में क्रमबद्ध किया जाएगा। name फ़ील्ड नाम के आगे ऋण चिह्न इंगित करता है कि परिणाम घटते क्रम में क्रमबद्ध हैं।

निम्न उदाहरण उपयोगकर्ता से प्राप्त फ़ील्ड के अनुसार लौटाए गए परिणाम को क्रमबद्ध करेगा, यदि कोई मान पारित नहीं किया गया है तो id फ़ील्ड के अनुसार क्रमबद्ध किया जाएगा।

परिणाम

संस्करण 3.1 और 3.2 में, Django order_by क्वेरी में तालिका नाम के साथ क्वेरी विधि को संयोजित करने की अनुमति देता है। यह भी इस भेद्यता का मुख्य कारण है।

तालिका नाम पारित करने से हमें सामान्य फ़ील्ड नाम पारित करने के समान परिणाम मिलता है

cve202135042_wolf तालिका का नाम है

सबसे पहले एप्लिकेशन सीधे order_by() फ़ंक्शन को कॉल करता है, order_by() फ़ंक्शन को संसाधित करने वाला कोड यहां परिभाषित है: django/db/models/query.py

order_by() फ़ंक्शन दो कार्य करता है

  1. order_by() द्वारा वर्तमान में कॉल किए जा रहे सभी तरीकों को हटा देता है और डिफ़ॉल्ट पैरामीटर को हटा देता है जब order_by एक अलग मान प्राप्त करता है।
  1. पैरामीटर को order_by में पारित करता है। add_ordering() फ़ंक्शन यह करता है
root@kitploit:~
def add_ordering(self, *ordering):
        """
        Add items from the 'ordering' sequence to the query's "order by"
        clause. These items are either field names (not column names) --
        possibly with a direction prefix ('-' or '?') -- or OrderBy
        expressions.

        If 'ordering' is empty, clear all ordering from the query.
        """
        errors = []
        for item in ordering:
            if isinstance(item, str):
                if '.' in item:
                    warnings.warn(
                        'Passing column raw column aliases to order_by() is '
                        'deprecated. Wrap %r in a RawSQL expression before '
                        'passing it to order_by().' % item,
                        category=RemovedInDjango40Warning,
                        stacklevel=3,
                    )
                    continue
                if item == '?':
                    continue
                if item.startswith('-'):
                    item = item[1:]
                if item in self.annotations:
                    continue
                if self.extra and item in self.extra:
                    continue
                # names_to_path() validates the lookup. A descriptive
                # FieldError will be raise if it's not.
                self.names_to_path(item.split(LOOKUP_SEP), self.model._meta)
            elif not hasattr(item, 'resolve_expression'):
                errors.append(item)
            if getattr(item, 'contains_aggregate', False):
                raise FieldError(
                    'Using an aggregate in order_by() without also including '
                    'it in annotate() is not allowed: %s' % item
                )
        if errors:
            raise FieldError('Invalid order_by arguments: %s' % errors)
        if ordering:
            self.order_by += ordering
        else:
            self.default_ordering = False
            

add_ordering() में पारित पैरामीटर एक सरणी है।

उदाहरण के लिए जब पैरामीटर इस प्रकार पारित किया जाता है: wolves = Wolf.objects.order_by( 'name' , 'id' ) तब, एप्लिकेशन इसे डेटाबेस में निम्नलिखित क्वेरी में परिवर्तित करेगा:

root@kitploit:~
SELECT "cve202135042_wolf"."id", "cve202135042_wolf"."name" FROM "cve202135042_wolf" ORDER BY "cve202135042_wolf"."name" ASC, "cve202135042_wolf"."id" ASC

जब पारित किया जाता है, add_ordering फ़ंक्शन सरणी में प्रत्येक तत्व की जांच करेगा, यदि यह एक string है, तो निम्नलिखित 5 मामलों की जांच की जाएगी:

  1. if '.' in item: यह जांचता है कि क्या यह एक कॉलम नाम वाली क्वेरी है और क्या उस कॉलम में SQL स्टेटमेंट में निर्दिष्ट तालिका नाम है। यदि हाँ, तो एक चेतावनी जारी की जाएगी और continue।
  2. if item == '?': यदि तत्व का मान '?' चिह्न है, तो आउटपुट परिणाम यादृच्छिक रूप से क्रमबद्ध किया जाएगा, continue।
  3. if item.startswith('-'): यदि item '-' वर्ण से शुरू होता है, तो क्वेरी का परिणाम DESC (घटते क्रम) में क्रमबद्ध किया जाएगा।
  4. if item in self.annotations: यह जांचता है कि कोई टिप्पणी है या नहीं, यदि हाँ, तो continue।
  5. if self.extra and item in self.extra: निर्धारित करता है कि कोई अतिरिक्त जोड़ है या नहीं और यदि हाँ तो continue।

5 जांचों के बाद, पैरामीटर को self.names_to_path(item.split(LOOKUP_SEP), self.model._meta) फ़ंक्शन में पारित किया जाता है ताकि यह जांचा जा सके कि यह एक मान्य कॉलम नाम है या नहीं, फिर यदि मान्य है तो उन्हें आगे की प्रक्रिया के लिए Query क्लास के self.ordering में जोड़ा जाएगा।

III. Django में SQL इंजेक्शन भेद्यता का विश्लेषण

0x31. कारण

Django का ORM क्वेरी में डाले गए डेटा को बहुत सख्ती से फ़िल्टर करता है, लेकिन इस बार कोड में किया गया परिवर्तन SQL इंजेक्शन का कारण बना क्योंकि लेखक ने यह धारणा बनाई थी कि यदि कॉलम नाम एक UUID (Universal Unique Identifer) कॉलम है तो order_by क्वेरी निष्पादित नहीं की जा सकती।

अर्थात, यदि पारित डेटा xxx-xxx-xxx-xxx (UUID का प्रारूप) है, तो क्वेरी निष्पादित नहीं की जा सकती।

परिवर्तन से पहले का कोड

root@kitploit:~
# django/db/models/sql/constants.py 
ORDER_PATTERN  =  _lazy_re_compile ( r '\?|[-+]?[.\w]+$' )

# django/db/models/sql/query.py 
def  add_ordering ( self ,  * ordering ): 
        errors  =  [] 
        for  item  in  ordering : 
            if  isinstance ( item ,  str )  and  ORDER_PATTERN . match ( item ): 
                if  '.'  in  item : 
                    warnings . warn ( 
                        'Passing column raw column aliases to order_by() is ' 
                        'deprecated. Wrap %r in a RawSQL expression before '
                        'passing it to order_by().'  %  item , 
                        category = RemovedInDjango40Warning , 
                        stacklevel = 3 , 
                    ) 
            elif  not  hasattr ( item ,  'resolve_expression' ): 
                errors . append ( item ) 
            if  getattr ( item ,  'contains_aggregate' ,  False ): 
                raise  FieldError ( 
                    'Using an aggregate in order_by() without also including ' 
                    'it in annotate() is not allowed: %s ' %  item 
                ) 
        if  errors : 
            raise  FieldError ( 'Invalid order_by arguments: %s '  %  errors ) 
        if  ordering : 
            self . order_by  +=  ordering 
        else : 
            self . default_ordering  =  False

उपरोक्त कोड से, हम देख सकते हैं कि यदि पैरामीटर ? से मेल खाता है या - से शुरू होता है और उसके बाद सामान्य वर्ण या . चिह्न होते हैं, तभी क्वेरी निष्पादित की जाती है।

इसलिए, जब कॉलम नाम एक UUID होता है, तो यह एक अमान्य मान होगा और इसे order_by में नहीं डाला जा सकता। इस प्रोसेसिंग कोड में परिवर्तन स्वीकार कर लिया गया था, इसे निम्नानुसार बदला गया: https://github.com/charettes/django/commit/513948735b799239f3ef8c89397592445e1a0cd5

इसने इनपुट डेटा को सत्यापित करने के लिए self.name_to_path फ़ंक्शन का उपयोग किया।

लेकिन जांच के बाद यदि item में . है, तो इसे तालिका नाम वाली क्वेरी माना जाता है, continue कमांड निष्पादित होता है, जिससे डेटा की वैधता की जांच के लिए self.name_to_path फ़ंक्शन का उपयोग सीधे छोड़ दिया जाता है।

get_order_by फ़ंक्शन में . चिह्न को संसाधित करने वाला कोड इस प्रकार है django/db/models/sql/compiler.py

root@kitploit:~
if  '.'  in  field : 
    table ,  col  =  col . split ( '.' ,  1 ) 
    order_by . append (( 
            OrderBy ( 
                RawSQL ( ' %s . %s '  %  ( 
                self . quote_name_unless_alias ( table ),  col ),  [ ]), 
                descending = descending 
            ),  False )) 
    continue

self.quote_name_unless_alias फ़ंक्शन तालिका नाम को संसाधित करता है, मान्य तालिका नामों को फ़िल्टर करता है और कॉलम नाम फ़िल्टरिंग को छोड़ देता है, इसलिए हम एक SQL इंजेक्शन स्टेटमेंट डाल सकते हैं।

0x32. पैच

वर्तमान Django 4.0 संस्करण में, . चिह्न के साथ तालिका नाम से क्वेरी करना हटा दिया गया है और अब समर्थित नहीं है, पैच संस्करण 3.1 और 3.2 के लिए जारी किया गया था। संस्करण 3.2 -> 3.2.4 और 3.1 -> 3.1.12 प्रभावित हैं। 3.2.x Fixed CVE-2021-35042 -- Prevented SQL injection in QuerySet.o…

3.1.x Fixed CVE-2021-35042 -- Prevented SQL injection in QuerySet.o…

संशोधन बहुत सरल है, पुराने ReGex के साथ डेटा जांच वापस लाई गई है

0x33. समाधान

Django को अप्रभावित संस्करण में अपडेट करें।

IV. डेमो

0x41. वातावरण

Docker & Docker-compose

0x42. सेटअप

  1. git clone https://github.com/WynSon/CVE-2021-35042.git
  2. प्रारंभिक सेटअप के लिए ./setup.sh चलाएँ
  3. sudo docker-compose up --build
  4. sudo docker exec -it cve-2021-35042_web_1 python manage.py makemigrations cve202135042
  5. sudo docker exec -it cve-2021-35042_web_1 python manage.py migrate
  6. नमूना डेटा लोड करने के लिए http://localhost:8000/load_example_data पर जाएँ:
  7. भेद्य पैरामीटर वाला पथ: http://localhost:8000/wolves/ http://localhost:8000/wolves/?order_by=name

स्थापना पूर्ण होने के बाद की स्क्रीन

0x43. शोषण

शर्त: शोषण करने में सक्षम होने के लिए, हमें किसी भी तरह से तालिका का नाम जानना अनिवार्य है :))

स्टेटमेंट इंजेक्ट करते समय, हमें तालिका का नाम जानना होगा तभी हम SQLi स्टेटमेंट निष्पादित कर सकते हैं।

गलत तालिका नाम दर्ज करने पर

सही तालिका नाम दर्ज करने पर, orderby क्वेरी सामान्य रूप से निष्पादित होती है।

इस समय स्टेटमेंट बन जाएगा SELECT "cve202135042_wolf"."id", "cve202135042_wolf"."name" FROM "cve202135042_wolf" ORDER BY ("cve202135042_wolf"."name") ASC

इस समय, हम पिछले order_by स्टेटमेंट को समाप्त कर सकते हैं और शोषण के लिए एक SQL स्टेटमेंट डाल सकते हैं।

SELECT "cve202135042_wolf"."id", "cve202135042_wolf"."name" FROM "cve202135042_wolf" ORDER BY ("cve202135042_wolf"."name"); SELECT * from cve202135042_wolf where id =1; --) ASC

V. संदर्भ

https://www.djangoproject.com/weblog/2021/jul/01/security-releases/ https://xz.aliyun.com/t/9834 https://www.bugxss.com/vulnerability-report/3095.html https://blankheart.top/2022/04/07/cve-2021-35042/ https://itcn.blog/p/1648921763575859.html https://github.com/YouGina/CVE-2021-35042

टूल डाउनलोड करें