PHP加密文件后,openssl命令解密报bad magic number错误
解决openssl命令解密PHP加密文件时的"bad magic number"错误
你遇到的问题核心是PHP的openssl_encrypt行为和openssl命令行工具的默认规则不匹配,主要有两个关键差异:
- Salt头差异:openssl命令行的
enc工具默认会在加密输出开头添加Salted__这个"magic number"标识,同时用密码+盐派生密钥;但你的PHP代码直接加密原始数据,没有添加这个salt头,这就是报错的直接原因。 - 密钥处理差异:AES-128需要16字节的密钥,你PHP代码里的
"password"只有8字节,PHP会自动用NULL字节补全到16字节;而openssl命令行如果只输入密码,会通过EVP_BytesToKey算法生成密钥,和PHP的补全方式完全不同。
下面给你两种可行的解决思路:
方法一:修改PHP代码,适配openssl命令行的默认格式
让PHP生成符合openssl命令行预期的加密输出(包含salt头+Base64编码),这样就能直接用你原来的解密命令:
$plaintext = "This string was AES-128 / ECB encrypted."; $password = "password"; $cipher = "AES-128-ECB"; // 生成openssl默认的8字节随机盐 $salt = random_bytes(8); // 用openssl默认的密钥派生算法生成16字节密钥(AES-128要求的长度) $key = openssl_pbkdf2($password, $salt, 16, 10000, 'sha256'); // ECB模式不需要IV,直接以原始二进制格式加密 $encrypted = openssl_encrypt($plaintext, $cipher, $key, OPENSSL_RAW_DATA); // 拼接salt头、加密数据,再做Base64编码(完全匹配openssl命令的输出格式) $output = base64_encode("Salted__" . $salt . $encrypted); // 写入文件 file_put_contents('myfile', $output);
现在执行你原来的解密命令,输入密码password就能正常解密:
openssl enc -aes-128-ecb -d -in myfile -out outputfile
方法二:修改openssl命令,适配你当前的PHP加密输出
如果你不想修改PHP代码,可以调整命令行参数,完全匹配PHP的加密逻辑:
因为你的PHP代码直接用补全后的password\0\0\0\0\0\0\0\0作为密钥,且没有添加salt头,解密命令需要指定这些细节:
openssl enc -aes-128-ecb -d -in myfile -out outputfile -nosalt -K 70617373776f72640000000000000000
参数说明:
-nosalt:告诉openssl不要寻找salt头,因为PHP没有添加-K:直接指定十六进制格式的密钥(70617373776f7264是password的十六进制,后面的0000000000000000是补全的8个NULL字节)
执行这个命令后,不需要输入密码,就能直接解密你的文件。
内容的提问来源于stack exchange,提问作者Dro
相关产品推荐
相关产品推荐

