genAESKeyFromPW(password, salt64[, length])
Last updated October 02, 2012
Version: 1 | Requires: CF9 | Library: SecurityLib
Description:
Normally when using AES with encrypt() and decrypt() you would use generateSecretKey("AES") to generate an encryption key. This key needs to be stored somewhere in order to decrypt the data encrypted with that key. In some cases, you may not want to store the encryption key but generate one based on other data, such as a password provided by the user (which you would then not store, so not even you can decrypt the data without the user's decryption password). This function provides a way to generate an AES key based on a provided password and salt.
Return Values:
Returns a string that is the generated encryption key.
Example:
<!--- Standard key generation method, generates a random AES key. --->
<cfset generatedKey = generateSecretKey("AES") />
<!--- Password method, generates an AES key based on a password and salt. --->
<!--- User would provide their encryption password to the system. --->
<!--- Password is case-sensitive and could be passed through LCase() or UCase() to negate case. --->
<cfset myPassword = "secret password" />
<!--- The system would generate a salt in Base64 for their account and store it along with their account information. --->
<!--- The salt is used by the key generator to help mitigate against dictionary attacks and is required. --->
<!--- It's recommended to use a salt generated based on Java's SecureRandom object. --->
<cfset mySalt64 = toBase64("some salt value") />
<!--- Call the password-based key generator with the password and salt. --->
<cfset generatedKey = genAESKeyFromPW(myPassword, mySalt64) />
<!--- The generated key drops right in where a key from generateSecretKey("AES) would go. --->
<cfset encrypted = encrypt("Hello World!", generatedKey, "AES", "Base64") />
<p><cfoutput>encrypted: #encrypted#</cfoutput></p>
<!--- Decryption works the same way. --->
<cfset decrypted = decrypt(encrypted, generatedKey, "AES", "Base64") />
<p><cfoutput>decrypted: #decrypted#</cfoutput></p>
Parameters:
Name | Description | Required |
---|---|---|
password | Password to use for encryption key | Yes |
salt64 | Salt to use for encyption key | Yes |
length | Key length | No |
Full UDF Source:
/**
* Generates an AES encryption key from a provided password and salt.
* v1.0 by Justin Scott
* v1.1 by Adam Cameron - converted to script, fixed trivial logic error with length argument
*
* @param password Password to use for encryption key (Required)
* @param salt64 Salt to use for encyption key (Required)
* @param length Key length (Optional)
* @return Returns a string that is the generated encryption key.
* @author Justin Scott (leviathan@darktech.org)
* @version 1.1, October 2, 2012
*/
string function genAESKeyFromPW(required string password, required string salt64, numeric length=128){
// Decode the salt value that was provided.
var salt = toString(toBinary(arguments.salt64));
// Go fetch Java's secret key factory so we can generate a key.
var keyFactory = createObject("java", "javax.crypto.SecretKeyFactory").getInstance("PBKDF2WithHmacSHA1");
// Define a key specification based on the password and salt that were provided.
var keySpec = createObject("java", "javax.crypto.spec.PBEKeySpec").init(
arguments.password.toCharArray(), // Convert the password to a character array (char[])
salt.getBytes(), // Convert the salt to a byte array (byte[])
javaCast("int", 1024), // Iterations as Java int
javaCast("int", arguments.length) // Key length as Java int (192 or 256 may be available depending on your JVM)
);
// Initialize the secret key based on the password/salt specification.
var tempSecret = keyFactory.generateSecret(keySpec);
// Generate the AES key based on our secret key.
var secretKey = createObject("java", "javax.crypto.spec.SecretKeySpec").init(tempSecret.getEncoded(), "AES");
// Return the generated key as a Base64-encoded string.
return toBase64(secretKey.getEncoded());
}
Search CFLib.org
Latest Additions
Raymond Camden added
QueryDeleteRows
November 04, 2017
Leigh added
nullPad
May 11, 2016
Raymond Camden added
stripHTML
May 10, 2016
Kevin Cotton added
date2ExcelDate
May 05, 2016
Raymond Camden added
CapFirst
April 25, 2016