Sunday, January 24, 2016

Secure Web Application Practices - XSS

Cross-Site Scripting (XSS) attacks are a type of injection, in which malicious scripts are injected into otherwise benign and trusted web sites. XSS attacks occur when an attacker uses a web application to send malicious code, generally in the form of a browser side script, to a different end user. Flaws that allow these attacks to succeed are quite widespread and occur anywhere a web application uses input from a user within the output it generates without validating or encoding it.
An attacker can use XSS to send a malicious script to an unsuspecting user. The end user’s browser has no way to know that the script should not be trusted, and will execute the script. Because it thinks the script came from a trusted source, the malicious script can access any cookies, session tokens, or other sensitive information retained by the browser and used with that site.
Following are the some of the practices that helps mitigate the risk of XSS in a web application.
  1. HTML Escape before inserting untrusted data into HTML element content. Untrusted data can be malicious scripts that when put into html context can cause it to execute and do nasty things. For example,

    <div>...ESCAPE UNTRUSTED DATA BEFORE PUTTING HERE...</div>

    In Aspnet, you can use AntiXssEncoder.HtmlEncode to encode data before putting into Html. Most of template bindings (for example Razor) do it by default for you.
  2. Attribute Escape before inserting untrusted data into HTML common attributes.

    <div attr=...ESCAPE UNTRUSTED DATA BEFORE PUTTING HERE...>content</div>

    In Aspnet, you can use AntiXssEncoder.HtmlAttributeEncode method to encode data before you put it as an attribute value of an html element. Again, most of template bindings take care of this for you if you are using one.
  3. JavaScript Escape before inserting untrusted data into JavaScript context. This applies to both javascript code and direct event handlers on html elements.
  4. <script>alert('...ESCAPE UNTRUSTED DATA BEFORE PUTTING HERE...')</script> 
    In Aspnet, you can use AntiXssEncoder.JavaScriptStringEncode to encode unsafe data to be used inside of a javascript context.
  5. CSS Escape and strictly validate before inserting untrusted data into HTML style property values. For instance,

    <style>selector { property : ...ESCAPE UNTRUSTED DATA BEFORE PUTTING HERE...; } </style>

    In Aspnet, you can use AntiXssEncoder.CssEncode to encode unsafe data before you use that in CSS styles.
  6. URL Escape before inserting untrusted data into HTML URL parameter values. For instance,
  7. <a href="http://www.somesite.com?test=...ESCAPE UNTRUSTED DATA BEFORE PUTTING HERE...">link</a >
    In Aspnet, you can AntiXssEncoder.UrlEncode to encode unsafe data before putting it into URL.
  8. Sanitize HTML Markup. If your application handles markup – untrusted input that is supposed to contain HTML – you should use some sanitization libary that can parse and clean HTML formatted text. HTMLSanitizer is one such great tool.
  9. Use HttpOnly cookies. Although this is not directly related to XSS, this is always a good practice to use HttpOnly cookies for sensitive cookies like SessionId, etc. This is mainly to help mitigate the risk after you do have an XSS risk.
  10. Whitelist allowable values. Rather than trying to encode and escape untrusted data, you should always see if it much easier to just sanitize the input and check if it aligns with what is expected in that input value. For instance, if the input is a product id in product search API, it might be easier to validate that against a regex that does not allow any of unsafe characters.
  11. Use native browser defenses. Internet explorer implements some native XSS defense that should be used (it is enabled by default) if possible. It honors a HTTP header named X-XSS-Protection that can be set to 0 for disabling it if you have some issues with it. Not a common defense, but it might make sense for applications for instance when all your users use IE only.
  12. Use Aspnet Request Validation. Aspnet by default has request validation enabled and it looks for malicious data in the input and blocks the request if it finds any.
  13. <system.web>
    <pages validateRequest="true"/>
    </system.web>
Like protection against any other kind of attacks, in XSS also it is advisable to have multiple level of defenses to help mitigate the risk of XSS. You would usually use a combination of encoding, securing cookies, native browser defenses, request validation and whitelisting to prevent against XSS attacks.


No comments: