This article mainly introduces the example of using OpenSSL to replace MCrypt in PHP7.1, this article gives you a very detailed introduction, the need for friends can refer to the following
In PHP development, the use of MCrypt-related functions can be easily AES encryption, decryption operations, but PHP7.1 mcrypt extension, so it is necessary to find another implementation. Using OpenSSL instead of mcrypt has been pointed out in the migration manual, but no specific examples have been given. There are many examples on the web that can replace most of the scenes, but they are not explained in detail. Similarly, simply using the online sample in a code scenario might lead to compatibility issues before and after code substitution, and here's a discussion of the specific code and why.
First we give the replacement code directly, and then we analyze the problem from the code. (The algorithm analyzed in this article is AES-128-CBC)
Replace Example
The example shows how the two mcrypt are used, mainly in terms of padding (the fill is explained below). Throughout the addition and decryption process, a little bit more complete code will be the self-implementation of the fill, remove the fill, simple code will directly ignore the fill, but both methods can run normally, in the actual development (prior to 7.1 version), it is recommended to add padding. Take a look at the following specific examples:
MCrypt not using padding
MCrypt Encryption:
$key = ' aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa '; $iv = ' aaaaaaaaaaaaaaaa '; $data = ' datastring '; $cipher = Mcrypt_module_open (mcrypt_rijndael_128, ', MCRYPT_MODE_CBC, '); Mcrypt_generic_init ($cipher, $key, $IV); $cipherText mcrypt_generic = ($cipher, $data); Mcrypt_generic_deinit ($cipher); Return Bin2Hex ($cipherText 256);
The same functionality of the OpenSSL encryption code:
$key = ' aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa '; $iv = ' aaaaaaaaaaaaaaaa '; $data = ' datastring ';
$data = $data. Str_repeat ("\x00", 16 (strlen ($data)%)); Double quotes can parse asc-ii code \x00 return Bin2Hex (Openssl_encrypt ($data, "AES-256-CBC", $key, Openssl_raw_data | Openssl_zero_padding, $iv));
MCrypt using padding
MCrypt Encryption:
$key = ' aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa '; $iv = ' aaaaaaaaaaaaaaaa '; $data = ' datastring '; Fill (remove fill reverse) $block = Mcrypt_get_block_size (mcrypt_rijndael_128, MCRYPT_MODE_CBC); $pad = $block-(strlen ($data)% $block); if ($pad <= $block) {$char = Chr ($pad); $data. = Str_repeat ($char, $pad);} $cipher = Mcrypt_module_open (Mcrypt_rijnda el_128, ', MCRYPT_MODE_CBC, '); Mcrypt_generic_init ($cipher, $key, $IV); $cipherText mcrypt_generic = ($cipher, $data); Mcrypt_generic_deinit ($cipher); Return Bin2Hex ($cipherText 256);
The same functionality of the OpenSSL encryption code:
$key = ' aaaaaaaaaaaaaaaaaaaaaaaaaaaaaa '; $iv = ' aaaaaaaaaaaaaaaa '; $data = ' datastring '; Return Bin2Hex (Openssl_encrypt ($data, ' AES-256-CBC ', $key, Openssl_raw_data | Openssl_zero_padding, $iv));
All of the examples above can be run successfully, with the first example (not using a fill, but populating in OpenSSL) and the second example (using padding, unused padding in OpenSSL) the same output before and after the substitution, with no compatibility issues. You can choose different alternatives depending on how the code is populated, but there are three details that need to be explained
Why should I have a fill?
Why is the name of the algorithm different after using OpenSSL replacement?
The next step is to specifically analyze the fill, algorithm.
Fill
The reason why there is padding is to start with the encryption algorithm. Because in the AES-128-CBC algorithm, the string to be encrypted is segmented by the length of every 16 bytes, which causes the segments with less than 16byte to be populated. So there are two types of examples: one is to use the default padding, and the other is to populate it autonomously. In the replacement with OpenSSL, how to select the Fill scheme requires an understanding of the default and autonomic padding for mcrypt and OpenSSL.
MCrypt default Padding
In the source code of PHP, you can see that the default will be filled with \x00, in fact, not to fill the \x00, from the source can be found, the first to apply for a 16-bit empty string, so the initialization of each byte is \x00, in fact, it can be said that there is no padding, but it is \x00 , the encrypted string that you get with the default padding is the following form:
MCrypt default Padding
Therefore, the decryption is to remove the redundant \x00. Of course, you can also be lazy, do not remove \x00. Because in PHP the string "string\x00" and string "strings" in addition to the length of the other than the same, the other performance is consistent, so there is no difference in appearance, the following code:
The tail contains a number of ' \x00 ' can be output true if ("string\x00" = = "string") {//in double quotes to parse \x00 echo true;}
\x00 Populated Example: (note the length of the string so that the \x00 fill will affect the length)
MCrypt Self-filling
The filling algorithm is performed with the following algorithm:
Add fill
/** * Fill Algorithm * @param string $source * @return String */function addpkcs7padding ($source) {$source = Trim ($source); $block = Mcrypt_get_block_size (mcrypt_rijndael_128, MCRYPT_MODE_CBC); $pad = $block-(strlen ($source)% $block); if ($pad <= $block) { $char = Chr ($pad); $source. = Str_repeat ($char, $pad); } return $source; }
After adding the padding, the string is actually in the following form:
Remove fill
/** * Remove Fill algorithm * @param string $source * @return String */function strippksc7padding ($source) {$source = Trim ($source); $c Har = substr ($source,-1); $num = Ord ($char); if ($num = =) return $source; $source = substr ($source, 0,-$num); return $source; }
OpenSSL default padding
The default mode is the same as the standard MCrypt, so in the second example, after using the fill algorithm as above, you can use the openssl_encrypt substitution directly without creating compatibility problems. The following form of the filled encrypted string:
It is important to note that fill and remove fills are built into the openssl_encrypt and openssl_decrypt, so you can use them directly, but you do not need to consider padding unless you need to implement the fill autonomously.
OpenSSL self-filling
Openssl_encrypt provides the option parameter to support autonomic padding, but the test case code for OpenSSL in the lookup php source finds the correct usage:
If we want to manage our own padding $padded _data = $data. Str_repeat (", strlen ($data)% 16)); $encrypted = Openssl_encrypt ($padded _data, $method, $password, openssl_raw_data| Openssl_zero_padding, $IV); $output = Openssl_decrypt ($encrypted, $method, $password, openssl_raw_data| Openssl_zero_padding, $IV); Var_dump (RTrim ($output)); (note: As above, openssl_zero_padding is not meant to be filled for 0)
Thus, we can explain that in the first example, Openssl_encrypt was added to the code reason for the self-charging \x00.
The above addition and decryption are different for the fill logic, which is well explained in the example above:
Example 1:
MCrypt encryption is not used in the fill, it is filled with \x00, so in the replacement of OpenSSL, you need to implement \x00 fill.
Example 2:
MCrypt encryption uses a standard fill, and OpenSSL is filled with a standard fill, so you can use it directly.
In this analysis, it is found that regardless of the fill strategy you need to be aware of the addition of padding when encrypting, you must remove the padding when decrypting. Now that the completion of the fill correlation in the example above is complete, let's look at how to choose the replacement algorithm.
Selection algorithm
In the example above, the question is, how did the AES-128-CBC algorithm in MCrypt replace the aes_256 in OpenSSL?
On this point, I also did not find a reasonable explanation, view source 1:30 will also not find the reason (ability Limited ~), but through the following information, or completed the function
OpenSSL decryption MCrypt AES data incompatibility Issues
Convert mcrypt_generic to Openssl_encrypt Ask Question
If a classmate find the reason, welcome to my message, thank you.
Summarize
For the part that uses MCrypt AES for encryption, if the problem is in the substitution process, you can start with the algorithm substitution or padding. At the same time it is necessary to meet the conditions are based on different fill options, replace the most important to consider compatibility issues, to ensure that no change after the replacement. Although there is only a slight difference----the tail of a few strings, but if the simultaneous modification in the multi-platform is also a nuisance, but the less the change of risk smaller.
This paper simply explains the AES algorithm, and the applicability of other algorithms remains to be researched.
The above is the whole content of this article, I hope that everyone's learning has helped, more relevant content please pay attention to topic.alibabacloud.com!