Bug 1845715 - Check for failure when getting RegExp match result template r=iain
[gecko.git] / parser / html / nsHtml5TreeOperation.h
blobdd5d1e8c4a69dc3b4264d458f887ea072271fc95
1 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this
3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 #ifndef nsHtml5TreeOperation_h
6 #define nsHtml5TreeOperation_h
8 #include "nsHtml5DocumentMode.h"
9 #include "nsHtml5HtmlAttributes.h"
10 #include "mozilla/dom/FromParser.h"
11 #include "mozilla/NotNull.h"
12 #include "mozilla/Variant.h"
13 #include "nsCharsetSource.h"
15 class nsIContent;
16 class nsHtml5TreeOpExecutor;
17 class nsHtml5DocumentBuilder;
18 namespace mozilla {
19 class Encoding;
21 namespace dom {
22 class Text;
23 } // namespace dom
24 } // namespace mozilla
26 struct uninitialized {};
28 // main HTML5 ops
29 struct opDetach {
30 nsIContent** mElement;
32 explicit opDetach(nsIContentHandle* aElement) {
33 mElement = static_cast<nsIContent**>(aElement);
37 struct opAppend {
38 nsIContent** mChild;
39 nsIContent** mParent;
40 mozilla::dom::FromParser mFromNetwork;
42 explicit opAppend(nsIContentHandle* aChild, nsIContentHandle* aParent,
43 mozilla::dom::FromParser aFromNetwork)
44 : mFromNetwork(aFromNetwork) {
45 mChild = static_cast<nsIContent**>(aChild);
46 mParent = static_cast<nsIContent**>(aParent);
50 struct opAppendChildrenToNewParent {
51 nsIContent** mOldParent;
52 nsIContent** mNewParent;
54 explicit opAppendChildrenToNewParent(nsIContentHandle* aOldParent,
55 nsIContentHandle* aNewParent) {
56 mOldParent = static_cast<nsIContent**>(aOldParent);
57 mNewParent = static_cast<nsIContent**>(aNewParent);
61 struct opFosterParent {
62 nsIContent** mChild;
63 nsIContent** mStackParent;
64 nsIContent** mTable;
66 explicit opFosterParent(nsIContentHandle* aChild,
67 nsIContentHandle* aStackParent,
68 nsIContentHandle* aTable) {
69 mChild = static_cast<nsIContent**>(aChild);
70 mStackParent = static_cast<nsIContent**>(aStackParent);
71 mTable = static_cast<nsIContent**>(aTable);
75 struct opAppendToDocument {
76 nsIContent** mContent;
78 explicit opAppendToDocument(nsIContentHandle* aContent) {
79 mContent = static_cast<nsIContent**>(aContent);
83 struct opAddAttributes {
84 nsIContent** mElement;
85 nsHtml5HtmlAttributes* mAttributes;
87 explicit opAddAttributes(nsIContentHandle* aElement,
88 nsHtml5HtmlAttributes* aAttributes)
89 : mAttributes(aAttributes) {
90 mElement = static_cast<nsIContent**>(aElement);
94 struct opCreateHTMLElement {
95 nsIContent** mContent;
96 nsAtom* mName;
97 nsHtml5HtmlAttributes* mAttributes;
98 mozilla::dom::HTMLContentCreatorFunction mCreator;
99 nsIContent** mIntendedParent;
100 mozilla::dom::FromParser mFromNetwork;
102 explicit opCreateHTMLElement(
103 nsIContentHandle* aContent, nsAtom* aName,
104 nsHtml5HtmlAttributes* aAttributes,
105 mozilla::dom::HTMLContentCreatorFunction aCreator,
106 nsIContentHandle* aIntendedParent, mozilla::dom::FromParser mFromNetwork)
107 : mName(aName),
108 mAttributes(aAttributes),
109 mCreator(aCreator),
110 mFromNetwork(mFromNetwork) {
111 mContent = static_cast<nsIContent**>(aContent);
112 mIntendedParent = static_cast<nsIContent**>(aIntendedParent);
113 aName->AddRef();
114 if (mAttributes == nsHtml5HtmlAttributes::EMPTY_ATTRIBUTES) {
115 mAttributes = nullptr;
120 struct opCreateSVGElement {
121 nsIContent** mContent;
122 nsAtom* mName;
123 nsHtml5HtmlAttributes* mAttributes;
124 mozilla::dom::SVGContentCreatorFunction mCreator;
125 nsIContent** mIntendedParent;
126 mozilla::dom::FromParser mFromNetwork;
128 explicit opCreateSVGElement(nsIContentHandle* aContent, nsAtom* aName,
129 nsHtml5HtmlAttributes* aAttributes,
130 mozilla::dom::SVGContentCreatorFunction aCreator,
131 nsIContentHandle* aIntendedParent,
132 mozilla::dom::FromParser mFromNetwork)
133 : mName(aName),
134 mAttributes(aAttributes),
135 mCreator(aCreator),
136 mFromNetwork(mFromNetwork) {
137 mContent = static_cast<nsIContent**>(aContent);
138 mIntendedParent = static_cast<nsIContent**>(aIntendedParent);
139 aName->AddRef();
140 if (mAttributes == nsHtml5HtmlAttributes::EMPTY_ATTRIBUTES) {
141 mAttributes = nullptr;
146 struct opCreateMathMLElement {
147 nsIContent** mContent;
148 nsAtom* mName;
149 nsHtml5HtmlAttributes* mAttributes;
150 nsIContent** mIntendedParent;
152 explicit opCreateMathMLElement(nsIContentHandle* aContent, nsAtom* aName,
153 nsHtml5HtmlAttributes* aAttributes,
154 nsIContentHandle* aIntendedParent)
155 : mName(aName), mAttributes(aAttributes) {
156 mContent = static_cast<nsIContent**>(aContent);
157 mIntendedParent = static_cast<nsIContent**>(aIntendedParent);
158 aName->AddRef();
159 if (mAttributes == nsHtml5HtmlAttributes::EMPTY_ATTRIBUTES) {
160 mAttributes = nullptr;
165 struct opSetFormElement {
166 nsIContent** mContent;
167 nsIContent** mFormElement;
169 explicit opSetFormElement(nsIContentHandle* aContent,
170 nsIContentHandle* aFormElement) {
171 mContent = static_cast<nsIContent**>(aContent);
172 mFormElement = static_cast<nsIContent**>(aFormElement);
176 struct opAppendText {
177 nsIContent** mParent;
178 char16_t* mBuffer;
179 int32_t mLength;
181 explicit opAppendText(nsIContentHandle* aParent, char16_t* aBuffer,
182 int32_t aLength)
183 : mBuffer(aBuffer), mLength(aLength) {
184 mParent = static_cast<nsIContent**>(aParent);
188 struct opFosterParentText {
189 nsIContent** mStackParent;
190 char16_t* mBuffer;
191 nsIContent** mTable;
192 int32_t mLength;
194 explicit opFosterParentText(nsIContentHandle* aStackParent, char16_t* aBuffer,
195 nsIContentHandle* aTable, int32_t aLength)
196 : mBuffer(aBuffer), mLength(aLength) {
197 mStackParent = static_cast<nsIContent**>(aStackParent);
198 mTable = static_cast<nsIContent**>(aTable);
202 struct opAppendComment {
203 nsIContent** mParent;
204 char16_t* mBuffer;
205 int32_t mLength;
207 explicit opAppendComment(nsIContentHandle* aParent, char16_t* aBuffer,
208 int32_t aLength)
209 : mBuffer(aBuffer), mLength(aLength) {
210 mParent = static_cast<nsIContent**>(aParent);
214 struct opAppendCommentToDocument {
215 char16_t* mBuffer;
216 int32_t mLength;
218 explicit opAppendCommentToDocument(char16_t* aBuffer, int32_t aLength)
219 : mBuffer(aBuffer), mLength(aLength){};
222 class nsHtml5TreeOperationStringPair {
223 private:
224 nsString mPublicId;
225 nsString mSystemId;
227 public:
228 nsHtml5TreeOperationStringPair(const nsAString& aPublicId,
229 const nsAString& aSystemId)
230 : mPublicId(aPublicId), mSystemId(aSystemId) {
231 MOZ_COUNT_CTOR(nsHtml5TreeOperationStringPair);
234 ~nsHtml5TreeOperationStringPair() {
235 MOZ_COUNT_DTOR(nsHtml5TreeOperationStringPair);
238 inline void Get(nsAString& aPublicId, nsAString& aSystemId) {
239 aPublicId.Assign(mPublicId);
240 aSystemId.Assign(mSystemId);
244 struct opAppendDoctypeToDocument {
245 nsAtom* mName;
246 nsHtml5TreeOperationStringPair* mStringPair;
248 explicit opAppendDoctypeToDocument(nsAtom* aName, const nsAString& aPublicId,
249 const nsAString& aSystemId) {
250 mName = aName;
251 aName->AddRef();
252 mStringPair = new nsHtml5TreeOperationStringPair(aPublicId, aSystemId);
256 struct opGetDocumentFragmentForTemplate {
257 nsIContent** mTemplate;
258 nsIContent** mFragHandle;
260 explicit opGetDocumentFragmentForTemplate(nsIContentHandle* aTemplate,
261 nsIContentHandle* aFragHandle) {
262 mTemplate = static_cast<nsIContent**>(aTemplate);
263 mFragHandle = static_cast<nsIContent**>(aFragHandle);
267 struct opGetFosterParent {
268 nsIContent** mTable;
269 nsIContent** mStackParent;
270 nsIContent** mParentHandle;
272 explicit opGetFosterParent(nsIContentHandle* aTable,
273 nsIContentHandle* aStackParent,
274 nsIContentHandle* aParentHandle) {
275 mTable = static_cast<nsIContent**>(aTable);
276 mStackParent = static_cast<nsIContent**>(aStackParent);
277 mParentHandle = static_cast<nsIContent**>(aParentHandle);
281 // Gecko-specific on-pop ops
282 struct opMarkAsBroken {
283 nsresult mResult;
285 explicit opMarkAsBroken(nsresult aResult) : mResult(aResult){};
288 struct opRunScript {
289 nsIContent** mElement;
290 nsAHtml5TreeBuilderState* mBuilderState;
291 int32_t mLineNumber;
293 explicit opRunScript(nsIContentHandle* aElement,
294 nsAHtml5TreeBuilderState* aBuilderState)
295 : mBuilderState(aBuilderState), mLineNumber(0) {
296 mElement = static_cast<nsIContent**>(aElement);
300 struct opRunScriptAsyncDefer {
301 nsIContent** mElement;
303 explicit opRunScriptAsyncDefer(nsIContentHandle* aElement) {
304 mElement = static_cast<nsIContent**>(aElement);
308 struct opPreventScriptExecution {
309 nsIContent** mElement;
311 explicit opPreventScriptExecution(nsIContentHandle* aElement) {
312 mElement = static_cast<nsIContent**>(aElement);
316 struct opDoneAddingChildren {
317 nsIContent** mElement;
319 explicit opDoneAddingChildren(nsIContentHandle* aElement) {
320 mElement = static_cast<nsIContent**>(aElement);
324 struct opDoneCreatingElement {
325 nsIContent** mElement;
327 explicit opDoneCreatingElement(nsIContentHandle* aElement) {
328 mElement = static_cast<nsIContent**>(aElement);
332 struct opUpdateCharsetSource {
333 nsCharsetSource mCharsetSource;
335 explicit opUpdateCharsetSource(nsCharsetSource aCharsetSource)
336 : mCharsetSource(aCharsetSource){};
339 struct opCharsetSwitchTo {
340 const mozilla::Encoding* mEncoding;
341 int32_t mCharsetSource;
342 int32_t mLineNumber;
344 explicit opCharsetSwitchTo(const mozilla::Encoding* aEncoding,
345 int32_t aCharsetSource, int32_t aLineNumber)
346 : mEncoding(aEncoding),
347 mCharsetSource(aCharsetSource),
348 mLineNumber(aLineNumber){};
351 struct opUpdateStyleSheet {
352 nsIContent** mElement;
354 explicit opUpdateStyleSheet(nsIContentHandle* aElement) {
355 mElement = static_cast<nsIContent**>(aElement);
359 struct opProcessOfflineManifest {
360 char16_t* mUrl;
362 explicit opProcessOfflineManifest(char16_t* aUrl) : mUrl(aUrl){};
365 struct opMarkMalformedIfScript {
366 nsIContent** mElement;
368 explicit opMarkMalformedIfScript(nsIContentHandle* aElement) {
369 mElement = static_cast<nsIContent**>(aElement);
373 struct opStreamEnded {};
375 struct opSetStyleLineNumber {
376 nsIContent** mContent;
377 int32_t mLineNumber;
379 explicit opSetStyleLineNumber(nsIContentHandle* aContent, int32_t aLineNumber)
380 : mLineNumber(aLineNumber) {
381 mContent = static_cast<nsIContent**>(aContent);
385 struct opSetScriptLineAndColumnNumberAndFreeze {
386 nsIContent** mContent;
387 int32_t mLineNumber;
388 int32_t mColumnNumber;
390 explicit opSetScriptLineAndColumnNumberAndFreeze(nsIContentHandle* aContent,
391 int32_t aLineNumber,
392 int32_t aColumnNumber)
393 : mLineNumber(aLineNumber), mColumnNumber(aColumnNumber) {
394 mContent = static_cast<nsIContent**>(aContent);
398 struct opSvgLoad {
399 nsIContent** mElement;
401 explicit opSvgLoad(nsIContentHandle* aElement) {
402 mElement = static_cast<nsIContent**>(aElement);
406 struct opMaybeComplainAboutCharset {
407 char* mMsgId;
408 bool mError;
409 int32_t mLineNumber;
411 explicit opMaybeComplainAboutCharset(char* aMsgId, bool aError,
412 int32_t aLineNumber)
413 : mMsgId(aMsgId), mError(aError), mLineNumber(aLineNumber){};
416 struct opMaybeComplainAboutDeepTree {
417 int32_t mLineNumber;
419 explicit opMaybeComplainAboutDeepTree(int32_t aLineNumber)
420 : mLineNumber(aLineNumber){};
423 struct opAddClass {
424 nsIContent** mElement;
425 char16_t* mClass;
427 explicit opAddClass(nsIContentHandle* aElement, char16_t* aClass)
428 : mClass(aClass) {
429 mElement = static_cast<nsIContent**>(aElement);
433 struct opAddViewSourceHref {
434 nsIContent** mElement;
435 char16_t* mBuffer;
436 int32_t mLength;
438 explicit opAddViewSourceHref(nsIContentHandle* aElement, char16_t* aBuffer,
439 int32_t aLength)
440 : mBuffer(aBuffer), mLength(aLength) {
441 mElement = static_cast<nsIContent**>(aElement);
445 struct opAddViewSourceBase {
446 char16_t* mBuffer;
447 int32_t mLength;
449 explicit opAddViewSourceBase(char16_t* aBuffer, int32_t aLength)
450 : mBuffer(aBuffer), mLength(aLength){};
453 struct opAddErrorType {
454 nsIContent** mElement;
455 char* mMsgId;
456 nsAtom* mName;
457 nsAtom* mOther;
459 explicit opAddErrorType(nsIContentHandle* aElement, char* aMsgId,
460 nsAtom* aName = nullptr, nsAtom* aOther = nullptr)
461 : mMsgId(aMsgId), mName(aName), mOther(aOther) {
462 mElement = static_cast<nsIContent**>(aElement);
463 if (aName) {
464 aName->AddRef();
466 if (aOther) {
467 aOther->AddRef();
472 struct opAddLineNumberId {
473 nsIContent** mElement;
474 int32_t mLineNumber;
476 explicit opAddLineNumberId(nsIContentHandle* aElement, int32_t aLineNumber)
477 : mLineNumber(aLineNumber) {
478 mElement = static_cast<nsIContent**>(aElement);
482 struct opStartLayout {};
484 struct opEnableEncodingMenu {};
486 typedef mozilla::Variant<
487 uninitialized,
488 // main HTML5 ops
489 opAppend, opDetach, opAppendChildrenToNewParent, opFosterParent,
490 opAppendToDocument, opAddAttributes, nsHtml5DocumentMode,
491 opCreateHTMLElement, opCreateSVGElement, opCreateMathMLElement,
492 opSetFormElement, opAppendText, opFosterParentText, opAppendComment,
493 opAppendCommentToDocument, opAppendDoctypeToDocument,
494 opGetDocumentFragmentForTemplate, opGetFosterParent,
495 // Gecko-specific on-pop ops
496 opMarkAsBroken, opRunScript, opRunScriptAsyncDefer,
497 opPreventScriptExecution, opDoneAddingChildren, opDoneCreatingElement,
498 opUpdateCharsetSource, opCharsetSwitchTo, opUpdateStyleSheet,
499 opProcessOfflineManifest, opMarkMalformedIfScript, opStreamEnded,
500 opSetStyleLineNumber, opSetScriptLineAndColumnNumberAndFreeze, opSvgLoad,
501 opMaybeComplainAboutCharset, opMaybeComplainAboutDeepTree, opAddClass,
502 opAddViewSourceHref, opAddViewSourceBase, opAddErrorType, opAddLineNumberId,
503 opStartLayout, opEnableEncodingMenu>
504 treeOperation;
506 class nsHtml5TreeOperation final {
507 template <typename T>
508 using NotNull = mozilla::NotNull<T>;
509 using Encoding = mozilla::Encoding;
511 public:
512 static nsresult AppendTextToTextNode(const char16_t* aBuffer,
513 uint32_t aLength,
514 mozilla::dom::Text* aTextNode,
515 nsHtml5DocumentBuilder* aBuilder);
517 static nsresult AppendText(const char16_t* aBuffer, uint32_t aLength,
518 nsIContent* aParent,
519 nsHtml5DocumentBuilder* aBuilder);
521 static nsresult Append(nsIContent* aNode, nsIContent* aParent,
522 nsHtml5DocumentBuilder* aBuilder);
524 static nsresult Append(nsIContent* aNode, nsIContent* aParent,
525 mozilla::dom::FromParser aFromParser,
526 nsHtml5DocumentBuilder* aBuilder);
528 static nsresult AppendToDocument(nsIContent* aNode,
529 nsHtml5DocumentBuilder* aBuilder);
531 static void Detach(nsIContent* aNode, nsHtml5DocumentBuilder* aBuilder);
533 static nsresult AppendChildrenToNewParent(nsIContent* aNode,
534 nsIContent* aParent,
535 nsHtml5DocumentBuilder* aBuilder);
537 static nsresult FosterParent(nsIContent* aNode, nsIContent* aParent,
538 nsIContent* aTable,
539 nsHtml5DocumentBuilder* aBuilder);
541 static nsresult AddAttributes(nsIContent* aNode,
542 nsHtml5HtmlAttributes* aAttributes,
543 nsHtml5DocumentBuilder* aBuilder);
545 static void SetHTMLElementAttributes(mozilla::dom::Element* aElement,
546 nsAtom* aName,
547 nsHtml5HtmlAttributes* aAttributes);
549 static nsIContent* CreateHTMLElement(
550 nsAtom* aName, nsHtml5HtmlAttributes* aAttributes,
551 mozilla::dom::FromParser aFromParser, nsNodeInfoManager* aNodeInfoManager,
552 nsHtml5DocumentBuilder* aBuilder,
553 mozilla::dom::HTMLContentCreatorFunction aCreator);
555 static nsIContent* CreateSVGElement(
556 nsAtom* aName, nsHtml5HtmlAttributes* aAttributes,
557 mozilla::dom::FromParser aFromParser, nsNodeInfoManager* aNodeInfoManager,
558 nsHtml5DocumentBuilder* aBuilder,
559 mozilla::dom::SVGContentCreatorFunction aCreator);
561 static nsIContent* CreateMathMLElement(nsAtom* aName,
562 nsHtml5HtmlAttributes* aAttributes,
563 nsNodeInfoManager* aNodeInfoManager,
564 nsHtml5DocumentBuilder* aBuilder);
566 static void SetFormElement(nsIContent* aNode, nsIContent* aParent);
568 static nsresult AppendIsindexPrompt(nsIContent* parent,
569 nsHtml5DocumentBuilder* aBuilder);
571 static nsresult FosterParentText(nsIContent* aStackParent, char16_t* aBuffer,
572 uint32_t aLength, nsIContent* aTable,
573 nsHtml5DocumentBuilder* aBuilder);
575 static nsresult AppendComment(nsIContent* aParent, char16_t* aBuffer,
576 int32_t aLength,
577 nsHtml5DocumentBuilder* aBuilder);
579 static nsresult AppendCommentToDocument(char16_t* aBuffer, int32_t aLength,
580 nsHtml5DocumentBuilder* aBuilder);
582 static nsresult AppendDoctypeToDocument(nsAtom* aName,
583 const nsAString& aPublicId,
584 const nsAString& aSystemId,
585 nsHtml5DocumentBuilder* aBuilder);
587 static nsIContent* GetDocumentFragmentForTemplate(nsIContent* aNode);
589 static nsIContent* GetFosterParent(nsIContent* aTable,
590 nsIContent* aStackParent);
592 static void PreventScriptExecution(nsIContent* aNode);
594 static void DoneAddingChildren(nsIContent* aNode);
596 static void DoneCreatingElement(nsIContent* aNode);
598 static void SvgLoad(nsIContent* aNode);
600 static void MarkMalformedIfScript(nsIContent* aNode);
602 nsHtml5TreeOperation();
604 ~nsHtml5TreeOperation();
606 inline void Init(const treeOperation& aOperation) {
607 NS_ASSERTION(mOperation.is<uninitialized>(),
608 "Op code must be uninitialized when initializing.");
609 mOperation = aOperation;
612 inline bool IsRunScript() { return mOperation.is<opRunScript>(); }
614 inline bool IsMarkAsBroken() { return mOperation.is<opMarkAsBroken>(); }
616 inline void SetSnapshot(nsAHtml5TreeBuilderState* aSnapshot, int32_t aLine) {
617 NS_ASSERTION(
618 IsRunScript(),
619 "Setting a snapshot for a tree operation other than eTreeOpRunScript!");
620 MOZ_ASSERT(aSnapshot, "Initialized tree op with null snapshot.");
621 opRunScript data = mOperation.as<opRunScript>();
622 data.mBuilderState = aSnapshot;
623 data.mLineNumber = aLine;
624 mOperation = mozilla::AsVariant(data);
627 nsresult Perform(nsHtml5TreeOpExecutor* aBuilder, nsIContent** aScriptElement,
628 bool* aInterrupted, bool* aStreamEnded);
630 private:
631 nsHtml5TreeOperation(const nsHtml5TreeOperation&) = delete;
632 nsHtml5TreeOperation& operator=(const nsHtml5TreeOperation&) = delete;
634 treeOperation mOperation;
637 #endif // nsHtml5TreeOperation_h