Bug 483155 - Put Gecko content creator function pointers on ElementName.

Tag UXP Issue #1344
This commit is contained in:
Gaming4JC
2020-01-18 23:50:33 -05:00
parent bec4d0ecdc
commit 9bf83c6a78
10 changed files with 513 additions and 81 deletions
@@ -0,0 +1,30 @@
/*
* Copyright (c) 2017 Mozilla Foundation
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
*/
/**
* Applied to an integer type to generate the unsigned variant in C++.
*/
package nu.validator.htmlparser.annotation;
public @interface Creator {
}
@@ -0,0 +1,30 @@
/*
* Copyright (c) 2017 Mozilla Foundation
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
*/
/**
* Applied to an integer type to generate the unsigned variant in C++.
*/
package nu.validator.htmlparser.annotation;
public @interface HtmlCreator {
}
@@ -0,0 +1,30 @@
/*
* Copyright (c) 2017 Mozilla Foundation
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
*/
/**
* Applied to an integer type to generate the unsigned variant in C++.
*/
package nu.validator.htmlparser.annotation;
public @interface SvgCreator {
}
@@ -24,10 +24,21 @@
package nu.validator.htmlparser.impl;
import java.util.Arrays;
import java.util.Collections;
import java.util.LinkedList;
import java.util.List;
// uncomment to regenerate self
//import java.io.BufferedReader;
//import java.io.File;
//import java.io.FileInputStream;
//import java.io.IOException;
//import java.io.InputStreamReader;
//import java.util.Arrays;
//import java.util.Collections;
//import java.util.HashMap;
//import java.util.LinkedList;
//import java.util.List;
//import java.util.Map;
//import java.util.Map.Entry;
//import java.util.regex.Matcher;
//import java.util.regex.Pattern;
import nu.validator.htmlparser.annotation.Inline;
import nu.validator.htmlparser.annotation.Local;
@@ -46,14 +57,14 @@ public final class ElementName
public static final int GROUP_MASK = 127;
/**
* Indicates that the element is not a pre-interned element. Forbidden
* on preinterned elements.
* Indicates that the element is not a pre-interned element. Forbidden on
* preinterned elements.
*/
public static final int NOT_INTERNED = (1 << 30);
/**
* Indicates that the element is in the "special" category. This bit
* should not be pre-set on MathML or SVG specials--only on HTML specials.
* Indicates that the element is in the "special" category. This bit should
* not be pre-set on MathML or SVG specials--only on HTML specials.
*/
public static final int SPECIAL = (1 << 29);
@@ -64,8 +75,8 @@ public final class ElementName
public static final int FOSTER_PARENTING = (1 << 28);
/**
* The element is scoping. This bit should be pre-set on elements
* that are scoping as HTML.
* The element is scoping. This bit should be pre-set on elements that are
* scoping as HTML.
*/
public static final int SCOPING = (1 << 27);
@@ -93,6 +104,10 @@ public final class ElementName
private @Local String camelCaseName;
// CPPONLY: private @HtmlCreator Object htmlCreator;
// CPPONLY: private @SvgCreator Object svgCreator;
/**
* The lowest 7 bits are the dispatch group. The high bits are flags.
*/
@@ -106,6 +121,14 @@ public final class ElementName
return camelCaseName;
}
// CPPONLY: @Inline public @HtmlCreator Object getHtmlCreator() {
// CPPONLY: return htmlCreator;
// CPPONLY: }
// CPPONLY: @Inline public @SvgCreator Object getSvgCreator() {
// CPPONLY: return svgCreator;
// CPPONLY: }
@Inline public int getFlags() {
return flags;
}
@@ -136,7 +159,8 @@ public final class ElementName
return -1;
}
@Inline static ElementName elementNameByBuffer(@NoLength char[] buf, int offset, int length, Interner interner) {
@Inline static ElementName elementNameByBuffer(@NoLength char[] buf,
int offset, int length, Interner interner) {
@Unsigned int hash = ElementName.bufToHash(buf, length);
int[] hashes;
hashes = ElementName.ELEMENT_HASHES;
@@ -161,7 +185,8 @@ public final class ElementName
* @param len
* @return
*/
@Inline private static @Unsigned int bufToHash(@NoLength char[] buf, int length) {
@Inline private static @Unsigned int bufToHash(@NoLength char[] buf,
int length) {
@Unsigned int len = length;
@Unsigned int first = buf[0];
first <<= 19;
@@ -191,15 +216,21 @@ public final class ElementName
}
private ElementName(@Local String name, @Local String camelCaseName,
// CPPONLY: @HtmlCreator Object htmlCreator, @SvgCreator Object
// CPPONLY: svgCreator,
int flags) {
this.name = name;
this.camelCaseName = camelCaseName;
// CPPONLY: this.htmlCreator = htmlCreator;
// CPPONLY: this.svgCreator = svgCreator;
this.flags = flags;
}
public ElementName() {
this.name = null;
this.camelCaseName = null;
// CPPONLY: this.htmlCreator = NS_NewHTMLUnknownElement;
// CPPONLY: this.svgCreator = NS_NewSVGUnknownElement;
this.flags = TreeBuilder.OTHER | NOT_INTERNED;
}
@@ -207,31 +238,139 @@ public final class ElementName
// The translator adds refcount debug code here.
}
@Inline public void setNameForNonInterned(@Local String name) {
@Inline public void setNameForNonInterned(@Local String name
// CPPONLY: , boolean custom
) {
// No need to worry about refcounting the local name, because in the
// C++ case the scoped atom table remembers its own atoms.
this.name = name;
this.camelCaseName = name;
// CPPONLY: if (custom) {
// CPPONLY: this.htmlCreator = NS_NewCustomElement;
// CPPONLY: } else {
// CPPONLY: this.htmlCreator = NS_NewHTMLUnknownElement;
// CPPONLY: }
// The assertion below relies on TreeBuilder.OTHER being zero!
// TreeBuilder.OTHER isn't referenced here, because it would create
// a circular C++ header dependency given that this method is inlined.
assert this.flags == ElementName.NOT_INTERNED;
}
// CPPONLY: public static final ElementName ISINDEX = new ElementName("isindex", "isindex", TreeBuilder.ISINDEX | SPECIAL);
// CPPONLY: @Inline public boolean isCustom() {
// CPPONLY: return this.htmlCreator == NS_NewCustomElement;
// CPPONLY: }
// CPPONLY: public static final ElementName ISINDEX = new ElementName(
// CPPONLY: "isindex", "isindex",
// CPPONLY: NS_NewHTMLUnknownElement, NS_NewSVGUnknownElement,
// CPPONLY: TreeBuilder.ISINDEX | SPECIAL);
// [NOCPP[
public static final ElementName ISINDEX = new ElementName("isindex", "isindex", TreeBuilder.OTHER);
// ]NOCPP]
public static final ElementName ANNOTATION_XML = new ElementName("annotation-xml", "annotation-xml", TreeBuilder.ANNOTATION_XML | SCOPING_AS_MATHML);
public static final ElementName ANNOTATION_XML = new ElementName(
"annotation-xml", "annotation-xml",
// CPPONLY: NS_NewHTMLUnknownElement, NS_NewSVGUnknownElement,
TreeBuilder.ANNOTATION_XML | SCOPING_AS_MATHML);
// START CODE ONLY USED FOR GENERATING CODE uncomment and run to regenerate
// private static final Pattern HTML_TAG_DEF = Pattern.compile(
// "^HTML_TAG\\(([^,]+),\\s*([^,]+),\\s*[^,]+\\).*$");
//
// private static final Pattern HTML_HTMLELEMENT_TAG_DEF = Pattern.compile(
// "^HTML_HTMLELEMENT_TAG\\(([^\\)]+)\\).*$");
//
// private static final Pattern SVG_TAG_DEF = Pattern.compile(
// "^SVG_(?:FROM_PARSER_)?TAG\\(([^,]+),\\s*([^\\)]+)\\).*$");
//
// private static final Map<String, String> htmlMap = new HashMap<String, String>();
//
// private static final Map<String, String> svgMap = new HashMap<String, String>();
//
// private static void ingestHtmlTags(File htmlList) throws IOException {
// // This doesn't need to be efficient, so let's make it easy to write.
// BufferedReader htmlReader = new BufferedReader(
// new InputStreamReader(new FileInputStream(htmlList), "utf-8"));
// try {
// String line;
// while ((line = htmlReader.readLine()) != null) {
// if (!line.startsWith("HTML_")) {
// continue;
// }
// if (line.startsWith("HTML_OTHER")) {
// continue;
// }
// Matcher m = HTML_TAG_DEF.matcher(line);
// if (m.matches()) {
// String iface = m.group(2);
// if ("Unknown".equals(iface)) {
// continue;
// }
// htmlMap.put(m.group(1), "NS_NewHTML" + iface + "Element");
// } else {
// m = HTML_HTMLELEMENT_TAG_DEF.matcher(line);
// if (!m.matches()) {
// throw new RuntimeException(
// "Malformed HTML element definition: " + line);
// }
// htmlMap.put(m.group(1), "NS_NewHTMLElement");
// }
// }
// } finally {
// htmlReader.close();
// }
// }
//
// private static void ingestSvgTags(File svgList) throws IOException {
// // This doesn't need to be efficient, so let's make it easy to write.
// BufferedReader svgReader = new BufferedReader(
// new InputStreamReader(new FileInputStream(svgList), "utf-8"));
// try {
// String line;
// while ((line = svgReader.readLine()) != null) {
// if (!line.startsWith("SVG_")) {
// continue;
// }
// Matcher m = SVG_TAG_DEF.matcher(line);
// if (!m.matches()) {
// throw new RuntimeException(
// "Malformed SVG element definition: " + line);
// }
// String name = m.group(1);
// if ("svgSwitch".equals(name)) {
// name = "switch";
// }
// svgMap.put(name, "NS_NewSVG" + m.group(2) + "Element");
// }
// } finally {
// svgReader.close();
// }
// }
//
// private static String htmlCreator(String name) {
// String creator = htmlMap.remove(name);
// if (creator != null) {
// return creator;
// }
// return "NS_NewHTMLUnknownElement";
// }
//
// private static String svgCreator(String name) {
// String creator = svgMap.remove(name);
// if (creator != null) {
// return creator;
// }
// return "NS_NewSVGUnknownElement";
// }
//
// /**
// * @see java.lang.Object#toString()
// */
// @Override public String toString() {
// return "(\"" + name + "\", \"" + camelCaseName + "\", " + decomposedFlags() + ")";
// return "(\"" + name + "\", \"" + camelCaseName + "\", \n// CPP"
// + "ONLY: " + htmlCreator(name) + ",\n//CPP" + "ONLY: "
// + svgCreator(camelCaseName) + ", \n" + decomposedFlags() + ")";
// }
//
// private String decomposedFlags() {
@@ -264,7 +403,9 @@ public final class ElementName
// char c = name.charAt(i);
// if (c == '-') {
// // if (!"annotation-xml".equals(name)) {
// // throw new RuntimeException("Non-annotation-xml element name with hyphen: " + name);
// // throw new RuntimeException(
// // "Non-annotation-xml element name with hyphen: "
// // + name);
// // }
// buf[i] = '_';
// } else if (c >= '0' && c <= '9') {
@@ -456,9 +597,23 @@ public final class ElementName
// /**
// * Regenerate self
// *
// * @param args
// * The args should be the paths to m-c files
// * parser/htmlparser/nsHTMLTagList.h and dom/svg/SVGTagList.h.
// */
// public static void main(String[] args) {
// File htmlList = new File(args[0]);
// File svgList = new File(args[1]);
// try {
// ingestHtmlTags(htmlList);
// } catch (IOException e) {
// throw new RuntimeException(e);
// }
// try {
// ingestSvgTags(svgList);
// } catch (IOException e) {
// throw new RuntimeException(e);
// }
//
// Arrays.sort(ELEMENT_NAMES);
// for (int i = 0; i < ELEMENT_NAMES.length; i++) {
// int hash = ELEMENT_NAMES[i].hash();
@@ -468,8 +623,9 @@ public final class ElementName
// }
// for (int j = i + 1; j < ELEMENT_NAMES.length; j++) {
// if (hash == ELEMENT_NAMES[j].hash()) {
// System.err.println("Hash collision: " + ELEMENT_NAMES[i].name
// + ", " + ELEMENT_NAMES[j].name);
// System.err.println(
// "Hash collision: " + ELEMENT_NAMES[i].name + ", "
// + ELEMENT_NAMES[j].name);
// return;
// }
// }
@@ -479,18 +635,20 @@ public final class ElementName
// if ("isindex".equals(el.name)) {
// continue;
// }
// System.out.println("public static final ElementName "
// + el.constName() + " = new ElementName" + el.toString()
// + ";");
// System.out.println(
// "public static final ElementName " + el.constName()
// + " = new ElementName" + el.toString() + ";");
// }
//
// LinkedList<ElementName> sortedNames = new LinkedList<ElementName>();
// Collections.addAll(sortedNames, ELEMENT_NAMES);
// ElementName[] levelOrder = new ElementName[ELEMENT_NAMES.length];
// int bstDepth = (int) Math.ceil(Math.log(ELEMENT_NAMES.length) / Math.log(2));
// int bstDepth = (int) Math.ceil(
// Math.log(ELEMENT_NAMES.length) / Math.log(2));
// fillLevelOrderArray(sortedNames, bstDepth, 0, levelOrder);
//
// System.out.println("private final static @NoLength ElementName[] ELEMENT_NAMES = {");
// System.out.println(
// "private final static @NoLength ElementName[] ELEMENT_NAMES = {");
// for (int i = 0; i < levelOrder.length; i++) {
// ElementName el = levelOrder[i];
// System.out.println(el.constName() + ",");
@@ -502,6 +660,13 @@ public final class ElementName
// System.out.println(Integer.toString(el.hash()) + ",");
// }
// System.out.println("};");
//
// for (Entry<String, String> entry : htmlMap.entrySet()) {
// System.err.println("Missing HTML element: " + entry.getKey());
// }
// for (Entry<String, String> entry : svgMap.entrySet()) {
// System.err.println("Missing SVG element: " + entry.getKey());
// }
// }
@@ -45,6 +45,11 @@ final class StackNode<T> {
private int refcount = 1;
/*
* Only valid for formatting elements
*/
// CPPONLY: private @HtmlCreator Object htmlCreator;
// [NOCPP[
private final TaintableLocatorImpl locator;
@@ -87,6 +92,10 @@ final class StackNode<T> {
// ]NOCPP]
// CPPONLY: public @HtmlCreator Object getHtmlCreator() {
// CPPONLY: return htmlCreator;
// CPPONLY: }
/**
* Constructor for copying. This doesn't take another <code>StackNode</code>
* because in C++ the caller is reponsible for reobtaining the local names
@@ -100,9 +109,10 @@ final class StackNode<T> {
* @param attributes
*/
StackNode(int flags, @NsUri String ns, @Local String name, T node,
@Local String popName, HtmlAttributes attributes
@Local String popName, HtmlAttributes attributes,
// CPPONLY: @HtmlCreator Object htmlCreator
// [NOCPP[
, TaintableLocatorImpl locator
TaintableLocatorImpl locator
// ]NOCPP]
) {
this.flags = flags;
@@ -112,6 +122,10 @@ final class StackNode<T> {
this.node = node;
this.attributes = attributes;
this.refcount = 1;
/*
* Need to track creator for formatting elements when copying.
*/
// CPPONLY: this.htmlCreator = htmlCreator;
// [NOCPP[
this.locator = locator;
// ]NOCPP]
@@ -136,6 +150,10 @@ final class StackNode<T> {
this.attributes = null;
this.refcount = 1;
assert elementName.isInterned() : "Don't use this constructor for custom elements.";
/*
* Not used for formatting elements, so no need to track creator.
*/
// CPPONLY: this.htmlCreator = null;
// [NOCPP[
this.locator = locator;
// ]NOCPP]
@@ -161,6 +179,11 @@ final class StackNode<T> {
this.attributes = attributes;
this.refcount = 1;
assert elementName.isInterned() : "Don't use this constructor for custom elements.";
/*
* Need to track creator for formatting elements in order to be able
* to clone them.
*/
// CPPONLY: this.htmlCreator = elementName.getHtmlCreator();
// [NOCPP[
this.locator = locator;
// ]NOCPP]
@@ -185,6 +208,10 @@ final class StackNode<T> {
this.node = node;
this.attributes = null;
this.refcount = 1;
/*
* Not used for formatting elements, so no need to track creator.
*/
// CPPONLY: this.htmlCreator = null;
// [NOCPP[
this.locator = locator;
// ]NOCPP]
@@ -212,6 +239,10 @@ final class StackNode<T> {
this.node = node;
this.attributes = null;
this.refcount = 1;
/*
* Not used for formatting elements, so no need to track creator.
*/
// CPPONLY: this.htmlCreator = null;
// [NOCPP[
this.locator = locator;
// ]NOCPP]
@@ -239,6 +270,10 @@ final class StackNode<T> {
this.node = node;
this.attributes = null;
this.refcount = 1;
/*
* Not used for formatting elements, so no need to track creator.
*/
// CPPONLY: this.htmlCreator = null;
// [NOCPP[
this.locator = locator;
// ]NOCPP]
@@ -1140,7 +1140,9 @@ public class Tokenizer implements Locator {
tagName = ElementName.ANNOTATION_XML;
} else {
nonInternedTagName.setNameForNonInterned(Portability.newLocalNameFromBuffer(strBuf, 0, strBufLen,
interner));
interner)
// CPPONLY: , true
);
tagName = nonInternedTagName;
}
} else {
@@ -1148,7 +1150,9 @@ public class Tokenizer implements Locator {
interner);
if (tagName == null) {
nonInternedTagName.setNameForNonInterned(Portability.newLocalNameFromBuffer(strBuf, 0, strBufLen,
interner));
interner)
// CPPONLY: , false
);
tagName = nonInternedTagName;
}
}
@@ -6699,7 +6703,9 @@ public class Tokenizer implements Locator {
publicIdentifier = null;
}
tagName = null;
nonInternedTagName.setNameForNonInterned(null);
nonInternedTagName.setNameForNonInterned(null
// CPPONLY: , false
);
attributeName = null;
// CPPONLY: nonInternedAttributeName.setNameForNonInterned(null);
tokenHandler.endTokenization();
@@ -6849,7 +6855,9 @@ public class Tokenizer implements Locator {
// In the C++ case, the atoms in the other tokenizer are from a
// different tokenizer-scoped atom table. Therefore, we have to
// obtain the correspoding atom from our own atom table.
nonInternedTagName.setNameForNonInterned(Portability.newLocalFromLocal(other.tagName.getName(), interner));
nonInternedTagName.setNameForNonInterned(Portability.newLocalFromLocal(other.tagName.getName(), interner)
// CPPONLY: , other.tagName.isCustom()
);
tagName = nonInternedTagName;
}
@@ -478,6 +478,18 @@ public abstract class TreeBuilder<T> implements TokenHandler,
protected void fatal() throws SAXException {
}
// CPPONLY: @Inline private @Creator Object htmlCreator(@HtmlCreator Object htmlCreator) {
// CPPONLY: @Creator Object creator;
// CPPONLY: creator.html = htmlCreator;
// CPPONLY: return creator;
// CPPONLY: }
// CPPONLY:
// CPPONLY: @Inline private @Creator Object svgCreator(@SvgCreator Object svgCreator) {
// CPPONLY: @Creator Object creator;
// CPPONLY: creator.svg = svgCreator;
// CPPONLY: return creator;
// CPPONLY: }
// [NOCPP[
protected final void fatal(Exception e) throws SAXException {
@@ -714,7 +726,8 @@ public abstract class TreeBuilder<T> implements TokenHandler,
// CPPONLY: if (tokenizer.isViewingXmlSource()) {
// CPPONLY: T elt = createElement("http://www.w3.org/2000/svg",
// CPPONLY: "svg",
// CPPONLY: tokenizer.emptyAttributes(), null);
// CPPONLY: tokenizer.emptyAttributes(), null,
// CPPONLY: svgCreator(NS_NewSVGSVGElement));
// CPPONLY: StackNode<T> node = new StackNode<T>(ElementName.SVG,
// CPPONLY: "svg",
// CPPONLY: elt);
@@ -1958,8 +1971,8 @@ public abstract class TreeBuilder<T> implements TokenHandler,
attributes.getValue(AttributeName.TYPE))) {
break intableloop;
}
appendVoidElementToCurrent(
name, attributes,
appendVoidInputToCurrent(
attributes,
formPointer);
selfClosing = false;
attributes = null; // CPP
@@ -2321,7 +2334,7 @@ public abstract class TreeBuilder<T> implements TokenHandler,
case INPUT:
reconstructTheActiveFormattingElements();
appendVoidElementToCurrentMayFoster(
name, attributes,
elementName, attributes,
formPointer);
selfClosing = false;
attributes = null; // CPP
@@ -4798,9 +4811,12 @@ public abstract class TreeBuilder<T> implements TokenHandler,
assert node == listOfActiveFormattingElements[nodeListPos];
assert node == stack[nodePos];
T clone = createElement("http://www.w3.org/1999/xhtml",
node.name, node.attributes.cloneAttributes(null), commonAncestor.node);
node.name, node.attributes.cloneAttributes(null), commonAncestor.node
// CPPONLY: , htmlCreator(node.getHtmlCreator())
);
StackNode<T> newNode = new StackNode<T>(node.getFlags(), node.ns,
node.name, clone, node.popName, node.attributes
// CPPONLY: , node.getHtmlCreator()
// [NOCPP[
, node.getLocator()
// ]NOCPP]
@@ -4827,11 +4843,14 @@ public abstract class TreeBuilder<T> implements TokenHandler,
}
T clone = createElement("http://www.w3.org/1999/xhtml",
formattingElt.name,
formattingElt.attributes.cloneAttributes(null), furthestBlock.node);
formattingElt.attributes.cloneAttributes(null), furthestBlock.node
// CPPONLY: , htmlCreator(formattingElt.getHtmlCreator())
);
StackNode<T> formattingClone = new StackNode<T>(
formattingElt.getFlags(), formattingElt.ns,
formattingElt.name, clone, formattingElt.popName,
formattingElt.attributes
// CPPONLY: , formattingElt.getHtmlCreator()
// [NOCPP[
, errorHandler == null ? null : new TaintableLocatorImpl(tokenizer)
// ]NOCPP]
@@ -5011,16 +5030,21 @@ public abstract class TreeBuilder<T> implements TokenHandler,
T clone;
if (currentNode.isFosterParenting()) {
clone = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", entry.name,
entry.attributes.cloneAttributes(null));
entry.attributes.cloneAttributes(null)
// CPPONLY: , htmlCreator(entry.getHtmlCreator())
);
} else {
clone = createElement("http://www.w3.org/1999/xhtml", entry.name,
entry.attributes.cloneAttributes(null), currentNode.node);
entry.attributes.cloneAttributes(null), currentNode.node
// CPPONLY: , htmlCreator(entry.getHtmlCreator())
);
appendElement(clone, currentNode.node);
}
StackNode<T> entryClone = new StackNode<T>(entry.getFlags(),
entry.ns, entry.name, clone, entry.popName,
entry.attributes
// CPPONLY: , entry.getHtmlCreator()
// [NOCPP[
, entry.getLocator()
// ]NOCPP]
@@ -5051,23 +5075,33 @@ public abstract class TreeBuilder<T> implements TokenHandler,
}
private T createAndInsertFosterParentedElement(@NsUri String ns, @Local String name,
HtmlAttributes attributes) throws SAXException {
return createAndInsertFosterParentedElement(ns, name, attributes, null);
HtmlAttributes attributes
// CPPONLY: , @Creator Object creator
) throws SAXException {
return createAndInsertFosterParentedElement(ns, name, attributes, null
// CPPONLY: , creator
);
}
private T createAndInsertFosterParentedElement(@NsUri String ns, @Local String name,
HtmlAttributes attributes, T form) throws SAXException {
HtmlAttributes attributes, T form
// CPPONLY: , @Creator Object creator
) throws SAXException {
int tablePos = findLastOrRoot(TreeBuilder.TABLE);
int templatePos = findLastOrRoot(TreeBuilder.TEMPLATE);
if (templatePos >= tablePos) {
T child = createElement(ns, name, attributes, form, stack[templatePos].node);
T child = createElement(ns, name, attributes, form, stack[templatePos].node
// CPPONLY: , creator
);
appendElement(child, stack[templatePos].node);
return child;
}
StackNode<T> node = stack[tablePos];
return createAndInsertFosterParentedElement(ns, name, attributes, form, node.node, stack[tablePos - 1].node);
return createAndInsertFosterParentedElement(ns, name, attributes, form, node.node, stack[tablePos - 1].node
// CPPONLY: , creator
);
}
private boolean isInStack(StackNode<T> node) {
@@ -5225,7 +5259,12 @@ public abstract class TreeBuilder<T> implements TokenHandler,
checkAttributes(attributes, "http://www.w3.org/1999/xhtml");
// ]NOCPP]
T currentNode = stack[currentPtr].node;
T elt = createElement("http://www.w3.org/1999/xhtml", "head", attributes, currentNode);
T elt = createElement("http://www.w3.org/1999/xhtml", "head", attributes, currentNode
/*
* head uses NS_NewHTMLSharedElement creator
*/
// CPPONLY: , htmlCreator(NS_NewHTMLSharedElement)
);
appendElement(elt, currentNode);
headPointer = elt;
StackNode<T> node = new StackNode<T>(ElementName.HEAD,
@@ -5257,9 +5296,13 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", "form", attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", "form", attributes
// CPPONLY: , htmlCreator(NS_NewHTMLFormElement)
);
} else {
elt = createElement("http://www.w3.org/1999/xhtml", "form", attributes, current.node);
elt = createElement("http://www.w3.org/1999/xhtml", "form", attributes, current.node
// CPPONLY: , htmlCreator(NS_NewHTMLFormElement)
);
appendElement(elt, current.node);
}
@@ -5290,9 +5333,13 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", elementName.getName(), attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", elementName.getName(), attributes
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
} else {
elt = createElement("http://www.w3.org/1999/xhtml", elementName.getName(), attributes, current.node);
elt = createElement("http://www.w3.org/1999/xhtml", elementName.getName(), attributes, current.node
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
appendElement(elt, current.node);
}
StackNode<T> node = new StackNode<T>(elementName, elt, clone
@@ -5313,7 +5360,9 @@ public abstract class TreeBuilder<T> implements TokenHandler,
// ]NOCPP]
// This method can't be called for custom elements
T currentNode = stack[currentPtr].node;
T elt = createElement("http://www.w3.org/1999/xhtml", elementName.getName(), attributes, currentNode);
T elt = createElement("http://www.w3.org/1999/xhtml", elementName.getName(), attributes, currentNode
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
appendElement(elt, currentNode);
if (ElementName.TEMPLATE == elementName) {
elt = getDocumentFragmentForTemplate(elt);
@@ -5340,9 +5389,13 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", popName, attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", popName, attributes
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
} else {
elt = createElement("http://www.w3.org/1999/xhtml", popName, attributes, current.node);
elt = createElement("http://www.w3.org/1999/xhtml", popName, attributes, current.node
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
appendElement(elt, current.node);
}
StackNode<T> node = new StackNode<T>(elementName, elt, popName
@@ -5374,9 +5427,13 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1998/Math/MathML", popName, attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/1998/Math/MathML", popName, attributes
// CPPONLY: , htmlCreator(null)
);
} else {
elt = createElement("http://www.w3.org/1998/Math/MathML", popName, attributes, current.node);
elt = createElement("http://www.w3.org/1998/Math/MathML", popName, attributes, current.node
// CPPONLY: , htmlCreator(null)
);
appendElement(elt, current.node);
}
StackNode<T> node = new StackNode<T>(elementName, elt, popName,
@@ -5423,9 +5480,13 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/2000/svg", popName, attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/2000/svg", popName, attributes
// CPPONLY: , svgCreator(elementName.getSvgCreator())
);
} else {
elt = createElement("http://www.w3.org/2000/svg", popName, attributes, current.node);
elt = createElement("http://www.w3.org/2000/svg", popName, attributes, current.node
// CPPONLY: , svgCreator(elementName.getSvgCreator())
);
appendElement(elt, current.node);
}
StackNode<T> node = new StackNode<T>(elementName, popName, elt
@@ -5449,10 +5510,14 @@ public abstract class TreeBuilder<T> implements TokenHandler,
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", elementName.getName(),
attributes, formOwner);
attributes, formOwner
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
} else {
elt = createElement("http://www.w3.org/1999/xhtml", elementName.getName(),
attributes, formOwner, current.node);
attributes, formOwner, current.node
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
appendElement(elt, current.node);
}
StackNode<T> node = new StackNode<T>(elementName, elt
@@ -5464,7 +5529,8 @@ public abstract class TreeBuilder<T> implements TokenHandler,
}
private void appendVoidElementToCurrentMayFoster(
@Local String name, HtmlAttributes attributes, T form) throws SAXException {
ElementName elementName, HtmlAttributes attributes, T form) throws SAXException {
@Local String name = elementName.getName();
// [NOCPP[
checkAttributes(attributes, "http://www.w3.org/1999/xhtml");
// ]NOCPP]
@@ -5475,10 +5541,14 @@ public abstract class TreeBuilder<T> implements TokenHandler,
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", name,
attributes, formOwner);
attributes, formOwner
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
} else {
elt = createElement("http://www.w3.org/1999/xhtml", name,
attributes, formOwner, current.node);
attributes, formOwner, current.node
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
appendElement(elt, current.node);
}
elementPushed("http://www.w3.org/1999/xhtml", name, elt);
@@ -5499,9 +5569,13 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", popName, attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/1999/xhtml", popName, attributes
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
} else {
elt = createElement("http://www.w3.org/1999/xhtml", popName, attributes, current.node);
elt = createElement("http://www.w3.org/1999/xhtml", popName, attributes, current.node
// CPPONLY: , htmlCreator(elementName.getHtmlCreator())
);
appendElement(elt, current.node);
}
elementPushed("http://www.w3.org/1999/xhtml", popName, elt);
@@ -5522,9 +5596,13 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/2000/svg", popName, attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/2000/svg", popName, attributes
// CPPONLY: , svgCreator(elementName.getSvgCreator())
);
} else {
elt = createElement("http://www.w3.org/2000/svg", popName, attributes, current.node);
elt = createElement("http://www.w3.org/2000/svg", popName, attributes, current.node
// CPPONLY: , svgCreator(elementName.getSvgCreator())
);
appendElement(elt, current.node);
}
elementPushed("http://www.w3.org/2000/svg", popName, elt);
@@ -5545,27 +5623,32 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> current = stack[currentPtr];
if (current.isFosterParenting()) {
fatal();
elt = createAndInsertFosterParentedElement("http://www.w3.org/1998/Math/MathML", popName, attributes);
elt = createAndInsertFosterParentedElement("http://www.w3.org/1998/Math/MathML", popName, attributes
// CPPONLY: , htmlCreator(null)
);
} else {
elt = createElement("http://www.w3.org/1998/Math/MathML", popName, attributes, current.node);
elt = createElement("http://www.w3.org/1998/Math/MathML", popName, attributes, current.node
// CPPONLY: , htmlCreator(null)
);
appendElement(elt, current.node);
}
elementPushed("http://www.w3.org/1998/Math/MathML", popName, elt);
elementPopped("http://www.w3.org/1998/Math/MathML", popName, elt);
}
private void appendVoidElementToCurrent(
@Local String name, HtmlAttributes attributes, T form) throws SAXException {
private void appendVoidInputToCurrent(HtmlAttributes attributes, T form) throws SAXException {
// [NOCPP[
checkAttributes(attributes, "http://www.w3.org/1999/xhtml");
// ]NOCPP]
// Can't be called for custom elements
T currentNode = stack[currentPtr].node;
T elt = createElement("http://www.w3.org/1999/xhtml", name, attributes,
form == null || fragment || isTemplateContents() ? null : form, currentNode);
T elt = createElement("http://www.w3.org/1999/xhtml", "input", attributes,
form == null || fragment || isTemplateContents() ? null : form, currentNode
// CPPONLY: , htmlCreator(NS_NewHTMLInputElement)
);
appendElement(elt, currentNode);
elementPushed("http://www.w3.org/1999/xhtml", name, elt);
elementPopped("http://www.w3.org/1999/xhtml", name, elt);
elementPushed("http://www.w3.org/1999/xhtml", "input", elt);
elementPopped("http://www.w3.org/1999/xhtml", "input", elt);
}
private void appendVoidFormToCurrent(HtmlAttributes attributes) throws SAXException {
@@ -5574,7 +5657,9 @@ public abstract class TreeBuilder<T> implements TokenHandler,
// ]NOCPP]
T currentNode = stack[currentPtr].node;
T elt = createElement("http://www.w3.org/1999/xhtml", "form",
attributes, currentNode);
attributes, currentNode
// CPPONLY: , htmlCreator(NS_NewHTMLFormElement)
);
formPointer = elt;
// ownership transferred to form pointer
appendElement(elt, currentNode);
@@ -5626,11 +5711,17 @@ public abstract class TreeBuilder<T> implements TokenHandler,
}
protected abstract T createElement(@NsUri String ns, @Local String name,
HtmlAttributes attributes, T intendedParent) throws SAXException;
HtmlAttributes attributes, T intendedParent
// CPPONLY: , @Creator Object creator
) throws SAXException;
protected T createElement(@NsUri String ns, @Local String name,
HtmlAttributes attributes, T form, T intendedParent) throws SAXException {
return createElement("http://www.w3.org/1999/xhtml", name, attributes, intendedParent);
HtmlAttributes attributes, T form, T intendedParent
// CPPONLY: , @Creator Object creator
) throws SAXException {
return createElement("http://www.w3.org/1999/xhtml", name, attributes, intendedParent
// CPPONLY: , creator
);
}
protected abstract T createHtmlElementSetAsRoot(HtmlAttributes attributes)
@@ -5659,7 +5750,9 @@ public abstract class TreeBuilder<T> implements TokenHandler,
// ]NOCPP]
protected T createAndInsertFosterParentedElement(@NsUri String ns, @Local String name,
HtmlAttributes attributes, T form, T table, T stackParent) throws SAXException {
HtmlAttributes attributes, T form, T table, T stackParent
// CPPONLY: , @Creator Object creator
) throws SAXException {
return createAndInsertFosterParentedElement(ns, name, attributes, table, stackParent);
};
@@ -5941,6 +6034,7 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> newNode = new StackNode<T>(node.getFlags(), node.ns,
node.name, node.node, node.popName,
node.attributes.cloneAttributes(null)
// CPPONLY: , node.getHtmlCreator()
// [NOCPP[
, node.getLocator()
// ]NOCPP]
@@ -5958,6 +6052,7 @@ public abstract class TreeBuilder<T> implements TokenHandler,
StackNode<T> newNode = new StackNode<T>(node.getFlags(), node.ns,
node.name, node.node, node.popName,
null
// CPPONLY: , node.getHtmlCreator()
// [NOCPP[
, node.getLocator()
// ]NOCPP]
@@ -6063,6 +6158,7 @@ public abstract class TreeBuilder<T> implements TokenHandler,
Portability.newLocalFromLocal(node.name, interner), node.node,
Portability.newLocalFromLocal(node.popName, interner),
node.attributes.cloneAttributes(null)
// CPPONLY: , node.getHtmlCreator()
// [NOCPP[
, node.getLocator()
// ]NOCPP]
@@ -6080,6 +6176,7 @@ public abstract class TreeBuilder<T> implements TokenHandler,
Portability.newLocalFromLocal(node.name, interner), node.node,
Portability.newLocalFromLocal(node.popName, interner),
null
// CPPONLY: , node.getHtmlCreator()
// [NOCPP[
, node.getLocator()
// ]NOCPP]