Better fix for bug 47852 (NAMESPACE_ERR not being thrown when setting Node.prefix). r/sr=sicking.
git-svn-id: svn://10.0.0.236/trunk@194509 18797224-902f-48f8-a5cc-f745e15eee43
This commit is contained in:
parent
eda09625d4
commit
78cadf3883
@ -786,6 +786,18 @@ public:
|
||||
return sInitialized;
|
||||
}
|
||||
|
||||
/**
|
||||
* Checks if the localname/prefix/namespace triple is valid wrt prefix
|
||||
* and namespace according to the Namespaces in XML and DOM Code
|
||||
* specfications.
|
||||
*
|
||||
* @param aLocalname localname of the node
|
||||
* @param aPrefix prefix of the node
|
||||
* @param aNamespaceID namespace of the node
|
||||
*/
|
||||
static PRBool IsValidNodeName(nsIAtom *aLocalName, nsIAtom *aPrefix,
|
||||
PRInt32 aNamespaceID);
|
||||
|
||||
private:
|
||||
static nsresult doReparentContentWrapper(nsIContent *aChild,
|
||||
JSContext *cx,
|
||||
|
||||
@ -1857,26 +1857,10 @@ nsContentUtils::GetNodeInfoFromQName(const nsAString& aNamespaceURI,
|
||||
}
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
nsIAtom* prefix = (*aNodeInfo)->GetPrefixAtom();
|
||||
nsIAtom* nil = nsnull;
|
||||
|
||||
// NAMESPACE_ERR: Raised if the qualifiedName is a malformed qualified name,
|
||||
// if the qualifiedName has a prefix and the namespaceURI is null, if the
|
||||
// qualifiedName has a prefix that is "xml" and the namespaceURI is different
|
||||
// from "http://www.w3.org/XML/1998/namespace", if the qualifiedName or its
|
||||
// prefix is "xmlns" and the namespaceURI is different from
|
||||
// "http://www.w3.org/2000/xmlns/", or if the namespaceURI is
|
||||
// "http://www.w3.org/2000/xmlns/" and neither the qualifiedName nor its
|
||||
// prefix is "xmlns".
|
||||
PRBool xmlPrefix = prefix == nsLayoutAtoms::xml;
|
||||
PRBool xmlns = (*aNodeInfo)->Equals(nsLayoutAtoms::xmlns, nil) ||
|
||||
prefix == nsLayoutAtoms::xmlns;
|
||||
|
||||
return (prefix && DOMStringIsNull(aNamespaceURI)) ||
|
||||
(xmlPrefix && nsID != kNameSpaceID_XML) ||
|
||||
(xmlns && nsID != kNameSpaceID_XMLNS) ||
|
||||
(nsID == kNameSpaceID_XMLNS && !xmlns) ?
|
||||
NS_ERROR_DOM_NAMESPACE_ERR : NS_OK;
|
||||
return nsContentUtils::IsValidNodeName((*aNodeInfo)->NameAtom(),
|
||||
(*aNodeInfo)->GetPrefixAtom(),
|
||||
(*aNodeInfo)->NamespaceID()) ?
|
||||
NS_OK : NS_ERROR_DOM_NAMESPACE_ERR;
|
||||
}
|
||||
|
||||
// static
|
||||
@ -3028,3 +3012,34 @@ nsContentUtils::RemoveRangeList(nsIContent *aContent)
|
||||
PL_DHashTableOperate(&sRangeListsHash, aContent, PL_DHASH_REMOVE);
|
||||
}
|
||||
}
|
||||
|
||||
/* static */
|
||||
PRBool
|
||||
nsContentUtils::IsValidNodeName(nsIAtom *aLocalName, nsIAtom *aPrefix,
|
||||
PRInt32 aNamespaceID)
|
||||
{
|
||||
if (!aPrefix) {
|
||||
// If the prefix is null, then either the QName must be xmlns or the
|
||||
// namespace must not be XMLNS.
|
||||
return (aLocalName == nsGkAtoms::xmlns) ==
|
||||
(aNamespaceID == kNameSpaceID_XMLNS);
|
||||
}
|
||||
|
||||
// If the prefix is non-null then the namespace must not be null.
|
||||
if (aNamespaceID == kNameSpaceID_None) {
|
||||
return PR_FALSE;
|
||||
}
|
||||
|
||||
// If the namespace is the XMLNS namespace then the prefix must be xmlns,
|
||||
// but the localname must not be xmlns.
|
||||
if (aNamespaceID == kNameSpaceID_XMLNS) {
|
||||
return aPrefix == nsGkAtoms::xmlns && aLocalName != nsGkAtoms::xmlns;
|
||||
}
|
||||
|
||||
// If the namespace is not the XMLNS namespace then the prefix must not be
|
||||
// xmlns.
|
||||
// If the namespace is the XML namespace then the prefix can be anything.
|
||||
// If the namespace is not the XML namespace then the prefix must not be xml.
|
||||
return aPrefix != nsGkAtoms::xmlns &&
|
||||
(aNamespaceID == kNameSpaceID_XML || aPrefix != nsGkAtoms::xml);
|
||||
}
|
||||
|
||||
@ -437,40 +437,15 @@ nsDOMAttribute::SetPrefix(const nsAString& aPrefix)
|
||||
nsCOMPtr<nsINodeInfo> newNodeInfo;
|
||||
nsCOMPtr<nsIAtom> prefix;
|
||||
|
||||
PRBool qnameIsXMLNS = mNodeInfo->NameAtom() == nsGkAtoms::xmlns &&
|
||||
!mNodeInfo->GetPrefixAtom();
|
||||
|
||||
if (!aPrefix.IsEmpty()) {
|
||||
prefix = do_GetAtom(aPrefix);
|
||||
if (!prefix) {
|
||||
return NS_ERROR_OUT_OF_MEMORY;
|
||||
}
|
||||
|
||||
// If the namespace of the attribute is null then setting a non-null prefix
|
||||
// isn't allowed.
|
||||
// If the QName of the attribute is |xmlns| then setting a non-null prefix
|
||||
// isn't allowed.
|
||||
// If the namespace of the attribute is the XMLNS namespace then setting
|
||||
// a prefix other than xmlns isn't allowed, if the namespace of the
|
||||
// attribute is not the XMLNS namespace then setting the prefix to xmlns
|
||||
// isn't allowed.
|
||||
if (mNodeInfo->NamespaceID() == kNameSpaceID_None || qnameIsXMLNS ||
|
||||
((mNodeInfo->NamespaceID() == kNameSpaceID_XMLNS) !=
|
||||
(prefix == nsGkAtoms::xmlns))) {
|
||||
return NS_ERROR_DOM_NAMESPACE_ERR;
|
||||
}
|
||||
}
|
||||
else if (!qnameIsXMLNS && mNodeInfo->NamespaceID() == kNameSpaceID_XMLNS) {
|
||||
// Setting the prefix to null on an attribute that is in the XMLNS
|
||||
// namespace but whose QName isn't |xmlns| is not allowed.
|
||||
return NS_ERROR_DOM_NAMESPACE_ERR;
|
||||
}
|
||||
|
||||
// If the namespace of the attribute is the XML namespace then setting a
|
||||
// prefix other than xml isn't allowed, if the namespace of the attribute is
|
||||
// not the XML namespace then setting the prefix to xml isn't allowed.
|
||||
if ((mNodeInfo->NamespaceID() == kNameSpaceID_XML) !=
|
||||
(prefix == nsGkAtoms::xml)) {
|
||||
if (!nsContentUtils::IsValidNodeName(mNodeInfo->NameAtom(), prefix,
|
||||
mNodeInfo->NamespaceID())) {
|
||||
return NS_ERROR_DOM_NAMESPACE_ERR;
|
||||
}
|
||||
|
||||
|
||||
@ -1063,24 +1063,10 @@ nsGenericElement::SetPrefix(const nsAString& aPrefix)
|
||||
if (!aPrefix.IsEmpty()) {
|
||||
prefix = do_GetAtom(aPrefix);
|
||||
NS_ENSURE_TRUE(prefix, NS_ERROR_OUT_OF_MEMORY);
|
||||
|
||||
// If the namespace of the element is null then setting a non-null prefix
|
||||
// isn't allowed.
|
||||
if (mNodeInfo->NamespaceID() == kNameSpaceID_None) {
|
||||
return NS_ERROR_DOM_NAMESPACE_ERR;
|
||||
}
|
||||
}
|
||||
|
||||
// If the namespace of the element is the XML namespace then setting a prefix
|
||||
// other than xml isn't allowed, if the namespace of the element is not the
|
||||
// XML namespace then setting the prefix to xml isn't allowed.
|
||||
// If the namespace of the element is the XMLNS namespace then setting a
|
||||
// prefix other than xmlns isn't allowed, if the namespace of the element is
|
||||
// not the XMLNS namespace then setting the prefix to xmlns isn't allowed.
|
||||
if (((mNodeInfo->NamespaceID() == kNameSpaceID_XML) !=
|
||||
(prefix == nsGkAtoms::xml)) ||
|
||||
((mNodeInfo->NamespaceID() == kNameSpaceID_XMLNS) !=
|
||||
(prefix == nsGkAtoms::xmlns))) {
|
||||
if (!nsContentUtils::IsValidNodeName(mNodeInfo->NameAtom(), prefix,
|
||||
mNodeInfo->NamespaceID())) {
|
||||
return NS_ERROR_DOM_NAMESPACE_ERR;
|
||||
}
|
||||
|
||||
|
||||
@ -344,9 +344,15 @@ nsXMLContentSerializer::ConfirmPrefix(nsAString& aPrefix,
|
||||
nsIDOMElement* aElement,
|
||||
PRBool aIsAttribute)
|
||||
{
|
||||
if (aPrefix.EqualsLiteral(kXMLNS) ||
|
||||
(aPrefix.EqualsLiteral("xml") &&
|
||||
aURI.EqualsLiteral("http://www.w3.org/XML/1998/namespace"))) {
|
||||
if (aPrefix.EqualsLiteral(kXMLNS)) {
|
||||
return PR_FALSE;
|
||||
}
|
||||
|
||||
if (aURI.EqualsLiteral("http://www.w3.org/XML/1998/namespace")) {
|
||||
// The prefix must be xml for this namespace. We don't need to declare it,
|
||||
// so always just set the prefix to xml.
|
||||
aPrefix.AssignLiteral("xml");
|
||||
|
||||
return PR_FALSE;
|
||||
}
|
||||
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user