Welcome!

Welcome to the official BlackBerry Support Community Forums.

This is your resource to discuss support topics with your peers, and learn from each other.

inside custom component

Java Development

Use Advanced Encryption

by BlackBerry Development Advisor ‎02-16-2010 01:38 PM - edited ‎09-16-2010 03:23 PM (4,473 Views)

Summary

 

This article applies to the following:

  • BlackBerry® wireless device
  • BlackBerry Java™ Development Environment (JDE)

Description

 

Data sent between a BlackBerry device and the BlackBerry Enterprise Server™ is encrypted using Triple DES (Date Encryption Standard) or AES (Advanced Encrption Standard). This is performed automatically and does not require application implementation to use it.

 

There are cases where encrypting data can be required, such as secure communication with an external application using the BlackBerry Mobile Data Server. Communication between the BlackBerry and BlackBerry Mobile Data Server would be automatically encrypted, but communication between the BlackBerry Mobile Data Server and an application server would not unless implemented in the BlackBerry application.

 

Note: The BlackBerry supports https, tls and ssl for secure communication beyond the BlackBerry Mobile Data Server.

 

The following is an example of how to use advanced encryption using AES on the BlackBerry device:

 

 

/*
* AdvancedCryptoDeveloperLab.java
*
* ©; Research In Motion Limited, 2003-2003
*/

package com.rim.samples.crypto;
import java.io.*;
import net.rim.device.api.crypto.*;
import net.rim.device.api.util.*;

/**
* This class provides the implementation for the Advanced Crypto Developer Lab excercise.
* This exercise will help you develop the necessary skills for utilizing public key
* cryptography in your applications.
*/
public class AdvancedCryptoDeveloperLab
{
public static void main( String[] args )
{
try {
String message = "Welcome to the Advanced Tutorial for the Crypto API";
byte[] data = message.getBytes();

// Create the RSAKeyPair that will be used for all of these operations.
RSAKeyPair senderKeyPair = new RSAKeyPair( new RSACryptoSystem( 1024 ));
RSAKeyPair recipientKeyPair = new RSAKeyPair( new RSACryptoSystem( 1024 ));

// First, we want to sign the data with the sender's private key.
byte[] signature = sign( senderKeyPair.getRSAPrivateKey(), data );

// Next, we want to encrypt the data for the recipient.
byte[] ciphertext = encrypt( recipientKeyPair.getRSAPublicKey(), data );

///////////////////////////////////////////////////////////////////////////
/// At this point pretend that the data has been sent to the recipient ///
/// and the recipient is going to decrypt and verify the data. ///
///////////////////////////////////////////////////////////////////////////

// Decrypt the data.
byte[] plaintext = decrypt( recipientKeyPair.getRSAPrivateKey(), ciphertext );

// Verify that the decrypted data equals the original message.
String message2 = new String( plaintext );

if( message.equals( message2 )) {
// The encryption/decryption operation worked as expected.
System.out.println( "Congratulations! You just encrypted and decrypted data." );
} else {
System.out.println( "Oops. The decrypted message should equal the original.
Check your code." );
}

// Verify the signature.
boolean verified = verify( senderKeyPair.getRSAPublicKey(), data, signature );

if( verified ) {
System.out.println( "Congratulations! You just signed and verified data." );
} else {
System.out.println( "Oops. The signature was not verified. Check your code." );
}
} catch( CryptoException e ) {
System.out.println( "An unexpected exception occurred.
Please verify your work or ask for help." );
} catch( IOException e ) {
System.out.println( "An unexpected exception occurred.
Please verify your work or ask for help." );
}
}

/**
* Encrypt the plaintext passed into this method using the public key.
* The ciphertext should be returned from the method.
* @param publicKey an RSAPublicKey that should be used for encrypting the data.
* @param plaintext the data to be encrypted.
* @return the ciphertext or encrypted data.
*/
private static byte[] encrypt( RSAPublicKey publicKey, byte[] plaintext )
throws CryptoException, IOException
{
// Create the encryptor engine.
RSAEncryptorEngine engine = new RSAEncryptorEngine( publicKey );

// Use the OAEP padding for the encryption. Note that this
// defaults to using SHA1.
OAEPFormatterEngine fengine = new OAEPFormatterEngine( engine );

ByteArrayOutputStream output = new ByteArrayOutputStream();
BlockEncryptor encryptor = new BlockEncryptor( fengine, output );

// Write out the data.
encryptor.write( plaintext );
encryptor.close();
output.close();

return output.toByteArray();
}

/**
* Decrypt the ciphertext passed into this method using the public key.
* The plaintext should be returned from the method.
* @param privateKey an RSAPrivateKey that should be used for decrypting the data.
* @param ciphertext the data to be decrypted.
* @return the plaintext or decrypted data.
*/
private static byte[] decrypt( RSAPrivateKey privateKey, byte[] ciphertext )
throws CryptoException, IOException
{
// Create the decryptor engine.
RSADecryptorEngine engine = new RSADecryptorEngine( privateKey );

// Use the OAEP padding.
OAEPUnformatterEngine uengine = new OAEPUnformatterEngine( engine );

ByteArrayInputStream input = new ByteArrayInputStream( ciphertext );
BlockDecryptor decryptor = new BlockDecryptor( uengine, input );

// Now, read in the data. Remember that the last 20 bytes represent the
// SHA1 hash of the decrypted data.
byte[] temp = new byte[ 100 ];
DataBuffer buffer = new DataBuffer();

for( ;; ) {
int bytesRead = decryptor.read( temp );
buffer.write( temp, 0, bytesRead );

if( bytesRead < 100 ) {
// We ran out of data.
break;
}
}

return buffer.getArray();
}

/**
* Use the data and the private key to produce a signature that will provide
* data integrity and data authentication.
* @param privateKey the private key to use for signing the data.
* @param data the data to be signed.
* @return the signature.
*/
private static byte[] sign( RSAPrivateKey privateKey, byte[] data )
throws CryptoException
{
// Create the PKCS1 signature signer. This is the standard method used
// to create a signature with an RSA key. Note that by default this uses
// a SHA digest.
PKCS1SignatureSigner signer = new PKCS1SignatureSigner( privateKey );
signer.update( data );

byte[] signature = new byte[ signer.getLength() ];
signer.sign( signature, 0 );

return signature;
}

/**
* Use the data and the public key to verifying that the signature is correct.
* @param publicKey the Public Key to use for verification.
* @param data the data that the signature was created with.
* @param signature the signature on the data.
* @return a boolean indicating whether or not the signature is valid.
*/
private static boolean verify( RSAPublicKey publicKey, byte[] data, byte[] signature )
throws CryptoException
{
PKCS1SignatureVerifier verifier = new PKCS1SignatureVerifier( publicKey, signature, 0 );
verifier.update( data );
return verifier.verify();
}
}

 

 

Contributors
Users Online
Currently online: 26 members 1,373 guests
Please welcome our newest community members: