2013-02-23 68 views
1

我有一個客戶端(安卓設備),生成一個公共+私鑰對。它將公鑰發送給服務器,服務器應該使用公鑰對一些數據進行加密並返回,以便客戶端稍後可以使用私鑰對其進行解密。我的php代碼記錄了一個警告,說明我提供的公鑰是無效的。Android KeyPairGenerator + php openssl_public_encrypt

在設備側,我生成密鑰對如下 -

KeyPairGenerator kpg = KeyPairGenerator.getInstance("RSA"); 
kpg.initialize(256); 
KeyPair kp = kpg.generateKeyPair(); 
PublicKey publicKey = kp.getPublic(); 

我然後BASE64編碼和POST它 -

String urlParameters = "productID=" + productID + "&publicKey=" 
       + URLEncoder.encode(Base64.encodeToString(publicKey.getEncoded(), 
         Base64.DEFAULT)); // without the URLEncoder, the + signs 
              // are turned into spaces 

在服務器端,我從提取公鑰POST參數並嘗試使用它來編碼一些數據 -

$publicKey = $_POST['publicKey']; 
$encryptedData = ''; 
$productData = 'test test test'; 
openssl_public_encrypt($productData, $encryptedData, $publicKey); 

這會導致錯誤出現t他在日誌中以下 -

PHP Warning: openssl_public_encrypt(): key parameter is not a valid public key 

我也曾嘗試使用它進行加密之前添加前綴和後綴的公共密鑰,但是這並沒有幫助 -

$publicKey = "-----BEGIN PUBLIC KEY-----\r\n" . $publicKey . "\r\n-----END PUBLIC KEY-----"; 

曾經打破了我的頭在這個一段時間,我在網上遇到的所有建議似乎都沒有幫助。任何想法將是最有幫助的!

+0

*嘆息* ...如何PHP擺脫這種惡劣的文檔? [手冊頁](http://php.net/manual/en/function.openssl-public-encrypt.php)甚至沒有說公鑰應該在什麼格式! – 2013-02-23 15:27:15

+0

請注意,將公鑰發送給另一方不足以避免中間人攻擊;你怎麼知道公鑰是來自正確的派對?任何人都可以給你發一個公鑰...... – 2013-02-23 17:08:54

+0

@owlstead:你有一個好點。我正在向服務器發送一個公鑰,這樣我就可以避免在設備端對硬件進行硬編碼/綁定私鑰。如果我使用對稱密鑰而不是傳遞它,我擔心密鑰可能會從android軟件包中提取。需要考慮這個更多我猜.. – ashutosh 2013-02-24 05:14:46

回答

1

託管終於通過使2個修改來解決這個問題 -

  1. 不得不使用Base64.NO_WRAP標誌,而不是Base64.DEFAULT在Java端。
  2. 添加在PHP中的前綴/後綴塊分割後 - $publicKey = "-----BEGIN PUBLIC KEY-----\r\n" . chunk_split($publicKey) . "-----END PUBLIC KEY-----";
相關問題