什么是AES?
引用中文维基百科的定义(浏览全文):
密码学中的高级加密标准(Advanced Encryption Standard,AES),又称Rijndael加密法,是美国联邦政府采用的一种区块加密标准。这个标准用来替代原先的DES,已经被多方分析且广为全世界所使用。经过五年的甄选流程,高级加密标准由美国国家标准与技术研究院 (NIST)于2001年11月26日发布于FIPS PUB 197,并在2002年5月26日成为有效的标准。2006年,高级加密标准已然成为对称密钥加密中最流行的算法之一。该算法为比利时密码学家Joan Daemen和Vincent Rijmen所设计,结合两位作者的名字,以Rijdael之命名之,投稿高级加密标准的甄选流程(Rijdael的发音近于 “Rhine doll”)。
AES 加密过程是在一个4×4的字节矩阵上运作,这个矩阵又称为“体(state)”,其初值就是一个明文区块(矩阵中一个元素大小就是明文区块中的一个 Byte)。(Rijndael加密法因支援更大的区块,其矩阵行数可视情况增加)加密时,各轮AES加密循环(除最后一轮外)均包含4个步骤:
1. AddRoundKey — 矩阵中的每一个字节都与该次循环的子密钥(round key)做XOR运算;每个子密钥由密钥生成方案产生。 2. SubBytes — 透过一个非线性的替换函数,用查找表的方式把每个字节替换成对应的字节。 3. ShiftRows — 将矩阵中的每个横列进行循环式移位。 4. MixColumns — 为了充分混合矩阵中各个直行的操作。这个步骤使用线性转换来混合每行内的四个字节。
最后一个加密循环中省略MixColumns步骤,而以另一个AddRoundKey取代。

如何在Android平台应用AES加密技术呢?
创建加密/解密类源代码:
01 |
import java.security.SecureRandom; |
03 |
import javax.crypto.Cipher; |
04 |
import javax.crypto.KeyGenerator; |
05 |
import javax.crypto.SecretKey; |
06 |
import javax.crypto.spec.SecretKeySpec; |
08 |
public class SimpleCrypto { |
10 |
public static String encrypt(String seed, String cleartext) throws Exception { |
11 |
byte [] rawKey = getRawKey(seed.getBytes()); |
12 |
byte [] result = encrypt(rawKey, cleartext.getBytes()); |
16 |
public static String decrypt(String seed, String encrypted) throws Exception { |
17 |
byte [] rawKey = getRawKey(seed.getBytes()); |
18 |
byte [] enc = toByte(encrypted); |
19 |
byte [] result = decrypt(rawKey, enc); |
20 |
return new String(result); |
23 |
private static byte [] getRawKey( byte [] seed) throws Exception { |
24 |
KeyGenerator kgen = KeyGenerator.getInstance( "AES" ); |
25 |
SecureRandom sr = SecureRandom.getInstance( "SHA1PRNG" ); |
28 |
SecretKey skey = kgen.generateKey(); |
29 |
byte [] raw = skey.getEncoded(); |
33 |
private static byte [] encrypt( byte [] raw, byte [] clear) throws Exception { |
34 |
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES" ); |
35 |
Cipher cipher = Cipher.getInstance( "AES" ); |
36 |
cipher.init(Cipher.ENCRYPT_MODE, skeySpec); |
37 |
byte [] encrypted = cipher.doFinal(clear); |
41 |
private static byte [] decrypt( byte [] raw, byte [] encrypted) throws Exception { |
42 |
SecretKeySpec skeySpec = new SecretKeySpec(raw, "AES" ); |
43 |
Cipher cipher = Cipher.getInstance( "AES" ); |
44 |
cipher.init(Cipher.DECRYPT_MODE, skeySpec); |
45 |
byte [] decrypted = cipher.doFinal(encrypted); |
49 |
public static String toHex(String txt) { |
50 |
return toHex(txt.getBytes()); |
52 |
public static String fromHex(String hex) { |
53 |
return new String(toByte(hex)); |
56 |
public static byte [] toByte(String hexString) { |
57 |
int len = hexString.length()/ 2 ; |
58 |
byte [] result = new byte [len]; |
59 |
for ( int i = 0 ; i < len; i++) |
60 |
result[i] = Integer.valueOf(hexString.substring( 2 *i, 2 *i+ 2 ), 16 ).byteValue(); |
64 |
public static String toHex( byte [] buf) { |
67 |
StringBuffer result = new StringBuffer( 2 *buf.length); |
68 |
for ( int i = 0 ; i < buf.length; i++) { |
69 |
appendHex(result, buf[i]); |
71 |
return result.toString(); |
73 |
private final static String HEX = "0123456789ABCDEF" ; |
74 |
private static void appendHex(StringBuffer sb, byte b) { |
75 |
sb.append(HEX.charAt((b>> 4 )& 0x0f )).append(HEX.charAt(b& 0x0f )); |
使用方法:
加密 –
1 |
String encryptingCode = SimpleCrypto.encrypt(masterPassword,originalText); |
解密 –
1 |
String originalText = SimpleCrypto.decrypt(masterpassword, encryptingCode); |
masterpassword: 密码。
encryptingCode:加密后的字符串。
originalText: 需要加密的字符串。
|