|
54 | 54 | import org.apache.commons.codec.binary.Base64; |
55 | 55 | import org.apache.commons.codec.digest.DigestUtils; |
56 | 56 | import org.apache.commons.lang3.StringUtils; |
| 57 | +import org.apache.xml.security.encryption.CipherData; |
57 | 58 | import org.apache.xml.security.encryption.EncryptedData; |
58 | 59 | import org.apache.xml.security.encryption.EncryptedKey; |
59 | 60 | import org.apache.xml.security.encryption.XMLCipher; |
@@ -899,6 +900,36 @@ public static void decryptElement(Element encryptedDataElement, PrivateKey input |
899 | 900 |
|
900 | 901 | XMLCipher xmlCipher = XMLCipher.getInstance(); |
901 | 902 | xmlCipher.init(XMLCipher.DECRYPT_MODE, null); |
| 903 | + |
| 904 | + /* Check if we have encryptedData with a KeyInfo that contains a RetrievalMethod to obtain the EncryptedKey. |
| 905 | + xmlCipher is not able to handle that so we move the EncryptedKey inside the KeyInfo element and |
| 906 | + replacing the RetrievalMethod. |
| 907 | + */ |
| 908 | + |
| 909 | + NodeList keyInfoInEncData = encryptedDataElement.getElementsByTagNameNS(Constants.NS_DS, "KeyInfo"); |
| 910 | + if (keyInfoInEncData.getLength() == 0) { |
| 911 | + throw new Exception("No KeyInfo inside EncryptedData element"); |
| 912 | + } |
| 913 | + |
| 914 | + NodeList childs = keyInfoInEncData.item(0).getChildNodes(); |
| 915 | + for (int i=0; i < childs.getLength(); i++) { |
| 916 | + if (childs.item(i).getLocalName() != null && childs.item(i).getLocalName().equals("RetrievalMethod")) { |
| 917 | + Element retrievalMethodElem = (Element)childs.item(i); |
| 918 | + if (!retrievalMethodElem.getAttribute("Type").equals("http://www.w3.org/2001/04/xmlenc#EncryptedKey")) { |
| 919 | + throw new Exception("Unsupported Retrieval Method found"); |
| 920 | + } |
| 921 | + |
| 922 | + String uri = retrievalMethodElem.getAttribute("URI").substring(1); |
| 923 | + |
| 924 | + NodeList encryptedKeyNodes = ((Element) encryptedDataElement.getParentNode()).getElementsByTagNameNS(Constants.NS_XENC, "EncryptedKey"); |
| 925 | + for (int j=0; j < encryptedKeyNodes.getLength(); j++) { |
| 926 | + if (((Element)encryptedKeyNodes.item(j)).getAttribute("Id").equals(uri)) { |
| 927 | + keyInfoInEncData.item(0).replaceChild(encryptedKeyNodes.item(j), childs.item(i)); |
| 928 | + } |
| 929 | + } |
| 930 | + } |
| 931 | + } |
| 932 | + |
902 | 933 | xmlCipher.setKEK(inputKey); |
903 | 934 | xmlCipher.doFinal(encryptedDataElement.getOwnerDocument(), encryptedDataElement, false); |
904 | 935 | } catch (Exception e) { |
|
0 commit comments