I've heard that PHP is somewhat secure because Apache won't allow the download of raw PHP. Is this reliable, though? For example, if you wanted to password protect something, but didn't want to create a database, would something like $pass = "123454321"; be safe?

Bottom line, is it safe to assume that nobody has access to the actual .php file?

  • As any question of security, the answer depends on your attack model. What case are you thinking of? Script kiddie with a web browser? Your average hacker, without access to the server but various networking tools? A hacker who broke into your server? – user7043 Nov 30 '12 at 21:34
  • 1
    The bottom line depends on system security, not language security. It is equally appropriate for all languages that are used to implement a publicly available service. This might be a better fit for the security stack exchange. – user40980 Nov 30 '12 at 21:34
  • 2
    @Ryathal At best related, not a duplicate. – user7043 Nov 30 '12 at 21:39

You're correct that Apache will send PHP scripts to the PHP interpreter, if correctly configured, but what you're describing is not secure.

Neither the language nor the webserver is relevant here, your configuration values should not be in a publicly accessible directory to begin with, there's absolutely no reason at all to have your configuration file under DocumentRoot.

Lastly, if anyone other than you have access to the server, you can never assume that nobody has access to your files.

  • Not to mention the horrors associated with throwing magic numbers all over the code base. – Ian Atkin Nov 30 '12 at 21:34
  • 2
    @IanAtkin What are you talking about? – user7043 Nov 30 '12 at 21:36
  • @delnan he's seen the magic number monster, he's prone to babbling incoherently. Yannis, no mention of the obscure risk of reverse engineering the values out speaking to why sensitive data should be encrypted in general so even if they are somehow retrieved regardless of other security measures, they are encrypted upon retrieval and need necessary keys to decrypt? .NET for example has for this exact reason built-in facilities for it's XML config files to have sections encrypted given a signing cert and .NET will encrypt/decrypt with that at runtime – Jimmy Hoffa Nov 30 '12 at 21:50
  • @JimmyHoffa Hey, now there's a mention ;P – yannis Nov 30 '12 at 21:51

If you don't make any mistakes, your PHP sources cannot be read from the outside: as long as apache is configured to handle .php files through mod_php, they will always be executed, never served raw.

However, mistakes are easy to make, and are frequently found in production code. Typical mistakes include:

  • Path traversal vulnerabilities. The typical pattern is that you construct a filename based on some user input (e.g. a $_GET parameter), and then serve this file through, say, readfile. For example, if you have readfile("/home/me/pages/{$_GET['pageid']}.html"), an attacker can easily plant something like "../../../../../../../../../../../etc/shadow".
  • PHP files with nonstandard extensions. Apache uses the extension to determine a file's MIME type, and then decides how to handle it based on that. config.php will be interpreted, but config.php.inc will not; since .inc is not a known extensions in most setups, Apache defaults to plain text, which means the source code can be requested over the net.
  • Code upload. Typically, such a vulnerability arises when you have file uploads that are handled improperly, e.g. allowing arbitrary directories in the uploaded filename, or uploading to a location under the document root. When an attacker can plant .php files in a location where they get executed, it is possible to run arbitrary PHP code on your server, including code that reads other scripts and extracts passwords.
  • Remote code execution vulnerabilities. Similar to code upload; if you have any eval, include, system, exec or similar calls in your code, and their arguments are partially user-supplied, you may be in trouble - improperly sanitized inputs to any of these constructs can allow attackers to run arbitrary PHP code or shell commands.
  • Displaying errors in the page output. Many errors and exception contain sensitive data, at least portions of the source code, but sometimes (e.g. PDOExceptions) even usernames and passwords.
  • Apache configuration mistakes. Apache is a powerful thing, full of obscure features, and some of them have security implications.

In addition to avoiding these pitfalls, you should put only those files under the document root that are intended to be called directly; any includes, data files, configuration files, libraries, etc., go into directories outside the document root.

  • 1
    I was typing up an answer touching on these exact points when I saw that there was a new answer...you said it a lot better. – jmoreno Dec 1 '12 at 0:27
  • 1
    Just a note: PDOException will reveal the username but not the password (it will reveal if you are using a password or not, but not the actual password). – yannis Dec 1 '12 at 0:37
  • 1
    @YannisRizos: I wouldn't count on it. It may have been fixed in newer PHP versions, but I've seen at least one 5.3 install where it would happily dump the password. – tdammers Dec 1 '12 at 12:49

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.