You can actually use the public key as third parameter and not the certificate.
If you can't make it work, make sure that :
1) Your public key is well formatted. It seems that it must have the ----BEGIN PUBLIC KEY---- and ----END PUBLIC KEY----
2) Your signature is in binary format. You can use the php base64_decode for this.
openssl_verify
(PHP 4 >= 4.0.4, PHP 5)
openssl_verify — İmzayı doğrular
Açıklama
genankim ile ilişkili genel anahtarı kullanarak
belirtilen veri için belirtilen
imza ile imza doğrulaması yapar.
Değiştirgeler
-
veri -
İmzalı veri.
-
imza -
Doğrulama için kullanılacak imza.
-
genankim -
Genel anahtarı tanımlayıcı kimlik.
-
algoritma -
OPENSSL_ALGO_SHA1öntanımlıdır. Daha ayrıntılı bilgi için İmzalama Algoritmaları bölümüne bakınız.
Dönen Değerler
İmza doğruysa 1, yanlışsa 0, hata oluşmuşsa -1 döner.
Sürüm Bilgisi
| Sürüm: | Açıklama |
|---|---|
| 5.0.0 |
algoritma değiştirgesi eklendi.
|
Örnekler
Örnek 1 - openssl_verify() örneği
<?php
// $veri ve $imza'nın veriyi ve imzayı içerdiği varsayılıyor
// Genel anahtarı sertifikadan alıp hazırlayalım
$dt = fopen("/src/openssl-0.9.6/demos/sign/cert.pem", "r");
$sert = fread($dt, 8192);
fclose($dt);
$genankim = openssl_get_publickey($sert);
// imza doğru mu, bir bakıbakıverelim
$ok = openssl_verify($veri, $imza, $genankim);
if ($ok == 1) {
echo "iyi";
} elseif ($ok == 0) {
echo "kötü";
} else {
echo "çirkin, bir hata oluştu";
}
// Anahtar belleğini serbest bırakalım
openssl_free_key($genankim);
?>
jeremie dot gomez at gmail dot com ¶
1 year ago
mikey at badpenguins dot com ¶
2 years ago
I spent days scouring the php openssl documentation trying to figure out how to do what sounds like a simple task - given two PEM encoded certificates, is one the signer of the other? Nowhere in the openssl_verify() documentation or comments is it explained where to obtain the signature of an existing certificate. The openssl_x509_parse() function looked promising, but it is an unstable API that may change.
I had to write my own code to determine if one cert signed another, it is located here: http://badpenguins.com/source/misc/isCertSigner.php?viewSource
In a nutshell here is what I learned...
The signature data in a signed X.509 certificate contains DER formatted data about the signature that is encrypted with the signers public key. The data contains a hash of the original subject certificate and information about what encryption algorithm was used to create the signature.
So you need to get this signature data and a copy of the original certificate with the issuer and signature sequences removed. Hash a copy of the original certificate (sans issuer/signature sequences) with the same algorithm the issuer used and if the hashes match, you have the issuer cert that signed the certificate.
Stiv ¶
7 years ago
I've finally found a way to verify signature. Sample in the documentation doesn't work. Code bellow DOES work :)
<?php
// $data is assumed to contain the data to be signed
// fetch certificate from file and ready it
$fp = fopen("path/file.pem", "r");
$cert = fread($fp, 8192);
fclose($fp);
// state whether signature is okay or not
// use the certificate, not the public key
$ok = openssl_verify($data, $signature, $cert);
if ($ok == 1) {
echo "good";
} elseif ($ok == 0) {
echo "bad";
} else {
echo "ugly, error checking signature";
}
?>
steve dot venable at lmco dot com ¶
10 years ago
A note about the openssl_verify() (and some of the other functions). The public key comes from a certificate in any of the support formats (as the example shows, use openssl_get_publickey() to get the resource id). But after some trial and error I found the signature string MUST BE BINARY. While no error occurs, passing a base64-formatted signature string (PEM format?), you simply get a mismatch. When I did the base64 decode myself, the verify returned a match (return value 1). You can simply drop the begin/end lines and take the output of the 'base64_decode()' function.
meint dot post at bigfoot dot com ¶
11 years ago
Anbybody trying to get a Win32 CryptoAPI based digital signature component to work with the openssl_verify() function should be aware that the CryptoAPI PKCS1 (RSA) method uses bytes in reverse order while the openssl_verify() method expects a correctly formatted PKCS1 digital signature (as should be). I learned this the hard way and it took me some time to dig this out. A simple solution in VBScript to reverse the byte order:
N = Len(Blob.Hex)
' reverse bytes in the signature using Hex format
For i = 1 To N - 1 Step 2
s = Mid(Blob, i, 2) & s
Next
s contains the digital signature in reverse order. Blob is an arbitrary binary container.
Send the signature off in Hex format and use a hex2bin method in PHP to convert to the correct format for openssl_verify(), i.e.
function hex2bin($data) {
$len = strlen($data);
return pack("H" . $len, $data);
}
That's it, hope it helps out. BTW I used ASPEncrypt to toy around with on Win32 platform. Works only with Internet Explorer but you could also use a Java applet and have none of the abovementioned problems :-)
devel@no-spam ¶
7 years ago
It should be noted that in order to verify a signature successfully, SHA-1 must be used to digest the data before signing.
If, for example, you are using Java to create a signature and you want to verify it in PHP, you must not use "MD5withRSA" or "SHA512withRSA" as the signature algorithm. Use "SHA1withRSA" or the like...
