Archive for October, 2009

In response to my previous post…

Saturday, October 31st, 2009

My last post, Don’t store passwords as plain text! I described a simple method to create a salted hash of a password for a more secure method of storing it in a database.  If you haven’t already done so, you should read that post, to learn WHY its bad to store passwords as plain text (if it isn’t obvious to you). I thought about the topic some more.  It is a very serious security issue, and so I decided that, if I’m going to make a post about the topic, I should be a little more informative.

I also read up a little on the topic.  It turns out that Jeff Atwood posted a pretty similiar post a couple years back.  Jeff made an assertion that I should make as well.  Like Jeff, I am not a cryptographer, so don’t trust my advice like I am a security EXPERT.  He also taught me about rainbow tables.  Rainbow tables, in short, are a massive database of precomputed hashes.  With our hash inside of a hash technique, the final hash product is too long for modern rainbow tables to be effective.  This is great and all, but there are a few problems with my method.  One thing you need to realize when dealing with system security is there will almost ALWAYS be security holes.  We do our best to prevent them, but we can’t promise to be 100% successful.

I’m going to revisit the salted hash to create a better salting, hashing, hacker-hater method of storing passwords.  I’ll make another disclaimer-like notice first.  Most people use only a handful of unique passwords (and by handful, I mean: one.. or two) across a galaxy of login systems.  If you develop a system to store a user’s password it is your responsibility to store it in the most secure way you can.  I don’t recommend you use my salty hash method, I simply mean for it to be an enlightening moment of: “Oh crap, I should really think about how I’m storing my users’ passwords.”  There are always security holes.  I’ve already thought about one in my original.  I thought my method worked well, because the salt wasn’t exposed in the stored value. I liked this, but then realized a problem: two user’s with the same password will generate the same hash.  This is much the problem with storing a non-salted hash, and is the principle used in cracking hashes via brute force/rainbow table.  Hashing strings until the two generated hashes match.

Here is my improved method, in (PHP) code:

// our password this time, is a little bit stronger than ‘password’
$password = “#aBc.123@”;

// some alpha-numeric values and special characters, for use in our salt
$salt_material = “abcdefghijklmnopqrstuvwxyz1234567890 \”!@#$%^&*()_=+-{}[],./<>?;’:”;

// salt will be a string of random length, 1-9
$salt_length = rand(1,9);
$salt = “”;

//build the salt from our material at random choice
for($i = 0; $i < $salt_length; $i++) {
$salt .= $salt_material[ rand(0, strlen($salt_material)-1) ];
}

// calculate the hashes, and then reverse the strings
// not sure about the added strength, but I like the idea of reversing the sums
$salt_sum = strrev( md5($salt) );
$password_sum = strrev( md5($password) );

// now create the sum of our salt + password
$salty_hash = md5( $salt_sum . $password_sum );

// create a hash which exposes our salt, so we know what it was.
// since our salt_length is only 1-9, this information doesn’t have to be
// separated, its always the first char
$resulting_hash = $salt_length . $salt . $salty_hash;

// for added measure, an idea I read elsewhere.
// again, not sure about the added strength, but I like the idea of it
$secure_hash = sha1($resulting_hash);

// and now, the final result
$final_product = $salt_length . $salt . $secure_hash;

Now, each time the hash is calculated, it should be a unique value, however we should be able to recreate it (provided the user inputs the correct password).  Four runs of the script resulted in the following hashes:

7{5@a#@@f77a51b733b65590d284b990099fc764239fbd63
4n+b44c38fe32b4f9a095d7534610bce0f4d72d2976f7
9r{j&f2i”t9ea7035cf81de87a07980e9884d26db67e510728
4;xd”a9ff52b67313cc2d183b977226747a6685540a43

Don’t store passwords as plain text!

Thursday, October 29th, 2009

Many websites will email your password to you if you have forgotten it.  When I create a new account on a website, I don’t want them to know my password!  They shouldn’t be storing my password somewhere as plain text.  Granted, the site could be storing a hashed version, and simply using an algorithm to unhash it, and send you back the unhashed version, but I don’t like this either.  I don’t want them to even be able to unhash my password!

No hashing algorithm is completely unbreakable.  Hashing algorithms such as MD5 or SHA-1 have been shown to be breakable (MD5 much more easily than SHA-1), but storing the MD5 hash of a password is still SIGNIFICANTLY more secure than storing the plain text, or an easily crackable custom hashing algorithm.  Cracking an MD5 sum can take a few minutes, several hours, or even days, depending on the CPU power available, SHA-1 even longer.

We can create an even more secure hash by combining the efforts of a custom hashing algorithm and MD5 to create a unique custom hashing mechanism.  This is an example of how you should store your users’ passwords. We want to “salt” the original string, and then hash the salted version, and store only the hash.  When it comes time to authenticate a user’s login attempt, we run their input through the hashing function.  If the two hashes match, they’ve inserted the correct password.

Here is an example of such a custom salted hash:

Our string to be hashed is “password.” First, let’s come up with a salting mechanism.  For this example, we’ll use something simple.  The salt used has to be retrievable and positively recreatable. “Password” has 8 characters.  Lets take (in PHP)

$salt = floor(strlen("password") / 2);

That is the length of the string, divided by two, rounded down to the nearest whole number.  In our case the answer is 4.  floor() does nothing for us here, but if the string length is odd we want a whole number, and we want the same whole number every time a string of that length is used.

Now we have our salt, 4.  Let’s hash up the 4.

$salt_sum = md5( decbin($salt) );

I took 4, converted it to binary (results in 100), and found the MD5 sum of that as a string, the result is: f899139df5e1059396431415e770c6dd

Lets prepend that to our input string, “password” and find the MD5 sum:

$hash = md5($salt_sum . "password");

Now, our result is: c88e94b4d0f8e1c303f3b79d131a2d13 — and THAT is what we want to store.  Now we can recreate that, and now our MD5 sum is incredibly difficult to break, with the pre-hashed value containing a 32 character “random” string, plus the original 8.

Getting started with Linux and the Command Line

Thursday, October 29th, 2009

Linux is great.  If you are in to developing websites, chances are, you’ll be working with Linux.  Problem is, a lot of people are afraid of the command line, or just don’t know enough commands to be comfortable working on a server via SSH.

Here are a few commands you’ll need to know to get started:

1. cd

cd stands for ‘change directory’ and is one you’ll probably use most frequently.  The syntax is very simple:

cd destination

A few tricks to know when working with this command:

cd ..

Changes to the directory UP one hierarchical level.

cd ../..

Changes to the director UP two hierarchical levels.. etc.

cd ../myFolder

Changes to a folder called ‘myFolder’ which is a subfolder of the current parent folder.  This is a relative path.

cd /

Changes to the root folder of the filesystem.

cd /var/www

Change to an absolute path.

cd ~

Change to your shell’s home directory.  By default, this is your system home directory, such as /home/yourUsername

cd ~/Desktop

Change to the Desktop folder under your home directory, equivalent to something such as cd /home/yourUsername/Desktop

2. cp

cp is the copy command, and is another frequently used command.  This is another command with very simple syntax.  Learning the syntax of cd is useful for using cp. The syntax is:

cp file-to-be-copied.php /destination/newfilename.php

Here are a few examples and tips for working with cp:

cp index.php home.php

Creates a copy of the index.php file, named home.php

cp index.php /someDirectory

Creates an index.php under the folder /someDirectory.  Not supplying the new name gives the copy the same name, index.php

cp someDirectory/ /destination/

Creates a folder ‘someDirectory’ under the ‘/destination’ folder.  This doesn’t copy any of the files, just the folder itself.

cp someDirectory/ newDirectoryName/

Creates a folder in the same directory with the name ‘newDirectoryName’ .. again, no files are copied just the folder (and its ownership/permissions). Apply a relative or absolute path before the directory name to create it somewhere else.

cp -r someDirectory/ newDirectoryName/

Creates a copy of the directory ‘someDirectory’ named ‘newDirectoryName’.  using the ‘-r’ flag will copy the folders contents “recursively.”

3. ls

ls is the command used to list all of the files in your present working directory.  It is as simple as typing: ls.  You can add flags for more views:

ls -a

will show you ALL files .. includes the hidden files (hidden files start with period, such as “.htaccess”)

ls -l

will show you the files in a list format. This method shows you more information about the file, such as the owner, the size, and the last modification date.

Combine the two flags, to get ls -al and you will see all files in a list format

4. pwd

pwd echoes out your “Present Working Directory” to the screen.  Cool.

5. rm

rm is the always useful remove command.  Type

rm filename.php

to remove the file ‘filename.php’. There are a lot of flags to be used with rm, but they can be dangerous. We’ll wait until you are more comfortable in the command line.

6. rmdir

rmdir is rm’s brother. rmdir clearly stands for “Remove Directory”.  You can only remove a directory that is empty.  If its not empty, you’ll first need to delete all of the files in the directory.  There are easier ways to remove things in bulk, or to remove non-empty directories, but as I said, they can be dangerous.  We’ll wait until you are more comfortable in the command line. :)

7. mv

mv stands for Move.  It is the command you’ll use to relocate files.  You can consider moving a file to be the same thing as renaming it.  Renaming a file from “fileA.php” to “fileB.php” is the same as moving its location to be “/directory/fileA.php to /directory/fileB.php.

Use mv as:

mv fileA.php fileB.php

to rename fileA to fileB.  Or you can use mv like:

mv fileA.php /some/other/dir/

to relocate fileA.php to /some/other/dir/fileA.php

This is all I have for now.  There will hopefully be more later.  Enjoy, n00bs :)

A handful of awesome websites

Wednesday, October 28th, 2009

Here is a handful of websites that I’ve found to be just plain awesome.  If you, too, create web pages for a living, I think you’ll dig.

  1. Iconfinder.net
  2. WebDesignDev
  3. GeoCities :)
  4. Quirksmode
  5. InstantDomainSearch
  6. Cooltext (For those not so professional in photoshop or gimp)
  7. Logomaker

That’s all I got right now.  This is what I use a lot for inspiration or resources.  You should already be  aware of most, if not all, of these sites.  Just giving them their due respect.

To all my readers, I’m sorry.

Wednesday, October 28th, 2009

This one goes out to all my readers.  Its been almost two weeks since I set up this blog and I’m just now posting my second post.  To make matters worse, this isn’t even a relevant post.  I will say I started a couple drafts, and soon I should have a real content-related post up.  I just wanted to take the time and say, “I haven’t forgotten about you.”

So here it is, I’m sorry readers of my blog.  I’ll now call each of you out by name, to show my sincerity:

Googlebot 2.1 – You were my first loyal reader. Thanks for your continued support!
Joker – You shared that awesome link about iPhones via the comments section.  I am eternally grateful! Thanks again!

It’s got that new blog smell

Friday, October 16th, 2009

Hi.  Nice to meet you. My name is Sean Jordan, and I make web sites.  I’d like to use this blog as a way to share some tips, great scripts, cool websites, and any other randomness I feel fitting.