2011-08-23 172 views
4

我想使用AES对Objective-C中的密码进行加密,然后使用PHP解密,但我遇到了两个问题。使用AES进行Objective-C加密并使用PHP解密

  1. 我加密密码,但它是一个NSData对象,所以我用Base64编码,但是当我在PHP解码,结果是nil。所以我不能解密它。
  2. 我可以在Objective-C中加密和解密密码,所以它是PHP的问题,但是当我使用AES进行加密然后使用base64进行编码时,结果并不相同。

这里是我的代码:

PHP:

$iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_ECB); 
    $iv = mcrypt_create_iv($iv_size, MCRYPT_RAND); 
    $key = "a16byteslongkey!"; 
    $plaintext = "iphone"; 
    $ciphertext = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key, $plaintext, MCRYPT_MODE_ECB, $iv); 
    $ciphertext = base64_encode($ciphertext); 
    echo "ciphertext: ".$ciphertext."<br/>"; 

    $ciphertext = base64_decode($ciphertext); 
    $plaintext = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $key, $ciphertext, MCRYPT_MODE_ECB, $iv); 
    echo "plaintext: ".$plaintext."<br/>"; 

输出:

ciphertext: SXNepKfh0IrlDDdkq4EdmQ== 
    plaintext: iphone 

的Objective-C:(此处获取完整的源代码:https://gist.github.com/838614

NSString *key = @"a16byteslongkey!"; 
    NSString *plaintext = @"iphone"; 

    NSString *ciphertext = [plaintext AES256EncryptWithKey: key]; 
    NSLog(@"ciphertext: %@", ciphertext); 

    plaintext = [ciphertext AES256DecryptWithKey: key]; 
    NSLog(@"plaintext: %@", plaintext); 

输出:

ciphertext: D19l3gsgXJlrLl7B2oCT6g== 
    plaintext: iphone 

我kCCKeySizeAES128取代kCCKeySizeAES256,并以“kCCOptionPKCS7Padding取代 “kCCOptionPKCS7Padding” | kCCOptionECBMode”,

+6

马上就好像你在PHP中使用128,在Obj-C中使用256 ......这将是一个问题。 –

+0

感谢您的回复,我用kCCKeySizeAES128替换了kCCKeySizeAES256,并用“kCCOptionPKCS7Padding&kCCOptionECBMode”替换了“kCCOptionPKCS7Padding”,但结果也不一样。有什么细节我应该改变? – pcrazyc

+2

你似乎是'base64_encode'在PHP中产生的字符串,但只是将其转换为Obj-C中的UTF8。显然,结果会有所不同。 –

回答

2

我有解决售后服务问题。

  1. 没有将代码从https://gist.github.com/838614
  2. 关键改变应该是32个字节。
  3. encryt的结果是不一样的,但如果你解密,他们将是一样的。

目标c:

NSString *key = @"a16byteslongkey!a16byteslongkey!"; 
NSString *plaintext = @"iphone"; 

NSString *ciphertext = [plaintext AES256EncryptWithKey: key]; 
NSLog(@"ciphertext: %@", ciphertext); 

plaintext = [ciphertext AES256DecryptWithKey: key]; 
NSLog(@"plaintext: %@", plaintext); 

输出:

ciphertext: I3chV+E2XUHeLCcJAhBaJQ== 
plaintext: iphone 

PHP:

$iv_size = mcrypt_get_iv_size(MCRYPT_RIJNDAEL_128, MCRYPT_MODE_ECB); 
$iv = mcrypt_create_iv($iv_size, MCRYPT_RAND); 
$key = 'a16byteslongkey!a16byteslongkey!'; 
$plaintext = "iphone"; 

$ciphertext = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key, $plaintext, MCRYPT_MODE_ECB); 
$base64encoded_ciphertext = base64_encode($ciphertext); 
echo "ciphertext: ".$base64encoded_ciphertext."<br/>"; 

$plaintext = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $key, base64_decode($base64encoded_ciphertext), MCRYPT_MODE_ECB); 
echo "plaintext: ".$plaintext."<br/>"; 

$base64encoded_ciphertext = "I3chV+E2XUHeLCcJAhBaJQ=="; 
$plaintext = mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $key, base64_decode($base64encoded_ciphertext), MCRYPT_MODE_ECB); 
echo "plaintext: ".trim($plaintext); 

输出:

ciphertext: kUr+YsYtb3Uy34li/GPcjg== 
plaintext: iphone 
plaintext: iphone 
+0

嗨,我开始研究一个项目,需要加密iOS上的数据和在运行PHP的服务器上解密它。你能给我详细的工作吗? 谢谢! – Shinichi

1

固定使用像

$iv2 = ''; 
    for ($i = 0; $i < 16; $i++) { 
     $iv2 .= "\0"; 
    } 
    mcrypt_decrypt(MCRYPT_RIJNDAEL_128, $key, base64_decode($text), MCRYPT_MODE_CBC, $iv2); 
  1. 有些东西不会改变从https://gist.github.com/838614
  2. 代码中的关键应该是32字节
  3. encryt的结果和解密是不一样的

我试过用这个字符串测试:

$plaintex = "fskfladsadsadfsfs dfskl;dfs a jadfsa ds'a' j afdjdfsaadfs' jdfas af 'ksfegfffffffffffffffffffffsdfsfgfsfdsdfddfsg"

并且结果是不同的。这里的任何人都知道原因可能是什么?

0

我怀疑这是填充程序。我已经通过确保将要加密的文本填充为带有空格的32个字符并且在解密例程返回结果之前处理这个问题,修剪掉多余的空格。

有官方的填充算法,但我发现他们没有工作。如果你加密一个长度为32个字符的字符串,那么即使填充程序错误,它也会忽略它。

相关问题