Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Securing Legacy Applications

Chris Cornutt
February 04, 2017

Securing Legacy Applications

It’s common to hear people preach “plan in security from the start” and in an ideal world you can. Here in the real world, though, we have legacy code that’s gathered over time and comes with a host of problems - (in)security included. What do you do when you’ve been commissioned with securing an application that’s showing its age? Follow along with me as a I step you through a list of tips and tricks you can use to discover security issues in your application and effectively fix them and secure your application.

Topics will include some of the most common vulnerability types, key places to look for potential issues and arm you with the tools and knowledge you’ll need to refactor that legacy application into something secure.

Presented at Sunshine PHP 2017

Chris Cornutt

February 04, 2017

More Decks by Chris Cornutt

Other Decks in Technology


  1. Understand the Scope Work from the outside in (general), then

    introduce security Identify and document where data changes hands
  2. Quick Hits: Globals Look for global use deeper in code

    In PHP, that’s superglobals first $_POST, $_GET, $_SERVER, $_COOKIE $_FILES, $_SESSION Get rid of these right now: $GLOBALS, $_REQUEST
  3. Quick Hits: Unfiltered Data Using values directly, no filtering/validation Also

    getRequestParam() Input::get() _request->getQuery() Dangerous concatenation Injection issues Solution: filter_var or filtering/validation libraries
  4. Quick Hits: Sensitive Logging User PII, credentials, tokens Logs are

    output too Log servers are often less secured Solution: Remove the sensitive information (and purge the logs!) Log only identifiers and hard-coded strings
  5. Quick Hits: Drop Catch-Alls Fallbacks are nice, until they’re not

    Be specific, like in routing Catch-alls make for sloppy code and difficult to manage dependencies. Solution: Remove them. Specify exact matches & functionality
  6. Quick Hits: Action Splitting REST-ey principle: GET reads, POST/PUT/DELETE updates

    Never the two (or three…or more?) shall meet Take advantage of framework-specific handling $app->get() requirements.sf_method Solution: Abstract out the handling by action Ensure proper protection (CSRF)
  7. Input Handling: Input Points Locating input points (remember your threat

    model?) grep is your best friend (naming conventions) Do you really need it or is it just lazy? Solution: Avoid user-controllable data sources Use the force….er filter.
  8. Input Handling: Determine Risk Reducing inputs reduces risk Examine context

    (especially mixed) Example: is it used in evaluation and output? Document risk points (threat model) Solution: Maintain data via stateful sources (sessions) All external data is tainted. Never forget.
  9. Validation: Do You? Not a priority, sadly. Same Origin Fallacy

    “It’s mine! All mine!” Libraries vs internal methods like filter_var or Respect\Validation Solution: Assess validation needs across application (do they repeat?) Remember the threat model for inputs. Fail fast.
  10. Validation: Sanitize Don’t use as a replacement for input validation.

    The more assumptions you make, the higher the risk factor. Consider output contexts too (HTML, JS, XML…) Solution: Validate first, then sanitize. Don’t try too hard.
  11. Templating: PHP PHP is not a templating language…no really. Largest

    refactor point in most legacy applications. Using methods to escape output? That’s templating. Evaluate options: template it all vs spot checks.
  12. Templating: Manual Prone to mistakes. Hard to manage effectively. Beware

    copy and paste all the things. Move slowly, replace most used first. Based on logging
  13. Templating: Special Output HTML is not the only context. Javascript,

    CSS, HTML attribute, plain-text, log output. Template (escape) for the context. HTML htmlspecialchars CSS Replace with &#[num] Javascript Replace with \x URL url encode
  14. Access Control: Now Determine current controls (Auth*) Determine coverage of

    controls Threat model! Look for over-engineering
  15. Access Control: Credentials Look for hard-coded values username, token, password

    Extract the values and protect Think about protection levels External tool, external file, external service
  16. Access Control: Endpoints Public, Private, Conditional Different protection levels Start

    with most used Protect at different levels router, endpoint, server - defense in depth! See if there’s a simpler way
  17. Access Control: User Determine user types Create a grid of

    types and endpoints Features == users? Administrator vs user
  18. Adding New Controls Can tools be consolidated (or removed)? Determine

    missing controls Are there 3rd party tools/libraries you can reuse? Simple is good, but sometimes complex is needed Are there interfaces with other systems
  19. Adding New Controls: Examples CSRF tokens injected automatically on render

    Encryption of data via libraries (ex: libsodium, defuse-php) Implementing a templating library Access control types: Access control list (ACL) Role-based access control (RBAC) Property-based access control Multi-factor authentication
  20. Changing Dev Process Hardest part in the whole process New

    code needs security guidance Manual code review Establish a pattern of security refactoring
  21. Changing Dev Process Integrate tools and services Scanners 3rd party

    services Pentesting Bug Bounty Refactor bite-size pieces, related to current development Build a culture of security