php - mysql password security

Discussions of secure PHP coding. Security in software is important, so don't be afraid to ask. And when answering: be anal. Nitpick. No security vulnerability is too small.

Moderator: General Moderators

petterg
Forum Newbie
Posts: 10
Joined: Mon Sep 26, 2005 8:24 am
Location: oslo, norway

php - mysql password security

Post by petterg »

I'm quite new to php so bare with me if this is discussed before.

I'm about to make a website based on php/mysql on apache server. (linux)

To have a php/mysql driven website the mysql username / password has to be stored in the php code somewhere - in cleartext - and the file where it's stored has to be readable by apache (the webserver). (Am I right about this?)

I see this as a risky way of storing paswords. It means that everyone with access to put php files (or other scripts) readable by apache on the same server could make a script to output the source of my php files - including the password - to a website! What is the workaround for this?
I was thinking a way to go could be if passwords was stored in a separate file to be included by the script, and the includedfile was only readable to the owner of the script - not readable by the apache user. Could this in some way be posible using setuid on the php file, like done on programs, or sudo, or any other way?
User avatar
Chris Corbyn
Breakbeat Nuttzer
Posts: 13098
Joined: Wed Mar 24, 2004 7:57 am
Location: Melbourne, Australia

Post by Chris Corbyn »

If you're on a shared server then there's a pretty good chance someone else could look at any of your files on that server. It depends on how well your host has set things up. I no longer used shared hosts as a result of several attacks on my scripts :(
User avatar
shiflett
Forum Contributor
Posts: 124
Joined: Sun Feb 06, 2005 11:22 am

Re: php - mysql password security

Post by shiflett »

petterg wrote:To have a php/mysql driven website the mysql username / password has to be stored in the php code somewhere - in cleartext - and the file where it's stored has to be readable by apache (the webserver). (Am I right about this?)
Read "What Can You Do?" near the end of this article:

http://shiflett.org/articles/security-corner-mar2004

Hope that helps.
User avatar
pickle
Briney Mod
Posts: 6445
Joined: Mon Jan 19, 2004 6:11 pm
Location: 53.01N x 112.48W
Contact:

Post by pickle »

Long story short, you don't need to store your passwords as plain text. You can either hash them yourself (using md5, sha1 or some other method), or let MySQL hash it.

Essentially, the procedure goes like this:

1) User enters plain text password when they sign up
2) Script takes plain text password and stores hashed password in database

Then,

1) User logs in by typing their password
2) Login script hashes what user typed in and uses that hashed value in the query to check if credentials are correct.

You should know though, that some of the more common hashing libraries (md5 and sha1) have been broken, so the guarantee that they're not breakable isn't 100%. Using a stronger encryption like SHA 256 will work (although it to will inevitably be broken as well).
Real programmers don't comment their code. If it was hard to write, it should be hard to understand.
petterg
Forum Newbie
Posts: 10
Joined: Mon Sep 26, 2005 8:24 am
Location: oslo, norway

Post by petterg »

It's a company server, but I'm the only person with root access. I can basicaly set it up however I want as long as it works for the company uses.
I know none of the current emploes have the knowledge to find passwords in my private php files, but now they're going to hire more ppl. I want to secure my scripts before all the new guys get login access.

Unless I'm missunderstanding the site Shiflett linked to - to store the mysqlpasswords in environment variables - everyone can just do a print_r($_SERVER) to see all passwords at once! At least when storing in a file they'll have to spend a few seconds to look for each of them.
User avatar
shiflett
Forum Contributor
Posts: 124
Joined: Sun Feb 06, 2005 11:22 am

Post by shiflett »

pickle wrote:Long story short, you don't need to store your passwords as plain text.
It looks like you're misunderstanding the question.

If not, I'd like to see how you can use the hash of a password to connect to MySQL. :-)
User avatar
shiflett
Forum Contributor
Posts: 124
Joined: Sun Feb 06, 2005 11:22 am

Post by shiflett »

petterg wrote:Unless I'm missunderstanding the site Shiflett linked to - to store the mysqlpasswords in environment variables - everyone can just do a print_r($_SERVER) to see all passwords at once! At least when storing in a file they'll have to spend a few seconds to look for each of them.
Are you wanting people to be able to log into MySQL but not know the access credentials? If so, that's quite a conundrum. :-)
petterg
Forum Newbie
Posts: 10
Joined: Mon Sep 26, 2005 8:24 am
Location: oslo, norway

Post by petterg »

pickle wrote:1) User enters plain text password when they sign up
2) Script takes plain text password and stores hashed password in database
Well, that's the way to go if the site uses a login. There will still be a need to store the password to access the database where the hashed passwords are stored.

But when the site is mysql powered - to lookup data and save logs without having the user log in the password still needs to be stored somewhere.
petterg
Forum Newbie
Posts: 10
Joined: Mon Sep 26, 2005 8:24 am
Location: oslo, norway

Post by petterg »

shiflett wrote: Are you wanting people to be able to log into MySQL but not know the access credentials? If so, that's quite a conundrum. :-)
They don't need to login. The script should login to get it's data / write it's statistics.
As far as I know this is what is used for most sites, like online newspapers. (The admins have to login with their own passwords.
User avatar
shiflett
Forum Contributor
Posts: 124
Joined: Sun Feb 06, 2005 11:22 am

Post by shiflett »

petterg wrote:They don't need to login. The script should login to get it's data / write it's statistics.
I'm just trying to make sure I understand the problem before trying to suggest a solution. As I'm understanding it, this sounds impossible.

It sounds to me like you have PHP developers who have read and write access to the code that connects to the database. Just to be clear, this means they can edit the file with mysql_connect(). This function takes the access credentials as arguments, yet you do not want these developers to be able to access this data. Does this sound right?

If so, then I think you'll find that this is impossible. You might look at one of these code obfuscator things, so that your developers have to include a file to connect to the database, and that file is very difficult to interpret. However, all you can really do is raise the bar - there's no way to hide this information from the person who uses it.

Hope that helps.
petterg
Forum Newbie
Posts: 10
Joined: Mon Sep 26, 2005 8:24 am
Location: oslo, norway

Post by petterg »

With this code anyone with access to put a phpscript on the webserver can read out all files apache has readaccess to:

Code: Select all

$filename = "path/to/my/includefile.php"; 
$handler = fopen($filename, r); 
$cont = fread($handle, filesize($filename)); 
$cont = str_replace("<?", "[PHP", $cont); 
$cont = str_replace("?>", "PHP]", $cont); 
echo "<textarea>$cont</textarea>
There are 4 kinds of users involded.
- The readers. They never login.
- The writers. They login to the mysql db to post/update the site
- The company employees. They have access to create php files on the webserver (including the codeexample above)
- Me. I have access to do whatever I want.

My goal is to give the readers access to read data without giving the employees access to get the mysql passwords that the script needs to use to read the data (using something similar to the posted code). As readers are loading different parts of the site there will be scripts storing statistics for which parts of the site is most popular (and some more). So the "hardcoded" password used for reading is not readonly. There are not much damage ppl can do with this password, but it's a prinsipal - it should not be that easy to find a password!

Did this clearify anything?

Edit: The phpfiles are owned by me:my_web_files and chmod = 640. Apache and me are the only users in the my_web_files group. The only way other users may access the code is through making apache run scripts.
sheila
Forum Commoner
Posts: 98
Joined: Mon Sep 05, 2005 9:52 pm
Location: Texas

Post by sheila »

It means that everyone with access to put php files (or other scripts) readable by apache on the same server could make a script to output the source of my php files - including the password - to a website!
Well, you either trust your fellow employees or you don't.

If you really don't trust them, then set up a separate development server for them to work on. When they complete scripts you install them on the live server.
Roja
Tutorials Group
Posts: 2692
Joined: Sun Jan 04, 2004 10:30 pm

Post by Roja »

sheila wrote:
It means that everyone with access to put php files (or other scripts) readable by apache on the same server could make a script to output the source of my php files - including the password - to a website!
Well, you either trust your fellow employees or you don't.

If you really don't trust them, then set up a separate development server for them to work on. When they complete scripts you install them on the live server.
In many cases, they arent fellow employees: They are other customers of a large shared hosting company, in which case you have little or no trust of those individuals.

Most shared hosts use a variety of protections to ensure that one webspace cannot read from another. Whether its open_basedir, safe_mode, suExec, or more esoteric solutions (virtual hosting anyone?). The risk is definitely real, but its definitely a per-host issue.

If its honestly a fear on a given host, test it, and if it allows it, ask the provider what they suggest to prevent it.
petterg
Forum Newbie
Posts: 10
Joined: Mon Sep 26, 2005 8:24 am
Location: oslo, norway

Post by petterg »

I trust the current emploees. But I don't trust those who are going to be hired soon.
Roja wrote:ask the provider what they suggest to prevent it.
Well, I kind of am the provider (as I'm the root user on the system). I need some help to prevent it!


Edit: I have the feeling there is a need to modify the php parser to make this work. Modify it so that ownership of files used by include and fopen has to be readable to the owner of the running script, or the include / fopen fuctions should fail. As it is today it's only required to be readable to the apache user.
Last edited by petterg on Tue Sep 27, 2005 12:34 pm, edited 1 time in total.
User avatar
feyd
Neighborhood Spidermoddy
Posts: 31559
Joined: Mon Mar 29, 2004 3:24 pm
Location: Bothell, Washington, USA

Post by feyd »

Give them a blackbox class that does a socket connection to a second instance of the web server, that instance would then access to the actual data files (run under a different user). The live site can use the normal version of the blackbox script.
Post Reply