Lets face it, we all suck at writing secure code. We do. SQL injection has been a known problem since 1998 and it’s still everywhere. Sweet zombie Jesus, if we can’t get that right after 16 years, we really do suck at writing secure code. So what the hell is wrong?
TL;DR – We keep choosing tools, libraries, and frameworks that let us fuck up all the time. We need to stop doing this, we need to value tools/libraries/frameworks that save us from ourselves and make them mainstream.
Programmers are human, and humans make mistakes. Humans go ahead without understanding what we’re doing. Humans are just as dumb as we are smart. Human’s cannot be trusted to get it right every time, whatever it is.
The first step to recovery is admitting we have a problem. Do you have a problem writing secure code, dear reader? Yes, yes you do. I’m glad you agree.
Good, moving on.
A lot of security vulnerabilities in modern code are when an attacker is able to trick the computer into thinking normal data (usernames, account balances, my little pony fanfiction *shudder*) is in fact code to be executed. This idea sum up most of the vulnerability classes you’re familiar with. Let’s look at some:
SQL Injection - This is where we can include SQL code (SQL is an interpreted language remember, although limited) into our data and have the database execute it. So an injection payload might be:
admin' OR 1=1 --
The first part “admin” is our data; it’s a username, the second part is SQL code. In the case of a SQL injection vulnerability the database has no way of differentiating between the data (“admin”) and the code (“OR 1=1 –”). This results in the attacker being able to execute almost any SQL code they want, which is bad. Like, seriously bad.
Again, “admin” is the data and “<script…” is the code to be executed. With XSS the browser can’t tell the difference and can result in defacement, session hijacking, credential theif, and so on and so forth, which is bad. Like, seriously bad.
It’s the same deal with almost any vulnerability that has “injection” in the title, like XML Injection (kind of), LDAP Injection, XPath Injection, EL Injection, YAML Injection, etc etc etc. I think you get my point. The ability for data to be misinterpreted as code is everywhere which puts as poor stupid humans in a very bad place when writing secure code.
Good news everyone! We have (mostly) solved part of this problem for the mainstream in the past, and we can do it again. Remember when memory corruption vulnerabilities were freaking everywhere? Things like stack overflows where I can send to a server my normal data, along with some machine code and have the that server execute the code. These used to be everywhere because human’s can’t be trusted to securely manage memory. Now, almost every single modern language is memory safe, meaning you don’t have to manually manage memory, and can’t accidentally mess it up and introduce security vulnerabilities.
We managed to fix the memory corruption problem by using languages that either ensure you can’t introduce these vulnerabilities, or it’s at least make it very very hard to do so. Unfortunately, the reason we use these languages is mostly because they’re better for the mainstream programmer and the security benefits are mostly a side effect. This means to me we still don’t value security enough to make major changes in our stack to have more secure programs.
This needs to change. We can do the same thing with the vulnerabilities I mentioned above, we can create tools/libraries/frameworks that do not allow programmers to introduce these problems. And to be fair, these do exist. It’s just the mainstream developer doesn’t really care enough to use them. It might be because they’re not better in the way Go/Rust/Python/Ruby is better than C for the mainstream programmer.
If we want secure programs, we have to value security as much as we value other things that make a tool/library/framework awesome. So please, next time you’re choosing your development stack make security important. Choose stuff that doesn’t allow you fuck up, because you know you can’t be trusted to get it right every time. If enough people do this, tool/library/framework developers will catch on and find ways to make it harder for us to fuck up while keeping the awesome sauce that makes us want to use their stuff.
That way we’ll all be better off in the end.