diff options
author | Chris Burdess <dog@bluezoo.org> | 2007-06-01 09:43:53 +0000 |
---|---|---|
committer | Chris Burdess <dog@bluezoo.org> | 2007-06-01 09:43:53 +0000 |
commit | a1721947a46086f4e15bc28b92a5b63cf8805bf8 (patch) | |
tree | 4c0fa7bb25c6807ef60a7edc665fa14f77a4450b /gnu/xml | |
parent | 6777f788a9f82babbf3bd508dcd0f1c636fdf220 (diff) | |
download | classpath-a1721947a46086f4e15bc28b92a5b63cf8805bf8.tar.gz |
2007-06-01 Robin Garner <robin.garner@anu.edu.au>
Fixes #32162
* gnu/xml/dom/DomNode.java: Correct concurrency problem when deep
cloning nodes.
Diffstat (limited to 'gnu/xml')
-rw-r--r-- | gnu/xml/dom/DomNode.java | 45 |
1 files changed, 33 insertions, 12 deletions
diff --git a/gnu/xml/dom/DomNode.java b/gnu/xml/dom/DomNode.java index 9af3f3e54..1cbdc2aec 100644 --- a/gnu/xml/dom/DomNode.java +++ b/gnu/xml/dom/DomNode.java @@ -1108,26 +1108,47 @@ public abstract class DomNode */ public Node cloneNode(boolean deep) { - DomNode node = (DomNode) clone(); - if (deep) { - DomDocument doc = (nodeType == DOCUMENT_NODE) ? - (DomDocument) node : node.owner; - boolean building = doc.building; + return cloneNodeDeepInternal(true, null); + } + + DomNode node = (DomNode) clone(); + if (nodeType == ENTITY_REFERENCE_NODE) + { + node.makeReadonly(); + } + notifyUserDataHandlers(UserDataHandler.NODE_CLONED, this, node); + return node; + } + + /** + * Returns a deep clone of this node. + */ + private DomNode cloneNodeDeepInternal(boolean root, DomDocument doc) + { + DomNode node = (DomNode) clone(); + boolean building = false; // Never used unless root is true + if (root) + { + doc = (nodeType == DOCUMENT_NODE) ? (DomDocument) node : node.owner; + building = doc.building; doc.building = true; // Permit certain structural rules - for (DomNode ctx = first; ctx != null; ctx = ctx.next) - { - DomNode newChild = (DomNode) ctx.cloneNode(deep); - newChild.setOwner(doc); - node.appendChild(newChild); - } - doc.building = building; + } + node.owner = doc; + for (DomNode ctx = first; ctx != null; ctx = ctx.next) + { + DomNode newChild = ctx.cloneNodeDeepInternal(false, doc); + node.appendChild(newChild); } if (nodeType == ENTITY_REFERENCE_NODE) { node.makeReadonly(); } + if (root) + { + doc.building = building; + } notifyUserDataHandlers(UserDataHandler.NODE_CLONED, this, node); return node; } |