“But, we took care of that before, didn’t we?” asked a participant in a web application security course I taught recently. It was a good, logical question. We were discussing “SQL injection” a process where an attacker enters database commands into a website field – in, say a forum or comment section – that could disclose data or vandalize the site if that code were executed. Earlier we’d seen techniques for ensuring that user-supplied data was free of potentially harmful information.
The specific technique we were discussing was the use of “prepared statements”. Briefly, the concept is that rather than using the user data directly, it is converted to a single item before being used in the database query, thus preventing it from being executed.
The participant wanted to know why we would do the sanitizing of user input and then take the extra step of using the prepared statement. My response was this was to implement defense in depth.
Most organizations use defense in depth on a network and system level. They may have, for example, anti-virus software on servers as well as on workstations. They may use firewalls on individual systems and at network borders.
The idea is used in the physical realm, too. Many secure sites have a guard at a point of ingress to the property (e.g. at a gate), as well as one at a building entry. Some have additional security in other areas, too, of course. The idea is to have multiple layers that need to be penetrated to instigate an attack.
Just as networks and physical environments need multiple layers of security, so does software. Be it a phone app, a website, or an operating system it is important to verify data when it is input and before it is used.
The first case is comparatively straightforward, although not always simple to implement well. When data is retrieved from a database, a user, or some other source, it is expected to have some characteristic: that might be a numerical value of a particular type and value range (integer 1 through 10 inclusive), a string representing a name, a time of day, or some other value. If the data is retrieved from a web form, for example, the software can request that the user re-enter it.
When programmers use data, they also expect it to be of a particular type and in range. If that value were to be of the wrong type of out of the expected range and it weren’t checked properly, it could cause the program to fail – never good. It might even damage other data or cause data to be exposed (a type of information leakage). Most programmers are taught to check for this at some time in their education. Self-taught coders may not be. In either case, most programmers learn to test data from the school of hard knocks, but not all of us do it every time (yes, I am including myself here, unfortunately).
You can learn more about defense in depth as it applies to web application security in LearningTree’s Securing Web Applications, Services, and Servers. When you combine input checking with verifying data before use, you create the protection of defense in depth. You add extra care to building software making it more robust and secure.