org.jcp.xml.dsig.internal.dom.DOMXMLSignature Maven / Gradle / Ivy
The newest version!
/* */ package org.jcp.xml.dsig.internal.dom;
/* */
/* */ import com.sun.org.apache.xml.internal.security.Init;
/* */ import com.sun.org.apache.xml.internal.security.exceptions.Base64DecodingException;
/* */ import com.sun.org.apache.xml.internal.security.utils.Base64;
/* */ import java.security.InvalidKeyException;
/* */ import java.security.Key;
/* */ import java.util.ArrayList;
/* */ import java.util.Collections;
/* */ import java.util.HashMap;
/* */ import java.util.List;
/* */ import java.util.logging.Level;
/* */ import java.util.logging.Logger;
/* */ import javax.xml.crypto.KeySelector;
/* */ import javax.xml.crypto.KeySelector.Purpose;
/* */ import javax.xml.crypto.KeySelectorException;
/* */ import javax.xml.crypto.KeySelectorResult;
/* */ import javax.xml.crypto.MarshalException;
/* */ import javax.xml.crypto.XMLCryptoContext;
/* */ import javax.xml.crypto.XMLStructure;
/* */ import javax.xml.crypto.dom.DOMCryptoContext;
/* */ import javax.xml.crypto.dsig.Manifest;
/* */ import javax.xml.crypto.dsig.Reference;
/* */ import javax.xml.crypto.dsig.SignatureMethod;
/* */ import javax.xml.crypto.dsig.SignedInfo;
/* */ import javax.xml.crypto.dsig.Transform;
/* */ import javax.xml.crypto.dsig.XMLObject;
/* */ import javax.xml.crypto.dsig.XMLSignContext;
/* */ import javax.xml.crypto.dsig.XMLSignature;
/* */ import javax.xml.crypto.dsig.XMLSignature.SignatureValue;
/* */ import javax.xml.crypto.dsig.XMLSignatureException;
/* */ import javax.xml.crypto.dsig.XMLValidateContext;
/* */ import javax.xml.crypto.dsig.dom.DOMSignContext;
/* */ import javax.xml.crypto.dsig.keyinfo.KeyInfo;
/* */ import org.w3c.dom.Document;
/* */ import org.w3c.dom.Element;
/* */ import org.w3c.dom.Node;
/* */
/* */ public final class DOMXMLSignature extends DOMStructure
/* */ implements XMLSignature
/* */ {
/* 47 */ private static Logger log = Logger.getLogger("org.jcp.xml.dsig.internal.dom");
/* */ private String id;
/* */ private XMLSignature.SignatureValue sv;
/* */ private KeyInfo ki;
/* */ private List objects;
/* */ private SignedInfo si;
/* 53 */ private Document ownerDoc = null;
/* 54 */ private Element localSigElem = null;
/* 55 */ private Element sigElem = null;
/* */ private boolean validationStatus;
/* 57 */ private boolean validated = false;
/* */ private KeySelectorResult ksr;
/* */ private HashMap signatureIdMap;
/* */
/* */ public DOMXMLSignature(SignedInfo si, KeyInfo ki, List objs, String id, String signatureValueId)
/* */ {
/* 81 */ if (si == null) {
/* 82 */ throw new NullPointerException("signedInfo cannot be null");
/* */ }
/* 84 */ this.si = si;
/* 85 */ this.id = id;
/* 86 */ this.sv = new DOMSignatureValue(signatureValueId);
/* 87 */ if (objs == null) {
/* 88 */ this.objects = Collections.EMPTY_LIST;
/* */ } else {
/* 90 */ List objsCopy = new ArrayList(objs);
/* 91 */ int i = 0; for (int size = objsCopy.size(); i < size; i++) {
/* 92 */ if (!(objsCopy.get(i) instanceof XMLObject)) {
/* 93 */ throw new ClassCastException("objs[" + i + "] is not an XMLObject");
/* */ }
/* */ }
/* */
/* 97 */ this.objects = Collections.unmodifiableList(objsCopy);
/* */ }
/* 99 */ this.ki = ki;
/* */ }
/* */
/* */ public DOMXMLSignature(Element sigElem, XMLCryptoContext context)
/* */ throws MarshalException
/* */ {
/* 110 */ this.localSigElem = sigElem;
/* 111 */ this.ownerDoc = this.localSigElem.getOwnerDocument();
/* */
/* 114 */ this.id = DOMUtils.getAttributeValue(this.localSigElem, "Id");
/* */
/* 117 */ Element siElem = DOMUtils.getFirstChildElement(this.localSigElem);
/* 118 */ this.si = new DOMSignedInfo(siElem, context);
/* */
/* 121 */ Element sigValElem = DOMUtils.getNextSiblingElement(siElem);
/* 122 */ this.sv = new DOMSignatureValue(sigValElem);
/* */
/* 125 */ Element nextSibling = DOMUtils.getNextSiblingElement(sigValElem);
/* 126 */ if ((nextSibling != null) && (nextSibling.getLocalName().equals("KeyInfo"))) {
/* 127 */ this.ki = new DOMKeyInfo(nextSibling, context);
/* 128 */ nextSibling = DOMUtils.getNextSiblingElement(nextSibling);
/* */ }
/* */
/* 132 */ if (nextSibling == null) {
/* 133 */ this.objects = Collections.EMPTY_LIST;
/* */ } else {
/* 135 */ List tempObjects = new ArrayList();
/* 136 */ while (nextSibling != null) {
/* 137 */ tempObjects.add(new DOMXMLObject(nextSibling, context));
/* 138 */ nextSibling = DOMUtils.getNextSiblingElement(nextSibling);
/* */ }
/* 140 */ this.objects = Collections.unmodifiableList(tempObjects);
/* */ }
/* */ }
/* */
/* */ public String getId() {
/* 145 */ return this.id;
/* */ }
/* */
/* */ public KeyInfo getKeyInfo() {
/* 149 */ return this.ki;
/* */ }
/* */
/* */ public SignedInfo getSignedInfo() {
/* 153 */ return this.si;
/* */ }
/* */
/* */ public List getObjects() {
/* 157 */ return this.objects;
/* */ }
/* */
/* */ public XMLSignature.SignatureValue getSignatureValue() {
/* 161 */ return this.sv;
/* */ }
/* */
/* */ public KeySelectorResult getKeySelectorResult() {
/* 165 */ return this.ksr;
/* */ }
/* */
/* */ public void marshal(Node parent, String dsPrefix, DOMCryptoContext context) throws MarshalException
/* */ {
/* 170 */ marshal(parent, null, dsPrefix, context);
/* */ }
/* */
/* */ public void marshal(Node parent, Node nextSibling, String dsPrefix, DOMCryptoContext context) throws MarshalException
/* */ {
/* 175 */ this.ownerDoc = DOMUtils.getOwnerDocument(parent);
/* */
/* 177 */ this.sigElem = DOMUtils.createElement(this.ownerDoc, "Signature", "http://www.w3.org/2000/09/xmldsig#", dsPrefix);
/* */
/* 183 */ if (dsPrefix == null) {
/* 184 */ this.sigElem.setAttributeNS("http://www.w3.org/2000/xmlns/", "xmlns", "http://www.w3.org/2000/09/xmldsig#");
/* */ }
/* */ else {
/* 187 */ this.sigElem.setAttributeNS("http://www.w3.org/2000/xmlns/", "xmlns:" + dsPrefix, "http://www.w3.org/2000/09/xmldsig#");
/* */ }
/* */
/* 193 */ ((DOMSignedInfo)this.si).marshal(this.sigElem, dsPrefix, context);
/* */
/* 196 */ ((DOMSignatureValue)this.sv).marshal(this.sigElem, dsPrefix, context);
/* */
/* 199 */ if (this.ki != null) {
/* 200 */ ((DOMKeyInfo)this.ki).marshal(this.sigElem, null, dsPrefix, context);
/* */ }
/* */
/* 204 */ int i = 0; for (int size = this.objects.size(); i < size; i++) {
/* 205 */ ((DOMXMLObject)this.objects.get(i)).marshal(this.sigElem, dsPrefix, context);
/* */ }
/* */
/* 209 */ DOMUtils.setAttributeID(this.sigElem, "Id", this.id);
/* */
/* 211 */ parent.insertBefore(this.sigElem, nextSibling);
/* */ }
/* */
/* */ public boolean validate(XMLValidateContext vc)
/* */ throws XMLSignatureException
/* */ {
/* 217 */ if (vc == null) {
/* 218 */ throw new NullPointerException("validateContext is null");
/* */ }
/* */
/* 221 */ if (this.validated) {
/* 222 */ return this.validationStatus;
/* */ }
/* */
/* 226 */ List refs = this.si.getReferences();
/* 227 */ boolean validateRefs = true;
/* 228 */ int i = 0; for (int size = refs.size(); (validateRefs) && (i < size); i++) {
/* 229 */ Reference ref = (Reference)refs.get(i);
/* 230 */ boolean refValid = ref.validate(vc);
/* 231 */ if (log.isLoggable(Level.FINE)) {
/* 232 */ log.log(Level.FINE, "Reference[" + ref.getURI() + "] is valid: " + refValid);
/* */ }
/* */
/* 235 */ validateRefs &= refValid;
/* */ }
/* 237 */ if (!validateRefs) {
/* 238 */ if (log.isLoggable(Level.FINE)) {
/* 239 */ log.log(Level.FINE, "Couldn't validate the References");
/* */ }
/* 241 */ this.validationStatus = false;
/* 242 */ this.validated = true;
/* 243 */ return this.validationStatus;
/* */ }
/* */
/* 247 */ boolean sigValidity = this.sv.validate(vc);
/* 248 */ if (!sigValidity) {
/* 249 */ this.validationStatus = false;
/* 250 */ this.validated = true;
/* 251 */ return this.validationStatus;
/* */ }
/* */
/* 255 */ boolean validateMans = true;
/* 256 */ if (Boolean.TRUE.equals(vc.getProperty("org.jcp.xml.dsig.validateManifests")))
/* */ {
/* 259 */ int i = 0; for (int size = this.objects.size(); (validateMans) && (i < size); i++) {
/* 260 */ XMLObject xo = (XMLObject)this.objects.get(i);
/* 261 */ List content = xo.getContent();
/* 262 */ int csize = content.size();
/* 263 */ for (int j = 0; (validateMans) && (j < csize); j++) {
/* 264 */ XMLStructure xs = (XMLStructure)content.get(j);
/* 265 */ if ((xs instanceof Manifest)) {
/* 266 */ if (log.isLoggable(Level.FINE)) {
/* 267 */ log.log(Level.FINE, "validating manifest");
/* */ }
/* 269 */ Manifest man = (Manifest)xs;
/* 270 */ List manRefs = man.getReferences();
/* 271 */ int rsize = manRefs.size();
/* 272 */ for (int k = 0; (validateMans) && (k < rsize); k++) {
/* 273 */ Reference ref = (Reference)manRefs.get(k);
/* 274 */ boolean refValid = ref.validate(vc);
/* 275 */ if (log.isLoggable(Level.FINE)) {
/* 276 */ log.log(Level.FINE, "Manifest ref[" + ref.getURI() + "] is valid: " + refValid);
/* */ }
/* */
/* 279 */ validateMans &= refValid;
/* */ }
/* */ }
/* */ }
/* */ }
/* */ }
/* */
/* 286 */ this.validationStatus = validateMans;
/* 287 */ this.validated = true;
/* 288 */ return this.validationStatus;
/* */ }
/* */
/* */ public void sign(XMLSignContext signContext) throws MarshalException, XMLSignatureException
/* */ {
/* 293 */ if (signContext == null) {
/* 294 */ throw new NullPointerException("signContext cannot be null");
/* */ }
/* 296 */ DOMSignContext context = (DOMSignContext)signContext;
/* 297 */ if (context != null) {
/* 298 */ marshal(context.getParent(), context.getNextSibling(), DOMUtils.getSignaturePrefix(context), context);
/* */ }
/* */
/* 303 */ List allReferences = new ArrayList(this.si.getReferences());
/* */
/* 307 */ this.signatureIdMap = new HashMap();
/* 308 */ this.signatureIdMap.put(this.id, this);
/* 309 */ this.signatureIdMap.put(this.si.getId(), this.si);
/* 310 */ List refs = this.si.getReferences();
/* 311 */ int i = 0; for (int size = refs.size(); i < size; i++) {
/* 312 */ Reference ref = (Reference)refs.get(i);
/* 313 */ this.signatureIdMap.put(ref.getId(), ref);
/* */ }
/* 315 */ int i = 0; for (int size = this.objects.size(); i < size; i++) {
/* 316 */ XMLObject obj = (XMLObject)this.objects.get(i);
/* 317 */ this.signatureIdMap.put(obj.getId(), obj);
/* 318 */ List content = obj.getContent();
/* 319 */ int j = 0; for (int csize = content.size(); j < csize; j++) {
/* 320 */ XMLStructure xs = (XMLStructure)content.get(j);
/* 321 */ if ((xs instanceof Manifest)) {
/* 322 */ Manifest man = (Manifest)xs;
/* 323 */ this.signatureIdMap.put(man.getId(), man);
/* 324 */ List manRefs = man.getReferences();
/* 325 */ int k = 0; for (int msize = manRefs.size(); k < msize; k++) {
/* 326 */ Reference ref = (Reference)manRefs.get(k);
/* 327 */ allReferences.add(ref);
/* 328 */ this.signatureIdMap.put(ref.getId(), ref);
/* */ }
/* */ }
/* */ }
/* */
/* */ }
/* */
/* 335 */ int i = 0; for (int size = allReferences.size(); i < size; i++) {
/* 336 */ DOMReference ref = (DOMReference)allReferences.get(i);
/* 337 */ digestReference(ref, signContext);
/* */ }
/* */
/* 341 */ int i = 0; for (int size = allReferences.size(); i < size; i++) {
/* 342 */ DOMReference ref = (DOMReference)allReferences.get(i);
/* 343 */ if (!ref.isDigested())
/* */ {
/* 346 */ ref.digest(signContext);
/* */ }
/* */ }
/* 349 */ Key signingKey = null;
/* 350 */ KeySelectorResult ksr = null;
/* */ try {
/* 352 */ ksr = signContext.getKeySelector().select(this.ki, KeySelector.Purpose.SIGN, this.si.getSignatureMethod(), signContext);
/* */
/* 355 */ signingKey = ksr.getKey();
/* 356 */ if (signingKey == null)
/* 357 */ throw new XMLSignatureException("the keySelector did not find a signing key");
/* */ }
/* */ catch (KeySelectorException kse)
/* */ {
/* 361 */ throw new XMLSignatureException("cannot find signing key", kse);
/* */ }
/* */
/* 365 */ byte[] val = null;
/* */ try {
/* 367 */ val = ((DOMSignatureMethod)this.si.getSignatureMethod()).sign(signingKey, (DOMSignedInfo)this.si, signContext);
/* */ }
/* */ catch (InvalidKeyException ike) {
/* 370 */ throw new XMLSignatureException(ike);
/* */ }
/* */
/* 373 */ if (log.isLoggable(Level.FINE)) {
/* 374 */ log.log(Level.FINE, "SignatureValue = " + val);
/* */ }
/* 376 */ ((DOMSignatureValue)this.sv).setValue(val);
/* */
/* 378 */ this.localSigElem = this.sigElem;
/* 379 */ this.ksr = ksr;
/* */ }
/* */
/* */ public boolean equals(Object o) {
/* 383 */ if (this == o) {
/* 384 */ return true;
/* */ }
/* */
/* 387 */ if (!(o instanceof XMLSignature)) {
/* 388 */ return false;
/* */ }
/* 390 */ XMLSignature osig = (XMLSignature)o;
/* */
/* 392 */ boolean idEqual = this.id == null ? false : osig.getId() == null ? true : this.id.equals(osig.getId());
/* */
/* 394 */ boolean keyInfoEqual = this.ki == null ? false : osig.getKeyInfo() == null ? true : this.ki.equals(osig.getKeyInfo());
/* */
/* 398 */ return (idEqual) && (keyInfoEqual) && (this.sv.equals(osig.getSignatureValue())) && (this.si.equals(osig.getSignedInfo())) && (this.objects.equals(osig.getObjects()));
/* */ }
/* */
/* */ private void digestReference(DOMReference ref, XMLSignContext signContext)
/* */ throws XMLSignatureException
/* */ {
/* 406 */ if (ref.isDigested()) {
/* 407 */ return;
/* */ }
/* */
/* 410 */ String uri = ref.getURI();
/* 411 */ if (Utils.sameDocumentURI(uri)) {
/* 412 */ String id = Utils.parseIdFromSameDocumentURI(uri);
/* 413 */ if ((id != null) && (this.signatureIdMap.containsKey(id))) {
/* 414 */ Object obj = this.signatureIdMap.get(id);
/* 415 */ if ((obj instanceof DOMReference)) {
/* 416 */ digestReference((DOMReference)obj, signContext);
/* 417 */ } else if ((obj instanceof Manifest)) {
/* 418 */ Manifest man = (Manifest)obj;
/* 419 */ List manRefs = man.getReferences();
/* 420 */ int i = 0; for (int size = manRefs.size(); i < size; i++) {
/* 421 */ digestReference((DOMReference)manRefs.get(i), signContext);
/* */ }
/* */
/* */ }
/* */
/* */ }
/* */
/* 429 */ if (uri.length() == 0) {
/* 430 */ List transforms = ref.getTransforms();
/* 431 */ int i = 0; for (int size = transforms.size(); i < size; i++) {
/* 432 */ Transform transform = (Transform)transforms.get(i);
/* 433 */ String transformAlg = transform.getAlgorithm();
/* 434 */ if ((transformAlg.equals("http://www.w3.org/TR/1999/REC-xpath-19991116")) || (transformAlg.equals("http://www.w3.org/2002/06/xmldsig-filter2")))
/* */ {
/* 436 */ return;
/* */ }
/* */ }
/* */ }
/* */ }
/* 441 */ ref.digest(signContext);
/* */ }
/* */
/* */ static
/* */ {
/* 62 */ Init.init();
/* */ }
/* */
/* */ public class DOMSignatureValue extends DOMStructure
/* */ implements XMLSignature.SignatureValue
/* */ {
/* */ private String id;
/* */ private byte[] value;
/* */ private String valueBase64;
/* */ private Element sigValueElem;
/* 451 */ private boolean validated = false;
/* */ private boolean validationStatus;
/* */
/* */ DOMSignatureValue(String id)
/* */ {
/* 455 */ this.id = id;
/* */ }
/* */
/* */ DOMSignatureValue(Element sigValueElem) throws MarshalException
/* */ {
/* */ try {
/* 461 */ this.value = Base64.decode(sigValueElem);
/* */ } catch (Base64DecodingException bde) {
/* 463 */ throw new MarshalException(bde);
/* */ }
/* */
/* 466 */ this.id = DOMUtils.getAttributeValue(sigValueElem, "Id");
/* 467 */ this.sigValueElem = sigValueElem;
/* */ }
/* */
/* */ public String getId() {
/* 471 */ return this.id;
/* */ }
/* */
/* */ public byte[] getValue() {
/* 475 */ return this.value == null ? null : (byte[])this.value.clone();
/* */ }
/* */
/* */ public boolean validate(XMLValidateContext validateContext)
/* */ throws XMLSignatureException
/* */ {
/* 481 */ if (validateContext == null) {
/* 482 */ throw new NullPointerException("context cannot be null");
/* */ }
/* */
/* 485 */ if (this.validated) {
/* 486 */ return this.validationStatus;
/* 490 */ }
/* */ SignatureMethod sm = DOMXMLSignature.this.si.getSignatureMethod();
/* 491 */ Key validationKey = null;
/* */ KeySelectorResult ksResult;
/* */ try {
/* 494 */ ksResult = validateContext.getKeySelector().select(DOMXMLSignature.this.ki, KeySelector.Purpose.VERIFY, sm, validateContext);
/* */
/* 496 */ validationKey = ksResult.getKey();
/* 497 */ if (validationKey == null)
/* 498 */ throw new XMLSignatureException("the keyselector did not find a validation key");
/* */ }
/* */ catch (KeySelectorException kse)
/* */ {
/* 502 */ throw new XMLSignatureException("cannot find validation key", kse);
/* */ }
/* */
/* */ try
/* */ {
/* 508 */ this.validationStatus = ((DOMSignatureMethod)sm).verify(validationKey, (DOMSignedInfo)DOMXMLSignature.this.si, this.value, validateContext);
/* */ }
/* */ catch (Exception e) {
/* 511 */ throw new XMLSignatureException(e);
/* */ }
/* */
/* 514 */ this.validated = true;
/* 515 */ DOMXMLSignature.this.ksr = ksResult;
/* 516 */ return this.validationStatus;
/* */ }
/* */
/* */ public boolean equals(Object o) {
/* 520 */ if (this == o) {
/* 521 */ return true;
/* */ }
/* */
/* 524 */ if (!(o instanceof XMLSignature.SignatureValue)) {
/* 525 */ return false;
/* */ }
/* 527 */ XMLSignature.SignatureValue osv = (XMLSignature.SignatureValue)o;
/* */
/* 529 */ boolean idEqual = this.id == null ? false : osv.getId() == null ? true : this.id.equals(osv.getId());
/* */
/* 533 */ return idEqual;
/* */ }
/* */
/* */ public void marshal(Node parent, String dsPrefix, DOMCryptoContext context)
/* */ throws MarshalException
/* */ {
/* 540 */ this.sigValueElem = DOMUtils.createElement(DOMXMLSignature.this.ownerDoc, "SignatureValue", "http://www.w3.org/2000/09/xmldsig#", dsPrefix);
/* */
/* 542 */ if (this.valueBase64 != null) {
/* 543 */ this.sigValueElem.appendChild(DOMXMLSignature.this.ownerDoc.createTextNode(this.valueBase64));
/* */ }
/* */
/* 547 */ DOMUtils.setAttributeID(this.sigValueElem, "Id", this.id);
/* 548 */ parent.appendChild(this.sigValueElem);
/* */ }
/* */
/* */ void setValue(byte[] value) {
/* 552 */ this.value = value;
/* 553 */ this.valueBase64 = Base64.encode(value);
/* 554 */ this.sigValueElem.appendChild(DOMXMLSignature.this.ownerDoc.createTextNode(this.valueBase64));
/* */ }
/* */ }
/* */ }
/* Location: E:\HYN\Java\trunk\ref\lib-dep\xmldsig\xmldsig.jar
* Qualified Name: org.jcp.xml.dsig.internal.dom.DOMXMLSignature
* JD-Core Version: 0.6.2
*/