I've heard it said that PHP is inherently insecure. Is this true? Why?
It is pretty hard for a language to be "inherently insecure" by my definition, since a good programmer can adapt. But PHP started out leaving a lot of minefields lying around for novices.
The initial versions of PHP paid little attention to security and the design had some big flaws. Security is hard to retrofit into the core software and into the libraries. Security training is hard in the best of circumstances, and even more so when a large subset of the developers are inexperienced and started off with bad defaults.
For example, it wasn't until version 4.2.0 that register_globals was disabled by default, so data received over the network was not inserted directly into the global namespace anymore. This feature is finally slated for complete removal in the next version.
The early release of PHP and the ease of deploying simple PHP applications also attracted many developers with little security awareness, and ensured a large number of applications, a significant number of which had remotely exploitable vulnerabilities. The size and vulnerability of the deployed base also attracted a lot of interest from the exploit community.
Here are some references and useful links
Some of these reasons are described in "Fractal of bad design".
PHP is the blind leading the blind. I read the PHP wikibook; it should be called "how to write a absolutely vulnerable application". I can't imagine that could be published in any other language.
Relation to security. If you read python docs for insecure things like serializing (pickle), you'll see a red warning on the top of the page "Don't use on untrusted input!". How about PHP?
In addition to previous item: in other languages, code is considered as a problem if you don't understand what it does and how it works. In PHP, code is considered as a problem if there are exploits in the wild.
PHP runs only as CGI, that means complete reinitialisation of a script on every request. And that causes hate to the frameworks: "They are slow!". But frameworks eliminate code injection vulnerabilities (SQL injections - to 100%). There is a principial difference: prepared statements are safe by default. You have to do nothing to protect yourself from SQL injections, that means you can't forget or don't know about it. Not using them is uncesure by default: you have a security flaw unless you fix it manually every time.
PHP interpreter itself is broken. That poisonous zero bugs where the API interpretes \0 as the string terminator while php itself doesn't - why doesn't python have it??
Weak typing (i.e., silent automatic conversion between strings/numbers/et al) is so complex that whatever minor programmer effort is saved is by no means worth it.
There are at least two points to this:
PHP is very ubiquitous, and this makes it an interesting target for hackers. It also means a lot of novice programmers use PHP, because it is easy to use. So you are more likely to pick up insecure code if you include third party libraries in your application.
And I guess the more important point is that PHP wasn't design to be used on the scale it is today. Rasmus Lerdorf wrote PHP to replace some Perl-scripts he used, and it grew from there. So security wasn't the most important aspect when he wrote it, and a lot of the things he decided to use back than (because it was easier to program in) are now security risks.
More popular subject is - more attention it derives. This is the first truth. Second truth is that PHP from the beginning was not very well designed and nowadays it has a lot of internal hacks to work well, that consistently leads to failures in security implementations, versions incompatibilities. As the best proof you can check MOPS. I really don't think that there is more to discuss.
No, it is not true. You can write secure code in PHP perfectly well. However, a lot of code written in PHP is insecure, and the reason for that is simple - PHP has relatively low barrier of entry, which means a lot of people that know little about security write in PHP. On the other hand, PHP is web-oriented, which means the public PHP application can be attacked by anyone on the internet (while, for example, C++ application for the desktop can usually be attacked only by somebody who already has access to the said desktop computer).
The main issues are the default configuration and the low barrier of entry.
The easiest way to deploy a PHP app is to install the inefficent horror called "Apache" with
mod_php, throw the poorly-developed app into
/var/www and watch the world burn. That will work, but is a security disaster.
For example, a Node.js app runs as its own process, in its own directory totally independent of the web root. The web root is only there to store assets and user-uploaded content, and can be omitted if the app doesn't need that (if it's just a REST API for example). If a .js file gets uploaded there, nothing bad will happen (it may do client-side damage like phishing or XSS but that's out of scope).
On the other hand, using our default PHP configuration, if a .php file gets uploaded and requested, it gets executed under the privileges of the legitimate app, can access and modify its files, access and exfiltrate sensitive data from the DB, etc. That is a disaster, and most compromises of PHP sites come from insecure file upload forms.
There are ways to make that secure, like separating the app and the content - the app's files shouldn't be accessible via the web root, and no file should be executed from the content directory. Most frameworks use that approach, where all your controllers, models and views reside in the
app directory, and a second
public directory holds all assets, uploaded content and a single
index.php file that is the entry point of the app and is used to bootstrap the framework and the app. You then configure the web server to use the
public directory as web root, and only execute
index.php while serving everything else as content. Even if a malicious
.php file is uploaded, it'll only get served as plain text, for the whole world to hurt their eyes in front of an idiot's attempt at a website compromise.
So why doesn't everyone do this ? Because of "hi how do i install laravel framework on cpanel free hosting? thx"
Because of people like those. The really low barrier of entry means quite a bit of PHP users aren't developers and don't want to become developers - note that I don't consider them developers because copy/pasting code from tutorials without understanding it doesn't mean being a developer, that only means being an irresponsible idiot - you become a developer only when you are able to take the time to understand what you're doing and how can you do things the right way. I may be biased, but that also means going to Stack Exchange and reading some basic stuff about server security before setting up an internet-facing web server. ;)
Given they can't use apply security guidelines nor use frameworks on shared hosting (and don't bother moving to VMs/dedicated servers because it requires some reading which they don't want to do because shared hosting seems good enough for them, and PHP shared hosting is often free) they continue to create crappy and insecure applications and deploy them on crappy and already compromised cPanel-powered shared hosting servers.
There are a lot of idiots who are able to write PHP code as it's a very simple language.
This results in lots of insecure code, especially
include($_GET['page'])-style (remote) code inclusion holes, XSS holes and SQL injection holes.
Python and Java are not so popular for people who never programmed before so there are less programming newbies and thus the chance of horrible insecure code is lower.
Another aspect: would Zend base their enterprise targeted PHP stack that is more vulnerable than competition? It is not the language that to be blamed for insecurity. It is the design. Bad design can be implemented in every language. Security is not a state, it's a process. And the massive contributor base of PHP does a pretty good job.
The code is stored in plaintext formatted text (. Php) files. It's not compiled or encrypted, so anyone who compromises your machine gets your source code. And if they have the source code then they also have the login details for the database and can run queries like drop, delete, insert or select. Even asp gets compiled before it is deployed. Most people who use php are intermediate developers who know very little about server security.
Then there's WordPress. Most php sites run WordPress. WordPress is a favourite for people with no server skills or programming skills. That means they don't know how to secure it properly. It's so widely used that any vulnerabilities that get discovered are published and exploited. Most developers have no idea what the code on their WordPress site is actually doing. Once again WordPress stores database login details in the plaintext wp-config.php file and has a very unsecure installation process. By default the installer is runnable without a password as long as the wp-config.php is configured and the database (without any tables) is set up. If you're not quick enough someone will run the installer for you and install some nice file management tools to read more files on your system. Then there is user enumeration and various other issues.
Many people are still using php 5.x for their projects. Some of those versions no longer receive security updates.
The php Community itself is also a danger to itself. So many tutorials out there encourage the use of localhost in database connection strings. Running your database on the same machine as your Web facing code, or a directly web facing machine in general is bad practice. The web facing machine should not have the database on it.