I have a Form which collects data, then submits this to SagePay, passing the data. This worked fine until we needed to update to PHP 7.2, and as mcrypt is no longer supported, we're switching to OpenSSL.
The form that gathers the data works fine but transporting the data doesn't encrypt and the transaction fails.
Code in functions file:
$protx_encryption_password = "my_password";
$protx_vendor = "my_vendor";
$data = "";
while(list($key,$value) = each($protx)) {
$data .= $key."=".$value."&";
}
$data = trim($data," &");
$crypt = openssl_encrypt($data, $protx_encryption_password);
function openssl_encrypt($string, $key) {
$iv = substr($value, 0, 16);
$ciphertext = substr($value, 16);
$key = hash('sha256', $key, true);
$crypt = openssl_encrypt(
$ciphertext, 'AES-256-CBC', $key,
OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING,
$iv
);
return rtrim($crypt, "\0");
}
The $crypt data is sent in a hidden field as before in the mcrypt version, I just need some help in getting the encryption working.
Previously in the mcrypt way:
$crypt = encryptAes($data, $protx_encryption_password);
function encryptAes($string, $key) {
// AES encryption, CBC blocking with PKCS5 padding then HEX encoding.
// Add PKCS5 padding to the text to be encypted.
$string = addPKCS5Padding($string);
// Perform encryption with PHP's MCRYPT module.
$crypt = mcrypt_encrypt(MCRYPT_RIJNDAEL_128, $key, $string, MCRYPT_MODE_CBC, $key);
// Perform hex encoding and return.
return "@" . strtoupper(bin2hex($crypt));
}
function addPKCS5Padding($input) {
$blockSize = 16;
$padd = "";
// Pad input to an even block size boundary.
$length = $blockSize - (strlen($input) % $blockSize);
for ($i = 1; $i <= $length; $i++)
{
$padd .= chr($length);
}
return $input . $padd;
}
This is the first OpenSSL encryption I've done so I'd appreciate any assistance with this. SagePay needs to be encrypted using AES-128 encryption with 128-bit block size in CBC mode with PCKS#5 (AES-128-CBC-PKCS#5). Any help would be truly helpful.