Je tente de déchiffrer un courriel S / MIME (envoyé à l'origine via Outlook) et de le faire, j'utilise l'API Bouncycastle. Je suis en train de courir dans un accroc, cependant.
J'ai, dans le magasin de certificats Windows, le certificat pour le destinataire. J'avais déjà utilisé pour envoyer un courrier électronique signé et crypté à l'autre partie, et ils l'utilisaient à son tour pour m'envoyer une réponse cryptée. J'ai ensuite exporté le certificat (avec clé privée) en tant que fichier .pfx et j'ai chargé ce fichier PFX dans un kingle Java. Cependant, cela ne fonctionne pas, et je soupçonne que c'est parce que les identificateurs de clé de sujet ne correspondent pas. P>
Voici le code que j'utilise pour obtenir l'identifiant de clé d'objet à partir du magasin de clés: P>
04 14 88 ed bb 7c 64 7b 41 63 48 0a 24 40 2b 3c d0 78 72 3c 30 b3
3 Réponses :
Toutes ces réponses sont cohérentes si vous comprenez toutes les spécifications, mais bien sûr, cela signifie qu'ils sont déroutants si vous ne le faites pas. Le premier endroit à regarder est dans RFC 5280, section 4.2.1.2 a>. Dans ce cas, la méthode (1) est utilisée. Suivant, regardez Section A.2 à la définition de KeyIntifier. Il est défini comme une chaîne d'octet. Regardez maintenant comment une chaîne d'octets ASN.1 octobre doit être encodé . Il devrait commencer par Hex 04 suivi de la longueur en octets (20 octets ou 14 hex) suivi de la chaîne d'octet réelle (le hachage SHA1). Donc, le contenu de l'extension doit être enfin, regardez la définition ASN.1 de Extension . Il dit que la valeur d'extension doit être codée sous forme de chaîne d'octet. Dans le cas de cette extension particulière, l'effet net est celui-ci est codé deux fois de suite dans une rangée d'octet. A ce niveau, la chaîne d'octet est la chaîne d'octets précédente qui comprend les deux octets d'en-tête Ceci est la valeur renvoyée par le x509extension.getExtensionValue () méthode. Maintenant, la partie intéressante de l'identifiant de la clé est que le hachage SHA1 qui commence par 04 14 code>, de sorte que la longueur est hexagère 16 et le codage est p>
88 code>, c'est donc ce que l'utilitaire Windows s'affiche. Évidemment, la méthode BouncyCastle que vous utilisez affiche l'extension sans décodage supplémentaire. P> p>
J'ai été capable de déchiffrer l'e-mail en utilisant directement la clé privée, mais je ne peux toujours pas le faire fonctionner en utilisant des méthodes non obsolètes. Je suppose que x509extension.getExtensionValue () devait se déshabiller une couche de codage de la valeur lorsqu'elle le renvoie. Cela ferait correspondre.
Aussi, je suppose que vous vouliez dire ... "Décodage supplémentaire"?
@ @Mark: re suppression d'une couche off. À l'origine, c'est ce que je pensais mais après un peu de considération, je pense maintenant que GetextensionValue () fait la bonne chose.
@Ggs: Vous êtes donc d'avis que le code pour correspondre à l'ID de clé de sujet est faux (doit être effectué 2x décodes sur le côté CERT et 1x décodage sur le côté SMIME), ou le message SMIME est codé de manière incorrecte?
@Mark: Voici comment je le mettit. La méthode GetextensionValue () n'est pas consciente de ce que la signification de l'extension que vous demandez est. La source est probablement très simple. Le code SMIME est plus au courant. Il sait que ceci est, pas seulement une extension, mais l'extension du suject fiable, et donc cette chaîne d'octet code en fait une autre chaîne d'octet. J'avoue que je ne suis pas trop familier avec l'API de BCMail, je devine une sorte de deviner.
est le message S / MIME créé par Outlook 2010? p>
Si oui, voir Brinkers Martijn P>
Non, cela ne semble pas être le problème ici. Il y a définitivement un sujfidentifier, il ne correspond pas à ce que le certificat a.
La réponse acceptée de Gregs m'a aidé beaucoup.
Le code qui finit par travailler pour moi est le suivant: P>
X509Certificate certificate = ... byte[] encExtensionSubjectKeyIdentifier = certificate.getExtensionValue(Extension.subjectKeyIdentifier.getId()); // Unwrap first 'layer' ASN1Primitive skiPrimitive = JcaX509ExtensionUtils.parseExtensionValue(encExtensionSubjectKeyIdentifier); // Unwrap second 'layer' byte[] keyIdentifier = ASN1OctetString.getInstance(skiPrimitive.getEncoded()).getOctets(); // Use keyIdentifier in e.g. CMS SignerInfo SignerInfoGenerator signerInfoGenerator = jcaSignerInfoGeneratorBuilder.build(sha1Signer, keyIdentifier);