openssl_verify and "error:0906D06C:PEM routines:PEM_read_bio:no start line"
I am trying to use OpenSSL function for RSA sign/verify in PHP.
When I try to do openssl_verify
using my public key, I am getting this error: error:0906D06C:PEM routines:PEM_read_bio:no start line
, but the function itself works correctly (returns 0 if messages was modified, and 1 if intact). openssl_sign
works fine.
How can I fix it?
Currently, I use public key generated by openssl:
define("SC_MSG_PUBLIC", <<<EOD
-----BEGIN PUBLIC KEY-----
MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBALjPcOckMHDVLiUstcRwwx8kF5PzsiEs
rskyndWisbXMLU9BHomXwL7Qg2L91jE+sNSobkzBDF41CbwDiNlofZUCAwEAAQ==
-----END PUBLIC KEY-----
EOD
);
Any ideas why this error triggers, but things works fine?
Tried to generate public key out of private, and use it, but it appeared to be exactly the same, same error message :-S
$pkey = openssl_pkey_get_private(SC_MSG_PRIVATE);
$keyDetails = openssl_pkey_get_details($pkey);
file_put_contents('c:\publickey', $keyDetails['key']);
Also, I've tried to 开发者_如何学Goinstall newer versions of everything (PHP 5.3.1, OpenSSL 1.0.0a) - same result. And, I am on windows.
Have you tried to call openssl_verify() with a (maybe self-signed) certificate containing your public key instead of a pure public key ?
As far as I know, some PHP OpenSSL functions do not properly support naked public keys although it seems strange that it does verify correctly in spite of the error.
<?php
$private = openssl_pkey_get_private(file_get_contents('private'), 'passphrase');
// This causes the "no start line" error when using a naked public key:
$public = openssl_pkey_get_public(file_get_contents('public')); // <-- this should be cert
echo openssl_error_string()."\n";
openssl_sign('Test', $sig, $private);
var_dump(openssl_verify('Test', $sig, $public));
echo openssl_error_string()."\n";
?>
Example for converting a public key to a simple certificate in a Linux/UNIX shell such as bash (refer to the OpenSSL documentation or some tutorials for more):
# Create certificate request
openssl req -new -days 3600 -key [PRIVATE-KEY-FILE] -out [REQUEST-TMP-FILE]
# Create certificate from request
RANDFILE=[RANDOM-TMP-FILE] openssl x509 -req -in [REQUEST-TMP-FILE] -signkey [PRIVATE-KEY-FILE] -out [CERTIFICATE-OUT-FILE]
This will also create temporary files you might want to delete afterwards, namely [REQUEST-TMP-FILE] and [RANDOM-TMP-FILE].
PHP sample code can be found at http://de.php.net/manual/en/function.openssl-csr-new.php.
Where everyone else has an errno that is reset to zero automatically by successful operations, OpenSSL has an "error stack", that you need to empty manually. See function openssl_error_string which is implemented in terms of ERR_get_error. Chances are that the error message that you are seeing has nothing to do with your code; try adding this before your code:
while ($msg = openssl_error_string()) {};
and in between each line:
while ($msg = openssl_error_string())
echo "OpenSSL error when doing foo:" . $msg . "<br />\n";
You might have an easier time using phpseclib for signature creation / verification:
http://phpseclib.sourceforge.net/documentation/misc_crypt.html#misc_crypt_rsa_examples
Reason:
This error is usually caused by one corrupt character at the beginning of the .crt file. So, the chances are that you have an extra space, an extra character, an extra line, etc. in either the SSL Certificate file (.crt) or the SSL key file (.key).
Possible Solution(s):
- Check your .crt file.
- The character problem may be in your key, try this (without linebreaks, etc):
.
define("SC_MSG_PUBLIC", "MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBALjPcOckMHDVLiUstcRwwx8kF5PzsiEsrskyndWisbXMLU9BHomXwL7Qg2L91jE+sNSobkzBDF41CbwDiNlofZUCAwEAAQ==");
精彩评论