importjavax.crypto.Cipher;importjavax.crypto.KeyGenerator;importjavax.crypto.SecretKey;importjavax.crypto.spec.GCMParameterSpec;importjavax.crypto.spec.IvParameterSpec;importjava.security.SecureRandom;importjava.util.Base64;publicclassAESUtil{privatestaticfinalStringAES="AES";publicstaticStringencrypt(String plaintext,byte[] key,String mode)throwsException{Cipher cipher =Cipher.getInstance(AES+"/"+ mode +"/PKCS5Padding");SecretKey secretKey =newSecretKeySpec(key,AES);
cipher.init(Cipher.ENCRYPT_MODE, secretKey);byte[] encrypted = cipher.doFinal(plaintext.getBytes());returnBase64.getEncoder().encodeToString(encrypted);}publicstaticStringdecrypt(String encryptedText,byte[] key,String mode)throwsException{Cipher cipher =Cipher.getInstance(AES+"/"+ mode +"/PKCS5Padding");SecretKey secretKey =newSecretKeySpec(key,AES);
cipher.init(Cipher.DECRYPT_MODE, secretKey);byte[] original = cipher.doFinal(Base64.getDecoder().decode(encryptedText));returnnewString(original);}publicstaticvoidmain(String[] args)throwsException{// Generate a random keyKeyGenerator keyGenerator =KeyGenerator.getInstance(AES);
keyGenerator.init(256);// AES-256SecretKey secretKey = keyGenerator.generateKey();byte[] key = secretKey.getEncoded();// Example usageString data ="Hello World";String encryptedECB =encrypt(data, key,"ECB");String decryptedECB =decrypt(encryptedECB, key,"ECB");String encryptedCTR =encrypt(data, key,"CTR");// For CTR, you need to provide an IVbyte[] iv =newbyte[16];// 128-bit IV for AESnewSecureRandom().nextBytes(iv);System.out.println("IV for CTR: "+Base64.getEncoder().encodeToString(iv));// For GCM, you need to provide an IV and specify the tag lengthbyte[] ivGCM =newbyte[12];// 96-bit IV for GCMnewSecureRandom().nextBytes(ivGCM);GCMParameterSpec gcmParamSpec =newGCMParameterSpec(128, ivGCM);Cipher gcmCipher =Cipher.getInstance("AES/GCM/NoPadding");
gcmCipher.init(Cipher.ENCRYPT_MODE, secretKey, gcmParamSpec);byte[] encryptedGCM = gcmCipher.doFinal(data.getBytes());byte[] tag = gcmCipher.getIV();// The tag is the IV used in GCM modeString encryptedGCMBase64 =Base64.getEncoder().encodeToString(encryptedGCM);System.out.println("Encrypted (GCM): "+ encryptedGCMBase64);System.out.println("Tag (GCM): "+Base64.getEncoder().encodeToString(tag));}}- 定义了一个`encrypt`和`decrypt`方法,它们接受模式作为参数。
- 对于CTR和GCM模式,需要提供一个初始化向量(IV)。使用`SecureRandom`生成了一个随机的IV。
- 对于GCM模式,还需要指定认证标签的长度,通常是128位。
- 加密和解密方法使用了`PKCS5Padding`填充方式,这在ECB和CTR模式中是合适的。然而,GCM模式通常使用`NoPadding`,因为GCM本身提供了认证机制,不需要填充。
-使用了`Base64`编码来处理加密后的字节数据,使其可以作为字符串打印或存储。