Я пытаюсь расшифровать в PHP, используя функции openssl_decrypt.
Проблема в том, что часть возвращаемой строки верна, а часть — тарабарщина.
`@M{-Y f{5678","token":null}`
Любая помощь будет оценена
Сначала я подумал, что это проблема с кодировкой, поэтому я попытался изменить кодировку с помощью этой функции, но безуспешно.
mb_convert_encoding($data,'UTF-8');
Вот простая функция, которую я использую
$secret = "#oc*Zd'&'&%rez`&;957.u1c:(|'%c81";
$data = "SsxrFLoAWTPP7t8AR1/QFXSkZF6Xl2DXGV8Ay90rXk1sgwN46CmSmWsBqTvhbeUT";
$decrypted=openssl_decrypt($data,'aes-256-cbc',$secret);
var_dump($decrypted);
это должен быть ожидаемый результат
`{"reg_no":"UP2345678","token":null}
Пожалуйста, редактировать ваш вопрос, чтобы включить исходный код, как вы зашифровали исходное сообщение/контент.
Режим Си-Би-Си требует IV. IV шифрования должен использоваться для расшифровки. В опубликованном примере в openssl_decrypt
-вызове не передается IV (что соответствует IV с 0-значениями), поэтому первый блок (1 блок = 16 байт) расшифровывается неправильно.
В принципе IV можно восстановить, если известны ключ, открытый текст и зашифрованный текст: расшифровывается первый блок зашифрованного текста (без IV), а результат подвергается операции XOR с первым блоком открытого текста. Это приводит к следующему IV для данных в опубликованном примере (в виде шестнадцатеричной строки): 3B297D2864244336363339332B2D2826
. Используя этот IV, вывод
$secret = "#oc*Zd'&'&%rez`&;957.u1c:(|'%c81";
$iv = hex2bin('3B297D2864244336363339332B2D2826');
$data = "SsxrFLoAWTPP7t8AR1/QFXSkZF6Xl2DXGV8Ay90rXk1sgwN46CmSmWsBqTvhbeUT";
$decrypted = openssl_decrypt($data, 'aes-256-cbc',$secret, 0, $iv);
print('Decrypted data: '.$decrypted);
соответствует ожидаемому результату:
{"reg_no":"UP2345678","token":null}
Обновлено:
Хотя я думаю, что это ясно, я хотел бы отметить, что способ, описанный ниже, конечно, не является обычным способом определения IV для расшифровки (это вообще не сработает, потому что открытый текст не известен). Обычно IV, используемый для шифрования, просто отправляется получателю вместе с зашифрованным текстом. Это возможно, потому что IV не нужно держать в секрете. т.е. в опубликованном примере IV по какой-то причине отсутствует, хотя на самом деле он должен присутствовать.
В любом случае, IV также можно определить следующим образом, используя открытый текст, шифртекст и ключ: В описании режима Си-Би-Си видно, что в начале шифрования первый блок открытого текста и IV являются XOR. -ed, после чего результат шифруется. Таким образом, IV можно определить, сначала расшифровав этот первый зашифрованный блок, а затем совместив результат XOR с открытым текстом. Соответствующий PHP-код:
// Step 1: Decrypt the first block of the ciphertext (no IV is used which is equivalent to a 0-IV)
$ciphertext = base64_decode('SsxrFLoAWTPP7t8AR1/QFXSkZF6Xl2DXGV8Ay90rXk1sgwN46CmSmWsBqTvhbeUT');
$ciphertextFirstBlock = substr($ciphertext, 0, 16); // First block / 16 Byte of encrypted data
$decryptedFirstBlock = openssl_decrypt($ciphertextFirstBlock, 'aes-256-cbc', $secret, OPENSSL_RAW_DATA | OPENSSL_ZERO_PADDING); // First block / 16 Byte of decrypted data
print('Decrypted first block: '.bin2hex($decryptedFirstBlock)."\n");
// Step 2: XOR the result with the first block of the plaintext
$plaintext = '{"reg_no":"UP2345678","token":null}';
$plaintextFirstBlock = substr($plaintext, 0 , 16); // First block / 16 Byte of plaintext
$ivReconstructed = $decryptedFirstBlock ^ $plaintextFirstBlock;
print('Reconstructed IV: '.bin2hex($ivReconstructed)."\n");
Цитата ** «IV можно восстановить, если известны ключ, открытый текст и зашифрованный текст» ** не могли бы вы объяснить, как вам удалось получить это 3B297D2864244336363339332B2D2826
На самом деле, я уже описал это («Первый блок зашифрованного текста расшифровывается (без IV) и результат XOR с первым блоком открытого текста».). Теперь я объяснил оба шага более подробно, см. Раздел редактирования в моем ответе.
Ваш ожидаемый результат не шифруется до указанного вами
$data
. СтрокаOIaeybkSaDbLjihuTbpL9k6aWHtXt3V4G2dLysVRSJZqW3Ep6if4LkjpzkrHOw+J
расшифровывается до ожидаемого результата{"reg_no":"UP2345678","token":null}
.