PHP OpenSSL擴展 - 對稱加密

PHP 在進入7.x 時代后,默認就不再附帶 mcrypt 擴展,mcrypt 將被 openssl_* 一族函數(shù)所替代。所以,對于 PHPer 來說,有必要學(xué)習(xí)一下 PHP 的 OpenSSL 擴展。

本文就先從 OpenSSL 擴展中的對稱加密說起。后面會陸續(xù)更多非對稱加密、數(shù)字簽名、數(shù)字證書等函數(shù)的講解。

PHP 的 OpenSSL 擴展中,對稱加密的相關(guān)函數(shù)有:

  • openssl_encrypt()
  • openssl_decrypt()
  • openssl_random_pseudo_bytes()
  • openssl_get_cipher_methods()
  • openssl_cipher_iv_length()

光看PHP的官方文檔還有點難理解。上一段代碼,更清楚地看下這些函數(shù)怎么完成加密的:

// 加密算法
1. $encryptMethod = 'aes-256-cbc';
// 明文數(shù)據(jù)
2. $data = 'Hello World';

// 生成IV
3. $ivLength = openssl_cipher_iv_length($encryptMethod);
4. $iv = openssl_random_pseudo_bytes($ivLength, $isStrong);
5. if (false === $iv && false === $isStrong) {
6.     die('IV generate failed');
7. }

// 加密
8. $encrypted = openssl_encrypt($data, $encryptMethod, 'secret', 0, $iv);
// 解密
9. $decrypted = openssl_decrypt($encrypted, $encryptMethod, 'secret', 0, $iv);

詳細解釋一下:

第 1 行 指定了加密算法。比如這段代碼使用 aes-256-cbc 算法加密。其實PHP的OpenSSL擴展支持很多種加密算法,想知道所有對稱加密算法名稱列表,可以調(diào)用 openssl_get_cipher_methods() 函數(shù),這會返回一個數(shù)組:

array(
  0 => 'AES-128-CBC',
  1 => 'AES-128-CBC-HMAC-SHA1',
  ...
  7 => 'AES-128-ECB',
  ...
  31 => 'BF-CBC',
  200 => 'seed-ofb',
)

你會發(fā)現(xiàn)函數(shù)返回將近200種加密算法,實際上沒有這么多,許多只是因為大小寫不同而重復(fù)了,比如 AES-128-CBCaes-128-cbc 實際上是同一種加密算法。如果去掉重復(fù)項,那么 PHP 的 OpenSSL 擴展支持大概100多種不同的加密算法。

第 3 ~ 7 行 生成了 IV。為什么要生成 IV,這個 IV 有什么用?

回顧一下 openssl_get_cipher_methods() 返回的加密算法列表,有很多名字中間帶有 “CBC” 字樣,這些加密算法使用了同一種加密模式,也就是 密碼分組鏈接模式(Cipher Block Chaining)

CBC 模式的加密算法中,明文會被分成若干個組,以組為單位加密。每個組的加密過程,依賴他前一個組的數(shù)據(jù):需要跟前一組的數(shù)據(jù)進行異或操作后生成本組的密文。那么最開頭的那個組又要依賴誰呢?依賴的就是 IV,所以這就是為什么 IV 要叫初始化向量。IV 是 初始化向量(initialization vector)的縮寫

IV 應(yīng)該是隨機生成的,所以代碼用到了 openssl_random_pseudo_bytes() 生成 IV。該函數(shù)接收一個 int,代表需要生成的 IV 的長度。

IV 長度隨加密算法不同而不同。一般人是記不住那么多算法需要的 IV 長度的。所以直接使用 openssl_cipher_iv_length() 函數(shù),這個函數(shù)返回一個 int,表示加密算法需要的 IV 長度:

echo openssl_cipher_iv_length('AES-256-CBC'); // 16
echo openssl_cipher_iv_length('BC-CBC'); // 8
echo openssl_cipher_iv_length('AES-128-ECB'); // 0

比如 AES-256-CBC 需要16位的 IV、 BC-CBC 需要 8 位的 IV、而AES-128-ECB 不需要 IV,所以返回了 0。

第 8 ~ 9 行 是加密和解密。分別使用了 openssl_encrypt()openssl_decrypt()。

  • 第一個參數(shù)是輸入,對 openssl_encrypt() 來說是明文串,對 openssl_decrypt() 來說是密文串
  • 第二個參數(shù)是指定加密 / 解密 算法
  • 第三個參數(shù)是加密 / 解密時需要用到的密碼,是個字符串
  • 第四個參數(shù)額外選項,沒有特殊需要可以保持默認值:0,
  • 第五個參數(shù)是 IV

這兩個函數(shù)除了第一個參數(shù)不同,其余參數(shù)都要保證相同才能順利解密。最后,在使用需要 IV 的加密算法時,需要注意:

  • 必須傳 $iv 參數(shù),不傳的話PHP將會拋出一個 Warning
  • IV 應(yīng)該是隨機生成的(比如用 openssl_random_pseudo_bytes() ),不能人為設(shè)定
  • 每次加密都應(yīng)該重新生成一次 IV ,不可偷懶多次加密采用相同 IV
  • IV 要隨著密文一起保存(不然就沒法解密了啦),可以直接附在密文串后面,也可以分開保存
最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • 這篇文章主要講述在Mobile BI(移動商務(wù)智能)開發(fā)過程中,在網(wǎng)絡(luò)通信、數(shù)據(jù)存儲、登錄驗證這幾個方面涉及的加密...
    雨_樹閱讀 3,057評論 0 6
  • 概述 之前一直對加密相關(guān)的算法知之甚少,只知道類似DES、RSA等加密算法能對數(shù)據(jù)傳輸進行加密,且各種加密算法各有...
    Henryzhu閱讀 3,234評論 0 14
  • 試內(nèi)容為《小學(xué)生必背古詩70首》,這個是早有規(guī)定的。開學(xué)不久,老師們就按照教育局文件精神給同學(xué)們布置了這項課外閱讀...
    心雨格格閱讀 302評論 0 0
  • 《金剛狼與小狼女》 這副鉛筆稿畫的是金剛狼抱著X-23小狼女的景象。因為是鉛筆稿,是為了之后的上顏色做準備。預(yù)計上...
    樸領(lǐng)閱讀 1,219評論 6 7
  • 每個人的現(xiàn)在和未來是有什么決定的呢?有人說是命運之神在背后推動的,有人說未來掌握在自己手中,于我而言,它是由過去的...
    米果媽閱讀 1,102評論 4 14

友情鏈接更多精彩內(nèi)容