Home  >  Article  >  Backend Development  >  How PHP uses asymmetric encryption in OpenSSL encryption

How PHP uses asymmetric encryption in OpenSSL encryption

醉折花枝作酒筹
醉折花枝作酒筹Original
2021-06-02 17:50:281831browse

This article will introduce to you the method of asymmetric encryption in PHP using OpenSSL encryption. It has certain reference value. Friends in need can refer to it. I hope it will be helpful to everyone.

How PHP uses asymmetric encryption in OpenSSL encryption

#In the last article, we learned some relevant theoretical knowledge about symmetric and asymmetric encryption, and also learned how to use OpenSSL to perform symmetric encryption operations. Today, we will go one step further and learn how asymmetric encryption is implemented in OpenSSL.

Generate private key

Through previous learning, we know that asymmetric encryption requires a public key and a private key respectively. Let's first generate a private key, which is a key stored on our end. Please remember that the private key cannot be given to others at any time!

$config = array(
    "private_key_bits" => 4096, // 指定应该使用多少位来生成私钥
);

$res = openssl_pkey_new($config); // 根据配置信息生成私钥

openssl_pkey_export($res, $privateKey); // 将一个密钥的可输出表示转换为字符串
var_dump($privateKey); 
// -----BEGIN PRIVATE KEY-----
// MIIJQgIBADANBgkqhkiG9w0BAQEFAASCCSwwggkoAgEAAoICAQDFMLW+9t3fNX4C
// YBuV0ILSyPAdSYVXtE4CLv32OvNk9yQZgF2nL/ZuIbBGRcYo2Hf5B31doGrAFDGu
// NoTR+WA7CBjKROFr/+yValsMFIeiKNtttWMkmBciysDJoEoyd6wjDD+kcHQdoJVo
// ……
// -----END PRIVATE KEY-----

A very simple function openssl_pkey_new(), which receives a parameter, which is a configurable and optional parameter. The generated result is a private key handle, which is not something we can read directly, so we use openssl_pkey_export() to extract the output string.

The content in the comments is the private key information we generated. The private key information is generally relatively large, so the following content is omitted.

Extract the public key

The next step is to generate the public key. In fact, the public key is extracted from the private key. Therefore, when we use encryption and decryption, we can use private keys or public keys to operate with each other.

$publicKey = openssl_pkey_get_details($res); // 抽取公钥信息
var_dump($publicKey);
// array(4) {
//     ["bits"]=>
//     int(4096)
//     ["key"]=>
//     string(800) "-----BEGIN PUBLIC KEY-----
//   MIICIjANBgkqhkiG9w0BAQEFAAOCAg8AMIICCgKCAgEAtOIImDdS0W0vAr5Ra1+E
//   hR2AJwQQwxntYKgTku8EmJRBX2vU+x8th8W8SnoGiVM/sOItG0HIe4Egf1UxoZHt
//   gI6r+jpAp7JbTN0sD/VTPDE09F21+hFGjIVBqrkcLPjuEbf7+tjmgAx8cG8WLGId
//   G8Hsub70kRANKJe1bCXIBUggRFk0sQGllxA/hxiG5wANqHTrdpJgJba+ahSi2+4H
//   UWnyCV1O3AaPyz6a12HNUsG4Eio/tWv/hOB9POt6nAqwPHuIbhp56i5bv1ijMJZM
//   jwRen5f/kwdZ01Ig2fi0uBoTR2y/EEaus7xBYpF/gGzZ/uM7cNUXcDyG5YluM/4R
//   MEv4msPMVGB72izItED+C6Cqftxl98iBFRDc+PISFbRSgOU/HsuBhKkM5SYzyi3I
//   Ypaej25++qLPqcA+EDr3JNDhNZ0GOhofCRtPq4dsr7iLLLRnZ0TnhIYe9wAbmO49
//   uthABNBkM54bG+omOfY4Bkn5n39CKpELbhIiXgOd+lA684XUS/2Aw3Dvelc9Gbag
//   oIFvb/wljPYsd0Zmd64CXBpTWbfwXC8K4vCKvFLjytcz2Yp4T6fVjbLT5RA6u8su
//   E0WwE4QTFNKhnM5OvfiMN+NMc3Y/esVfcin3eyvotdz4N6Tt45dkybkf6aQE3Scg
//   E/JBLIEEA+gjGTveY4cNUiECAwEAAQ==
//   -----END PUBLIC KEY-----
//   "
//     ["rsa"]=>
// ……

$publicKey = $publicKey['key'];

The content extracted using openssl_pkey_get_details() contains a lot of content. But the main thing we need is the public key under key.

Let’s go back and take a closer look at the contents of the public key and private key. Are they the same as the contents of the public and private keys in the HTTPS certificate we applied for, and are they similar to the ones we use openssl in our system? The key certificate generated by the command line is the same as the local one. They are the same thing in themselves, but they are applied differently in different scenarios. In addition to the asymmetric encryption key, the HTTPS certificate also contains CA information. If the CA does not pass, the browser will also consider the certificate to be invalid. Therefore, we cannot use the certificate we generated as an HTTPS certificate. The ones generated by themselves are generally used for SSH password-free login or GitHub password-free code warehouse operations.

Encrypt and decrypt data

Okay, the public key and private key have been generated, then we are about to perform the most important encryption and decryption operations.

$data = '测试非对称加密';

// 公钥加密数据
openssl_public_encrypt($data, $encrypted, $publicKey);
var_dump($encrypted);
// string(512) 

// 私钥解密数据
openssl_private_decrypt($encrypted, $decrypted, $privateKey);
var_dump($decrypted);
// string(21) "测试非对称加密"

Here, we use the most standard public key encryption and private key decryption for testing. In fact, the reverse is also possible. OpenSSL provides us with public key encryption and decryption and private key encryption and decryption functions.

Just like the illustration in the previous article, the other party obtains our public key, then encrypts the data and transmits it, and we decrypt the data through our own private key to obtain the original text. We can also obtain the other party's public key, encrypt the returned data and transmit it to the other party, and then the other party uses its own private key to decrypt and obtain the original data we passed to it.

HTTPS obtains the public key through a certificate issued by the CA. The browser encrypts the request data and transmits it to the server. The server also uses the same principle to send ciphertext data to the browser client. Therefore, during data transmission, transmission using HTTPS will be more secure. Even if it is intercepted, the other party will not have the key provided by the certificate to decrypt it. This is why all apps and mini-program applications now require the use of HTTPS. Of course, if we do website development, it is best to use HTTPS. Even Baidu has made corresponding adjustments to the inclusion of HTTPS.

Signature and Verification

Next we will touch on the concept of signature. When two ends communicate, how do we know that the currently transmitted data must have been sent by the other end? Has any hacker tampered with it? This can be verified through the signature mechanism.

// 利用私钥生成签名
openssl_sign($data, $signature, $privateKey, OPENSSL_ALGO_SHA256);
var_dump($signature);

// 公钥验证签名
$r = openssl_verify($data, $signature, $publicKey, OPENSSL_ALGO_SHA256);
var_dump($r);
// int(1)

We use openssl_sign() to generate a private key signature for the original data, and then we can use openssl_verify() to verify whether the data signature is consistent through the public key.

When used, the sender generates a signature through its own private key. Since the signature content is garbled, we can base64_encode() it and then pass it to the receiver together with the encrypted data. The receiver then uses the public key and verifies whether the original data has been tampered with based on the signature content.

// 发送方签名
$resquestSign = base64_encode($signature);

// 假设通过网络请求发送了数据
// ……
// 接收到获得签名及原始数据
// $signature = $_POST['sign'];
// openssl_private_decrypt($_POST['data'], $data, $privateKey); 

$responseSign = base64_decode($signature);
// 验证数据有没有被篡改
$r = openssl_verify($data, $signature, $publicKey, OPENSSL_ALGO_SHA256);
var_dump($r);
// int(1)

// 假设被篡改
$data = '我被修改了';
$r = openssl_verify($data, $signature, $publicKey, OPENSSL_ALGO_SHA256);
var_dump($r);
// int(0)

Summary

Does today’s content feel much more complicated than symmetric encryption? Especially the newly introduced concept of signature, in fact, many certificate-related contents are related to data signature. In other words, HTTPS seems to be a simple one, but in fact the browser and openssl on the server side have done a lot of things for us, which is far more than just going to the CA to apply for a set of certificates and then configuring them in Nginx. So, next, what we are going to learn is the content related to generating certificates. Fasten your seat belts and the car will continue to drive.

Test code:

https://github.com/zhangyue0503/dev-blog/blob/master/php/202007/source/PHP%E7%9A%84OpenSSL%E5%8A%A0%E5%AF%86%E6%89%A9%E5%B1%95%E5%AD%A6%E4%B9%A0%EF%BC%88%E4%BA%8C%EF%BC%89%EF%BC%9A%E9%9D%9E%E5%AF%B9%E7%A7%B0%E5%8A%A0%E5%AF%86.php

推荐学习:php视频教程

The above is the detailed content of How PHP uses asymmetric encryption in OpenSSL encryption. For more information, please follow other related articles on the PHP Chinese website!

Statement:
The content of this article is voluntarily contributed by netizens, and the copyright belongs to the original author. This site does not assume corresponding legal responsibility. If you find any content suspected of plagiarism or infringement, please contact admin@php.cn