Click Here!
home account info subscribe login search My ITKnowledge FAQ/help site map contact us


 
Brief Full
 Advanced
      Search
 Search Tips
To access the contents, click the chapter and section titles.

Perl CGl Programming: No experience required.
(Publisher: Sybex, Inc.)
Author(s): Erik Strom
ISBN: 0782121578
Publication Date: 11/01/97

Bookmark It

Search this book:
 
Previous Table of Contents Next


Reading and Writing Encrypted Passwords

Consider the problem of creating a password for a Web page. The most obvious solution would be to first think of a good password, then store it in a file that you could open any time the password is required to verify whether it’s the correct one or not.

But how would you store it? In a text file? Theoretically, anyone with access to your system could open the file and read the password, thus breaking through your security barrier. Could you hide the password file somewhere? Of course, but then it’s only secure until the wrong person finds it.

The best solution is to encode the password in a way that only you can decode. That way, any number of people can read it, but they won’t be able to decipher it.

This is precisely the way passwords are stored on UNIX systems. But how do you encode—or encrypt—the passwords in a way that would be difficult to break, except by the right people? The solution on UNIX is a function in the C-language standard library called crypt, which, based on a key that you provide, takes a string and so mangles it that it can be stored in a text file in an obvious place for all the world to see. When a user enters a password, the system software uses crypt again to mangle what was entered and compares it with the version in the password file. If they match, the password’s good.

Because of Perl’s deep roots in UNIX and the C programming language, it also includes the crypt function. You can use it to password-protect a Web page.

As usual, we’ll start small and work up from there. The following program will start you on your way to encrypting and decrypting passwords:

   #!/perl/bin/perl

   # encrypt.pl
   # First version. Takes a password from the command
   # line, encrypts it, and prints it to the screen.

       $PassWordString = $ARGV[0];       # Get command line argument.

   # Use crypt() with a "salt" of ""to encrypt the string
   # that was entered.

       $EncryptedPassword = crypt ($PassWordString, "");
   # Now print the encrypted version back to the screen.
       print "Encrypted password is $EncryptedPassword\n";
   #                    End encrypt.pl

Save this little program as encrypt.pl and run it from the command line a few times with different arguments. You can see in the output, illustrated in Figure 13.8, how crypt has worked to render unreadable the original string.


Figure 13.8:  Some possible passwords and their encrypted versions

Creating a Password File

The stripped-down version of encrypt.pl is useful only so you can see what happens to a string when crypt gets through with it. It is clear from running this example that the encrypted string bears no resemblance at all to what you typed in.

An explanation of exactly how crypt works could easily fill a doctoral dissertation, so we won’t go into its encryption algorithms here. How secure is it? UNIX gurus and encryption experts would maintain that it can be broken, but not easily and not without the help of a very powerful computer running very sophisticated software. Thieves and vandals look for the easy marks; it is doubtful that many miscreants will want to employ the kind of firepower that would be required to break your password file, assuming they can even get to it.

Besides, crypt is secure enough that you are restricted by federal law from exporting software that uses it!

As for the call to crypt itself, it’s fairly straightforward. The Perl specification for the function goes like this:

   crypt (PLAINTEXT, SALT);

where PLAINTEXT is the unencrypted string and SALT is either an initial key—we used an empty string in the first version of encrypt.pl—or the encrypted string. The function returns PLAINTEXT encrypted according to SALT, and that’s how you use it to check for a valid password. The following Perl conditional expression shows how it works:

   if (crypt ($PasswordString, $EncryptedPassword) eq $EncryptedPassword)
      {
      # The password is OK.
   }

A few simple modifications to encrypt.pl will enable you to use the script to create a password file.

   #!/perl/bin/perl

   # encrypt.pl
   # Second version. Takes a password from the command
   # line, encrypts it, and writes it to a file.

       $PwdFileName = "password";       # A name for password file.
       $PassWordString = $ARGV[0];      # Get command line argument.

   # Use crypt() with a "salt" of "" to encrypt the string
   # that was entered.

       $EncryptedPassword = crypt ($PassWordString, "");

   # Now create the password file and write the encrypted string.

       open (PWD, ">$PwdFileName") ||
           die "Can’t open $PwdFileName for writing: $!\n";

       print PWD $EncryptedPassword;
       close (PWD);

   #                    End encrypt.pl

There’s nothing in this script that you haven’t done before. Now you can move it to the directory in which you will store the password file and run it with your chosen password as an argument. We’ll presume that you don’t have anyone looking over your shoulder while you do this!


WARNING:  Do not store encrypt.pl in any directory from which CGI programs can be started through the Web server. It could be entered in an intruder’s Web browser as a URL, and that would be the end of your password file.

Just to make sure the password works, let’s create another Perl script to test it.

   #!/perl/bin/perl

   # test.pl
   # Testing the password file…

       $PwdFileName = "password";
       $PasswordString = $ARGV[0];

   # Open the file…

       open (PWD, $PwdFileName) ||
           die "Can’t open $PwdFileName for reading: $!\n";

   # Read the encrypted password.

       $EncryptedPassword = <PWD>;

   # Do the comparison with crypt()

       if (crypt ($PasswordString, $EncryptedPassword) eq $EncryptedPassword)
           {
           print "Password is OK\n";
           }
       else
           {
           print "Incorrect password…Try again\n";
           }

   #                    End test.pl

Save this script as test.pl and run it a few times, using the real password as an argument and then using some incorrect ones. You should see something similar to the display in Figure 13.9.


Figure 13.9:  The results of a Perl script to test the password file


Previous Table of Contents Next


Products |  Contact Us |  About Us |  Privacy  |  Ad Info  |  Home

Use of this site is subject to certain Terms & Conditions, Copyright © 1996-2000 EarthWeb Inc.
All rights reserved. Reproduction whole or in part in any form or medium without express written permission of EarthWeb is prohibited.