Reputation: 9793
I need to sign an XML-File in Java, which needs to contain 3 Reference
s.
While 2 of them are valid (expected digest == actual digest), one is invalid.
The relevant part of the XML Looks like:
<QualifyingProperties xmlns="http://uri.etsi.org/01903/v1.3.2#" Target="Signature1">
<SignedProperties Id="SignedProperties_1">
<SignedSignatureProperties>
<SigningTime>2014-11-27T13:49:36</SigningTime>
</SignedSignatureProperties>
</SignedProperties>
</QualifyingProperties>
The Reference
only references the Element
"SignedProperties" and its children.
As you can see the "QualifyingProperties" Element
defines a namespace (xmlns="http://uri.etsi.org/01903/v1.3.2#"
) and i guess thats the problem:
After having a look at the log i found, that the "Pre-Digest" Value looks like:
<SignedProperties xmlns="http://uri.etsi.org/01903/v1.3.2#" Id="SignedProperties_1">
<SignedSignatureProperties>
<SigningTime>2014-11-27T13:49:36</SigningTime>
</SignedSignatureProperties>
</SignedProperties>
While the "SignedProperties" Element
in the real file does not contain the namespace, but its parent does.
I found out, that the actual digest matches the SHA-256 of the "Pre-Digest" value, while the expected digest matches the SHA-256 of the real file (without the namespace).
The Reference
is created with the following code:
Reference sigPropRef = fac.newReference("#SignedProperties_1", fac.newDigestMethod(DigestMethod.SHA256, null),
Collections.singletonList(sigPropTransform), "http://uri.etsi.org/01903#SignedProperties", "reference-signedpropeties"
);
Where the sigPropTransform
is a CanonicalizationMethod.EXCLUSIVE
Transform
.
My question is, how can i solve the problem, i.e. how can i prevent the namespace to be added to the "SignedProperties" Element
, before calculating the digest?
If you need any other informations please leave a comment, i am pretty new to this theme, so i am not sure which informations are relevant and which not.
Thanks a lot!
EDIT: After playing arround a bit, it seems to me, that the "actual digest" is the digest, the validator calculated, while the "expected digest" is the digest inside the "DigestValue" Element
.
That means, that the digest value inside my file matches the SHA-256 of the referenced filepart, but the validator for some reason calculates the digest WITh the parents namespace.
So i guess what i need is to include the parents namespace in my digest calculation.
EDIT: I continued playing arround and now i have not only the Pre-Digest value of the validator but also the one of my "digest calculation".
That one gives me:
<SignedProperties Id="SignedProperties_1"><SignedSignatureProperties><SigningTime>2014-11-27T15:51:26</SigningTime></SignedSignatureProperties></SignedProperties>
when i give it the following Transform
:
Transform sigPropTransform = fac.newTransform(CanonicalizationMethod.EXCLUSIVE, (ExcC14NParameterSpec)null);
And:
<SignedProperties xmlns:ds="some-url" xmlns:msg="some-other-url" Id="SignedProperties_1"><SignedSignatureProperties><SigningTime>2014-11-27T15:52:49</SigningTime></SignedSignatureProperties></SignedProperties>
when i don't give it any Transform
.
The namespace xmlns="http://uri.etsi.org/01903/v1.3.2#"
is never included.
How do i include it?
Upvotes: 0
Views: 1890
Reputation: 9793
After a few more tries i finally found the actuall problem, as well as the solution:
As i allready stated in the question, the digest calculation did not use the parents namespace, defined as xmlns="http://uri.etsi.org/01903/v1.3.2#"
.
This was, because i did never "register" it as a namespace, but i only added it as a normal Attribute
.
To "register" the namespace i need to call setAttributeNS
instead of setAttribute
.
The code then looks something like:
Element eQualifyingProperties= doc.createElement("QualifyingProperties");
eQualifyingProperties.setAttributeNS("http://www.w3.org/2000/xmlns/", "xmlns", "http://uri.etsi.org/01903/v1.3.2#");
The first parameter is the namespace-uri of the Attribute
and since the Attribute
is a namespace it is the URI of the XML-Namespaces.
The second parameter is the attribute-name, since it should not have any praefix it is simply "xmlns".
The third parameter is the actual attibute-value, which is the namespace-uri i want to "register".
The Element eQualifyingProperties
is the parent of the "SignedProperties" Element
.
After registering the namespace as a real namespace (not as an attribute), the defined Transform
Transform sigPropTransform = fac.newTransform(CanonicalizationMethod.EXCLUSIVE, (ExcC14NParameterSpec)null);
includes it in the digest calculation.
I found this solution in this answer on SO.
Upvotes: 0