Unlocking the Secrets of Java Cryptography Extensions: The Basics
In today's wired world, securing data from loss or theft is a top priority for companies that want to stay out of the headlines. Data encryption is a valuable tool for protecting a company's most valuable asset: customer data. Here, you will learn about cryptography and using the Java Cryptography Extension (JCE) to provide the security needed to protect that data.
What Is Cryptography?
Before getting started with Java cryptography, it is helpful to have a basic understanding of what cryptography is. At its most basic level, cryptography is a means of taking human-readable information, called plaintext, performing an encryption algorithm called a cipher on the plaintext, and producing encoded output, called ciphertext, that cannot easily be interpreted. Decryption is the reverse process of taking the ciphertext and converting it back into plaintext.
To do this, both participants in this process need to know what cipher algorithm is being used and must have access to a key, which is a unique value that is applied to the cipher to produce ciphertext or plaintext, depending on whether one is encrypting or decrypting. The key can be private, meaning that both parties agree on the key value ahead of time, or can derive it somehow by computation. This is known as key agreement.
A key also can be public, meaning that the sending party publishes the key along with the data. When a public key is used, the recipient of the data receives a private key that was also generated at encryption time separately and uses this value to decrypt the data.
A password is an example of a private key. The parties exchanging data agree on the password ahead of time, and the sender encrypts the data based on the password. When the receiver decrypts the data, he enters the password, which is then applied to the cipher to obtain the plaintext version. This is not particularly secure, as it is a fairly trivial exercise to crack a password cipher with enough computing power. However, to make password-based encryption more secure, a random number, known as a salt, is often introduced into the encryption scheme.
Other, more secure private key encryption schemes, such as the Advanced Encryption Standard (AES), Data Encryption Standard (DES), and Triple-DES are widely used. These are examples of block ciphers, and apply the cipher algorithm to a set number of bits of data at one time based on the private key. Other ciphers, such as RC4, encrypt and decrypt data in varying lengths at one time, and may change how they behave depending on key characteristics or characteristics of the plaintext. Because most data is larger than a single block, the encryption algorithm is repeated over and over again on subsequent blocks of data until all of the data is encrypted. The encryption algorithm may compute variations on the key value used to do the encryption depending on which block of data is being encrypted. These approaches are much more secure than the simple transformation mechanism used by a password encryption scheme.
Public key encryption algorithms, such as Diffie-Hellman and RSA, rely on the fact that the private key that is used to decrypt the data cannot be derived from the public key used to encrypt it. The sender encrypts the data using the public key and generates a mathematically related private key that is then sent to the recipient. The recipient uses the private key and the published public key to decrypt the data.
The most secure protocol for doing any sort of encryption that involves sending a private key to the data recipient is to encrypt the data using one encryption scheme and to encrypt the key using another. This adds another layer of security to the exchange of information, because one cannot decrypt the data without correctly decrypting the key first.
Besides simply encrypting and decrypting data, cryptography in the information age now includes message integrity checking, authenticating the identity of the sender/receiver of the message, and the use of digital signatures.
Installing the JCE
The JCE is referred to as an "extension" because it was only available as an extension to the normally supplied Java class libraries in JDK1.2 and 1.3. As of JDK1.4 and higher, however, the JCE is included with every JDK release. This includes a service-provider API, which allows outside vendors to provide new, pluggable encryption algorithms conforming to the Java Cryptography Architecture specification (JCA), as well as Sun's implementation of the JCA, referred to as the "Sun JCE." In the following code examples, you will examine the use of the Sun JCE, and also learn how to set up a third-party JCE provider's class library for use in your Java programs. The examples use the BouncyCastle JCE implementation, which is available at http://www.bouncycastle.org/.
Before following any of the installation instructions, be absolutely certain you know where the JDK/JRE you are currently running is located. You may have multiple instances of the JDK/JRE on your machine, or possibly both the JDK and JRE. If you update the wrong version, you will likely see this exception when running the examples:
java.lang.SecurityException: Unsupported keysize or algorithm parameters
By default, the JRE is restricted to particular encryption algorithms and limited encryption strength, or so-called "strong encryption." This restriction is put in place so that the JCE and applications that use it can be freely imported by other countries whose governments restrict the use of cryptography. These restrictions are not applicable in most countries, so the first step is to install the unlimited strength policy files. First, download the unrestricted policy files by going to http://java.sun.com/javase/downloads/index_jdk5.jsp and clicking the link next to "Cryptography Extension (JCE) Unlimited Strength Jurisdiction Policy Files." The download file is currently called jce_policy-1_5_0.zip.
After downloading the file, unzip it using the appropriate zip tool for your platform. The file contains a directory called /jce, which contains the files local_policy.jar and us_export_policy.jar. To install the files, go to the $java_home/jre/lib/security folder, back up the existing strong-encryption files, and copy the unrestricted policy files to this directory.
Next, to set up the third-party JCE provider, you must set up the java.security file and include the provider's class libraries in the system's classpath. To update the java.security file, go to $java_home/jre/lib/security, edit the java.security file, and add the provider. The third-party provider must be placed after all of the Sun providers to avoid problems. A sample is shown below:
As you can see, entries 1-5 refer to the Sun JCE. The entry for the third-party software is entry 6, which refers to the provider's service provider class.
Now, to install the class libraries from BouncyCastle, download the complete class library suite, which is packaged in crypto-139.zip. After downloading and unzipping the file, you should see a directory called crypto-139, which contains all of the source code, signed .jar files, test classes, and other files provided by BouncyCastle for a complete build. Although you can build the appropriate .jar files yourself, it is more convenient to simply copy the ones provided from the /crypto-139/jars directory. Copy all of the .jar files for your particular version of the JDK—for example, files with "jdk15" in the name for JDK1.5—to your $java_home/jre/lib/ext directory, and you're done installing. This will install all of the features offered by BouncyCastle, including the JCE classes, certificate signing, Open PGP, and so forth.