Hi,
ich hab mir mit einigem Zeitaufwand mal Bouncycastle angesehen und versucht, (D)TLS-Server + (D)TLS-Client zu basteln.
Mein Ziel ist es jetzt, die Client/Server-Zertifikate zur Authentifizierung zu benutzen:
Aus den Bouncycastle-Tests (MockTlsClient) hab ich also folgende Methode:
In notifyServerCertificate() wird also das Server-Zertifikat validiert.
Hier stellt sich meine erste Frage: Wie genau soll ich die Keys verifizieren?
TLSTestUtils.fingerprint() liefert hier den Hex-Wert der SHA256-codierten DER-Codierung des Server-Zertifikats (
).
Eine weitere Frage, eher aus Interesse: Wenn ich jetzt das Server-Zertifikat regulär, also an Hand der Root-Zertifikate prüfen wollte, wie würde ich das anstellen?
Im Version 2 Wiki von Bouncycastle steht:
Noch eine letzte Frage:
getClientCredentials() schickt die Client-Zertifikate an den Server, oder?
ich hab mir mit einigem Zeitaufwand mal Bouncycastle angesehen und versucht, (D)TLS-Server + (D)TLS-Client zu basteln.
Mein Ziel ist es jetzt, die Client/Server-Zertifikate zur Authentifizierung zu benutzen:
- Jeder Server/Client generiert sich ein Zertifikat
- Jeder Client/Server bekommt eine Datenbank mit PublicKeys, mit denen er sich verbindet.
- Wenn eine neue TLS-Verbindung aufgebaut wird, sieht der Server/Client in seiner Datenbank nach, ob er den PublicKey seines Gegenübers kennt, und verbindet sich.
Aus den Bouncycastle-Tests (MockTlsClient) hab ich also folgende Methode:
Code:
public TlsAuthentication getAuthentication() throws IOException {
return new TlsAuthentication() {
public void notifyServerCertificate(org.bouncycastle.crypto.tls.Certificate serverCertificate)
throws IOException {
Certificate[] chain = serverCertificate.getCertificateList();
System.out.println("TLS client received server certificate chain of length " + chain.length);
for (int i = 0; i != chain.length; i++) {
Certificate entry = chain[i];
// TODO Create fingerprint based on certificate signature
// algorithm digest
System.out.println(" fingerprint:SHA-256 " + TlsTestUtils.fingerprint(entry) + " ("
+ entry.getSubject() + ")");
}
}
public TlsCredentials getClientCredentials(CertificateRequest certificateRequest)
throws IOException {
short[] certificateTypes = certificateRequest.getCertificateTypes();
if (certificateTypes == null || !Arrays.contains(certificateTypes, ClientCertificateType.rsa_sign)) {
return null;
}
return TlsTestUtils.loadSignerCredentials(context, certificateRequest.getSupportedSignatureAlgorithms(),
SignatureAlgorithm.rsa, "x509-client.pem", "x509-client-key.pem");
}
};
}
In notifyServerCertificate() wird also das Server-Zertifikat validiert.
Hier stellt sich meine erste Frage: Wie genau soll ich die Keys verifizieren?
TLSTestUtils.fingerprint() liefert hier den Hex-Wert der SHA256-codierten DER-Codierung des Server-Zertifikats (
- Ich könnte mir also den Fingerprint des Zertifikats generieren und diesen vergleichen
- ich codiere den DER-String als BASE64 und speichere den ab
Eine weitere Frage, eher aus Interesse: Wenn ich jetzt das Server-Zertifikat regulär, also an Hand der Root-Zertifikate prüfen wollte, wie würde ich das anstellen?
Im Version 2 Wiki von Bouncycastle steht:
Was genau soll das machen? Wo bekomme ich den certHolder her?In the case of the lightweight API, assuming we have a suitable public key in the lwPubKey object, the code for doing the signature verification looks as follows:
Code:ContentVerifierProvider contentVerifierProvider = new BcRSAContentVerifierProviderBuilder( new DefaultDigestAlgorithmIdentifierFinder()).build(lwPubKey); if (!certHolder.isSignatureValid(contentVerifierProvider)) { System.err.println("signature invalid"); }
Noch eine letzte Frage:
getClientCredentials() schickt die Client-Zertifikate an den Server, oder?
Zuletzt bearbeitet:
(Typo)