I'm trying to implement in swift
the equivalent of my code in java. Basically is an AES
implementation with GCM
padding and I'm using a key derivation for that. In swift
I'm using the CryptoSwift
library.
My issue is that I cannot get the same encrypted text in swift
.
After a very long research I couldn't find any solutions for my problem, I even saw the test code of the CryptoSwift
library repository to get any ideas but with no luck
This is my java code:
GCMParameterSpec ivParameterSpec = new GCMParameterSpec(128, "ivVector".getBytes());
SecretKeyFactory secretKeyFactory = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
KeySpec keySpec = new PBEKeySpec("myPassword".toCharArray(), "salt".getBytes(), 1000, 256);
SecretKey tmp = secretKeyFactory.generateSecret(keySpec);
key = new SecretKeySpec(tmp.getEncoded(), "AES");
encryptCipher = Cipher.getInstance("AES/GCM/NoPadding");
encryptCipher.init(Cipher.ENCRYPT_MODE, key, ivParameterSpec);
byte[] encryptedWord = Base64.encode(encryptCipher.doFinal("example".getBytes("UTF-8")));
And this is my swift code:
do{
keyDerivation = try PKCS5.PBKDF2(password: "myPassword".bytes, salt: "salt".bytes, iterations: 1000, keyLength: 32, variant: .sha1).calculate()
let gcm = GCM(iv: keyDerivation, mode: .combined)
let aes = try AES(key: keyDerivation, blockMode: gcm, padding: .noPadding)
let encryptedText = try aes.encrypt("example".bytes)
}catch{
print(error)
}
Any help would be appreciated.
Your IV doesn't match in both cases. In Java you use a string, and in Swift you use the derived key in keyDerivation
.
Furthermore, you should make sure that you use the same character encoding. I'd not use getBytes
or similar for either language. Explicitly specifying UTF-8 is probably best.
Note that the Java PBKDF2WithHmacSHA1
may handle password encoding in a rather peculiar way, so some kind of input validation on the password is probably in order.
Needless to say, the salt should be random for each call to encrypt, not static. I presume this is just test code though.