In PHP, cryptography is mostly used for encrypting information and generating checksum or digests. Using cryptography can provide a lot of added security when done right, but it can also give a false feeling of security.
This paragraph can only give you some ideas on the use of cryptography. If you really want to get your hands dirty, you should consult some good information on cryptography. The standard work on cryptography is Bruce Schneier’s Applied Cryptography, which is both very thorough and surprisingly readable. His website (www.counterpane.com/labs.html) is also a good starting point for finding cryptographic information on the Internet.
In PHP most of the cryptographic functions are provides by the mcrypt (hq.hellug.gr/~mcrypt/) and mhash (www.schumann.cx/mhash/) libraries. You need to install these libraries on your system and configure PHP to use them using the --with-mcrypt and --with-hash options.
When compiling PHP with mcrypt support it is possible you will run into compilation problems. The compiler will start complaining about RC2 (and other things) not being declared. This is caused by the fact that the file functions/mcrypt.c in PHP versions 3.0.12 and older is not completely in-sync with current releases of the mcrypt library. The preferred way of fixing this would be upgrading to PHP version 3.0.13. Another way to fix this would be to get a newer version of mcrypt.c from the CVS repository. You can do this by following this URL: http://cvs.php.net/cvsweb.cgi/functions/mcrypt.c?rev=1.11
There are essentially two types of cryptography: public key and secret key. Sometimes the terms asymmetric and symmetric are used.
Public key cryptography can be called asymmetric, because the keys for encrypting and decrypting a message are not the same: you publish the public key and keep your private key a secret. After you have published your public key, people can send you messages only you can read. To do this, they encrypt the messages with your public key. To decrypt the message one would need the private key. Since you are the only one who has access to this key, you are the only one who can read this message. You can also use your private key to sign messages. People can use your public key to verify that you have written a message. Such a digital signature could be used in court to prove someone sent an email message. The PGP (Pretty Good Privacy) and GPG (GNU Privacy Guard, the free alternative to PGP) software can be used with PHP to do public key cryptography. You can find more information about PGP and GPG at www.pgp.com and www.gnupg.org. The problem with public key cryptography is that it is rather slow and the keys are huge (usually 512 to 2048 bits).
Secret key cryptography can be called symmetric because the same key is used for encrypting and decrypting data. This is the reason why you need to keep the key absolutely safe. In fact, in programs such as PGP and GPG public key cryptography is mostly used for signing messages and sending secret keys in a secure fashion. The actual encryption of the message is done with secret key cryptography. As noted before, secret key cryptography is much faster and uses comparatively small keys (usually 40 – 128 bits).
If you have a need for encryption in your application, you will probably want to use secret cryptography. There is a whole range of algorithms to choose from: DES, TripleDES, Blowfish, IDEA and RC5, these are only a few. It is important to know that some algorithms are considered insecure (such as DES and RC2), while others are considered to be very secure (Blowfish, RC5 and IDEA for example). The security supplied by the host algorithm depends on the key size. Not very long ago, a group PCs connected via the Internet (in effect creating a very fast supercomputer) decrypted a message that had been encrypted with the RC5 algorithm using a 56-bit key in less than two days (www.distributed.net). If the message had been encrypted with a 128-bit key, this would have been impossible. Simply said, encrypting a message with a 41-bit key is twice as secure as encrypting it with a 40-bit key. In practice it is more complex than this, but this should make it clear how much more secure than a 128-bit key is. In PHP, encryption will mostly be used to exchange information between two webservers or between a webserver and a browser in a secure way.
What may be confusing is the fact that most encryption algorithms (or ciphers) can be run in several modes. Encryption algorithms can be used in four different modes:
ECB, Electronic Code Book
ECB mode is best used for encrypting small pieces of data that contain of which the contents are mostly random (such as other encryption keys). Because of the way ECB mode works it is probably safer to avoid using this mode, unless have a good reason to use ECB mode. You should use CBC mode, since that mode is considerably safer. With ECB mode, each block of data (you can get the size of a block with the mcrypt_get_block_size function) is separately encrypted.
CBC, Cipher Block Chaining
CBC mode is probably the mode you will use most often. If you don’t exactly know what mode to use, use this one.
CFB, Cipher Feedback
This is meant for encrypting byte streams. You probably will not need to use this mode.
OFB, Output Feedback
The use of the OFB mode is similar to CFB mode. You probably will not need OFB mode.
Below is an example of the use of the mcrypt functions. This example uses encryption in CBC mode.
$encrypteddata now contains an encrypted version of the array. The extra bin2hex step is necessary because mcrypt_ecb outputs binary data. You will need to use bin2hex, urlencode or another, similar function before you can use it in a cookie or a form variable. You decrypt the data with the same process in reverse.
For the CBC, CFB and OFB mode you can also specify an initialization vector (IV). This adds some extra security. Both sides need to have the same IV. If the decrypting side does not have the correct IV, the data cannot be decrypted. You could generate an IV from a password, as shown below.
(You may need to use MCRYPT_RAND instead of MCRYPT_DEV_RANDOM on some servers. If you do, please do not forget to initialize the random generator.)
Note that storing data on your server is probably not going to add any security. The reason for that is the fact that you will need to store the key on the same server, effectively defeating any benefits storing data in an encrypted form had.
Using Hash Functions
Most encryption algorithms can also be used to generate a hash or digest. The most well known example of a hash is probably a CRC value, used by compression programs (such as ARJ or GZIP) to check whether the archive was damaged or not. The hash of a piece of data can uniquely identify that piece of data.
Hashes are often used for storing passwords. If you store the hash of a password, you have a away of verifying a password when someone logs in without having to store the actual passwords on your server. For instance, the htpasswd program that comes with Apache generates a password file that contains hashes of the passwords you give it. It is very difficult, almost impossible, to generate a working password from a hash of that password.
In PHP scripts, you can use the crypt function to generate a hash from a password. If you need to generate a hash of a much larger piece of data, you should use the mhash module. In order to use the mhash function PHP needs to be compiled with mhash support. Unlike the mcrypt module the mhash module should compile without any problems.
Below is an example of using mhash to generate the 32-bit CRC of a piece of data.
The call to bin2hex is necessary because mhash outputs binary data, just like the mcrypt functions.
©1998 Wrox Press Limited, US and UK.
blog comments powered by Disqus