Use non-random initialization vector (IV)
使用非随机初始化向量(IV)
描述
使用非随机初始化向量会使应用程序容易受到字典攻击。
以下示例演示了硬编码静态IV的不当设置:
public; class InsecureExample {
@Override
public void; run() throws; Exception;{
byte;[]; IV = "0123456789abcdef".getBytes();
String; clearText = "Jan van Eyck was here 1434";
String; key = "ThisIs128bitSize";
SecretKeySpec; skeySpec = new SecretKeySpec(key.getBytes(), "AES");
Cipher; cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
cipher;.init(Cipher.ENCRYPT_MODE;, skeySpec;, new; IvParameterSpec(IV))
byte;[]; encryptedMessage = cipher.doFinal(clearText.getBytes());
Log;.i(TAG, String.format("Message: %s";, Base64;.encodeToString(encryptedMessage, Base64.DEFAULT;)))
}
}
建议
为了缓解与IV相关的加密缺陷,请考虑以下建议:
- 每次加密使用唯一的IV: 每次加密操作都必须使用唯一的IV。使用相同的密钥重复使用相同的IV可能会导致安全漏洞,例如暴露密文中的模式或助长重放攻击等。
- 随机性: IV应使用密码学上安全的随机数生成器(Java为
SecureRandom,Swift为SecRandomCopyBytes)生成。这种随机性确保攻击者无法预测IV,从而防止加密安全性被削弱。 - IV长度: IV的长度取决于所使用的加密算法。例如,在AES中,AES-128的IV长度通常为128位(16字节),AES-192为192位(24字节),AES-256为256位(32字节)。务必为加密算法使用适当长度的IV。
import java.security.SecureRandom
import javax.crypto.spec.IvParameterSpec
object IVGenerator {
fun generateIV(length: Int): ByteArray {
val iv = ByteArray(length)
val secureRandom = SecureRandom()
secureRandom.nextBytes(iv)
return iv
}
}
fun main() {
val ivLength = 16 // Length of IV in bytes
val iv = IVGenerator.generateIV(ivLength)
println("Generated IV: ${bytesToHex(iv)}")
}
fun bytesToHex(bytes: ByteArray): String {
return bytes.joinToString("") { "%02x".format(it) }
}
import CryptoKit
func generateIV(length: Int) -> Data {
var iv = Data(count: length)
_ = iv.withUnsafeMutableBytes { ivPtr in
guard let ivBaseAddress = ivPtr.baseAddress else { return }
_ = SecRandomCopyBytes(kSecRandomDefault, length, ivBaseAddress)
}
return iv
}
let ivLength = 16 // Length of IV in bytes
let iv = generateIV(length: ivLength)
print("Generated IV: \(iv.hexEncodedString())")
extension Data {
func hexEncodedString() -> String {
return map { String(format: "%02hhx", $0) }.joined()
}
}
import 'dart:typed_data';
import 'dart:math';
Uint8List generateIV(int length) {
final random = Random.secure();
return Uint8List.fromList(List.generate(length, (index) => random.nextInt(256)));
}
void main() {
final ivLength = 16; // Length of IV in bytes
final iv = generateIV(ivLength);
print('Generated IV: ${bytesToHex(iv)}');
}
String bytesToHex(Uint8List bytes) {
return bytes.map((byte) => byte.toRadixString(16).padLeft(2, '0')).join();
}
链接
标准
- OWASP_MASVS_L1:
- MSTG_CRYPTO_2
- MSTG_CRYPTO_3
- MSTG_CRYPTO_4
- OWASP_MASVS_L2:
- MSTG_CRYPTO_2
- MSTG_CRYPTO_3
- MSTG_CRYPTO_4
- PCI_STANDARDS:
- REQ_2_2
- REQ_3_6
- REQ_3_7
- REQ_4_2
- REQ_6_2
- OWASP_MASVS_v2_1:
- MASVS_CRYPTO_1
- MASVS_CRYPTO_2
- SOC2_CONTROLS:
- CC_2_1
- CC_4_1
- CC_6_7
- CC_7_1
- CC_7_2
- CC_7_4
- CC_7_5
- CNIL_FOR_DEVELOPERS:
- DEVELOPERS_4_1_4
- HIPAA_CONTROLS:
- SECURITY251
- SECURITY212
- SECURITY213