Monday, August 30, 2010
Rails 3 HTML Encodes by Default
<%= h(@unsafe_user_input) %>
In Rails 3, the default is to automatically HTML encode. The "h" tag is no longer necessary. Instead, developers must go out of their way to output HTML content to the page using the "raw" tag. For example:
<%= raw(@unsafe_user_input) %>
I think the Rails developers took a really strong stance on this issue and it will result in a safer Ruby on Rails ecosystem.
Please see the video below for more details:
http://rubyonrails.org/screencasts/rails3/xss-ujs
There is also a really great Rails security guide found here:
http://guides.rubyonrails.org/security.html
Wednesday, February 24, 2010
Reducing Information Disclosure in WCF Data Services
Reference WCF Service
We will use the following WCF service as a starting point.
Here is a successful SOAP request.
The WCF Help Page and WSDL are accessible as shown below.
The following two errors occur when parameters are omitted in the web service call or when we try to divide by zero.
ASP.NET Custom Errors: No Help At All
Unlike ASP.NET web services, exception handling in WCF data services is not the least bit affected by enabling custom errors. When custom errors are enabled, full stack traces, local file paths, and other information is returned to the consumer.
Explicit Try/Catch Blocks: 100% Effective, But What If You Miss One
Try/Catch blocks are just as effective as in ASP.NET Web Services. Here's the code.
And the result.
As stated in the ASP.NET Web Services article, there is always a chance that we could miss a try/catch block. We need some sort of backup solution to catch any exceptions that we miss.
includeExceptionDetailInFaults="false": A Great Backup to Try/Catch Blocks
In WCF Data Services, this functionality seems more complete and it is just as easy to implement as in the last article. Simply set the "includeExceptionDetailInFaults" attribute to "false" in the "serviceDebug" XML element of the Web.config file.
Stack traces and other detailed error information are now suppressed.
Removing the WSDL and WCF Help Pages
Help pages and the WSDL can easily be removed for WCF services. The "serviceMetadata" and "serviceDebug" XML elements in the Web.config file have attributes to specifically control these items.
When the appropriate attributes are set to "false", the help page and the WSDL show up as blank pages.
Once this change has been made, it will be necessary to communicate WSDLs or web service signatures with partners through some other channel.
WCF Metadata Exchange (MEX)
There is one additional issue to address with WCF Data Services, and that is to disable the Metadata Exchange (MEX) endpoint. Clients and attackers can query MEX endpoints to learn about web service signatures and configuration. For more information about MEX, see the following articles:
An example HTTP request and response used to query a MEX endpoint is shown below.
Additionally, an attacker can utilize the WCF Test Client to capture this data and query the service.
This behavior can be disabled by removing the MEX end-point. In the Web.Config file below, the end-point is commented out.
After the configuration change, the MEX endpoint is no longer accessible.
Wednesday, February 10, 2010
Reducing Information Disclosure in ASP.NET Web Services
Many applications use external web services to allow partners, WPF/Silverlight applications, cloud components, or other entities to access information and functionality. Trusted parties can use SOAP, REST, or AJAX requests to communicate with ASP.NET Web Service end-points.
Since standard protocols are used to connect with these components, malicious users can also issue requests to your web services. In some cases, web services provide detailed information regarding the method calls and parameters available, as well as detailed error messages for failed attacks. It's important to reduce the amount of information provided to attackers by ASP.NET web services.
Reference Web Service
First, let's start with a basic ASP.NET Web Service. The code is provided below.
This web service accepts a dividend and a divisor and it returns the quotient. Since this is a simple demonstration, the code does not include any functionality or data that an attacker would likely target, but the concepts that are demonstrated still apply.
If we run this application and visit the Math.asmx page, a description page is displayed. The description page lists all the web service methods, parameters, and even provides example SOAP requests for calling the methods. Since I am accessing the service locally, it also provides an HTML form to test the functionality. Depending on the settings in the Web.Config file, this form may or may not be available to external users.
In addition to the description page, the WSDL document is also accessible.
A client can call this service using a SOAP or REST request, as shown below.
By default, the application displays detailed error messages. Two example exceptions are shown below. The first exception is due to a divide by zero condition; the second is due to missing parameter values in the SOAP request.
ASP.NET Custom Errors: 80% Effective
ASP.NET applications have a Custom Error Handler that can be used to control the detail level of error messages provided to clients. It is very easy to configure the Custom Error Handler in the Web.Config file. See the "customErrors" XML element in the screenshot below.
After enabling Custom Error Handling, the error messages for the divide by zero condition shows much less detail. We have eliminated the stack trace information; however the title of the error is still present. In a real world web service, SQL Exceptions such as "Unclosed Quotation Mark" would still be shown. Simply enabling Custom Errors is not enough to resolve this information disclosure issue.
Explicit Try/Catch Blocks: 100% Effective, But What If You Miss One
It's considered a best practice to catch and correctly handle any exceptions that occur within code. This technique is also important for preventing detailed error messages from reaching the client. Consider the code below.
In this sample, we catch the divide by zero exception and then just return 0. In a real world application, a much more robust solution should probably be implemented. This new code results in no business functionality related exception being shown the user.
Suppress Returning Exceptions: A Great Backup to Try/Catch Blocks
Wouldn't it be nice if there was a "customErrors" style solution for web services? The "diagnostics" XML element within the web services section of the ASP.NET Web.Config file can provide this type of functionality.
This configuration change results in the following limited error message for the divide by zero condition.
This solution is very effective; however there is one caveat. Both explicit try/catch blocks and the Web.Config change still will not control error conditions that occur due to missing parameters or incorrect value types.
This solution provides a great catch all for situations where an explicit try/catch block may be missed.
Removing the WSDL and Service Description Pages
A quick Web.Config change can be used to disable WSDLs and description pages.
Once this change has been made, it will be necessary to communicate WSDLs or web service signatures with partners through some other channel.
Saturday, September 19, 2009
Using Microsoft's AntiXSS Library 3.1
The sections below are an attempt to provide one-to-one mappings of the ESAPI Encoder calls and the AntiXSS calls needed to satisfy each section of the OWASP XSS Prevention Cheat Sheet.
Setup
Version 3.1 of the AntiXSS library can be obtained at the following URL:
http://www.microsoft.com/downloads/details.aspx?familyid=051EE83C-5CCF-48ED-8463-02F56A6BFC09&displaylang=en
By default, the installer places files in the "C:\Program Files\Microsoft Information Security\Microsoft Anti-Cross Site Scripting Library v3.1\" directory.
In Visual Studio, developers can add a reference to the AntiXSS Library by selecting the DLL located at "C:\<AntiXSS Library Base Directory>\Library\AntiXSSLibrary.dll".
Help files, complete with examples and theory, are located at "C:\<AntiXSS Library Base Directory>\Help\Anti-XSS_Library_Help.chm".
Usage
The following sections should map rules and OWASP ESAPI Encoder calls listed in the XSS Prevention Cheat Sheet to Microsoft AntiXSS Library Calls.
Rule #0: Never Insert Untrusted Data Except in Allowed Locations
This rule holds true as described by the Cheat Sheet. No mapping is required for the AntiXSS Library.
Rule #1: HTML Escape Before Inserting Untrusted Data into HTML Element Content
ESAPI Encoder Example:
String safe = ESAPI.encoder().encodeForHTML( request.getParameter( "input" ) );
AntiXSS Equivalent:
string safe = Microsoft.Security.Application.AntiXss.HtmlEncode( Request.QueryString[ "input" ] );
Rule #2: Attribute Escape Before Inserting Untrusted Data into HTML Common Attributes
ESAPI Encoder Example:
String safe = ESAPI.encoder().encodeForHTMLAttribute( request.getParameter( "input" ) );
AntiXSS Equivalent:
string safe = Microsoft.Security.Application.AntiXss.HtmlAttributeEncode( Request.QueryString[ "input" ] );
Rule #3: JavaScript Escape Before Inserting Untrusted Data into HTML JavaScript Data Values
ESAPI Encoder Example:
String safe = ESAPI.encoder().encodeForJavaScript( request.getParameter( "input" ) );
AntiXSS Equivalent:
string safe = Microsoft.Security.Application.AntiXss.JavaScriptEncode( Request.QueryString[ "input" ] );
Rule #4: CSS Escape Before Inserting Untrusted Data into HTML Style Property Values
ESAPI Encoder Example:
String safe = ESAPI.encoder().encodeForCSS( request.getParameter( "input" ) );
AntiXSS Equivalent:
No direct equivalent
Thursday, May 7, 2009
Struts 2 Security Addons Code Repository
The code repository can be found below, and it allows anyone to download the code and use it within their own project.
http://code.google.com/p/struts2securityaddons/
Additionally, you can see discussion of these modules in my earlier blog posts:
- http://nickcoblentz.blogspot.com/2008/09/jsessionid-regeneration-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/http-caching-headers-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/ssltls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/custom-error-pages-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/csrf-prevention-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/page-level-access-controls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/12/page-level-access-controls-in-struts-2.html
Monday, May 4, 2009
Light-weight Code Review as You Program (Not After You're Done)
When the IDE starts up, it gets an updated list of insecure methods and hints from a web service. Right now I am in the very early stages, so It isn't real pretty or refined yet. For now, I am calling the project Just-in-Time (JIT) Secure Code.
The video below demonstrates the concept in NetBeans.
OWASP ISWG: Struts 2/WebWork Gap Analysis
I had the opportunity to contribute research and code to this paper. The appendix section contains several code examples showing how one might:
- Create an authentication interceptor
- Create a roles interceptor (Enforced page-level access controls based on a user's privilege level)
- Create a caching headers interceptor
- Prevent CSRF vulnerabilities using the built in tokenSession Interceptor
- Implement a custom error handler
- Create an interceptor that enforces SSL
- Regenerate session IDs when users cross an authentication boundary
http://www.owasp.org/index.php/Image:A_Gap_Analysis_of_Application_Security_in_Struts2.pdf
The code repository containing updated struts 2 modules can be found below:
http://code.google.com/p/struts2securityaddons/
Additionally, you can see discussion of these modules in my earlier blog posts:
- http://nickcoblentz.blogspot.com/2008/09/jsessionid-regeneration-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/http-caching-headers-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/ssltls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/custom-error-pages-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/csrf-prevention-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/page-level-access-controls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/12/page-level-access-controls-in-struts-2.html
Friday, December 19, 2008
Page-Level Access Controls in Struts 2 - Part 2
Applications should ensure users are properly authenticated and have sufficient permissions to access pages before content is displayed. Page-level access controls are one security control that enforces this behavior.
Struts 2 RolesInterceptor
In Part 2 of the page-level access controls article, a RolesInterceptor has been added to the struts.xml file. The "roleActions" parameter, passed to the interceptor, contains a list of actions allowed for each role. The "*" role indicates that any role can access the action.
Struts.xml
RolesInterceptor
In the ProcessSimpleLogin action, the "role" session variable has been added to include the name of the role that the user belongs to.
ProcessSimpleLogin
The code repository containing updated struts 2 modules can be found below:
http://code.google.com/p/struts2securityaddons/
Additionally, you can see discussion of these modules in my earlier blog posts:
- http://nickcoblentz.blogspot.com/2008/09/jsessionid-regeneration-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/http-caching-headers-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/ssltls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/custom-error-pages-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/csrf-prevention-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/page-level-access-controls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/12/page-level-access-controls-in-struts-2.html
Thursday, November 20, 2008
Page-Level Access Controls in Struts 2 - Part 1
Applications should ensure users are properly authenticated and have sufficient permissions to access pages before content is displayed. Page-level access controls are one security control that enforces this behavior.
Part 1 and 2 of this article describes one of many ways to implement a Struts 2 AuthenticationInterceptor and a RolesInterceptor to verify users have authenticated successfully and belong to an approved role before allowing access to pages. The key features targeted by both interceptors include a default deny policy and a centralized location for defining access control rules.
In the struts.xml file below, the AuthenticationInterceptor is defined and included in the defaultSecurityStackWithAuthentication. The "excludeActions" parameter provided to the interceptor lists the actions that do not require users to be authenticated. In this case, the "Login" and "ProcessSimpleLogin" actions do not require authentication, however the "Internal" page does require authentication.
(Click the image above to view the XML)
AuthenticationInterceptor
(Click the image above to view the code)
ProcessSimpleLogin
The code repository containing updated struts 2 modules can be found below:
http://code.google.com/p/struts2securityaddons/
Additionally, you can see discussion of these modules in my earlier blog posts:
- http://nickcoblentz.blogspot.com/2008/09/jsessionid-regeneration-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/http-caching-headers-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/ssltls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/custom-error-pages-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/csrf-prevention-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/page-level-access-controls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/12/page-level-access-controls-in-struts-2.html
Monday, November 10, 2008
CSRF Prevention in Struts 2
Cross-site request forgery, one of the OWASP Top 10 vulnerabilities for 2007, is an attack in which a malicious user causes a victim's browser to make a request without the user's consent. This attack is generally propagated by a third party site.
The example below shows how a CSRF attack might affect a web application that allows customers to request rental movies to be mailed to their house.
A customer logs into her movie rental web site and selects some movies to add to her queue. Next, instead of logging out of the application, she types in the address for her favorite news site, reads a few online comics, and does some research on used cars.
Unfortunately, before the customer began her research, an attacker had discovered a persistent cross-site scripting vulnerability on one of the used car sites. The attacker had also exploited this vulnerability to include a simple image tag containing a URL similar to the one below:
<img src="http://www.fakemovierentalsite.com/addMovieToQueueBeginning?movieId=12345" />
When this image tag loaded in the customer's browser, a request was sent to the movie rental application to add an embarrassing movie to the beginning of the customer's queue.
One strategy to address CSRF attacks is to require and validate one-time values included in requests to sensitive functionality. For more information, please view the OWASP explanation found here.
Struts 2 tokenSessionInterceptor
The tokenSessionInterceptor, provided by struts 2, allows developers to add CSRF protection quite easily. In the example below, the tokenSessionInterceptor was added to the interceptor stack. A parameter has been passed to the interceptor to ensure it will not be triggered on each request.
In the ProcessSimpleLogin action, the tokenSessionInterceptor is referenced again. In this case, a parameter is passed to the interceptor to ensure it verifies a valid token has been sent for this action only.

(Click the image above to view the XML)
In order to include the proper token within the page, the <s:token /> tag is included as shown below.
This strategy ensures the ProcessSimpleLogin action executes only if a one-time token has been associated with the user's session, the request includes this token, and the token has been used only one time.
The code repository containing updated struts 2 modules can be found below:
http://code.google.com/p/struts2securityaddons/
Additionally, you can see discussion of these modules in my earlier blog posts:
- http://nickcoblentz.blogspot.com/2008/09/jsessionid-regeneration-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/http-caching-headers-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/ssltls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/custom-error-pages-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/csrf-prevention-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/page-level-access-controls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/12/page-level-access-controls-in-struts-2.html
Sunday, November 2, 2008
Custom Error Pages in Struts 2
When attackers target a particular application, they typically spend some time gathering information about the application's components, framework, and architecture. One way attackers may gather this type of information is through error messages.
Error messages often disclose SQL queries, code fragments, file names, or other sensitive information. An example is shown below.
Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.9.0.3) Gecko/2008092417 Firefox/3.0.3 xx.xx.xx.xx 10/18/08 17:49:20 clientid=&id= http://www.google.com/search?q=
[Microsoft][ODBC SQL Server Driver][SQL Server]Line 1: Incorrect syntax near '='.
SQL = "SELECT * FROM logins WHERE clientid ="
Data Source = "AFE2003"
The error occurred while processing an element with a general identifier of (CFQUERY), occupying document position (40:2) to (40:47) in the template file E:\inetpub\i\somesite\showinv\Application.cfm.
The disclosure of this information can be avoided using custom error pages. Applications, frameworks, or servers can be configured to redirect users to a custom error page that does not disclose stack traces, debugging information, or verbose error messages.Struts 2 Custom Error Pages
Struts 2 includes an Exception Interceptor in its default stack. Developers can utilize this interceptor to catch errors and redirect users to a page containing a generic error message. One example is shown below.
Custom Error Page
Struts.xml
The code repository containing updated struts 2 modules can be found below:
http://code.google.com/p/struts2securityaddons/
Additionally, you can see discussion of these modules in my earlier blog posts:
- http://nickcoblentz.blogspot.com/2008/09/jsessionid-regeneration-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/http-caching-headers-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/ssltls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/custom-error-pages-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/csrf-prevention-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/page-level-access-controls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/12/page-level-access-controls-in-struts-2.html
Sunday, October 19, 2008
SSL/TLS in Struts 2
SSL/TLS provides an encrypted communication channel that a client and server can use to exchange messages without an attacker eavesdropping or manipulating data in transit. This is an important security control to include within a web application to ensure attackers cannot steal user's authentication session cookies or observe user's credentials as they are transmitted to the server.
Web applications and their environments should ensure users can only access sensitive applications over an encrypted communication channel (https for example). Firewalls, application servers, or applications themselves can enforce this behavior.
Requiring SSL/TLS in Struts 2
One way to ensure users connect using SSL or TLS within struts is to create an interceptor to verify this connection. An example has been provided below.
SSLRequired.jsp
RequireSSLInterceptor
Struts.xml
http://code.google.com/p/struts2securityaddons/
Additionally, you can see discussion of these modules in my earlier blog posts:
- http://nickcoblentz.blogspot.com/2008/09/jsessionid-regeneration-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/http-caching-headers-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/ssltls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/10/custom-error-pages-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/csrf-prevention-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/11/page-level-access-controls-in-struts-2.html
- http://nickcoblentz.blogspot.com/2008/12/page-level-access-controls-in-struts-2.html