Signatur
Beschreibung
openssl_pkcs7_verify() liest eine S/MIME-signierte Nachricht aus einer Datei und prüft die enthaltene PKCS#7-Signatur. Damit lässt sich sicherstellen, dass eine E-Mail oder ein Dokument tatsächlich vom angegebenen Absender stammt und seit der Signierung nicht verändert wurde.
Die Funktion versucht standardmäßig, die gesamte Zertifikatskette anhand der CA-Zertifikate des Systems zu validieren. Dieses Verhalten kann über den Parameter flags gesteuert werden. Wichtige Flags sind PKCS7_NOVERIFY (keine Zertifikatsprüfung), PKCS7_NOCHAIN (keine Kettenprüfung) und PKCS7_NOINTERN (Zertifikate nicht aus der Nachricht laden).
Wenn der Parameter signers_certificates_filename angegeben wird, speichert PHP die Zertifikate der Unterzeichner in dieser Datei im PEM-Format. So können die Zertifikate anschließend weiterverarbeitet oder zur späteren Überprüfung gespeichert werden. Über content kann der entschlüsselte, signaturfreie Inhalt der Nachricht in eine Datei geschrieben werden.
Die Funktion eignet sich für sichere E-Mail-Verarbeitung, z. B. in Webmailer-Backends, Postfachverarbeitungen oder Dokumenten-Workflows, in denen die Authentizität und Integrität von Nachrichten gewährleistet sein muss.
Parameter
| Name | Typ | Default | Beschreibung |
|---|---|---|---|
| $filename Pflicht | string | Pfad zur Datei, die die S/MIME-signierte Nachricht enthält. Die Nachricht muss im PEM- oder DER-Format mit PKCS#7-Signatur vorliegen. | |
| $flags Pflicht | int | Bitmaske aus PKCS7_*-Konstanten, die das Verifikationsverhalten steuern. Z. B. PKCS7_NOVERIFY unterdrückt die Zertifikatsprüfung, PKCS7_TEXT entfernt den MIME-Textbereich beim Ausgabe des Inhalts. |
|
| $signers_certificates_filename | ?string | null | Optionaler Dateipfad, in den PHP die PEM-kodierten Zertifikate der Unterzeichner schreibt. Nützlich, um die Identität des Signierers zu ermitteln. |
| $ca_info | array | [] | Array mit Informationen über vertrauenswürdige CA-Zertifikate. Kann Dateipfade oder Verzeichnisse zu PEM-Zertifikaten enthalten, die als Vertrauensanker dienen. |
| $extracerts_filename | ?string | null | Optionaler Pfad zu einer Datei mit zusätzlichen Zwischenzertifikaten im PEM-Format, die bei der Kettenprüfung berücksichtigt werden sollen. |
| $content | ?string | null | Optionaler Dateipfad, in den der eigentliche (entschlüsselte, signaturfreie) Nachrichteninhalt geschrieben wird. |
| $pk7 | ?string | null | Optionaler Dateipfad, in den die PKCS#7-Struktur (die Signatur selbst) im PEM-Format gespeichert wird. Seit PHP 7.2.0 verfügbar. |
Rückgabewert
true zurück, wenn die Signatur gültig ist, false bei ungültiger Signatur und -1 bei einem Fehler (z. B. nicht lesbare Datei oder fehlerhaftes Format).Beispiele
Einfache Signaturprüfung einer S/MIME-Nachricht
<?php
$signedFile = '/pfad/zur/signierten_nachricht.eml';
$signerCertFile = '/tmp/signer_cert.pem';
$contentFile = '/tmp/nachricht_inhalt.txt';
$result = openssl_pkcs7_verify(
$signedFile,
0, // Standardprüfung inkl. Zertifikatskette
$signerCertFile, // Signierzertifikat hier speichern
[], // System-CAs verwenden
null,
$contentFile // Nachrichteninhalt extrahieren
);
if ($result === true) {
echo "Signatur ist gültig." . PHP_EOL;
echo "Nachrichteninhalt:" . PHP_EOL;
echo file_get_contents($contentFile);
} elseif ($result === false) {
echo "Ungültige Signatur!" . PHP_EOL;
} else {
echo "Fehler bei der Signaturprüfung." . PHP_EOL;
echo openssl_error_string() . PHP_EOL;
}
Signaturprüfung ohne Zertifikatsvalidierung (für Tests)
<?php
$signedFile = '/pfad/zur/signierten_nachricht.eml';
// PKCS7_NOVERIFY: Zertifikatskette wird nicht geprüft
// Sinnvoll z. B. bei selbstsignierten Zertifikaten in Testumgebungen
$result = openssl_pkcs7_verify(
$signedFile,
PKCS7_NOVERIFY
);
if ($result === true) {
echo "Signatur formal korrekt (Zertifikat nicht geprüft)." . PHP_EOL;
} elseif ($result === false) {
echo "Signaturprüfung fehlgeschlagen." . PHP_EOL;
} else {
echo "Verarbeitungsfehler: " . openssl_error_string() . PHP_EOL;
}
Eigene CA-Zertifikate für Kettenprüfung angeben
<?php
$signedFile = '/pfad/zur/signierten_nachricht.eml';
$caCertFile = '/etc/ssl/certs/eigene_ca.pem';
$result = openssl_pkcs7_verify(
$signedFile,
0,
null,
[$caCertFile] // Eigene CA als Vertrauensanker
);
if ($result === true) {
echo "Nachricht erfolgreich gegen eigene CA verifiziert." . PHP_EOL;
} else {
echo "Verifikation fehlgeschlagen oder Fehler aufgetreten." . PHP_EOL;
}
// Wichtig · Fallstricke
Sicherheitshinweis: Verwende PKCS7_NOVERIFY niemals in Produktionsumgebungen ohne zusätzliche Sicherheitsmaßnahmen, da damit die Zertifikatsprüfung vollständig deaktiviert wird und gefälschte Signaturen akzeptiert werden könnten.
Dateipfade: Die Funktion erwartet zwingend einen Dateipfad für die signierte Nachricht – keine Strings oder Streams. Stelle sicher, dass die Datei lesbar ist und das korrekte Format (PEM-Envelope) aufweist, da die Funktion sonst -1 zurückgibt.
Rückgabewert -1 vs. false: Die Unterscheidung zwischen Fehler (-1) und ungültiger Signatur (false) ist wichtig. Prüfe deshalb mit striktem Vergleich (===), nicht mit == oder losem Wahrheitswert, da -1 in PHP als truthy gilt.
Seit PHP 7.2.0 steht der siebte Parameter pk7 zur Verfügung, mit dem die rohe PKCS#7-Signaturstruktur gespeichert werden kann. Für ältere PHP-Versionen muss dieser Parameter weggelassen werden.