Document.h (219224B)
1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */ 3 /* This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #ifndef mozilla_dom_Document_h___ 8 #define mozilla_dom_Document_h___ 9 10 #include <bitset> 11 #include <cstddef> 12 #include <cstdint> 13 #include <new> 14 15 #include "ErrorList.h" 16 #include "MainThreadUtils.h" 17 #include "Units.h" 18 #include "imgIRequest.h" 19 #include "js/RootingAPI.h" 20 #include "js/friend/DOMProxy.h" 21 #include "mozilla/AlreadyAddRefed.h" 22 #include "mozilla/Assertions.h" 23 #include "mozilla/Attributes.h" 24 #include "mozilla/BasicEvents.h" 25 #include "mozilla/CORSMode.h" 26 #include "mozilla/CallState.h" 27 #include "mozilla/ContentBlockingNotifier.h" 28 #include "mozilla/FlushType.h" 29 #include "mozilla/FunctionRef.h" 30 #include "mozilla/LinkedList.h" 31 #include "mozilla/Maybe.h" 32 #include "mozilla/MozPromise.h" 33 #include "mozilla/NotNull.h" 34 #include "mozilla/OriginTrials.h" 35 #include "mozilla/PageloadEvent.h" 36 #include "mozilla/PointerLockManager.h" 37 #include "mozilla/PreloadService.h" 38 #include "mozilla/RefPtr.h" 39 #include "mozilla/RenderingPhase.h" 40 #include "mozilla/Result.h" 41 #include "mozilla/SegmentedVector.h" 42 #include "mozilla/ServoStyleSet.h" 43 #include "mozilla/StorageAccessAPIHelper.h" 44 #include "mozilla/TimeStamp.h" 45 #include "mozilla/UniquePtr.h" 46 #include "mozilla/UseCounter.h" 47 #include "mozilla/WeakPtr.h" 48 #include "mozilla/css/StylePreloadKind.h" 49 #include "mozilla/dom/AnimationFrameProvider.h" 50 #include "mozilla/dom/AnimationTimelinesController.h" 51 #include "mozilla/dom/DocumentOrShadowRoot.h" 52 #include "mozilla/dom/Element.h" 53 #include "mozilla/dom/EventTarget.h" 54 #include "mozilla/dom/LargestContentfulPaint.h" 55 #include "mozilla/dom/Nullable.h" 56 #include "mozilla/dom/RadioGroupContainer.h" 57 #include "mozilla/dom/TreeOrderedArray.h" 58 #include "mozilla/dom/UserActivation.h" 59 #include "mozilla/dom/ViewportMetaData.h" 60 #include "mozilla/dom/WakeLockBinding.h" 61 #include "nsAtom.h" 62 #include "nsCOMArray.h" 63 #include "nsCOMPtr.h" 64 #include "nsClassHashtable.h" 65 #include "nsCompatibility.h" 66 #include "nsContentListDeclarations.h" 67 #include "nsCycleCollectionParticipant.h" 68 #include "nsDebug.h" 69 #include "nsGkAtoms.h" 70 #include "nsHashKeys.h" 71 #include "nsIChannel.h" 72 #include "nsIChannelEventSink.h" 73 #include "nsIClassifiedChannel.h" 74 #include "nsID.h" 75 #include "nsIDocumentViewer.h" 76 #include "nsIInterfaceRequestor.h" 77 #include "nsILoadContext.h" 78 #include "nsILoadGroup.h" 79 #include "nsILoadInfo.h" 80 #include "nsINode.h" 81 #include "nsIObserver.h" 82 #include "nsIParser.h" 83 #include "nsIPrincipal.h" 84 #include "nsIProgressEventSink.h" 85 #include "nsIReferrerInfo.h" 86 #include "nsIRequestObserver.h" 87 #include "nsIScriptObjectPrincipal.h" 88 #include "nsIStreamListener.h" 89 #include "nsISupports.h" 90 #include "nsISupportsUtils.h" 91 #include "nsITransportSecurityInfo.h" 92 #include "nsIURI.h" 93 #include "nsIWeakReferenceUtils.h" 94 #include "nsLiteralString.h" 95 #include "nsPIDOMWindow.h" 96 #include "nsPropertyTable.h" 97 #include "nsRefPtrHashtable.h" 98 #include "nsString.h" 99 #include "nsTArray.h" 100 #include "nsTHashMap.h" 101 #include "nsTHashSet.h" 102 #include "nsTLiteralString.h" 103 #include "nsTObserverArray.h" 104 #include "nsThreadUtils.h" 105 #include "nsURIHashKey.h" 106 #include "nsWeakReference.h" 107 #include "nsWindowSizes.h" 108 #include "nscore.h" 109 110 // XXX We need to include this here to ensure that DefaultDeleter for Servo 111 // types is specialized before the template is instantiated. Probably, this 112 // should be included at some other place already that's generated by cbindgen. 113 #include "mozilla/ServoBindingTypes.h" 114 115 // windows.h #defines CreateEvent 116 #ifdef CreateEvent 117 # undef CreateEvent 118 #endif 119 120 #ifdef MOZILLA_INTERNAL_API 121 # include "mozilla/dom/DocumentBinding.h" 122 #else 123 namespace mozilla { 124 namespace dom { 125 class ElementCreationOptionsOrString; 126 } // namespace dom 127 } // namespace mozilla 128 #endif // MOZILLA_INTERNAL_API 129 130 class InfallibleAllocPolicy; 131 class JSObject; 132 class JSTracer; 133 class PLDHashTable; 134 class PolicyContainer; 135 class gfxUserFontSet; 136 class mozIDOMWindowProxy; 137 class nsCachableElementsByNameNodeList; 138 class nsCommandManager; 139 class nsContentList; 140 class nsCycleCollectionTraversalCallback; 141 class nsDOMCaretPosition; 142 class nsDOMNavigationTiming; 143 class nsDocShell; 144 class nsFrameLoader; 145 class nsFrameLoaderOwner; 146 class nsGenericHTMLElement; 147 class nsGlobalWindowInner; 148 class nsHTMLDocument; 149 class nsHtml5TreeOpExecutor; 150 class nsIAppWindow; 151 class nsIAsyncVerifyRedirectCallback; 152 class nsIBFCacheEntry; 153 class nsIContent; 154 class nsIContentSecurityPolicy; 155 class nsIContentSink; 156 class nsICookieJarSettings; 157 class nsIDOMXULCommandDispatcher; 158 class nsIDocShell; 159 class nsIDocShellTreeItem; 160 class nsIDocumentEncoder; 161 class nsIDocumentObserver; 162 class nsIEventTarget; 163 class nsIFrame; 164 class nsIGlobalObject; 165 class nsIHTMLCollection; 166 class nsIInputStream; 167 class nsILayoutHistoryState; 168 class nsIObjectLoadingContent; 169 class nsIPermissionDelegateHandler; 170 class nsIPolicyContainer; 171 class nsIRequest; 172 class nsIRunnable; 173 class nsIScriptGlobalObject; 174 class nsISecurityConsoleMessage; 175 class nsISerialEventTarget; 176 class nsIStructuredCloneContainer; 177 class nsIVariant; 178 class nsNodeInfoManager; 179 class nsPIWindowRoot; 180 class nsPresContext; 181 class nsRange; 182 class nsSimpleContentList; 183 class nsTextNode; 184 class nsViewManager; 185 class nsViewportInfo; 186 class nsXULPrototypeDocument; 187 class nsXULPrototypeElement; 188 struct JSContext; 189 struct nsFont; 190 191 namespace mozilla { 192 class AbstractThread; 193 class AttributeStyles; 194 class CanvasUsage; 195 class StyleSheet; 196 class EditorBase; 197 class EditorCommand; 198 class Encoding; 199 class ErrorResult; 200 class EventListenerManager; 201 class FullscreenExit; 202 class FullscreenRequest; 203 class HTMLEditor; 204 struct LangGroupFontPrefs; 205 class PendingFullscreenEvent; 206 class PermissionDelegateHandler; 207 class PresShell; 208 class ScrollTimelineAnimationTracker; 209 class ServoStyleSet; 210 enum class StyleOrigin : uint8_t; 211 class SMILAnimationController; 212 enum class StyleCursorKind : uint8_t; 213 class SVGContextPaint; 214 enum class ColorScheme : uint8_t; 215 enum class StyleRuleChangeKind : uint32_t; 216 struct StyleUseCounters; 217 template <typename> 218 class OwningNonNull; 219 struct URLExtraData; 220 221 namespace css { 222 class Loader; 223 class ImageLoader; 224 class Rule; 225 } // namespace css 226 227 namespace dom { 228 class AnonymousContent; 229 class Attr; 230 class AutoSuppressNotifyingDevToolsOfNodeRemovals; 231 class XULBroadcastManager; 232 class XULPersist; 233 class BrowserBridgeChild; 234 class ChromeObserver; 235 class ClientInfo; 236 class ClientState; 237 class CDATASection; 238 class Comment; 239 class CSSImportRule; 240 class DocumentL10n; 241 class DocumentFragment; 242 class DocumentTimeline; 243 class DocumentType; 244 class DOMImplementation; 245 class DOMIntersectionObserver; 246 class DOMStringList; 247 class Event; 248 class EventListener; 249 struct FailedCertSecurityInfo; 250 class FeaturePolicy; 251 class FontFaceSet; 252 class FragmentDirective; 253 class FrameRequestCallback; 254 class HighlightRegistry; 255 class HTMLAllCollection; 256 class HTMLBodyElement; 257 class HTMLInputElement; 258 class HTMLMetaElement; 259 class HTMLDialogElement; 260 class HTMLSharedElement; 261 class HTMLVideoElement; 262 class HTMLImageElement; 263 class IntegrityPolicy; 264 enum class InteractiveWidget : uint8_t; 265 struct LifecycleCallbackArgs; 266 class Link; 267 class Location; 268 class MediaQueryList; 269 struct NetErrorInfo; 270 class NodeFilter; 271 class NodeInfo; 272 class NodeIterator; 273 enum class OrientationType : uint8_t; 274 enum class PopoverAttributeState : uint8_t; 275 class ProcessingInstruction; 276 class Promise; 277 class ScriptLoader; 278 class Selection; 279 class ServiceWorkerDescriptor; 280 class ShadowRoot; 281 class SVGDocument; 282 class SVGElement; 283 class SVGSVGElement; 284 class SVGUseElement; 285 class ImageDocument; 286 class Touch; 287 class TouchList; 288 class TreeWalker; 289 class TrustedHTMLOrString; 290 class OwningTrustedHTMLOrString; 291 enum class ViewportFitType : uint8_t; 292 class ViewTransition; 293 class ViewTransitionUpdateCallbackOrStartViewTransitionOptions; 294 class WakeLockSentinel; 295 class WindowContext; 296 class WindowGlobalChild; 297 class WindowProxyHolder; 298 struct Wireframe; 299 class WorkerDocumentListener; 300 class XPathEvaluator; 301 class XPathExpression; 302 class XPathNSResolver; 303 class XPathResult; 304 class BrowsingContext; 305 306 class nsUnblockOnloadEvent; 307 308 template <typename, typename> 309 class CallbackObjectHolder; 310 311 enum class CallerType : uint32_t; 312 313 enum BFCacheStatus { 314 NOT_ALLOWED = 1 << 0, // Status 0 315 EVENT_HANDLING_SUPPRESSED = 1 << 1, // Status 1 316 SUSPENDED = 1 << 2, // Status 2 317 UNLOAD_LISTENER = 1 << 3, // Status 3 318 REQUEST = 1 << 4, // Status 4 319 ACTIVE_GET_USER_MEDIA = 1 << 5, // Status 5 320 ACTIVE_PEER_CONNECTION = 1 << 6, // Status 6 321 CONTAINS_EME_CONTENT = 1 << 7, // Status 7 322 CONTAINS_MSE_CONTENT = 1 << 8, // Status 8 323 HAS_ACTIVE_SPEECH_SYNTHESIS = 1 << 9, // Status 9 324 HAS_USED_VR = 1 << 10, // Status 10 325 CONTAINS_REMOTE_SUBFRAMES = 1 << 11, // Status 11 326 NOT_ONLY_TOPLEVEL_IN_BCG = 1 << 12, // Status 12 327 ABOUT_PAGE = 1 << 13, // Status 13 328 RESTORING = 1 << 14, // Status 14 329 BEFOREUNLOAD_LISTENER = 1 << 15, // Status 15 330 ACTIVE_LOCK = 1 << 16, // Status 16 331 ACTIVE_WEBTRANSPORT = 1 << 17, // Status 17 332 PAGE_LOADING = 1 << 18, // Status 18 333 }; 334 335 } // namespace dom 336 } // namespace mozilla 337 338 namespace mozilla::net { 339 class ChannelEventQueue; 340 class EarlyHintConnectArgs; 341 } // namespace mozilla::net 342 343 // Must be kept in sync with xpcom/rust/xpcom/src/interfaces/nonidl.rs 344 #define NS_IDOCUMENT_IID \ 345 {0xce1f7627, 0x7109, 0x4977, {0xba, 0x77, 0x49, 0x0f, 0xfd, 0xe0, 0x7a, 0xaa}} 346 347 using mozilla::performance::pageload_event::PageloadEventData; 348 349 namespace mozilla::dom { 350 351 class Document; 352 class DOMStyleSheetSetList; 353 class ResizeObserver; 354 class ResizeObserverController; 355 class PostMessageEvent; 356 357 #define DEPRECATED_OPERATION(_op) e##_op, 358 enum class DeprecatedOperations : uint16_t { 359 #include "nsDeprecatedOperationList.h" 360 eDeprecatedOperationCount 361 }; 362 #undef DEPRECATED_OPERATION 363 364 class ExternalResourceMap { 365 public: 366 using SubDocEnumFunc = FunctionRef<CallState(Document&)>; 367 using SubDocTestFunc = FunctionRef<bool(const Document* aDocument)>; 368 369 /** 370 * A class that represents an external resource load that has begun but 371 * doesn't have a document yet. Observers can be registered on this object, 372 * and will be notified after the document is created. Observers registered 373 * after the document has been created will NOT be notified. When observers 374 * are notified, the subject will be the newly-created document, the topic 375 * will be "external-resource-document-created", and the data will be null. 376 * If document creation fails for some reason, observers will still be 377 * notified, with a null document pointer. 378 */ 379 class ExternalResourceLoad : public nsISupports { 380 public: 381 virtual ~ExternalResourceLoad() = default; 382 383 void AddObserver(nsIObserver* aObserver) { 384 MOZ_ASSERT(aObserver, "Must have observer"); 385 mObservers.AppendElement(aObserver); 386 } 387 388 const nsTArray<nsCOMPtr<nsIObserver>>& Observers() { return mObservers; } 389 390 protected: 391 AutoTArray<nsCOMPtr<nsIObserver>, 8> mObservers; 392 }; 393 394 ExternalResourceMap(); 395 396 /** 397 * Request an external resource document. This does exactly what 398 * Document::RequestExternalResource is documented to do. 399 */ 400 Document* RequestResource(nsIURI* aURI, nsIReferrerInfo* aReferrerInfo, 401 nsINode* aRequestingNode, 402 Document* aDisplayDocument, 403 ExternalResourceLoad** aPendingLoad); 404 405 /** 406 * Enumerate the resource documents. See 407 * Document::EnumerateExternalResources. 408 */ 409 void EnumerateResources(SubDocEnumFunc aCallback) const; 410 411 /** Recursively collect subresources and their subdocuments too */ 412 void CollectDescendantDocuments(nsTArray<RefPtr<Document>>& aDocs, 413 SubDocTestFunc) const; 414 415 /** 416 * Traverse ourselves for cycle-collection 417 */ 418 void Traverse(nsCycleCollectionTraversalCallback* aCallback) const; 419 420 /** 421 * Shut ourselves down (used for cycle-collection unlink), as well 422 * as for document destruction. 423 */ 424 void Shutdown() { 425 mPendingLoads.Clear(); 426 mMap.Clear(); 427 mHaveShutDown = true; 428 } 429 430 bool HaveShutDown() const { return mHaveShutDown; } 431 432 // Needs to be public so we can traverse them sanely 433 struct ExternalResource { 434 ~ExternalResource(); 435 RefPtr<Document> mDocument; 436 nsCOMPtr<nsIDocumentViewer> mViewer; 437 nsCOMPtr<nsILoadGroup> mLoadGroup; 438 }; 439 440 // Hide all our viewers 441 void HideViewers(); 442 443 // Show all our viewers 444 void ShowViewers(); 445 446 protected: 447 class PendingLoad : public ExternalResourceLoad, public nsIStreamListener { 448 ~PendingLoad() = default; 449 450 public: 451 explicit PendingLoad(Document* aDisplayDocument) 452 : mDisplayDocument(aDisplayDocument) {} 453 454 NS_DECL_ISUPPORTS 455 NS_DECL_NSISTREAMLISTENER 456 NS_DECL_NSIREQUESTOBSERVER 457 458 /** 459 * Start aURI loading. This will perform the necessary security checks and 460 * so forth. 461 */ 462 nsresult StartLoad(nsIURI* aURI, nsIReferrerInfo* aReferrerInfo, 463 nsINode* aRequestingNode); 464 /** 465 * Set up an nsIDocumentViewer based on aRequest. This is guaranteed to 466 * put null in *aViewer and *aLoadGroup on all failures. 467 */ 468 nsresult SetupViewer(nsIRequest* aRequest, nsIDocumentViewer** aViewer, 469 nsILoadGroup** aLoadGroup); 470 471 private: 472 RefPtr<Document> mDisplayDocument; 473 nsCOMPtr<nsIStreamListener> mTargetListener; 474 nsCOMPtr<nsIURI> mURI; 475 }; 476 friend class PendingLoad; 477 478 class LoadgroupCallbacks final : public nsIInterfaceRequestor { 479 ~LoadgroupCallbacks() = default; 480 481 public: 482 explicit LoadgroupCallbacks(nsIInterfaceRequestor* aOtherCallbacks) 483 : mCallbacks(aOtherCallbacks) {} 484 NS_DECL_ISUPPORTS 485 NS_DECL_NSIINTERFACEREQUESTOR 486 private: 487 // The only reason it's safe to hold a strong ref here without leaking is 488 // that the notificationCallbacks on a loadgroup aren't the docshell itself 489 // but a shim that holds a weak reference to the docshell. 490 nsCOMPtr<nsIInterfaceRequestor> mCallbacks; 491 492 // Use shims for interfaces that docshell implements directly so that we 493 // don't hand out references to the docshell. The shims should all allow 494 // getInterface back on us, but other than that each one should only 495 // implement one interface. 496 497 // XXXbz I wish we could just derive the _allcaps thing from _i 498 #define DECL_SHIM(_i, _allcaps) \ 499 class _i##Shim final : public nsIInterfaceRequestor, public _i { \ 500 ~_i##Shim() {} \ 501 \ 502 public: \ 503 _i##Shim(nsIInterfaceRequestor* aIfreq, _i* aRealPtr) \ 504 : mIfReq(aIfreq), mRealPtr(aRealPtr) { \ 505 NS_ASSERTION(mIfReq, "Expected non-null here"); \ 506 NS_ASSERTION(mRealPtr, "Expected non-null here"); \ 507 } \ 508 NS_DECL_ISUPPORTS \ 509 NS_FORWARD_NSIINTERFACEREQUESTOR(mIfReq->) \ 510 NS_FORWARD_##_allcaps(mRealPtr->) private \ 511 : nsCOMPtr<nsIInterfaceRequestor> mIfReq; \ 512 nsCOMPtr<_i> mRealPtr; \ 513 }; 514 515 DECL_SHIM(nsILoadContext, NSILOADCONTEXT) 516 DECL_SHIM(nsIProgressEventSink, NSIPROGRESSEVENTSINK) 517 DECL_SHIM(nsIChannelEventSink, NSICHANNELEVENTSINK) 518 #undef DECL_SHIM 519 }; 520 521 /** 522 * Add an ExternalResource for aURI. aViewer and aLoadGroup might be null 523 * when this is called if the URI didn't result in an XML document. This 524 * function makes sure to remove the pending load for aURI, if any, from our 525 * hashtable, and to notify its observers, if any. 526 */ 527 nsresult AddExternalResource(nsIURI* aURI, nsIDocumentViewer* aViewer, 528 nsILoadGroup* aLoadGroup, 529 Document* aDisplayDocument); 530 531 nsClassHashtable<nsURIHashKey, ExternalResource> mMap; 532 nsRefPtrHashtable<nsURIHashKey, PendingLoad> mPendingLoads; 533 bool mHaveShutDown; 534 }; 535 536 // The current status for a preload. 537 enum class SheetPreloadStatus : uint8_t { 538 // There's no need to preload anything, the sheet is already in-memory. 539 AlreadyComplete, 540 // The load is in-progress. There's no guarantee that a load was started, it 541 // could be coalesced with other redundant loads. 542 InProgress, 543 // Something went wrong, and we errored out. 544 Errored, 545 }; 546 547 //---------------------------------------------------------------------- 548 549 enum class LoadedAsData : uint8_t { 550 // Not "loaded as data" 551 No, 552 // The "loaded as data" case: scripting disabled and CSS loader creation made 553 // lazy 554 AsData, 555 }; 556 557 // Document interface. This is implemented by all document objects in 558 // Gecko. 559 class Document : public nsINode, 560 public DocumentOrShadowRoot, 561 public nsSupportsWeakReference, 562 public nsIScriptObjectPrincipal, 563 public SupportsWeakPtr, 564 private LinkedListElement<Document> { 565 friend class DocumentOrShadowRoot; 566 friend class LinkedList<Document>; 567 friend class LinkedListElement<Document>; 568 569 protected: 570 Document(const char* aContentType, LoadedAsData aLoadedAsData); 571 virtual ~Document(); 572 573 Document(const Document&) = delete; 574 Document& operator=(const Document&) = delete; 575 576 public: 577 using ExternalResourceLoad = dom::ExternalResourceMap::ExternalResourceLoad; 578 using ReferrerPolicyEnum = dom::ReferrerPolicy; 579 using AdoptedStyleSheetCloneCache = 580 nsRefPtrHashtable<nsPtrHashKey<const StyleSheet>, StyleSheet>; 581 582 // nsINode overrides the new operator for DOM Arena allocation. 583 // to use the default one, we need to bring it back again 584 void* operator new(size_t aSize) { return ::operator new(aSize); } 585 586 /** 587 * Called when XPCOM shutdown. 588 */ 589 static void Shutdown(); 590 591 NS_INLINE_DECL_STATIC_IID(NS_IDOCUMENT_IID) 592 593 NS_DECL_ISUPPORTS_INHERITED 594 NS_IMETHOD_(void) DeleteCycleCollectable() override; 595 596 NS_DECL_ADDSIZEOFEXCLUDINGTHIS 597 598 NS_DECL_CYCLE_COLLECTION_SKIPPABLE_SCRIPT_HOLDER_CLASS_AMBIGUOUS(Document, 599 nsINode) 600 601 #define NS_DOCUMENT_NOTIFY_OBSERVERS(func_, params_) \ 602 do { \ 603 for (RefPtr obs : mObservers.ForwardRange()) { \ 604 if (obs->IsCallbackEnabled(nsIMutationObserver::k##func_)) { \ 605 obs->func_ params_; \ 606 } \ 607 } \ 608 /* FIXME(emilio): Apparently we can keep observing from the BFCache? That \ 609 looks bogus. */ \ 610 if (PresShell* presShell = GetObservingPresShell()) { \ 611 presShell->func_ params_; \ 612 } \ 613 } while (0) 614 615 nsIPrincipal* EffectiveCookiePrincipal() const; 616 617 nsIPrincipal* EffectiveStoragePrincipal() const; 618 619 // nsIScriptObjectPrincipal 620 nsIPrincipal* GetPrincipal() final { return NodePrincipal(); } 621 622 nsIPrincipal* GetEffectiveCookiePrincipal() final { 623 return EffectiveCookiePrincipal(); 624 } 625 626 nsIPrincipal* GetEffectiveStoragePrincipal() final { 627 return EffectiveStoragePrincipal(); 628 } 629 630 // You should probably not be using this function, since it performs no checks 631 // to ensure that the partitioned principal should really be used here. It is 632 // only designed to be used in very specific circumstances, such as when 633 // inheriting the document/storage principal. 634 nsIPrincipal* PartitionedPrincipal() final { return mPartitionedPrincipal; } 635 636 // Gets the appropriate principal to check the URI against a blocklist / 637 // allowlist. 638 nsIPrincipal* GetPrincipalForPrefBasedHacks() const; 639 640 void ClearActiveCookieAndStoragePrincipals() { 641 mActiveStoragePrincipal = nullptr; 642 mActiveCookiePrincipal = nullptr; 643 } 644 645 // EventTarget 646 void GetEventTargetParent(EventChainPreVisitor& aVisitor) override; 647 EventListenerManager* GetOrCreateListenerManager() override; 648 EventListenerManager* GetExistingListenerManager() const override; 649 650 // This helper class must be set when we dispatch beforeunload and unload 651 // events in order to avoid unterminate sync XHRs. 652 class MOZ_RAII PageUnloadingEventTimeStamp { 653 RefPtr<Document> mDocument; 654 bool mSet; 655 656 public: 657 explicit PageUnloadingEventTimeStamp(Document* aDocument) 658 : mDocument(aDocument), mSet(false) { 659 MOZ_ASSERT(aDocument); 660 if (mDocument->mPageUnloadingEventTimeStamp.IsNull()) { 661 mDocument->SetPageUnloadingEventTimeStamp(); 662 mSet = true; 663 } 664 } 665 666 ~PageUnloadingEventTimeStamp() { 667 if (mSet) { 668 mDocument->CleanUnloadEventsTimeStamp(); 669 } 670 } 671 }; 672 673 void ApplyCspFromLoadInfo(nsILoadInfo* aLoadInfo); 674 675 /** 676 * Let the document know that we're starting to load data into it. 677 * @param aCommand The parser command. Must not be null. 678 * XXXbz It's odd to have that here. 679 * @param aChannel The channel the data will come from. The channel must be 680 * able to report its Content-Type. 681 * @param aLoadGroup The loadgroup this document should use from now on. 682 * Note that the document might not be the only thing using 683 * this loadgroup. 684 * @param aContainer The container this document is in. This may be null. 685 * XXXbz maybe we should make it more explicit (eg make the 686 * container an nsIWebNavigation or nsIDocShell or 687 * something)? 688 * @param [out] aDocListener the listener to pump data from the channel into. 689 * Generally this will be the parser this document 690 * sets up, or some sort of data-handler for media 691 * documents. 692 * @param aReset whether the document should call Reset() on itself. If this 693 * is false, the document will NOT set its principal to the 694 * channel's owner, will not clear any event listeners that are 695 * already set on it, etc. 696 * 697 * Once this has been called, the document will return false for 698 * MayStartLayout() until SetMayStartLayout(true) is called on it. Making 699 * sure this happens is the responsibility of the caller of 700 * StartDocumentLoad(). 701 * 702 * This function has an implementation, and does some setup, but does NOT set 703 * *aDocListener; this is the job of subclasses. 704 */ 705 virtual nsresult StartDocumentLoad(const char* aCommand, nsIChannel* aChannel, 706 nsILoadGroup* aLoadGroup, 707 nsISupports* aContainer, 708 nsIStreamListener** aDocListener, 709 bool aReset) = 0; 710 void StopDocumentLoad(); 711 712 virtual void SetSuppressParserErrorElement(bool aSuppress) {} 713 virtual bool SuppressParserErrorElement() { return false; } 714 715 virtual void SetSuppressParserErrorConsoleMessages(bool aSuppress) {} 716 virtual bool SuppressParserErrorConsoleMessages() { return false; } 717 718 // nsINode 719 void InsertChildBefore( 720 nsIContent* aKid, nsIContent* aBeforeThis, bool aNotify, ErrorResult& aRv, 721 nsINode* aOldParent = nullptr, 722 MutationEffectOnScript aMutationEffectOnScript = 723 MutationEffectOnScript::DropTrustWorthiness) override; 724 void RemoveChildNode(nsIContent* aKid, bool aNotify, 725 const BatchRemovalState* = nullptr, 726 nsINode* aNewParent = nullptr, 727 MutationEffectOnScript aMutationEffectOnScript = 728 MutationEffectOnScript::DropTrustWorthiness) final; 729 nsresult Clone(dom::NodeInfo* aNodeInfo, nsINode** aResult) const override { 730 return NS_ERROR_NOT_IMPLEMENTED; 731 } 732 nsresult CloneDocHelper(Document* clone) const; 733 734 Document* GetLatestStaticClone() const { return mLatestStaticClone; } 735 736 /** 737 * Signal that the document title may have changed 738 * (see Document::GetTitle). 739 * @param aBoundTitleElement true if an HTML or SVG <title> element 740 * has just been bound to the document. 741 */ 742 virtual void NotifyPossibleTitleChange(bool aBoundTitleElement); 743 744 /** 745 * Return the URI for the document. May return null. If it ever stops being 746 * able to return null, we can make sure nsINode::GetBaseURI/GetBaseURIObject 747 * also never return null. 748 * 749 * The value returned corresponds to the "document's address" in 750 * HTML5. As such, it may change over the lifetime of the document, for 751 * instance as a result of the user navigating to a fragment identifier on 752 * the page, or as a result to a call to pushState() or replaceState(). 753 * 754 * https://html.spec.whatwg.org/multipage/dom.html#the-document%27s-address 755 */ 756 nsIURI* GetDocumentURI() const { return mDocumentURI; } 757 758 /** 759 * Return the original URI of the document. This is the same as the 760 * document's URI unless that has changed from its original value (for 761 * example, due to history.pushState() or replaceState() being invoked on the 762 * document). 763 * 764 * This method corresponds to the "creation URL" in HTML5 and, once set, 765 * doesn't change over the lifetime of the document. 766 * 767 * https://html.spec.whatwg.org/multipage/webappapis.html#creation-url 768 */ 769 nsIURI* GetOriginalURI() const { return mOriginalURI; } 770 771 /** 772 * Set the URI for the document. This also sets the document's original URI, 773 * if it's null. 774 */ 775 void SetDocumentURI(nsIURI* aURI); 776 777 /** 778 * Set the URI for the document loaded via XHR, when accessed from 779 * chrome privileged script. 780 */ 781 void SetChromeXHRDocURI(nsIURI* aURI) { mChromeXHRDocURI = aURI; } 782 783 /** 784 * Set the base URI for the document loaded via XHR, when accessed from 785 * chrome privileged script. 786 */ 787 void SetChromeXHRDocBaseURI(nsIURI* aURI) { mChromeXHRDocBaseURI = aURI; } 788 789 /** 790 * The CSP in general is stored in the ClientInfo, but we also cache 791 * the CSP on the document so subresources loaded within a document 792 * can query that cached CSP instead of having to deserialize the CSP 793 * from the Client. 794 * 795 * Please note that at the time of CSP parsing the Client is not 796 * available yet, hence we sync CSP of document and Client when the 797 * Client becomes available within nsGlobalWindowInner::EnsureClientSource(). 798 */ 799 nsIContentSecurityPolicy* GetPreloadCsp() const; 800 void SetPreloadCsp(nsIContentSecurityPolicy* aPreloadCSP); 801 802 void GetCspJSON(nsString& aJSON); 803 804 /** 805 * Set referrer policy and upgrade-insecure-requests flags 806 */ 807 void ApplySettingsFromCSP(bool aSpeculative); 808 809 nsIPolicyContainer* GetPolicyContainer() const; 810 void SetPolicyContainer(nsIPolicyContainer* aPolicyContainer); 811 812 already_AddRefed<nsIParser> CreatorParserOrNull() { 813 nsCOMPtr<nsIParser> parser = mParser; 814 return parser.forget(); 815 } 816 817 /** 818 * ReferrerInfo getter for Document.webidl. 819 */ 820 nsIReferrerInfo* ReferrerInfo() const { return GetReferrerInfo(); } 821 822 nsIReferrerInfo* GetReferrerInfo() const { return mReferrerInfo; } 823 824 nsIReferrerInfo* GetPreloadReferrerInfo() const { 825 return mPreloadReferrerInfo; 826 } 827 /** 828 * Return the referrer policy of the document. Return "default" if there's no 829 * valid meta referrer tag found in the document. 830 * Referrer policy should be inherited from parent if the iframe is srcdoc 831 */ 832 ReferrerPolicyEnum GetReferrerPolicy() const; 833 834 /** 835 * GetReferrerPolicy() for Document.webidl. 836 */ 837 ReferrerPolicyEnum ReferrerPolicy() const { return GetReferrerPolicy(); } 838 839 /** 840 * The referrer policy that was used for the fetch of this document, what the 841 * spec calls "request referrer policy". Not to be confused with the history 842 * policy container's referrer policy, which dictates the policy for fetches 843 * made by this document (see ReferrerPolicy()). 844 * 845 * See: https://html.spec.whatwg.org/#document-state-request-referrer-policy 846 */ 847 ReferrerPolicyEnum ReferrerPolicyUsedToFetchThisDocument() const; 848 849 /** 850 * If true, this flag indicates that all mixed content subresource 851 * loads for this document (and also embeded browsing contexts) will 852 * be blocked. 853 */ 854 bool GetBlockAllMixedContent(bool aPreload) const { 855 if (aPreload) { 856 return mBlockAllMixedContentPreloads; 857 } 858 return mBlockAllMixedContent; 859 } 860 861 /** 862 * If true, this flag indicates that all subresource loads for this 863 * document need to be upgraded from http to https. 864 * This flag becomes true if the CSP of the document itself, or any 865 * of the document's ancestors up to the toplevel document makes use 866 * of the CSP directive 'upgrade-insecure-requests'. 867 */ 868 bool GetUpgradeInsecureRequests(bool aPreload) const { 869 if (aPreload) { 870 return mUpgradeInsecurePreloads; 871 } 872 return mUpgradeInsecureRequests; 873 } 874 875 void SetReferrerInfo(nsIReferrerInfo*); 876 877 /* 878 * Referrer policy from <meta name="referrer" content=`policy`> 879 * will have higher priority than referrer policy from Referrer-Policy 880 * header. So override the old ReferrerInfo if we get one from meta 881 */ 882 void UpdateReferrerInfoFromMeta(const nsAString& aMetaReferrer, 883 bool aPreload); 884 885 /** 886 * Set the principals responsible for this document. Chances are, you do not 887 * want to be using this. 888 */ 889 void SetPrincipals(nsIPrincipal* aPrincipal, 890 nsIPrincipal* aPartitionedPrincipal); 891 892 /** 893 * Returns true if exempt from HTTPS-Only Mode upgrade. 894 */ 895 uint32_t HttpsOnlyStatus() const { return mHttpsOnlyStatus; } 896 897 /** 898 * Return the LoadGroup for the document. May return null. 899 */ 900 already_AddRefed<nsILoadGroup> GetDocumentLoadGroup() const { 901 nsCOMPtr<nsILoadGroup> group = do_QueryReferent(mDocumentLoadGroup); 902 return group.forget(); 903 } 904 905 /** 906 * Return the fallback base URL for this document, as defined in the HTML 907 * specification. Note that this can return null if there is no document URI. 908 * 909 * XXXbz: This doesn't implement the bits for about:blank yet. 910 */ 911 nsIURI* GetFallbackBaseURI() const { 912 if (mIsSrcdocDocument && mParentDocument) { 913 return mParentDocument->GetDocBaseURI(); 914 } 915 return mDocumentURI; 916 } 917 918 /** 919 * Return the referrer from document URI as defined in the Referrer Policy 920 * specification. 921 * https://w3c.github.io/webappsec-referrer-policy/#determine-requests-referrer 922 * While document is an iframe srcdoc document, let document be document's 923 * browsing context's browsing context container's node document. 924 * Then referrer should be document's URL 925 */ 926 927 nsIURI* GetDocumentURIAsReferrer() const { 928 if (mIsSrcdocDocument && mParentDocument) { 929 return mParentDocument->GetDocumentURIAsReferrer(); 930 } 931 return mDocumentURI; 932 } 933 934 /** 935 * Return the base URI for relative URIs in the document (the document uri 936 * unless it's overridden by SetBaseURI, HTML <base> tags, etc.). The 937 * returned URI could be null if there is no document URI. If the document is 938 * a srcdoc document and has no explicit base URL, return the parent 939 * document's base URL. 940 */ 941 nsIURI* GetDocBaseURI() const { 942 if (mDocumentBaseURI) { 943 return mDocumentBaseURI; 944 } 945 return GetFallbackBaseURI(); 946 } 947 948 nsIURI* GetBaseURI(bool aTryUseXHRDocBaseURI = false) const final; 949 950 void SetBaseURI(nsIURI* aURI); 951 952 /** 953 * Resolves a URI based on the document's base URI. 954 */ 955 Result<OwningNonNull<nsIURI>, nsresult> ResolveWithBaseURI( 956 const nsAString& aURI); 957 958 /** 959 * Return the URL data which style system needs for resolving url value. 960 * This method attempts to use the cached object in mCachedURLData, but 961 * if the base URI, document URI, or principal has changed since last 962 * call to this function, or the function is called the first time for 963 * the document, a new one is created. 964 */ 965 URLExtraData* DefaultStyleAttrURLData(); 966 nsIReferrerInfo* ReferrerInfoForInternalCSSAndSVGResources(); 967 968 /** 969 * Get/Set the base target of a link in a document. 970 */ 971 void GetBaseTarget(nsAString& aBaseTarget) const { 972 aBaseTarget = mBaseTarget; 973 } 974 975 void SetBaseTarget(const nsString& aBaseTarget) { mBaseTarget = aBaseTarget; } 976 977 /** 978 * Return a standard name for the document's character set. 979 */ 980 NotNull<const Encoding*> GetDocumentCharacterSet() const { 981 return mCharacterSet; 982 } 983 984 /** 985 * Set the document's character encoding. 986 */ 987 void SetDocumentCharacterSet(NotNull<const Encoding*> aEncoding); 988 989 int32_t GetDocumentCharacterSetSource() const { return mCharacterSetSource; } 990 991 // This method MUST be called before SetDocumentCharacterSet if 992 // you're planning to call both. 993 void SetDocumentCharacterSetSource(int32_t aCharsetSource) { 994 mCharacterSetSource = aCharsetSource; 995 } 996 997 /** 998 * Get the Content-Type of this document. 999 */ 1000 void GetContentType(nsAString& aContentType); 1001 1002 /** 1003 * Set the Content-Type of this document. 1004 */ 1005 void SetContentType(const nsACString& aContentType); 1006 1007 /** 1008 * Return the language of this document, or null if not set. 1009 */ 1010 nsAtom* GetContentLanguage() const { return mContentLanguage.get(); } 1011 1012 void GetContentLanguageForBindings(DOMString&) const; 1013 1014 // The states BidiEnabled and MathMLEnabled should persist across multiple 1015 // views (screen, print) of the same document. 1016 1017 /** 1018 * Check if the document contains bidi data. 1019 * If so, we have to apply the Unicode Bidi Algorithm. 1020 */ 1021 bool GetBidiEnabled() const { return mBidiEnabled; } 1022 1023 /** 1024 * Indicate the document contains bidi data. 1025 * Currently, we cannot disable bidi, because once bidi is enabled, 1026 * it affects a frame model irreversibly, and plays even though 1027 * the document no longer contains bidi data. 1028 */ 1029 void SetBidiEnabled() { mBidiEnabled = true; } 1030 1031 /** 1032 * Whether a document is the initial document in its window, and if so, 1033 * which stage of initialness it is in. 1034 */ 1035 enum class InitialStatus : uint8_t { 1036 // The first stage of an initial document. No navigation has occured, 1037 // we might navigate away or commit to this document by firing load. 1038 IsInitialUncommitted, 1039 // An explicit navigation to `about:blank` occured. Load was fired or will 1040 // be soon. 1041 IsInitialCommitted, 1042 // document.open() was called on the initial document. 1043 IsInitialButExplicitlyOpened, 1044 // This document is not initial 1045 NeverInitial, 1046 }; 1047 1048 /** 1049 * Ask this document if the "is initial about:blank" flag is set, i.e. 1050 * it is the initial document in its window. 1051 * https://html.spec.whatwg.org/#is-initial-about:blank 1052 */ 1053 bool IsInitialDocument() const { 1054 return mInitialStatus == InitialStatus::IsInitialUncommitted || 1055 mInitialStatus == InitialStatus::IsInitialCommitted; 1056 } 1057 1058 /** 1059 * Ask this document whether it has ever been an initial document in its 1060 * window. 1061 */ 1062 bool IsEverInitialDocument() const { 1063 return mInitialStatus != InitialStatus::NeverInitial; 1064 } 1065 1066 /** 1067 * Ask this document whether it is the initial document in its window and 1068 * no navigation to about:blank has yet occured that would cause us to commit 1069 * to it. 1070 */ 1071 bool IsUncommittedInitialDocument() const { 1072 return mInitialStatus == InitialStatus::IsInitialUncommitted; 1073 } 1074 1075 InitialStatus GetInitialStatus() const { return mInitialStatus; } 1076 1077 /** 1078 * Tell this document whether it's the initial document in its window. 1079 * Should be called when creating the initial `about:blank`, when committing 1080 * to it, and from `document.open()`. 1081 */ 1082 void SetInitialStatus(Document::InitialStatus aStatus); 1083 1084 /** 1085 * Returns true if this is the initial document in its window 1086 * and we are currently committing to it. 1087 */ 1088 bool InitialAboutBlankLoadCompleting() const { 1089 return mInitialAboutBlankLoadCompleting; 1090 } 1091 1092 void BeginInitialAboutBlankLoadCompleting(nsIChannel* aChannel); 1093 1094 void EndInitialAboutBlankLoadCompleting() { 1095 mInitialAboutBlankLoadCompleting = false; 1096 } 1097 1098 void SetLoadedAsData(bool aLoadedAsData, bool aConsiderForMemoryReporting); 1099 1100 TimeStamp GetLoadingOrRestoredFromBFCacheTimeStamp() const { 1101 return mLoadingOrRestoredFromBFCacheTimeStamp; 1102 } 1103 void SetLoadingOrRestoredFromBFCacheTimeStampToNow() { 1104 mLoadingOrRestoredFromBFCacheTimeStamp = TimeStamp::Now(); 1105 } 1106 1107 /** 1108 * Normally we assert if a runnable labeled with one DocGroup touches data 1109 * from another DocGroup. Calling IgnoreDocGroupMismatches() on a document 1110 * means that we can touch that document from any DocGroup without asserting. 1111 */ 1112 void IgnoreDocGroupMismatches() { mIgnoreDocGroupMismatches = true; } 1113 1114 /** 1115 * Get the bidi options for this document. 1116 * @see nsBidiUtils.h 1117 */ 1118 uint32_t GetBidiOptions() const { return mBidiOptions; } 1119 1120 /** 1121 * Set the bidi options for this document. This just sets the bits; 1122 * callers are expected to take action as needed if they want this 1123 * change to actually change anything immediately. 1124 * @see nsBidiUtils.h 1125 */ 1126 void SetBidiOptions(uint32_t aBidiOptions) { mBidiOptions = aBidiOptions; } 1127 1128 /** 1129 * Returns true if the document holds a CSP 1130 * delivered through an HTTP Header. 1131 */ 1132 bool GetHasCSPDeliveredThroughHeader() { 1133 return mHasCSPDeliveredThroughHeader; 1134 } 1135 1136 /** 1137 * Return a promise which resolves to the content blocking events. 1138 */ 1139 using GetContentBlockingEventsPromise = MozPromise<uint32_t, bool, true>; 1140 [[nodiscard]] RefPtr<GetContentBlockingEventsPromise> 1141 GetContentBlockingEvents(); 1142 1143 /** 1144 * Get the sandbox flags for this document. 1145 * @see nsSandboxFlags.h for the possible flags 1146 */ 1147 uint32_t GetSandboxFlags() const { return mSandboxFlags; } 1148 1149 Maybe<nsILoadInfo::CrossOriginEmbedderPolicy> GetEmbedderPolicy() const { 1150 return mEmbedderPolicy; 1151 } 1152 1153 void SetEmbedderPolicy( 1154 const Maybe<nsILoadInfo::CrossOriginEmbedderPolicy>& aCOEP) { 1155 mEmbedderPolicy = aCOEP; 1156 } 1157 1158 /** 1159 * Get string representation of sandbox flags (null if no flags are set) 1160 */ 1161 void GetSandboxFlagsAsString(nsAString& aFlags); 1162 1163 /** 1164 * Set the sandbox flags for this document. 1165 * @see nsSandboxFlags.h for the possible flags 1166 */ 1167 void SetSandboxFlags(uint32_t sandboxFlags) { mSandboxFlags = sandboxFlags; } 1168 1169 /** 1170 * Called when the document was decoded as UTF-8 and decoder encountered no 1171 * errors. 1172 */ 1173 void EnableEncodingMenu() { mEncodingMenuDisabled = false; } 1174 1175 /** 1176 * Called to disable client access to cookies through the document.cookie API 1177 * from user JavaScript code. 1178 */ 1179 void DisableCookieAccess() { mDisableCookieAccess = true; } 1180 1181 bool CookieAccessDisabled() const { return mDisableCookieAccess; } 1182 1183 void SetLinkHandlingEnabled(bool aValue) { mLinksEnabled = aValue; } 1184 bool LinkHandlingEnabled() { return mLinksEnabled; } 1185 1186 /** 1187 * Set compatibility mode for this document 1188 */ 1189 void SetCompatibilityMode(nsCompatibility aMode); 1190 1191 /** 1192 * Called to disable client access to document.write() API from user 1193 * JavaScript code. 1194 */ 1195 void SetDocWriteDisabled(bool aDisabled) { mDisableDocWrite = aDisabled; } 1196 1197 /** 1198 * Whether a document.write() call is in progress. 1199 */ 1200 bool IsWriting() const { return mWriteLevel != uint32_t(0); } 1201 1202 /** 1203 * Access HTTP header data (this may also get set from other 1204 * sources, like HTML META tags). 1205 */ 1206 void GetHeaderData(nsAtom* aHeaderField, nsAString& aData) const; 1207 void SetHeaderData(nsAtom* aheaderField, const nsAString& aData); 1208 1209 /** 1210 * Set Early Hint data, moves the arrays into the function, leaving the 1211 * passed variables empty 1212 */ 1213 void SetEarlyHints(nsTArray<net::EarlyHintConnectArgs>&& aEarlyHints); 1214 const nsTArray<net::EarlyHintConnectArgs>& GetEarlyHints() const { 1215 return mEarlyHints; 1216 } 1217 1218 /** 1219 * Create a new presentation shell that will use aContext for its 1220 * presentation context (presentation contexts <b>must not</b> be 1221 * shared among multiple presentation shells). The caller of this 1222 * method is responsible for calling BeginObservingDocument() on the 1223 * presshell if the presshell should observe document mutations. 1224 */ 1225 MOZ_CAN_RUN_SCRIPT already_AddRefed<PresShell> CreatePresShell( 1226 nsPresContext* aContext, nsSubDocumentFrame* aEmbedderFrame); 1227 void DeletePresShell(); 1228 1229 PresShell* GetPresShell() const { 1230 return GetBFCacheEntry() ? nullptr : mPresShell; 1231 } 1232 1233 inline PresShell* GetObservingPresShell() const; 1234 1235 // Return whether the presshell for this document is safe to flush. 1236 bool IsSafeToFlush() const; 1237 1238 inline nsPresContext* GetPresContext() const; 1239 1240 bool HasShellOrBFCacheEntry() const { return mPresShell || mBFCacheEntry; } 1241 1242 // Instead using this method, what you probably want is 1243 // RemoveFromBFCacheSync() as we do in MessagePort and BroadcastChannel. 1244 void DisallowBFCaching(uint32_t aStatus = BFCacheStatus::NOT_ALLOWED); 1245 1246 bool IsBFCachingAllowed() const { return !mBFCacheDisallowed; } 1247 1248 // Accepts null to clear the BFCache entry too. 1249 void SetBFCacheEntry(nsIBFCacheEntry* aEntry); 1250 1251 nsIBFCacheEntry* GetBFCacheEntry() const { return mBFCacheEntry; } 1252 1253 // Removes this document from the BFCache, if it is cached, and returns 1254 // true if it was. 1255 bool RemoveFromBFCacheSync(); 1256 1257 /** 1258 * Return the parent document of this document. Will return null 1259 * unless this document is within a compound document and has a 1260 * parent. Note that this parent chain may cross chrome boundaries. 1261 */ 1262 Document* GetInProcessParentDocument() const { return mParentDocument; } 1263 1264 /** 1265 * Set the parent document of this document. 1266 */ 1267 void SetParentDocument(Document* aParent) { 1268 mParentDocument = aParent; 1269 if (aParent) { 1270 RecomputeResistFingerprinting(); 1271 mIgnoreDocGroupMismatches = aParent->mIgnoreDocGroupMismatches; 1272 } 1273 } 1274 1275 void SetCurrentContextPaint(const SVGContextPaint* aContextPaint) { 1276 mCurrentContextPaint = aContextPaint; 1277 } 1278 1279 const SVGContextPaint* GetCurrentContextPaint() const { 1280 return mCurrentContextPaint; 1281 } 1282 1283 /** 1284 * Set the sub document for aContent to aSubDoc. 1285 */ 1286 nsresult SetSubDocumentFor(Element* aContent, Document* aSubDoc); 1287 1288 /** 1289 * Get the sub document for aContent 1290 */ 1291 Document* GetSubDocumentFor(nsIContent* aContent) const; 1292 1293 /** 1294 * Get the content node for which this document is a sub document. 1295 */ 1296 Element* GetEmbedderElement() const; 1297 1298 /** 1299 * Return the doctype for this document. 1300 */ 1301 DocumentType* GetDoctype() const; 1302 1303 /** 1304 * Return the root element for this document. 1305 */ 1306 Element* GetRootElement() const; 1307 1308 Selection* GetSelection(ErrorResult& aRv); 1309 1310 void MakeBrowsingContextNonSynthetic(); 1311 nsresult HasStorageAccessSync(bool& aHasStorageAccess); 1312 already_AddRefed<Promise> HasStorageAccess(ErrorResult& aRv); 1313 1314 StorageAccessAPIHelper::PerformPermissionGrant CreatePermissionGrantPromise( 1315 nsPIDOMWindowInner* aInnerWindow, nsIPrincipal* aPrincipal, 1316 bool aHasUserInteraction, bool aRequireUserInteraction, 1317 const Maybe<nsCString>& aTopLevelBaseDomain, bool aFrameOnly); 1318 1319 already_AddRefed<Promise> RequestStorageAccess(ErrorResult& aRv); 1320 1321 already_AddRefed<Promise> RequestStorageAccessForOrigin( 1322 const nsAString& aThirdPartyOrigin, const bool aRequireUserInteraction, 1323 ErrorResult& aRv); 1324 1325 already_AddRefed<Promise> RequestStorageAccessUnderSite( 1326 const nsAString& aSerializedSite, ErrorResult& aRv); 1327 already_AddRefed<Promise> CompleteStorageAccessRequestFromSite( 1328 const nsAString& aSerializedOrigin, ErrorResult& aRv); 1329 1330 bool UseRegularPrincipal() const; 1331 1332 /** 1333 * Gets the event target to dispatch key events to if there is no focused 1334 * content in the document. 1335 */ 1336 virtual Element* GetUnfocusedKeyEventTarget(); 1337 1338 /** 1339 * Retrieve information about the viewport as a data structure. 1340 * This will return information in the viewport META data section 1341 * of the document. This can be used in lieu of ProcessViewportInfo(), 1342 * which places the viewport information in the document header instead 1343 * of returning it directly. 1344 * 1345 * @param aDisplaySize size of the on-screen display area for this 1346 * document, in device pixels. 1347 * 1348 * NOTE: If the site is optimized for mobile (via the doctype), this 1349 * will return viewport information that specifies default information. 1350 */ 1351 nsViewportInfo GetViewportInfo(const ScreenIntSize& aDisplaySize); 1352 1353 void SetMetaViewportData(UniquePtr<ViewportMetaData> aData); 1354 1355 // Returns a ViewportMetaData for this document. 1356 ViewportMetaData GetViewportMetaData() const; 1357 1358 /** 1359 * True iff this doc will ignore manual character encoding overrides. 1360 */ 1361 virtual bool WillIgnoreCharsetOverride() { return true; } 1362 1363 /** 1364 * Return whether the document was created by a srcdoc iframe. 1365 */ 1366 bool IsSrcdocDocument() const { return mIsSrcdocDocument; } 1367 1368 /** 1369 * Sets whether the document was created by a srcdoc iframe. 1370 */ 1371 void SetIsSrcdocDocument(bool aIsSrcdocDocument) { 1372 mIsSrcdocDocument = aIsSrcdocDocument; 1373 } 1374 1375 /* 1376 * Gets the srcdoc string from within the channel (assuming both exist). 1377 * Returns a void string if this isn't a srcdoc document or if 1378 * the channel has not been set. 1379 */ 1380 nsresult GetSrcdocData(nsAString& aSrcdocData); 1381 1382 already_AddRefed<AnonymousContent> InsertAnonymousContent(ErrorResult&); 1383 void RemoveAnonymousContent(AnonymousContent&); 1384 nsTArray<RefPtr<AnonymousContent>>& GetAnonymousContents() { 1385 return mAnonymousContents; 1386 } 1387 Element* GetCustomContentContainer() const { return mCustomContentContainer; } 1388 1389 private: 1390 void CreateCustomContentContainerIfNeeded(); 1391 void RemoveCustomContentContainer(); 1392 1393 public: 1394 TimeStamp GetPageUnloadingEventTimeStamp() const { 1395 if (!mParentDocument) { 1396 return mPageUnloadingEventTimeStamp; 1397 } 1398 1399 TimeStamp parentTimeStamp( 1400 mParentDocument->GetPageUnloadingEventTimeStamp()); 1401 if (parentTimeStamp.IsNull()) { 1402 return mPageUnloadingEventTimeStamp; 1403 } 1404 1405 if (!mPageUnloadingEventTimeStamp || 1406 parentTimeStamp < mPageUnloadingEventTimeStamp) { 1407 return parentTimeStamp; 1408 } 1409 1410 return mPageUnloadingEventTimeStamp; 1411 } 1412 1413 void NotifyLayerManagerRecreated(); 1414 1415 // Add an element to the list of elements that need their mapped attributes 1416 // resolved to a declaration block. 1417 // 1418 // These are weak pointers, manually unschedule them when an element is 1419 // removed from the tree. 1420 void ScheduleForPresAttrEvaluation(Element* aElement); 1421 1422 // Un-schedule an element scheduled by ScheduleForPresAttrEvaluation, 1423 // generally when it's unbound from the tree. 1424 void UnscheduleForPresAttrEvaluation(Element* aElement); 1425 1426 // Resolve all presentational attributes scheduled in 1427 // ScheduleForPresAttrEvaluation 1428 void ResolveScheduledPresAttrs() { 1429 if (mLazyPresElements.IsEmpty()) { 1430 return; 1431 } 1432 DoResolveScheduledPresAttrs(); 1433 } 1434 1435 Maybe<ClientInfo> GetClientInfo() const; 1436 Maybe<ClientState> GetClientState() const; 1437 Maybe<ServiceWorkerDescriptor> GetController() const; 1438 1439 // Given a node, get a weak reference to it and append that reference to 1440 // mBlockedNodesByClassifier. Can be used later on to look up a node in it. 1441 // (e.g., by the UI) 1442 // / 1443 void AddBlockedNodeByClassifier(nsINode* aNode) { 1444 if (aNode) { 1445 mBlockedNodesByClassifier.AppendElement(do_GetWeakReference(aNode)); 1446 } 1447 } 1448 1449 // Returns the size of the mBlockedNodesByClassifier array. 1450 // 1451 // This array contains nodes that have been blocked to prevent user tracking, 1452 // fingerprinting, cryptomining, etc. They most likely have had their 1453 // nsIChannel canceled by the URL classifier (Safebrowsing). 1454 // 1455 // A script can subsequently use GetBlockedNodesByClassifier() 1456 // to get a list of references to these nodes. 1457 // 1458 // Note: 1459 // This expresses how many tracking nodes have been blocked for this document 1460 // since its beginning, not how many of them are still around in the DOM tree. 1461 // Weak references to blocked nodes are added in the mBlockedNodesByClassifier 1462 // array but they are not removed when those nodes are removed from the tree 1463 // or even garbage collected. 1464 size_t BlockedNodeByClassifierCount() const { 1465 return mBlockedNodesByClassifier.Length(); 1466 } 1467 1468 // Returns strong references to mBlockedNodesByClassifier. (Document.h) 1469 // This array contains nodes that have been blocked to prevent 1470 // user tracking. They most likely have had their nsIChannel 1471 // canceled by the URL classifier (Safebrowsing). 1472 already_AddRefed<nsSimpleContentList> BlockedNodesByClassifier() const; 1473 1474 // Helper method that returns true if the document has storage-access sandbox 1475 // flag. 1476 bool StorageAccessSandboxed() const; 1477 1478 // Helper method that returns true if storage access API is enabled and 1479 // the passed flag has storage-access sandbox flag. 1480 static bool StorageAccessSandboxed(uint32_t aSandboxFlags); 1481 1482 // Returns the cookie jar settings for this and sub contexts. 1483 nsICookieJarSettings* CookieJarSettings(); 1484 1485 // Set the cookieJarSettings to the document. 1486 void SetCookieJarSettings(nsICookieJarSettings* aCookieJarSettings) { 1487 MOZ_ASSERT(aCookieJarSettings); 1488 mCookieJarSettings = aCookieJarSettings; 1489 } 1490 1491 // Returns whether this document is using unpartitioned cookies 1492 bool UsingStorageAccess(); 1493 1494 // Returns whether the document is on the 3PCB exception list. 1495 bool IsOn3PCBExceptionList() const; 1496 1497 // Returns whether the storage access permission of the document is granted by 1498 // the allow list. 1499 bool HasStorageAccessPermissionGrantedByAllowList(); 1500 1501 // Increments the document generation. 1502 inline void Changed() { ++mGeneration; } 1503 1504 // Returns the current generation. 1505 inline int32_t GetGeneration() const { return mGeneration; } 1506 1507 // Adds cached sizes values to aSizes if there's any 1508 // cached value and if the document generation hasn't 1509 // changed since the cache was created. 1510 // Returns true if sizes were added. 1511 bool GetCachedSizes(nsTabSizes* aSizes); 1512 1513 // Sets the cache sizes for the current generation. 1514 void SetCachedSizes(nsTabSizes* aSizes); 1515 1516 /** 1517 * Should be called when an element's editable changes as a result of 1518 * changing its contentEditable attribute/property. 1519 * 1520 * The change should be +1 if the contentEditable attribute/property was 1521 * changed to true, -1 if it was changed to false. 1522 */ 1523 void ChangeContentEditableCount(Element*, int32_t aChange); 1524 MOZ_CAN_RUN_SCRIPT void DeferredContentEditableCountChange(Element*); 1525 1526 enum class EditingState : int8_t { 1527 eTearingDown = -2, 1528 eSettingUp = -1, 1529 eOff = 0, 1530 eDesignMode, 1531 eContentEditable 1532 }; 1533 1534 /** 1535 * Returns the editing state of the document (not editable, contentEditable or 1536 * designMode). 1537 */ 1538 EditingState GetEditingState() const { return mEditingState; } 1539 1540 /** 1541 * Returns whether the document is editable. 1542 */ 1543 bool IsEditingOn() const { 1544 return GetEditingState() == EditingState::eDesignMode || 1545 GetEditingState() == EditingState::eContentEditable; 1546 } 1547 1548 class MOZ_STACK_CLASS nsAutoEditingState { 1549 public: 1550 nsAutoEditingState(Document* aDoc, EditingState aState) 1551 : mDoc(aDoc), mSavedState(aDoc->mEditingState) { 1552 aDoc->mEditingState = aState; 1553 } 1554 ~nsAutoEditingState() { mDoc->mEditingState = mSavedState; } 1555 1556 private: 1557 RefPtr<Document> mDoc; 1558 EditingState mSavedState; 1559 }; 1560 friend class nsAutoEditingState; 1561 1562 /** 1563 * Set the editing state of the document. Don't use this if you want 1564 * to enable/disable editing, call EditingStateChanged() or 1565 * SetDesignMode(). 1566 */ 1567 void SetEditingState(EditingState aState) { mEditingState = aState; } 1568 1569 /** 1570 * Called when this Document's editor is destroyed. 1571 */ 1572 void TearingDownEditor(); 1573 1574 void SetKeyPressEventModel(uint16_t aKeyPressEventModel); 1575 1576 // Gets the next form number. 1577 // 1578 // Used by nsContentUtils::GenerateStateKey to get a unique number for each 1579 // parser inserted form element. 1580 int32_t GetNextFormNumber() { return mNextFormNumber++; } 1581 1582 // Gets the next form control number. 1583 // 1584 // Used by nsContentUtils::GenerateStateKey to get a unique number for each 1585 // parser inserted form control element. 1586 int32_t GetNextControlNumber() { return mNextControlNumber++; } 1587 1588 PreloadService& Preloads() { return mPreloadService; } 1589 1590 bool HasThirdPartyChannel(); 1591 1592 bool ShouldIncludeInTelemetry() const; 1593 1594 void AddMediaElementWithMSE(); 1595 void RemoveMediaElementWithMSE(); 1596 1597 void DoNotifyPossibleTitleChange(); 1598 1599 void InitFeaturePolicy(const Variant<Nothing, FeaturePolicyInfo, Element*>& 1600 aContainerFeaturePolicy); 1601 nsresult InitFeaturePolicy(nsIChannel* aChannel); 1602 1603 void EnsureNotEnteringAndExitFullscreen(); 1604 1605 protected: 1606 friend class nsUnblockOnloadEvent; 1607 1608 nsresult InitPolicyContainer(nsIChannel* aChannel); 1609 nsresult InitCSP(nsIChannel* aChannel); 1610 nsresult InitIntegrityPolicy(nsIChannel* aChannel); 1611 nsresult InitCOEP(nsIChannel* aChannel); 1612 nsresult InitDocPolicy(nsIChannel* aChannel); 1613 nsresult InitTLSCertificateBinding(nsIChannel* aChannel); 1614 1615 nsresult InitReferrerInfo(nsIChannel* aChannel); 1616 1617 void PostUnblockOnloadEvent(); 1618 1619 void DoUnblockOnload(); 1620 1621 void DoResolveScheduledPresAttrs(); 1622 1623 void RetrieveRelevantHeaders(nsIChannel* aChannel); 1624 1625 void TryChannelCharset(nsIChannel* aChannel, int32_t& aCharsetSource, 1626 NotNull<const Encoding*>& aEncoding, 1627 nsHtml5TreeOpExecutor* aExecutor); 1628 1629 MOZ_CAN_RUN_SCRIPT void DispatchContentLoadedEvents(); 1630 1631 // TODO: Convert this to MOZ_CAN_RUN_SCRIPT (bug 1415230) 1632 MOZ_CAN_RUN_SCRIPT_BOUNDARY void DispatchPageTransition( 1633 EventTarget* aDispatchTarget, const nsAString& aType, bool aInFrameSwap, 1634 bool aPersisted, bool aOnlySystemGroup); 1635 1636 // Call this before the document does something that will unbind all content. 1637 // That will stop us from doing a lot of work as each element is removed. 1638 void WillRemoveRoot(); 1639 1640 Element* GetRootElementInternal() const; 1641 1642 void SetPageUnloadingEventTimeStamp() { 1643 MOZ_ASSERT(!mPageUnloadingEventTimeStamp); 1644 mPageUnloadingEventTimeStamp = TimeStamp::NowLoRes(); 1645 } 1646 1647 void CleanUnloadEventsTimeStamp() { 1648 MOZ_ASSERT(mPageUnloadingEventTimeStamp); 1649 mPageUnloadingEventTimeStamp = TimeStamp(); 1650 } 1651 1652 /** 1653 * Clears any Servo element data stored on Elements in the document. 1654 */ 1655 void ClearStaleServoData(); 1656 1657 /** 1658 * Do the tree-disconnection that ResetToURI and document.open need to do. 1659 */ 1660 void DisconnectNodeTree(); 1661 1662 /** 1663 * MaybeDispatchCheckKeyPressEventModelEvent() dispatches 1664 * "CheckKeyPressEventModel" event to check whether we should dispatch 1665 * keypress events in confluent model or split model. This should be 1666 * called only when mEditingState is changed to eDesignMode or 1667 * eConentEditable at first time. 1668 */ 1669 void MaybeDispatchCheckKeyPressEventModelEvent(); 1670 1671 /* Midas implementation */ 1672 nsCommandManager* GetMidasCommandManager(); 1673 1674 MOZ_CAN_RUN_SCRIPT_BOUNDARY nsresult TurnEditingOff(); 1675 1676 // MOZ_CAN_RUN_SCRIPT_BOUNDARY because this is called from all sorts 1677 // of places, and I'm pretty sure the exact ExecCommand call it 1678 // makes cannot actually run script. 1679 MOZ_CAN_RUN_SCRIPT_BOUNDARY nsresult EditingStateChanged(); 1680 1681 void MaybeEditingStateChanged(); 1682 1683 public: 1684 // Get the root <html> element, or return null if there isn't one (e.g. 1685 // if the root isn't <html>) 1686 Element* GetHtmlElement() const; 1687 // Returns the first child of GetHtmlContent which has the given tag and is 1688 // not aContentToIgnore, or nullptr if that doesn't exist. 1689 Element* GetHtmlChildElement( 1690 nsAtom* aTag, const nsIContent* aContentToIgnore = nullptr) const; 1691 // Get the canonical <body> element, or return null if there isn't one (e.g. 1692 // if the root isn't <html> or if the <body> isn't there) 1693 HTMLBodyElement* GetBodyElement( 1694 const nsIContent* aContentToIgnore = nullptr) const; 1695 // Get the canonical <head> element, or return null if there isn't one (e.g. 1696 // if the root isn't <html> or if the <head> isn't there) 1697 Element* GetHeadElement() const { 1698 return GetHtmlChildElement(nsGkAtoms::head); 1699 } 1700 // Get the "body" in the sense of document.body: The first <body> or 1701 // <frameset> that's a child of a root <html> 1702 nsGenericHTMLElement* GetBody() const; 1703 // Set the "body" in the sense of document.body. 1704 void SetBody(nsGenericHTMLElement* aBody, ErrorResult& rv); 1705 // Get the "head" element in the sense of document.head. 1706 HTMLSharedElement* GetHead() const; 1707 1708 ServoStyleSet* StyleSetForPresShell() const { 1709 MOZ_ASSERT(!!mStyleSet.get()); 1710 return mStyleSet.get(); 1711 } 1712 1713 inline ServoStyleSet& EnsureStyleSet() const; 1714 1715 // ShadowRoot has APIs that can change styles. This notifies the shell that 1716 // stlyes applicable in the shadow tree have potentially changed. 1717 void RecordShadowStyleChange(ShadowRoot&); 1718 1719 // Needs to be called any time the applicable style can has changed, in order 1720 // to schedule a style flush and setup all the relevant state. 1721 // 1722 // If we know the stylesheet change applies only to a shadow tree we can avoid 1723 // some work (like updating the font-face-set / counter-styles / etc, as those 1724 // are global). 1725 void ApplicableStylesChanged(bool aKnownInShadowTree = false); 1726 1727 // Whether we filled the style set with any style sheet. Only meant to be used 1728 // from DocumentOrShadowRoot::Traverse. 1729 bool StyleSetFilled() const { return mStyleSetFilled; } 1730 1731 /** 1732 * Accessors to the collection of stylesheets owned by this document. 1733 * Style sheets are ordered, most significant last. 1734 */ 1735 1736 void InsertSheetAt(size_t aIndex, StyleSheet&); 1737 1738 /** 1739 * Add a stylesheet to the document 1740 * 1741 * TODO(emilio): This is only used by parts of editor that are no longer in 1742 * use by m-c or c-c, so remove. 1743 */ 1744 void AddStyleSheet(StyleSheet* aSheet) { 1745 MOZ_ASSERT(aSheet); 1746 InsertSheetAt(SheetCount(), *aSheet); 1747 } 1748 1749 /** 1750 * Notify the document that the applicable state of the sheet changed 1751 * and that observers should be notified and style sets updated 1752 */ 1753 void StyleSheetApplicableStateChanged(StyleSheet&); 1754 void PostStyleSheetApplicableStateChangeEvent(StyleSheet&); 1755 void PostStyleSheetRemovedEvent(StyleSheet&); 1756 void PostCustomPropertyRegistered(const dom::PropertyDefinition&); 1757 1758 enum additionalSheetType { 1759 eAgentSheet, 1760 eUserSheet, 1761 eAuthorSheet, 1762 AdditionalSheetTypeCount 1763 }; 1764 1765 nsresult LoadAdditionalStyleSheet(additionalSheetType aType, 1766 nsIURI* aSheetURI); 1767 nsresult AddAdditionalStyleSheet(additionalSheetType aType, 1768 StyleSheet* aSheet); 1769 void RemoveAdditionalStyleSheet(additionalSheetType aType, nsIURI* sheetURI); 1770 1771 StyleSheet* GetFirstAdditionalAuthorSheet() { 1772 return mAdditionalSheets[eAuthorSheet].SafeElementAt(0); 1773 } 1774 1775 /** 1776 * Returns the index that aSheet should be inserted at to maintain document 1777 * ordering. 1778 */ 1779 size_t FindDocStyleSheetInsertionPoint(const StyleSheet& aSheet); 1780 1781 /** 1782 * Get this document's CSSLoader. This is guaranteed not to return null 1783 * during normal loads but will return null when loading as data if 1784 * EnsureCSSLoader() or EnsureStyleImageLoader() hasn't been 1785 * called previously. 1786 */ 1787 css::Loader* GetExistingCSSLoader() const { return mCSSLoader; } 1788 1789 /** 1790 * Get this document's CSS loader. If it doesn't already exist, which 1791 * is possible in the loaded as data case, this first creates the CSS 1792 * loader and style image loader and then returns the former. 1793 */ 1794 css::Loader& EnsureCSSLoader() { 1795 if (!mCSSLoader) { 1796 CreateCSSAndStyleImageLoaders(); 1797 } 1798 return *mCSSLoader; 1799 } 1800 1801 /** 1802 * Get this document's StyleImageLoader. This is guaranteed not to return null 1803 * during normal loads but will return null when loading as data with 1804 * styling disabled. 1805 */ 1806 css::ImageLoader* GetExistingStyleImageLoader() const { 1807 return mStyleImageLoader; 1808 } 1809 1810 /** 1811 * Get this document's style image loader. If it doesn't already exist, 1812 * which is possible in the loaded as data case, this first creates the CSS 1813 * loader and style image loader and then returns the latter. 1814 */ 1815 css::ImageLoader& EnsureStyleImageLoader() { 1816 if (!mStyleImageLoader) { 1817 CreateCSSAndStyleImageLoaders(); 1818 } 1819 return *mStyleImageLoader; 1820 } 1821 1822 private: 1823 void CreateCSSAndStyleImageLoaders(bool aLazy = true); 1824 1825 public: 1826 /** 1827 * Get the channel that was passed to StartDocumentLoad or Reset for this 1828 * document. Note that this may be null in some cases (eg if 1829 * StartDocumentLoad or Reset were never called) 1830 */ 1831 nsIChannel* GetChannel() const { return mChannel; } 1832 1833 /** 1834 * Get this document's attribute stylesheet. May return null if 1835 * there isn't one. 1836 */ 1837 AttributeStyles* GetAttributeStyles() const { return mAttributeStyles.get(); } 1838 1839 virtual void SetScriptGlobalObject(nsIScriptGlobalObject* aGlobalObject); 1840 1841 /** 1842 * Get/set the object from which the context for the event/script handling can 1843 * be got. Normally GetScriptHandlingObject() returns the same object as 1844 * GetScriptGlobalObject(), but if the document is loaded as data, 1845 * non-null may be returned, even if GetScriptGlobalObject() returns null. 1846 * aHasHadScriptHandlingObject is set true if document has had the object 1847 * for event/script handling. Do not process any events/script if the method 1848 * returns null, but aHasHadScriptHandlingObject is true. 1849 */ 1850 nsIScriptGlobalObject* GetScriptHandlingObject( 1851 bool& aHasHadScriptHandlingObject) const { 1852 aHasHadScriptHandlingObject = mHasHadScriptHandlingObject; 1853 return mScriptGlobalObject ? mScriptGlobalObject.get() 1854 : GetScriptHandlingObjectInternal(); 1855 } 1856 void SetScriptHandlingObject(nsIScriptGlobalObject* aScriptObject); 1857 1858 /** 1859 * Get the object that is used as the scope for all of the content 1860 * wrappers whose owner document is this document. Unlike the script global 1861 * object, this will only return null when the global object for this 1862 * document is truly gone. Use this object when you're trying to find a 1863 * content wrapper in XPConnect. 1864 */ 1865 nsIGlobalObject* GetScopeObject() const; 1866 void SetScopeObject(nsIGlobalObject* aGlobal); 1867 1868 /** 1869 * Return the window containing the document (the outer window). 1870 */ 1871 nsPIDOMWindowOuter* GetWindow() const { 1872 return mWindow ? mWindow->GetOuterWindow() : GetWindowInternal(); 1873 } 1874 1875 bool IsInBackgroundWindow() const { 1876 auto* outer = mWindow ? mWindow->GetOuterWindow() : nullptr; 1877 return outer && outer->IsBackground(); 1878 } 1879 1880 /** 1881 * Return the inner window used as the script compilation scope for 1882 * this document. If you're not absolutely sure you need this, use 1883 * GetWindow(). 1884 */ 1885 nsPIDOMWindowInner* GetInnerWindow() const { 1886 return mRemovedFromDocShell ? nullptr : mWindow; 1887 } 1888 1889 /** 1890 * Return the outer window ID. 1891 */ 1892 uint64_t OuterWindowID() const { 1893 nsPIDOMWindowOuter* window = GetWindow(); 1894 return window ? window->WindowID() : 0; 1895 } 1896 1897 /** 1898 * Return the inner window ID. 1899 */ 1900 uint64_t InnerWindowID() const { 1901 nsPIDOMWindowInner* window = GetInnerWindow(); 1902 return window ? window->WindowID() : 0; 1903 } 1904 1905 /** 1906 * Return WindowGlobalChild that is associated with the inner window. 1907 */ 1908 WindowGlobalChild* GetWindowGlobalChild() { 1909 return GetInnerWindow() ? GetInnerWindow()->GetWindowGlobalChild() 1910 : nullptr; 1911 } 1912 1913 /** 1914 * Return WindowContext associated with the inner window. 1915 */ 1916 WindowContext* GetWindowContext() const { 1917 return GetInnerWindow() ? GetInnerWindow()->GetWindowContext() : nullptr; 1918 } 1919 1920 bool IsTopLevelWindowInactive() const { 1921 return mState.HasState(DocumentState::WINDOW_INACTIVE); 1922 } 1923 1924 /** 1925 * Get the script loader for this document. Non-null for normal loads 1926 * and null when loaded as data. 1927 */ 1928 dom::ScriptLoader* GetScriptLoader() { return mScriptLoader; } 1929 1930 /** 1931 * Add/Remove an element to the document's id and name hashes 1932 */ 1933 void AddToIdTable(Element* aElement, nsAtom* aId); 1934 void RemoveFromIdTable(Element* aElement, nsAtom* aId); 1935 void AddToNameTable(Element* aElement, nsAtom* aName); 1936 void RemoveFromNameTable(Element* aElement, nsAtom* aName); 1937 void AddToDocumentNameTable(nsGenericHTMLElement* aElement, nsAtom* aName); 1938 void RemoveFromDocumentNameTable(nsGenericHTMLElement* aElement, 1939 nsAtom* aName); 1940 1941 /** 1942 * Returns all elements in the top layer in the insertion order. 1943 */ 1944 nsTArray<Element*> GetTopLayer() const; 1945 1946 bool TopLayerContains(Element&) const; 1947 1948 // Do the "fullscreen element ready check" from the fullscreen spec. 1949 // It returns true if the given element is allowed to go into fullscreen. 1950 // It is responsive to dispatch "fullscreenerror" event when necessary. 1951 bool FullscreenElementReadyCheck(FullscreenRequest&); 1952 1953 /** 1954 * When this is called on content process, this asynchronously requests that 1955 * the document make aElement the fullscreen element, and move into fullscreen 1956 * mode. The current fullscreen element (if any) is pushed onto the top layer, 1957 * and it can be returned to fullscreen status by calling 1958 * RestorePreviousFullscreenState(). 1959 * If on chrome process, this is synchronously. 1960 * 1961 * Note that requesting fullscreen in a document also makes the element which 1962 * contains this document in this document's parent document fullscreen. i.e. 1963 * the <iframe> or <browser> that contains this document is also mode 1964 * fullscreen. This happens recursively in all ancestor documents. 1965 */ 1966 void RequestFullscreen(UniquePtr<FullscreenRequest> aRequest, 1967 bool aApplyFullscreenDirectly = false); 1968 1969 private: 1970 void RequestFullscreenInContentProcess(UniquePtr<FullscreenRequest> aRequest, 1971 bool aApplyFullscreenDirectly); 1972 void RequestFullscreenInParentProcess(UniquePtr<FullscreenRequest> aRequest, 1973 bool aApplyFullscreenDirectly); 1974 1975 // Pushes aElement onto the top layer 1976 void TopLayerPush(Element&); 1977 1978 // Removes the topmost element for which aPredicate returns true from the top 1979 // layer. The removed element, if any, is returned. 1980 Element* TopLayerPop(FunctionRef<bool(Element*)> aPredicate); 1981 1982 // Removes the given element from the top layer. The removed element, if any, 1983 // is returned. 1984 Element* TopLayerPop(Element&); 1985 1986 MOZ_CAN_RUN_SCRIPT bool TryAutoFocusCandidate(Element& aElement); 1987 1988 public: 1989 void SetAncestorOriginsList(nsTArray<nsString>&& aAncestorOriginsList); 1990 Span<const nsString> GetAncestorOriginsList() const; 1991 // https://html.spec.whatwg.org/#concept-location-ancestor-origins-list 1992 already_AddRefed<DOMStringList> AncestorOrigins() const; 1993 1994 // Removes all the elements with fullscreen flag set from the top layer, and 1995 // clears their fullscreen flag. 1996 void CleanupFullscreenState(); 1997 1998 // Pops the fullscreen element from the top layer and clears its 1999 // fullscreen flag. Returns whether there was any fullscreen element. 2000 enum class UpdateViewport : bool { No, Yes }; 2001 bool PopFullscreenElement(UpdateViewport = UpdateViewport::Yes); 2002 2003 // Pushes the given element into the top of top layer and set fullscreen 2004 // flag. 2005 void SetFullscreenElement(Element&); 2006 2007 // Whether we has pending fullscreen request. 2008 bool HasPendingFullscreenRequests(); 2009 2010 void AddPendingFullscreenEvent(UniquePtr<PendingFullscreenEvent>); 2011 2012 MOZ_CAN_RUN_SCRIPT void RunFullscreenSteps(); 2013 2014 /** 2015 * When Esc key is pressed, cancel the dialog element if the document is 2016 * blocked by the dialog or hide popover if popover is shown. 2017 */ 2018 MOZ_CAN_RUN_SCRIPT void HandleEscKey(); 2019 2020 /** 2021 * Process any active CloseWatchers in the document, such 2022 * as fullscreen elements, popovers, dialogs. 2023 */ 2024 MOZ_CAN_RUN_SCRIPT void ProcessCloseRequest(); 2025 2026 /** 2027 * When pointer events on the document occur, close the top-most 2028 * light-dismiss dialog as mLastDialogPointerdownTarget. 2029 */ 2030 MOZ_CAN_RUN_SCRIPT void HandleLightDismissOpenDialogs(WidgetEvent*); 2031 2032 void AddModalDialog(HTMLDialogElement&); 2033 void RemoveModalDialog(HTMLDialogElement&); 2034 void AddOpenDialog(HTMLDialogElement&); 2035 void RemoveOpenDialog(HTMLDialogElement&); 2036 bool HasOpenDialogs() const; 2037 HTMLDialogElement* GetTopMostOpenDialog(); 2038 bool DialogIsInOpenDialogsList(HTMLDialogElement&); 2039 2040 void SetLastDialogPointerdownTarget(HTMLDialogElement&); 2041 void ClearLastDialogPointerdownTarget() { 2042 mLastDialogPointerdownTarget = nullptr; 2043 } 2044 HTMLDialogElement* GetLastDialogPointerdownTarget(); 2045 2046 /** 2047 * Called when a frame in a child process has entered fullscreen or when a 2048 * fullscreen frame in a child process changes to another origin. 2049 * aFrameElement is the frame element which contains the child-process 2050 * fullscreen document. 2051 */ 2052 void RemoteFrameFullscreenChanged(Element* aFrameElement); 2053 2054 /** 2055 * Called when a frame in a remote child document has rolled back fullscreen 2056 * so that all its top layer are empty; we must continue the 2057 * rollback in this parent process' doc tree branch which is fullscreen. 2058 * Note that only one branch of the document tree can have its documents in 2059 * fullscreen state at one time. We're in inconsistent state if a 2060 * fullscreen document has a parent and that parent isn't fullscreen. We 2061 * preserve this property across process boundaries. 2062 */ 2063 void RemoteFrameFullscreenReverted(); 2064 2065 /** 2066 * Restores the previous fullscreen element to fullscreen status. If there 2067 * is no former fullscreen element, this exits fullscreen, moving the 2068 * top-level browser window out of fullscreen mode. 2069 */ 2070 void RestorePreviousFullscreenState(UniquePtr<FullscreenExit>); 2071 2072 /** 2073 * Returns true if this document is a fullscreen leaf document, i.e. it 2074 * is in fullscreen mode and has no fullscreen children. 2075 */ 2076 bool IsFullscreenLeaf(); 2077 2078 /** 2079 * Returns the document which is at the root of this document's branch 2080 * in the in-process document tree. Returns nullptr if the document isn't 2081 * fullscreen. 2082 */ 2083 Document* GetFullscreenRoot() const { return mFullscreenRoot; } 2084 2085 size_t CountFullscreenElements() const; 2086 2087 /** 2088 * Sets the fullscreen root to aRoot. This stores a weak reference to aRoot 2089 * in this document. 2090 */ 2091 void SetFullscreenRoot(Document* aRoot) { mFullscreenRoot = aRoot; } 2092 2093 /** 2094 * Synchronously cleans up the fullscreen state on the given document. 2095 * 2096 * Calling this without performing fullscreen transition could lead 2097 * to undesired effect (the transition happens after document state 2098 * flips), hence it should only be called either by nsGlobalWindow 2099 * when we have performed the transition, or when it is necessary to 2100 * clean up the state immediately. Otherwise, AsyncExitFullscreen() 2101 * should be called instead. 2102 * 2103 * aDocument must not be null. 2104 */ 2105 static void ExitFullscreenInDocTree(Document* aDocument); 2106 2107 /** 2108 * Ask the document to exit fullscreen state asynchronously. 2109 * 2110 * Different from ExitFullscreenInDocTree(), this allows the window 2111 * to perform fullscreen transition first if any. 2112 * 2113 * If aDocument is null, it will exit fullscreen from all documents 2114 * in all windows. 2115 */ 2116 static void AsyncExitFullscreen(Document* aDocument); 2117 2118 /** 2119 * Handles any pending fullscreen in aDocument or its subdocuments. 2120 * 2121 * Returns whether there is any fullscreen request handled. 2122 */ 2123 static bool HandlePendingFullscreenRequests(Document* aDocument); 2124 2125 /** 2126 * Clear pending fullscreen in aDocument. 2127 */ 2128 static void ClearPendingFullscreenRequests(Document* aDocument); 2129 2130 // ScreenOrientation related APIs 2131 2132 void ClearOrientationPendingPromise(); 2133 bool SetOrientationPendingPromise(Promise* aPromise); 2134 Promise* GetOrientationPendingPromise() const { 2135 return mOrientationPendingPromise; 2136 } 2137 2138 //---------------------------------------------------------------------- 2139 2140 // Document notification API's 2141 2142 /** 2143 * Add a new observer of document change notifications. Whenever 2144 * content is changed, appended, inserted or removed the observers are 2145 * informed. An observer that is already observing the document must 2146 * not be added without being removed first. 2147 */ 2148 void AddObserver(nsIDocumentObserver* aObserver); 2149 2150 /** 2151 * Remove an observer of document change notifications. This will 2152 * return false if the observer cannot be found. 2153 */ 2154 bool RemoveObserver(nsIDocumentObserver* aObserver); 2155 2156 // Observation hooks used to propagate notifications to document observers. 2157 // BeginUpdate must be called before any batch of modifications of the 2158 // content model or of style data, EndUpdate must be called afterward. 2159 // To make this easy and painless, use the mozAutoDocUpdate helper class. 2160 void BeginUpdate(); 2161 void EndUpdate(); 2162 uint32_t UpdateNestingLevel() { return mUpdateNestLevel; } 2163 2164 void BeginLoad(); 2165 virtual void EndLoad(); 2166 2167 enum ReadyState { 2168 READYSTATE_UNINITIALIZED = 0, 2169 READYSTATE_LOADING = 1, 2170 READYSTATE_INTERACTIVE = 3, 2171 READYSTATE_COMPLETE = 4 2172 }; 2173 // Set the readystate of the document. If aUpdateTimingInformation is true, 2174 // this will record relevant timestamps in the document's performance timing. 2175 // Some consumers (document.open is the only one right now, actually) don't 2176 // want to do that, though. 2177 void SetReadyStateInternal(ReadyState, bool aUpdateTimingInformation = true); 2178 ReadyState GetReadyStateEnum() { return mReadyState; } 2179 2180 void NotifyLoading(bool aNewParentIsLoading, const ReadyState& aCurrentState, 2181 ReadyState aNewState); 2182 2183 void NotifyAbortedLoad(); 2184 2185 // Notify that an element changed state. This must happen under a 2186 // scriptblocker but NOT within a begin/end update. 2187 void ElementStateChanged(Element*, ElementState); 2188 2189 // Update a set of document states that may have changed. 2190 // This should only be called by callers whose state is also reflected in the 2191 // implementation of Document::State. 2192 // 2193 // aNotify controls whether we notify our DocumentStatesChanged observers. 2194 void UpdateDocumentStates(DocumentState aMaybeChangedStates, bool aNotify); 2195 2196 void ResetDocumentDirection(); 2197 2198 // Observation hooks for style data to propagate notifications 2199 // to document observers 2200 void RuleChanged(StyleSheet&, css::Rule*, const StyleRuleChange&); 2201 void RuleAdded(StyleSheet&, css::Rule&); 2202 void RuleRemoved(StyleSheet&, css::Rule&); 2203 void SheetCloned(StyleSheet&) {} 2204 void ImportRuleLoaded(StyleSheet&); 2205 2206 /** 2207 * Flush notifications for this document and its parent documents 2208 * (since those may affect the layout of this one). 2209 */ 2210 void FlushPendingNotifications(FlushType aType); 2211 2212 /** 2213 * Another variant of the above FlushPendingNotifications. This function 2214 * takes a ChangesToFlush to specify whether throttled animations are flushed 2215 * or not. 2216 * If in doubt, use the above FlushPendingNotifications. 2217 */ 2218 MOZ_CAN_RUN_SCRIPT_BOUNDARY 2219 void FlushPendingNotifications(ChangesToFlush aFlush); 2220 2221 /** 2222 * Calls FlushPendingNotifications on any external resources this document 2223 * has. If this document has no external resources or is an external resource 2224 * itself this does nothing. This should only be called with 2225 * aType >= FlushType::Style. 2226 */ 2227 void FlushExternalResources(FlushType aType); 2228 2229 void AddWorkerDocumentListener(WorkerDocumentListener* aListener); 2230 void RemoveWorkerDocumentListener(WorkerDocumentListener* aListener); 2231 2232 // Triggers an update of <svg:use> element shadow trees. 2233 void UpdateSVGUseElementShadowTrees() { 2234 if (mSVGUseElementsNeedingShadowTreeUpdate.IsEmpty()) { 2235 return; 2236 } 2237 DoUpdateSVGUseElementShadowTrees(); 2238 } 2239 2240 /** 2241 * Only to be used inside Gecko, you can't really do anything with the 2242 * pointer outside Gecko anyway. 2243 */ 2244 nsNodeInfoManager* NodeInfoManager() const { return mNodeInfoManager; } 2245 2246 /** 2247 * Reset the document using the given channel and loadgroup. This works 2248 * like ResetToURI, but also sets the document's channel to aChannel. 2249 * The principal of the document will be set from the channel. 2250 */ 2251 virtual void Reset(nsIChannel* aChannel, nsILoadGroup* aLoadGroup); 2252 2253 /** 2254 * Reset this document to aURI, aLoadGroup, aPrincipal and 2255 * aPartitionedPrincipal. aURI must not be null. If aPrincipal is null, a 2256 * content principal based on aURI will be used. 2257 */ 2258 virtual void ResetToURI(nsIURI* aURI, nsILoadGroup* aLoadGroup, 2259 nsIPrincipal* aPrincipal, 2260 nsIPrincipal* aPartitionedPrincipal); 2261 2262 /** 2263 * Set the container (docshell) for this document. Virtual so that 2264 * docshell can call it. 2265 */ 2266 virtual void SetContainer(nsDocShell* aContainer); 2267 2268 /** 2269 * Get the container (docshell) for this document. 2270 */ 2271 nsISupports* GetContainer() const; 2272 2273 /** 2274 * Get the container's load context for this document. 2275 */ 2276 nsILoadContext* GetLoadContext() const; 2277 2278 /** 2279 * Get docshell the for this document. 2280 */ 2281 nsIDocShell* GetDocShell() const; 2282 2283 /** 2284 * Set and get XML declaration. If aVersion is null there is no declaration. 2285 * aStandalone takes values -1, 0 and 1 indicating respectively that there 2286 * was no standalone parameter in the declaration, that it was given as no, 2287 * or that it was given as yes. 2288 */ 2289 void SetXMLDeclaration(const char16_t* aVersion, const char16_t* aEncoding, 2290 const int32_t aStandalone); 2291 void GetXMLDeclaration(nsAString& aVersion, nsAString& aEncoding, 2292 nsAString& Standalone); 2293 2294 /** 2295 * Returns the bits for the color-scheme specified by the 2296 * <meta name="color-scheme">. 2297 */ 2298 uint8_t GetColorSchemeBits() const { return mColorSchemeBits; } 2299 2300 /** 2301 * Traverses the DOM and computes the supported color schemes as per 2302 * https://html.spec.whatwg.org/#meta-color-scheme 2303 */ 2304 void RecomputeColorScheme(); 2305 void AddColorSchemeMeta(HTMLMetaElement&); 2306 void RemoveColorSchemeMeta(HTMLMetaElement&); 2307 2308 /** 2309 * Returns true if this is what HTML 5 calls an "HTML document" (for example 2310 * regular HTML document with Content-Type "text/html", image documents and 2311 * media documents). Returns false for XHTML and any other documents parsed 2312 * by the XML parser. 2313 */ 2314 bool IsHTMLDocument() const { return mType == eHTML; } 2315 bool IsHTMLOrXHTML() const { return mType == eHTML || mType == eXHTML; } 2316 bool IsImageDocument() const { 2317 return MediaDocumentKind() == MediaDocumentKind::Image; 2318 } 2319 bool IsXMLDocument() const { return !IsHTMLDocument(); } 2320 bool IsSVGDocument() const { return mType == eSVG; } 2321 bool LoadsFullXULStyleSheetUpFront() { 2322 if (IsSVGDocument()) { 2323 return false; 2324 } 2325 return AllowXULXBL(); 2326 } 2327 2328 bool IsScriptEnabled() const; 2329 2330 /** 2331 * Returns true if this document was created from a nsXULPrototypeDocument. 2332 */ 2333 bool LoadedFromPrototype() const { return mPrototypeDocument; } 2334 2335 /* Returns true if we're currently in Android's PiP mode. */ 2336 bool InAndroidPipMode() const; 2337 2338 /** 2339 * Returns the prototype the document was created from, or null if it was not 2340 * created from a prototype. 2341 */ 2342 nsXULPrototypeDocument* GetPrototype() const { return mPrototypeDocument; } 2343 2344 bool IsTopLevelContentDocument() const { return mIsTopLevelContentDocument; } 2345 void SetIsTopLevelContentDocument(bool aIsTopLevelContentDocument) { 2346 mIsTopLevelContentDocument = aIsTopLevelContentDocument; 2347 } 2348 2349 bool IsContentDocument() const { return mIsContentDocument; } 2350 void SetIsContentDocument(bool aIsContentDocument) { 2351 mIsContentDocument = aIsContentDocument; 2352 } 2353 2354 void ProcessMETATag(HTMLMetaElement* aMetaElement); 2355 2356 void TerminateParserAndDisableScripts(); 2357 2358 /** 2359 * Create an element with the specified name, prefix and namespace ID. 2360 * Returns null if element name parsing failed. 2361 */ 2362 already_AddRefed<Element> CreateElem(const nsAString& aName, nsAtom* aPrefix, 2363 int32_t aNamespaceID, 2364 const nsAString* aIs = nullptr); 2365 2366 /** 2367 * Get the security info (i.e. SSL state etc) that the document got 2368 * from the channel/document that created the content of the 2369 * document. 2370 * 2371 * @see nsIChannel 2372 */ 2373 nsITransportSecurityInfo* GetSecurityInfo() { return mSecurityInfo; } 2374 2375 /** 2376 * Get the channel that failed to load and resulted in an error page, if it 2377 * exists. This is only relevant to error pages. 2378 */ 2379 nsIChannel* GetFailedChannel() const { return mFailedChannel; } 2380 2381 /** 2382 * This function checks if the document that is trying to access 2383 * GetNetErrorInfo is a trusted about net error page or not. 2384 */ 2385 static bool CallerIsTrustedAboutNetError(JSContext* aCx, JSObject* aObject); 2386 2387 /** 2388 * This function checks if the document that is trying to access 2389 * ReloadWithHttpsOnlyException is a trusted HTTPS only error page. 2390 */ 2391 static bool CallerIsTrustedAboutHttpsOnlyError(JSContext* aCx, 2392 JSObject* aObject); 2393 2394 /** 2395 * Get security info like error code for a failed channel. This 2396 * property is only exposed to about:neterror documents. 2397 */ 2398 void GetNetErrorInfo(mozilla::dom::NetErrorInfo& aInfo, ErrorResult& aRv); 2399 2400 /** 2401 * This function checks if the document that is trying to access 2402 * GetFailedCertSecurityInfo is a trusted cert error page or not. 2403 */ 2404 static bool CallerIsTrustedAboutCertError(JSContext* aCx, JSObject* aObject); 2405 2406 /** 2407 * This function checks if the caller has access to privileged chrome APIs 2408 * such as the storage access API and inAndroidPipMode. We only allow such 2409 * APIs to be called by system principal and the built-in webcompat addon. 2410 */ 2411 static bool CallerIsSystemPrincipalOrWebCompatAddon(JSContext* aCx, 2412 JSObject* aObject); 2413 2414 /** 2415 * Get the security info (i.e. certificate validity, errorCode, etc) for a 2416 * failed Channel. This property is only exposed for about:certerror 2417 * documents. 2418 */ 2419 void GetFailedCertSecurityInfo(mozilla::dom::FailedCertSecurityInfo& aInfo, 2420 ErrorResult& aRv); 2421 2422 /** 2423 * Set the channel that failed to load and resulted in an error page. 2424 * This is only relevant to error pages. 2425 */ 2426 void SetFailedChannel(nsIChannel* aChannel) { mFailedChannel = aChannel; } 2427 2428 /** 2429 * Returns the default namespace ID used for elements created in this 2430 * document. 2431 */ 2432 int32_t GetDefaultNamespaceID() const { return mDefaultElementType; } 2433 2434 void RemoveAllProperties(); 2435 void RemoveAllPropertiesFor(nsINode* aNode); 2436 2437 nsPropertyTable& PropertyTable() { return mPropertyTable; } 2438 2439 /** 2440 * Sets the ID used to identify this part of the multipart document 2441 */ 2442 void SetPartID(uint32_t aID) { mPartID = aID; } 2443 2444 /** 2445 * Return the ID used to identify this part of the multipart document 2446 */ 2447 uint32_t GetPartID() const { return mPartID; } 2448 2449 /** 2450 * Sanitize the document by resetting all input elements and forms that have 2451 * autocomplete=off to their default values. 2452 * TODO: Convert this to MOZ_CAN_RUN_SCRIPT (bug 1415230) 2453 */ 2454 MOZ_CAN_RUN_SCRIPT_BOUNDARY void Sanitize(); 2455 2456 /** 2457 * Enumerate all subdocuments. 2458 * The enumerator callback should return CallState::Continue to continue 2459 * enumerating, or CallState::Stop to stop. This will never get passed a null 2460 * aDocument. 2461 */ 2462 using SubDocEnumFunc = dom::ExternalResourceMap::SubDocEnumFunc; 2463 void EnumerateSubDocuments(SubDocEnumFunc aCallback); 2464 2465 /** 2466 * Collect all the descendant documents for which |aCalback| returns true. 2467 * The callback function must not mutate any state for the given document. 2468 * Note that, unlike EnumerateSubDocuments, this recurses into nested 2469 * subdocuments. 2470 */ 2471 using SubDocTestFunc = dom::ExternalResourceMap::SubDocTestFunc; 2472 enum class IncludeSubResources : bool { No, Yes }; 2473 void CollectDescendantDocuments(nsTArray<RefPtr<Document>>& aDescendants, 2474 IncludeSubResources, SubDocTestFunc) const; 2475 2476 /** 2477 * Check whether it is safe to cache the presentation of this document 2478 * and all of its subdocuments (depending on the 3rd param). This method 2479 * checks the following conditions recursively: 2480 * - Some document types, such as plugin documents, cannot be safely cached. 2481 * - If there are any pending requests, we don't allow the presentation 2482 * to be cached. Ideally these requests would be suspended and resumed, 2483 * but that is difficult in some cases, such as XMLHttpRequest. 2484 * - If there are any beforeunload or unload listeners, we must fire them 2485 * for correctness, but this likely puts the document into a state where 2486 * it would not function correctly if restored. 2487 * 2488 * |aNewRequest| should be the request for a new document which will 2489 * replace this document in the docshell. The new document's request 2490 * will be ignored when checking for active requests. If there is no 2491 * request associated with the new document, this parameter may be null. 2492 * 2493 * |aBFCacheCombo| is used as a bitmask to indicate what the status 2494 * combination is when we try to BFCache aNewRequest 2495 */ 2496 virtual bool CanSavePresentation(nsIRequest* aNewRequest, 2497 uint32_t& aBFCacheCombo, 2498 bool aIncludeSubdocuments, 2499 bool aAllowUnloadListeners = true); 2500 2501 /** 2502 * Pass principals if the correct ones are known when calling Init. That way 2503 * NodeInfoManager doesn't need to create a temporary null principal. 2504 */ 2505 virtual nsresult Init(nsIPrincipal* aPrincipal, 2506 nsIPrincipal* aPartitionedPrincipal); 2507 2508 /** 2509 * Notify the document that its associated DocumentViewer is being destroyed. 2510 * This releases circular references so that the document can go away. 2511 * Destroy() is only called on documents that have a content viewer. 2512 */ 2513 virtual void Destroy(); 2514 2515 // https://wicg.github.io/document-picture-in-picture/#close-on-destroy 2516 void CloseAnyAssociatedDocumentPiPWindows(); 2517 2518 /** 2519 * Notify the document that its associated DocumentViewer is no longer 2520 * the current viewer for the docshell. The document might still 2521 * be rendered in "zombie state" until the next document is ready. 2522 * The document should save form control state. 2523 */ 2524 void RemovedFromDocShell(); 2525 2526 /** 2527 * Get the layout history state that should be used to save and restore state 2528 * for nodes in this document. This may return null; if that happens state 2529 * saving and restoration is not possible. 2530 */ 2531 already_AddRefed<nsILayoutHistoryState> GetLayoutHistoryState() const; 2532 2533 /** 2534 * Methods that can be used to prevent onload firing while an event that 2535 * should block onload is posted. onload is guaranteed to not fire until 2536 * either all calls to BlockOnload() have been matched by calls to 2537 * UnblockOnload() or the load has been stopped altogether (by the user 2538 * pressing the Stop button, say). 2539 */ 2540 void BlockOnload(); 2541 /** 2542 * @param aFireSync whether to fire onload synchronously. If false, 2543 * onload will fire asynchronously after all onload blocks have been 2544 * removed. It will NOT fire from inside UnblockOnload. If true, 2545 * onload may fire from inside UnblockOnload. 2546 */ 2547 void UnblockOnload(bool aFireSync); 2548 2549 // Only BlockOnload should call this! 2550 void AsyncBlockOnload(); 2551 2552 void BlockDOMContentLoaded() { ++mBlockDOMContentLoaded; } 2553 2554 MOZ_CAN_RUN_SCRIPT_BOUNDARY void UnblockDOMContentLoaded(); 2555 2556 /** 2557 * Notification that the page has been shown, for documents which are loaded 2558 * into a DOM window. This corresponds to the completion of document load, 2559 * or to the page's presentation being restored into an existing DOM window. 2560 * This notification fires applicable DOM events to the content window. See 2561 * PageTransitionEvent.webidl for a description of the |aPersisted| 2562 * parameter. If aDispatchStartTarget is null, the pageshow event is 2563 * dispatched on the ScriptGlobalObject for this document, otherwise it's 2564 * dispatched on aDispatchStartTarget. If |aOnlySystemGroup| is true, the 2565 * event is only dispatched to listeners in the system group. 2566 * Note: if aDispatchStartTarget isn't null, the showing state of the 2567 * document won't be altered. 2568 */ 2569 virtual void OnPageShow(bool aPersisted, EventTarget* aDispatchStartTarget, 2570 bool aOnlySystemGroup = false); 2571 2572 /** 2573 * Notification that the page has been hidden, for documents which are loaded 2574 * into a DOM window. This corresponds to the unloading of the document, or 2575 * to the document's presentation being saved but removed from an existing 2576 * DOM window. This notification fires applicable DOM events to the content 2577 * window. See PageTransitionEvent.webidl for a description of the 2578 * |aPersisted| parameter. If aDispatchStartTarget is null, the pagehide 2579 * event is dispatched on the ScriptGlobalObject for this document, 2580 * otherwise it's dispatched on aDispatchStartTarget. If |aOnlySystemGroup| is 2581 * true, the event is only dispatched to listeners in the system group. 2582 * Note: if aDispatchStartTarget isn't null, the showing state of the 2583 * document won't be altered. 2584 */ 2585 void OnPageHide(bool aPersisted, EventTarget* aDispatchStartTarget, 2586 bool aOnlySystemGroup = false); 2587 2588 /* 2589 * We record the set of links in the document that are relevant to 2590 * style. 2591 */ 2592 /** 2593 * Notification that an element is a link that is relevant to style. 2594 */ 2595 void AddStyleRelevantLink(Link* aLink) { 2596 NS_ASSERTION(aLink, "Passing in a null link. Expect crashes RSN!"); 2597 #ifdef DEBUG 2598 NS_ASSERTION(!mStyledLinks.Contains(aLink), 2599 "Document already knows about this Link!"); 2600 mStyledLinksCleared = false; 2601 #endif 2602 mStyledLinks.Insert(aLink); 2603 } 2604 2605 /** 2606 * Notification that an element is a link and its URI might have been 2607 * changed or the element removed. If the element is still a link relevant 2608 * to style, then someone must ensure that AddStyleRelevantLink is 2609 * (eventually) called on it again. 2610 */ 2611 void ForgetLink(Link* aLink) { 2612 MOZ_ASSERT(aLink, "Passing in a null link. Expect crashes RSN!"); 2613 MOZ_ASSERT(mStyledLinks.Contains(aLink) || mStyledLinksCleared, 2614 "Document knows nothing about this Link!"); 2615 mStyledLinks.Remove(aLink); 2616 } 2617 2618 // Refreshes the hrefs of all the links in the document. 2619 void RefreshLinkHrefs(); 2620 2621 /** 2622 * Support for window.matchMedia() 2623 */ 2624 2625 already_AddRefed<MediaQueryList> MatchMedia(const nsACString& aMediaQueryList, 2626 CallerType aCallerType); 2627 2628 LinkedList<MediaQueryList>& MediaQueryLists() { return mDOMMediaQueryLists; } 2629 2630 using ContentIdentifiersForLCPType = 2631 nsTHashMap<NoMemMoveKey<nsPtrHashKey<const Element>>, 2632 AutoTArray<WeakPtr<PreloaderBase>, 1>>; 2633 2634 ContentIdentifiersForLCPType& ContentIdentifiersForLCP() { 2635 return mContentIdentifiersForLCP; 2636 } 2637 2638 /** 2639 * Get the compatibility mode for this document 2640 */ 2641 nsCompatibility GetCompatibilityMode() const { return mCompatMode; } 2642 2643 /** 2644 * Check whether we've ever fired a DOMTitleChanged event for this 2645 * document. 2646 */ 2647 bool HaveFiredDOMTitleChange() const { return mHaveFiredTitleChange; } 2648 2649 /** 2650 * Marks as not-going-to-be-collected for the given generation of 2651 * cycle collection. 2652 */ 2653 void MarkUncollectableForCCGeneration(uint32_t aGeneration) { 2654 mMarkedCCGeneration = aGeneration; 2655 } 2656 2657 /** 2658 * Gets the cycle collector generation this document is marked for. 2659 */ 2660 uint32_t GetMarkedCCGeneration() { return mMarkedCCGeneration; } 2661 2662 /** 2663 * Returns whether this document is cookie averse. See 2664 * https://html.spec.whatwg.org/multipage/dom.html#cookie-averse-document-object 2665 */ 2666 bool IsCookieAverse() const { 2667 // If we are a document that "has no browsing context." 2668 if (!GetInnerWindow()) { 2669 return true; 2670 } 2671 2672 // If we are a document "whose URL's scheme is not a network scheme." 2673 // NB: Explicitly allow file: URIs to store cookies. 2674 2675 return !NodePrincipal()->SchemeIs("http") && 2676 !NodePrincipal()->SchemeIs("https") && 2677 !NodePrincipal()->SchemeIs("file"); 2678 } 2679 2680 bool IsLoadedAsData() const { return mLoadedAsData; } 2681 2682 void SetAddedToMemoryReportAsDataDocument() { 2683 mAddedToMemoryReportingAsDataDocument = true; 2684 } 2685 2686 void UnregisterFromMemoryReportingForDataDocument(); 2687 2688 bool MayStartLayout() { return mMayStartLayout; } 2689 2690 void SetMayStartLayout(bool aMayStartLayout); 2691 2692 already_AddRefed<nsIDocumentEncoder> GetCachedEncoder(); 2693 2694 void SetCachedEncoder(already_AddRefed<nsIDocumentEncoder> aEncoder); 2695 2696 // In case of failure, the document really can't initialize the frame loader. 2697 nsresult InitializeFrameLoader(nsFrameLoader* aLoader); 2698 // In case of failure, the caller must handle the error, for example by 2699 // finalizing frame loader asynchronously. 2700 nsresult FinalizeFrameLoader(nsFrameLoader* aLoader, nsIRunnable* aFinalizer); 2701 // Removes the frame loader of aShell from the initialization list. 2702 void TryCancelFrameLoaderInitialization(nsIDocShell* aShell); 2703 2704 /** 2705 * Check whether this document is a root document that is not an 2706 * external resource. 2707 */ 2708 bool IsRootDisplayDocument() const { 2709 return !mParentDocument && !mDisplayDocument; 2710 } 2711 2712 bool ChromeRulesEnabled() const { return mChromeRulesEnabled; } 2713 2714 bool IsInChromeDocShell() const { 2715 const Document* root = this; 2716 while (const Document* displayDoc = root->GetDisplayDocument()) { 2717 root = displayDoc; 2718 } 2719 return root->mInChromeDocShell; 2720 } 2721 2722 bool IsBeingUsedAsImage() const { return mIsBeingUsedAsImage; } 2723 2724 void SetIsBeingUsedAsImage() { mIsBeingUsedAsImage = true; } 2725 2726 bool IsSVGGlyphsDocument() const { return mIsSVGGlyphsDocument; } 2727 2728 void SetIsSVGGlyphsDocument() { mIsSVGGlyphsDocument = true; } 2729 2730 bool IsResourceDoc() const { 2731 return IsBeingUsedAsImage() || // Are we a helper-doc for an SVG image? 2732 mHasDisplayDocument; // Are we an external resource doc? 2733 } 2734 2735 /** 2736 * Get the document for which this document is an external resource. This 2737 * will be null if this document is not an external resource. Otherwise, 2738 * GetDisplayDocument() will return a non-null document, and 2739 * GetDisplayDocument()->GetDisplayDocument() is guaranteed to be null. 2740 */ 2741 Document* GetDisplayDocument() const { return mDisplayDocument; } 2742 2743 /** 2744 * Set the display document for this document. aDisplayDocument must not be 2745 * null. 2746 */ 2747 void SetDisplayDocument(Document* aDisplayDocument) { 2748 MOZ_ASSERT(!GetPresShell() && !GetContainer() && !GetWindow(), 2749 "Shouldn't set mDisplayDocument on documents that already " 2750 "have a presentation or a docshell or a window"); 2751 MOZ_ASSERT(aDisplayDocument, "Must not be null"); 2752 MOZ_ASSERT(aDisplayDocument != this, "Should be different document"); 2753 MOZ_ASSERT(!aDisplayDocument->GetDisplayDocument(), 2754 "Display documents should not nest"); 2755 mDisplayDocument = aDisplayDocument; 2756 mHasDisplayDocument = !!aDisplayDocument; 2757 } 2758 2759 /** 2760 * Request an external resource document for aURI. This will return the 2761 * resource document if available. If one is not available yet, it will 2762 * start loading as needed, and the pending load object will be returned in 2763 * aPendingLoad so that the caller can register an observer to wait for the 2764 * load. If this function returns null and doesn't return a pending load, 2765 * that means that there is no resource document for this URI and won't be 2766 * one in the future. 2767 * 2768 * @param aURI the URI to get 2769 * @param aReferrerInfo the referrerInfo of the request 2770 * @param aRequestingNode the node making the request 2771 * @param aPendingLoad the pending load for this request, if any 2772 */ 2773 Document* RequestExternalResource(nsIURI* aURI, 2774 nsIReferrerInfo* aReferrerInfo, 2775 nsINode* aRequestingNode, 2776 ExternalResourceLoad** aPendingLoad); 2777 2778 /** 2779 * Enumerate the external resource documents associated with this document. 2780 * The enumerator callback should return CallState::Continue to continue 2781 * enumerating, or CallState::Stop to stop. This callback will never get 2782 * passed a null aDocument. 2783 */ 2784 void EnumerateExternalResources(SubDocEnumFunc aCallback) const; 2785 2786 dom::ExternalResourceMap& ExternalResourceMap() { 2787 return mExternalResourceMap; 2788 } 2789 2790 /** 2791 * Return whether the document is currently showing (in the sense of 2792 * OnPageShow() having been called already and OnPageHide() not having been 2793 * called yet. 2794 */ 2795 bool IsShowing() const { return mIsShowing; } 2796 2797 /** 2798 * Return whether the document is currently visible (in the sense of 2799 * OnPageHide having been called and OnPageShow not yet having been called) 2800 */ 2801 bool IsVisible() const { return mVisible; } 2802 2803 /** 2804 * Return whether the document has completely finished loading, in the spec 2805 * sense. We only store a bool though, whereas spec stores when loading 2806 * finished. See https://html.spec.whatwg.org/#completely-loaded-time 2807 */ 2808 bool IsCompletelyLoaded() const { return mIsCompletelyLoaded; } 2809 2810 void SetSuppressedEventListener(EventListener* aListener); 2811 2812 EventListener* GetSuppressedEventListener() { 2813 return mSuppressedEventListener; 2814 } 2815 2816 /** 2817 * Return true when this document is active, i.e., an active document 2818 * in a content viewer and not in the bfcache. 2819 * This does NOT match the "active document" concept in the WHATWG spec - 2820 * see IsCurrentActiveDocument. 2821 */ 2822 bool IsActive() const; 2823 2824 /** 2825 * Return true if this is the current active document for its 2826 * docshell. Note that a docshell may have multiple active documents 2827 * due to the bfcache -- this should be used when you need to 2828 * differentiate the *current* active document from any active 2829 * documents. 2830 */ 2831 bool IsCurrentActiveDocument() const { 2832 nsPIDOMWindowInner* inner = GetInnerWindow(); 2833 return inner && inner->IsCurrentInnerWindow() && inner->GetDoc() == this; 2834 } 2835 2836 /* 2837 * Return true if the documents current url can be re-written to `aTargetURL`. 2838 * This implements https://html.spec.whatwg.org/#can-have-its-url-rewritten. 2839 */ 2840 bool CanRewriteURL(nsIURI* aTargetURL, bool aReportErrors = true) const; 2841 2842 /** 2843 * Return true if this document is fully active as described by spec. 2844 * https://html.spec.whatwg.org/multipage/document-sequences.html#fully-active 2845 */ 2846 bool IsFullyActive() const { 2847 nsPIDOMWindowInner* inner = GetInnerWindow(); 2848 return inner && inner->IsFullyActive(); 2849 } 2850 2851 /* 2852 * Return if this document has been scrolled since the given last scroll 2853 * generation. 2854 * 2855 * Similar to: https://html.spec.whatwg.org/#has-been-scrolled-by-the-user. 2856 */ 2857 bool HasBeenScrolledSince(const uint32_t& aLastScrollGeneration) const; 2858 uint32_t LastScrollGeneration() const; 2859 2860 /** 2861 * Returns whether this document should perform image loads. 2862 */ 2863 bool ShouldLoadImages() const { 2864 // We check IsBeingUsedAsImage() so that SVG documents loaded as 2865 // images can themselves have data: URL image references. 2866 return IsCurrentActiveDocument() || IsBeingUsedAsImage() || 2867 IsStaticDocument(); 2868 } 2869 2870 void SetHasPrintCallbacks() { 2871 MOZ_DIAGNOSTIC_ASSERT(IsStaticDocument()); 2872 mHasPrintCallbacks = true; 2873 } 2874 2875 bool HasPrintCallbacks() const { return mHasPrintCallbacks; } 2876 2877 /** 2878 * Register/Unregister the ActivityObserver into mActivityObservers to listen 2879 * the document's activity changes such as OnPageHide, visibility, activity. 2880 * The ActivityObserver objects can be nsIObjectLoadingContent or 2881 * nsIDocumentActivity or HTMLMEdiaElement. 2882 */ 2883 void RegisterActivityObserver(nsISupports* aSupports); 2884 bool UnregisterActivityObserver(nsISupports* aSupports); 2885 // Enumerate all the observers in mActivityObservers by the aEnumerator. 2886 using ActivityObserverEnumerator = FunctionRef<void(nsISupports*)>; 2887 void EnumerateActivityObservers(ActivityObserverEnumerator aEnumerator); 2888 2889 void NotifyActivityChanged(); 2890 2891 // Indicates whether mAnimationController has been (lazily) initialized. 2892 // If this returns true, we're promising that GetAnimationController() 2893 // will have a non-null return value. 2894 bool HasAnimationController() { return !!mAnimationController; } 2895 2896 // Getter for this document's SMIL Animation Controller. Performs lazy 2897 // initialization, if this document supports animation and if 2898 // mAnimationController isn't yet initialized. 2899 // 2900 // If HasAnimationController is true, this is guaranteed to return non-null. 2901 SMILAnimationController* GetAnimationController(); 2902 2903 // Gets the tracker for scroll-driven animations that are waiting to start. 2904 // Returns nullptr if there is no scroll-driven animation tracker for this 2905 // document which will be the case if there have never been any scroll-driven 2906 // animations in the document. 2907 ScrollTimelineAnimationTracker* GetScrollTimelineAnimationTracker() { 2908 return mScrollTimelineAnimationTracker; 2909 } 2910 2911 // Gets the tracker for scroll-driven animations that are waiting to start and 2912 // creates it if it doesn't already exist. As a result, the return value 2913 // will never be nullptr. 2914 ScrollTimelineAnimationTracker* GetOrCreateScrollTimelineAnimationTracker(); 2915 2916 /** 2917 * Prevents user initiated events from being dispatched to the document and 2918 * subdocuments. 2919 */ 2920 void SuppressEventHandling(uint32_t aIncrease = 1); 2921 2922 /** 2923 * Unsuppress event handling. 2924 * @param aFireEvents If true, delayed events (focus/blur) will be fired 2925 * asynchronously. 2926 */ 2927 MOZ_CAN_RUN_SCRIPT_BOUNDARY void UnsuppressEventHandlingAndFireEvents( 2928 bool aFireEvents); 2929 2930 uint32_t EventHandlingSuppressed() const { return mEventsSuppressed; } 2931 2932 bool IsEventHandlingEnabled() const { 2933 return !EventHandlingSuppressed() && mScriptGlobalObject; 2934 } 2935 2936 void MaybeScheduleRenderingPhases(RenderingPhases); 2937 void MaybeScheduleRendering() { 2938 MaybeScheduleRenderingPhases(AllRenderingPhases()); 2939 } 2940 void MaybeScheduleFrameRequestCallbacks() { 2941 if (HasFrameRequestCallbacks()) { 2942 MaybeScheduleRenderingPhases({RenderingPhase::AnimationFrameCallbacks}); 2943 } 2944 } 2945 bool IsRenderingSuppressed() const; 2946 2947 void DecreaseEventSuppression() { 2948 MOZ_ASSERT(mEventsSuppressed); 2949 --mEventsSuppressed; 2950 MaybeScheduleRendering(); 2951 } 2952 2953 /** 2954 * Some clipboard commands are unconditionally enabled on some documents, so 2955 * as to always dispatch copy / paste events even though you'd normally not be 2956 * able to copy. 2957 */ 2958 bool AreClipboardCommandsUnconditionallyEnabled() const; 2959 2960 /** 2961 * Note a ChannelEventQueue which has been suspended on the document's behalf 2962 * to prevent XHRs from running content scripts while event handling is 2963 * suppressed. The document is responsible for resuming the queue after 2964 * event handling is unsuppressed. 2965 */ 2966 void AddSuspendedChannelEventQueue(net::ChannelEventQueue* aQueue); 2967 2968 /** 2969 * Returns true if a postMessage event should be suspended instead of running. 2970 * The document is responsible for running the event later, in the order they 2971 * were received. 2972 */ 2973 bool SuspendPostMessageEvent(PostMessageEvent* aEvent); 2974 2975 /** 2976 * Run any suspended postMessage events, or clear them. 2977 */ 2978 void FireOrClearPostMessageEvents(bool aFireEvents); 2979 2980 /** 2981 * Flag whether we're about to fire the window's load event for this document. 2982 */ 2983 void SetLoadEventFiring(bool aFiring) { mLoadEventFiring = aFiring; } 2984 2985 /** 2986 * Test whether we should be firing a load event for this document after a 2987 * document.close(). This is public and on Document, instead of being private 2988 * to Document, because we need to go through the normal docloader logic 2989 * for the readystate change to READYSTATE_COMPLETE with the normal timing and 2990 * semantics of firing the load event; we just don't want to fire the load 2991 * event if this tests true. So we need the docloader to be able to access 2992 * this state. 2993 * 2994 * This method should only be called at the point when the load event is about 2995 * to be fired. It resets the "skip" flag, so it is not idempotent. 2996 */ 2997 bool SkipLoadEventAfterClose() { 2998 bool skip = mSkipLoadEventAfterClose; 2999 mSkipLoadEventAfterClose = false; 3000 return skip; 3001 } 3002 3003 /** 3004 * Increment https://html.spec.whatwg.org/#ignore-destructive-writes-counter 3005 */ 3006 void IncrementIgnoreDestructiveWritesCounter() { 3007 ++mIgnoreDestructiveWritesCounter; 3008 } 3009 3010 /** 3011 * Decrement https://html.spec.whatwg.org/#ignore-destructive-writes-counter 3012 */ 3013 void DecrementIgnoreDestructiveWritesCounter() { 3014 --mIgnoreDestructiveWritesCounter; 3015 } 3016 3017 bool IsDNSPrefetchAllowed() const { return mAllowDNSPrefetch; } 3018 3019 /** 3020 * Returns true if this document is allowed to contain XUL element and 3021 * use non-builtin XBL bindings. 3022 */ 3023 bool AllowXULXBL() { 3024 return mAllowXULXBL == eTriTrue ? true 3025 : mAllowXULXBL == eTriFalse ? false 3026 : InternalAllowXULXBL(); 3027 } 3028 3029 /** 3030 * Returns true if this document is allowed to load DTDs from UI resources 3031 * no matter what. 3032 */ 3033 bool SkipDTDSecurityChecks() { return mSkipDTDSecurityChecks; } 3034 3035 void ForceEnableXULXBL() { mAllowXULXBL = eTriTrue; } 3036 3037 void ForceSkipDTDSecurityChecks() { mSkipDTDSecurityChecks = true; } 3038 3039 /** 3040 * Returns the template content owner document that owns the content of 3041 * HTMLTemplateElement. 3042 */ 3043 Document* GetTemplateContentsOwner(); 3044 3045 Document* GetTemplateContentsOwnerIfExists() const { 3046 return mTemplateContentsOwner.get(); 3047 } 3048 3049 bool IsTemplateContentsOwner() const { 3050 // Template contents owner documents are the template contents owner of 3051 // themselves. 3052 return mTemplateContentsOwner == this; 3053 } 3054 3055 /** 3056 * Returns true if this document is a static clone of a normal document. 3057 * 3058 * We create static clones for print preview and printing (possibly other 3059 * things in future). 3060 * 3061 * Note that static documents are also "loaded as data" (if this method 3062 * returns true, IsLoadedAsData() will also return true). 3063 */ 3064 bool IsStaticDocument() const { return mIsStaticDocument; } 3065 3066 /** 3067 * Clones the document along with any subdocuments, stylesheet, etc. 3068 * 3069 * The resulting document and everything it contains (including any 3070 * sub-documents) are created purely via cloning. The returned documents and 3071 * any sub-documents are "loaded as data" documents to preserve the state as 3072 * it was during the clone process (we don't want external resources to load 3073 * and replace the cloned resources). 3074 * 3075 * @param aCloneContainer The container for the clone document. 3076 * @param aDocumentViewer The viewer for the clone document. Must be the 3077 * viewer of aCloneContainer, but callers must have a 3078 * reference to it already and ensure it's not null. 3079 * @param aPrintSettings The print settings for this clone. 3080 * @param aOutHasInProcessPrintCallbacks Self-descriptive. 3081 */ 3082 already_AddRefed<Document> CreateStaticClone( 3083 nsIDocShell* aCloneContainer, nsIDocumentViewer* aDocumentViewer, 3084 nsIPrintSettings* aPrintSettings, bool* aOutHasInProcessPrintCallbacks); 3085 3086 /** 3087 * If this document is a static clone, this returns the original 3088 * document. 3089 */ 3090 Document* GetOriginalDocument() const { 3091 MOZ_ASSERT(!mOriginalDocument || !mOriginalDocument->GetOriginalDocument()); 3092 return mOriginalDocument; 3093 } 3094 3095 /** 3096 * If this document is a static clone, let the original document know that 3097 * we're going away and then release our reference to it. 3098 */ 3099 void UnlinkOriginalDocumentIfStatic(); 3100 3101 /** 3102 * These are called by the parser as it encounters <picture> tags, the end of 3103 * said tags, and possible picture <source srcset> sources respectively. These 3104 * are used to inform ResolvePreLoadImage() calls. Unset attributes are 3105 * expected to be marked void. 3106 * 3107 * NOTE that the parser does not attempt to track the current picture nesting 3108 * level or whether the given <source> tag is within a picture -- it is only 3109 * guaranteed to order these calls properly with respect to 3110 * ResolvePreLoadImage. 3111 */ 3112 3113 void PreloadPictureOpened() { mPreloadPictureDepth++; } 3114 3115 void PreloadPictureClosed(); 3116 3117 void PreloadPictureImageSource(const nsAString& aSrcsetAttr, 3118 const nsAString& aSizesAttr, 3119 const nsAString& aTypeAttr, 3120 const nsAString& aMediaAttr); 3121 3122 /** 3123 * Called by the parser to resolve an image for preloading. The parser will 3124 * call the PreloadPicture* functions to inform us of possible <picture> 3125 * nesting and possible sources, which are used to inform URL selection 3126 * responsive <picture> or <img srcset> images. Unset attributes are expected 3127 * to be marked void. 3128 * If this image is for <picture> or <img srcset>, aIsImgSet will be set to 3129 * true, false otherwise. 3130 */ 3131 already_AddRefed<nsIURI> ResolvePreloadImage(nsIURI* aBaseURI, 3132 const nsAString& aSrcAttr, 3133 const nsAString& aSrcsetAttr, 3134 const nsAString& aSizesAttr, 3135 bool* aIsImgSet); 3136 /** 3137 * Called by nsParser to preload images. Can be removed and code moved 3138 * to nsPreloadURIs::PreloadURIs() in file nsParser.cpp whenever the 3139 * parser-module is linked with gklayout-module. aCrossOriginAttr should 3140 * be a void string if the attr is not present. 3141 * aIsImgSet is the value got from calling ResolvePreloadImage, it is true 3142 * when this image is for loading <picture> or <img srcset> images. 3143 */ 3144 void MaybePreLoadImage(nsIURI* uri, const nsAString& aCrossOriginAttr, 3145 ReferrerPolicyEnum aReferrerPolicy, bool aIsImgSet, 3146 bool aLinkPreload, const nsAString& aFetchPriority); 3147 void PreLoadImage(nsIURI* uri, const nsAString& aCrossOriginAttr, 3148 ReferrerPolicyEnum aReferrerPolicy, bool aIsImgSet, 3149 bool aLinkPreload, uint64_t aEarlyHintPreloaderId, 3150 const nsAString& aFetchPriority); 3151 3152 /** 3153 * Called by images to forget an image preload when they start doing 3154 * the real load. 3155 */ 3156 void ForgetImagePreload(nsIURI* aURI); 3157 3158 /** 3159 * Called by the parser or the preload service to preload style sheets. 3160 * aCrossOriginAttr should be a void string if the attr is not present. 3161 */ 3162 SheetPreloadStatus PreloadStyle(nsIURI* aURI, const Encoding* aEncoding, 3163 const nsAString& aCrossOriginAttr, 3164 ReferrerPolicyEnum aReferrerPolicy, 3165 const nsAString& aNonce, 3166 const nsAString& aIntegrity, 3167 css::StylePreloadKind, 3168 uint64_t aEarlyHintPreloaderId, 3169 const nsAString& aFetchPriority); 3170 3171 /** 3172 * Returns true if the locale used for the document specifies a direction of 3173 * right to left. For chrome documents, this comes from the chrome registry. 3174 * This is used to determine the current state for the :-moz-locale-dir 3175 * pseudoclass so once can know whether a document is expected to be rendered 3176 * left-to-right or right-to-left. 3177 */ 3178 bool IsDocumentRightToLeft(); 3179 3180 /** 3181 * Called by Parser for link rel=preconnect 3182 */ 3183 void MaybePreconnect(nsIURI* uri, CORSMode aCORSMode); 3184 3185 /** 3186 * Set the document's pending state object (as serialized using structured 3187 * clone). 3188 */ 3189 void SetStateObject(nsIStructuredCloneContainer* scContainer); 3190 3191 /** 3192 * Set the document's pending state object to the same state object as 3193 * aDocument. 3194 */ 3195 void SetStateObjectFrom(Document* aDocument) { 3196 SetStateObject(aDocument->mStateObjectContainer); 3197 } 3198 3199 // Whether we're a media document or not. 3200 enum class MediaDocumentKind { 3201 NotMedia, 3202 Video, 3203 Image, 3204 }; 3205 3206 virtual enum MediaDocumentKind MediaDocumentKind() const { 3207 return MediaDocumentKind::NotMedia; 3208 } 3209 3210 DocumentState State() const { return mState; } 3211 3212 nsISupports* GetCurrentContentSink(); 3213 3214 void ElementWithAutoFocusInserted(Element* aAutoFocusCandidate); 3215 MOZ_CAN_RUN_SCRIPT void FlushAutoFocusCandidates(); 3216 void ScheduleFlushAutoFocusCandidates(); 3217 bool HasAutoFocusCandidates() const { 3218 return !mAutoFocusCandidates.IsEmpty(); 3219 } 3220 3221 void SetAutoFocusFired(); 3222 3223 void SetScrollToRef(nsIURI* aDocumentURI); 3224 MOZ_CAN_RUN_SCRIPT void ScrollToRef(); 3225 void ResetScrolledToRefAlready() { mScrolledToRefAlready = false; } 3226 3227 void SetChangeScrollPosWhenScrollingToRef(bool aValue) { 3228 mChangeScrollPosWhenScrollingToRef = aValue; 3229 } 3230 3231 using DocumentOrShadowRoot::GetElementById; 3232 using DocumentOrShadowRoot::GetElementsByClassName; 3233 using DocumentOrShadowRoot::GetElementsByTagName; 3234 using DocumentOrShadowRoot::GetElementsByTagNameNS; 3235 3236 DocumentTimeline* Timeline(); 3237 const AnimationTimelinesController& TimelinesController() const { 3238 return mTimelinesController; 3239 } 3240 AnimationTimelinesController& TimelinesController() { 3241 return mTimelinesController; 3242 } 3243 void UpdateHiddenByContentVisibilityForAnimations(); 3244 3245 SVGSVGElement* GetSVGRootElement() const; 3246 3247 nsresult ScheduleFrameRequestCallback(FrameRequestCallback& aCallback, 3248 uint32_t* aHandle); 3249 void CancelFrameRequestCallback(uint32_t aHandle); 3250 3251 void ScheduleVideoFrameCallbacks(HTMLVideoElement* aElement); 3252 void CancelVideoFrameCallbacks(HTMLVideoElement* aElement); 3253 3254 /** 3255 * Put this document's video frame request callbacks into the provided 3256 * list, and forget about them. 3257 */ 3258 void TakeVideoFrameRequestCallbacks( 3259 nsTArray<RefPtr<HTMLVideoElement>>& aVideoCallbacks); 3260 3261 /** Whether we have any scheduled frame request */ 3262 bool HasFrameRequestCallbacks() const { 3263 return !mFrameRequestManager.IsEmpty(); 3264 } 3265 3266 dom::FrameRequestManager& FrameRequestManager() { 3267 return mFrameRequestManager; 3268 } 3269 3270 /** 3271 * @return true if this document's frame request callbacks should be 3272 * throttled. We throttle requestAnimationFrame for documents which aren't 3273 * visible (e.g. scrolled out of the viewport). 3274 */ 3275 bool ShouldThrottleFrameRequests() const; 3276 3277 // This returns true when the document tree is being teared down. 3278 bool InUnlinkOrDeletion() { return mInUnlinkOrDeletion; } 3279 3280 void TrackImage(imgIRequest*); 3281 enum class RequestDiscard : bool { No = false, Yes }; 3282 void UntrackImage(imgIRequest*, RequestDiscard = RequestDiscard::No); 3283 3284 // Makes the images on this document locked/unlocked. By default, the locking 3285 // state is unlocked/false. 3286 bool GetLockingImages() const { return mLockingImages; } 3287 void SetLockingImages(bool); 3288 3289 // Makes the images on this document capable of having their animation 3290 // active or suspended. An Image will animate as long as at least one of its 3291 // owning Documents needs it to animate; otherwise it can suspend. 3292 void SetImageAnimationState(bool); 3293 void PropagateMediaFeatureChangeToTrackedImages(const MediaFeatureChange&); 3294 3295 // Adds an element to mResponsiveContent when the element is 3296 // added to the tree. 3297 void AddResponsiveContent(HTMLImageElement* aContent) { 3298 MOZ_ASSERT(aContent); 3299 mResponsiveContent.Insert(aContent); 3300 } 3301 3302 // Removes an element from mResponsiveContent when the element is 3303 // removed from the tree. 3304 void RemoveResponsiveContent(HTMLImageElement* aContent) { 3305 MOZ_ASSERT(aContent); 3306 mResponsiveContent.Remove(aContent); 3307 } 3308 3309 void ScheduleSVGUseElementShadowTreeUpdate(SVGUseElement&); 3310 void UnscheduleSVGUseElementShadowTreeUpdate(SVGUseElement& aElement) { 3311 mSVGUseElementsNeedingShadowTreeUpdate.Remove(&aElement); 3312 } 3313 3314 bool SVGUseElementNeedsShadowTreeUpdate(SVGUseElement& aElement) const { 3315 return mSVGUseElementsNeedingShadowTreeUpdate.Contains(&aElement); 3316 } 3317 3318 using ShadowRootSet = nsTHashSet<ShadowRoot*>; 3319 3320 void AddComposedDocShadowRoot(ShadowRoot& aShadowRoot) { 3321 mComposedShadowRoots.Insert(&aShadowRoot); 3322 } 3323 3324 void RemoveComposedDocShadowRoot(ShadowRoot& aShadowRoot) { 3325 mComposedShadowRoots.Remove(&aShadowRoot); 3326 } 3327 3328 // If you're considering using this, you probably want to use 3329 // ShadowRoot::IsComposedDocParticipant instead. This is just for 3330 // sanity-checking. 3331 bool IsComposedDocShadowRoot(ShadowRoot& aShadowRoot) { 3332 return mComposedShadowRoots.Contains(&aShadowRoot); 3333 } 3334 3335 const ShadowRootSet& ComposedShadowRoots() const { 3336 return mComposedShadowRoots; 3337 } 3338 3339 // WebIDL method for chrome code. 3340 void GetConnectedShadowRoots(nsTArray<RefPtr<ShadowRoot>>&) const; 3341 3342 void SynchronouslyUpdateRemoteBrowserDimensions( 3343 bool aIncludeInactive = false); 3344 3345 // Notifies any responsive content added by AddResponsiveContent upon media 3346 // features values changing. 3347 void NotifyMediaFeatureValuesChanged(); 3348 3349 nsresult GetStateObject(JS::MutableHandle<JS::Value> aState); 3350 3351 nsDOMNavigationTiming* GetNavigationTiming() const { return mTiming; } 3352 3353 void SetNavigationTiming(nsDOMNavigationTiming* aTiming); 3354 3355 inline void SetPageloadEventFeature( 3356 performance::pageload_event::DocumentFeature aFeature) { 3357 mPageloadEventData.SetDocumentFeature(aFeature); 3358 } 3359 3360 nsContentList* ImageMapList(); 3361 3362 // Add aLink to the set of links that need their status resolved. 3363 void RegisterPendingLinkUpdate(Link* aLink); 3364 3365 // Update state on links in mLinksToUpdate. 3366 void FlushPendingLinkUpdates(); 3367 3368 bool HasWarnedAbout(DeprecatedOperations aOperation) const; 3369 void WarnOnceAbout( 3370 DeprecatedOperations aOperation, bool asError = false, 3371 const nsTArray<nsString>& aParams = nsTArray<nsString>()) const; 3372 3373 #define DOCUMENT_WARNING(_op) e##_op, 3374 enum DocumentWarnings { 3375 #include "nsDocumentWarningList.h" 3376 eDocumentWarningCount 3377 }; 3378 #undef DOCUMENT_WARNING 3379 bool HasWarnedAbout(DocumentWarnings aWarning) const; 3380 void WarnOnceAbout( 3381 DocumentWarnings aWarning, bool asError = false, 3382 const nsTArray<nsString>& aParams = nsTArray<nsString>()) const; 3383 3384 // This method may fire a DOM event; if it does so it will happen 3385 // synchronously. 3386 // 3387 // Whether the event fires is controlled by the argument. 3388 enum class DispatchVisibilityChange { No, Yes }; 3389 void UpdateVisibilityState( 3390 DispatchVisibilityChange = DispatchVisibilityChange::Yes); 3391 3392 // Posts an event to call UpdateVisibilityState. 3393 void PostVisibilityUpdateEvent(); 3394 3395 bool IsSyntheticDocument() const { return mIsSyntheticDocument; } 3396 3397 // Adds the size of a given node, which must not be a document node, to the 3398 // window sizes passed-in. 3399 static void AddSizeOfNodeTree(nsINode&, nsWindowSizes&); 3400 3401 // Note: Document is a sub-class of nsINode, which has a 3402 // SizeOfExcludingThis function. However, because Document objects can 3403 // only appear at the top of the DOM tree, we have a specialized measurement 3404 // function which returns multiple sizes. 3405 virtual void DocAddSizeOfExcludingThis(nsWindowSizes& aWindowSizes) const; 3406 // DocAddSizeOfIncludingThis doesn't need to be overridden by sub-classes 3407 // because Document inherits from nsINode; see the comment above the 3408 // declaration of nsINode::SizeOfIncludingThis. 3409 virtual void DocAddSizeOfIncludingThis(nsWindowSizes& aWindowSizes) const; 3410 3411 void ConstructUbiNode(void* storage) override; 3412 3413 bool MayHaveDOMMutationObservers() { return mMayHaveDOMMutationObservers; } 3414 3415 void SetMayHaveDOMMutationObservers() { mMayHaveDOMMutationObservers = true; } 3416 3417 bool MayHaveAnimationObservers() { return mMayHaveAnimationObservers; } 3418 3419 void SetMayHaveAnimationObservers() { mMayHaveAnimationObservers = true; } 3420 3421 bool IsInSyncOperation() { return mInSyncOperationCount != 0; } 3422 3423 void SetIsInSyncOperation(bool aSync); 3424 3425 bool CreatingStaticClone() const { return mCreatingStaticClone; } 3426 3427 /** 3428 * Creates a new element in the HTML namespace with a local name given by 3429 * aTag. 3430 */ 3431 already_AddRefed<Element> CreateHTMLElement(nsAtom* aTag); 3432 3433 // WebIDL API 3434 nsIGlobalObject* GetParentObject() const { return GetScopeObject(); } 3435 static already_AddRefed<Document> Constructor(const GlobalObject& aGlobal, 3436 ErrorResult& rv); 3437 DOMImplementation* GetImplementation(ErrorResult& rv); 3438 [[nodiscard]] nsresult GetURL(nsString& retval) const; 3439 [[nodiscard]] nsresult GetDocumentURI(nsString& retval) const; 3440 // Return the URI for the document. 3441 // The returned value may differ if the document is loaded via XHR, and 3442 // when accessed from chrome privileged script and 3443 // from content privileged script for compatibility. 3444 void GetDocumentURIFromJS(nsString& aDocumentURI, CallerType aCallerType, 3445 ErrorResult& aRv) const; 3446 void GetCompatMode(nsString& retval) const; 3447 void GetCharacterSet(nsAString& retval) const; 3448 // Skip GetContentType, because our NS_IMETHOD version above works fine here. 3449 // GetDoctype defined above 3450 Element* GetDocumentElement() const { return GetRootElement(); } 3451 3452 WindowContext* GetTopLevelWindowContext() const; 3453 3454 // If the top-level ancestor content document for this document is in the same 3455 // process, returns it. Otherwise, returns null. This function is not 3456 // Fission-compatible, and should not be used in new code. 3457 Document* GetTopLevelContentDocumentIfSameProcess(); 3458 const Document* GetTopLevelContentDocumentIfSameProcess() const; 3459 3460 // Returns the associated app window if this is a top-level chrome document, 3461 // null otherwise. 3462 already_AddRefed<nsIAppWindow> GetAppWindowIfToplevelChrome() const; 3463 3464 already_AddRefed<Element> CreateElement( 3465 const nsAString& aTagName, const ElementCreationOptionsOrString& aOptions, 3466 ErrorResult& rv); 3467 already_AddRefed<Element> CreateElementNS( 3468 const nsAString& aNamespaceURI, const nsAString& aQualifiedName, 3469 const ElementCreationOptionsOrString& aOptions, ErrorResult& rv); 3470 already_AddRefed<Element> CreateXULElement( 3471 const nsAString& aTagName, const ElementCreationOptionsOrString& aOptions, 3472 ErrorResult& aRv); 3473 already_AddRefed<DocumentFragment> CreateDocumentFragment() const; 3474 already_AddRefed<nsTextNode> CreateTextNode(const nsAString& aData) const; 3475 already_AddRefed<nsTextNode> CreateEmptyTextNode() const; 3476 already_AddRefed<Comment> CreateComment(const nsAString& aData) const; 3477 already_AddRefed<ProcessingInstruction> CreateProcessingInstruction( 3478 const nsAString& target, const nsAString& data, ErrorResult& rv) const; 3479 already_AddRefed<nsINode> ImportNode(nsINode& aNode, bool aDeep, 3480 ErrorResult& rv) const; 3481 // TODO: Convert this to MOZ_CAN_RUN_SCRIPT (bug 1415230) 3482 MOZ_CAN_RUN_SCRIPT_BOUNDARY nsINode* AdoptNode( 3483 nsINode& aAdoptedNode, ErrorResult& rv, bool aAcceptShadowRoot = false); 3484 already_AddRefed<Event> CreateEvent(const nsAString& aEventType, 3485 CallerType aCallerType, 3486 ErrorResult& rv) const; 3487 already_AddRefed<nsRange> CreateRange(ErrorResult& rv); 3488 already_AddRefed<NodeIterator> CreateNodeIterator(nsINode& aRoot, 3489 uint32_t aWhatToShow, 3490 NodeFilter* aFilter, 3491 ErrorResult& rv) const; 3492 already_AddRefed<TreeWalker> CreateTreeWalker(nsINode& aRoot, 3493 uint32_t aWhatToShow, 3494 NodeFilter* aFilter, 3495 ErrorResult& rv) const; 3496 // Deprecated WebIDL bits 3497 already_AddRefed<CDATASection> CreateCDATASection(const nsAString& aData, 3498 ErrorResult& rv); 3499 already_AddRefed<Attr> CreateAttribute(const nsAString& aName, 3500 ErrorResult& rv); 3501 already_AddRefed<Attr> CreateAttributeNS(const nsAString& aNamespaceURI, 3502 const nsAString& aQualifiedName, 3503 ErrorResult& rv); 3504 void GetInputEncoding(nsAString& aInputEncoding) const; 3505 already_AddRefed<Location> GetLocation() const; 3506 void GetDomain(nsAString& aDomain); 3507 void SetDomain(const nsAString& aDomain, mozilla::ErrorResult& rv); 3508 void GetCookie(nsAString& aCookie, mozilla::ErrorResult& rv); 3509 void SetCookie(const nsAString& aCookie, mozilla::ErrorResult& rv); 3510 void GetReferrer(nsACString& aReferrer) const; 3511 void GetLastModified(nsAString& aLastModified) const; 3512 void GetReadyState(nsAString& aReadyState) const; 3513 3514 void GetTitle(nsAString& aTitle); 3515 void SetTitle(const nsAString& aTitle, ErrorResult& rv); 3516 void GetDir(nsAString& aDirection) const; 3517 void SetDir(const nsAString& aDirection); 3518 nsIHTMLCollection* Images(); 3519 nsIHTMLCollection* Embeds(); 3520 nsIHTMLCollection* Plugins() { return Embeds(); } 3521 nsIHTMLCollection* Links(); 3522 nsIHTMLCollection* Forms(); 3523 nsIHTMLCollection* Scripts(); 3524 already_AddRefed<nsContentList> GetElementsByName(const nsAString& aName) { 3525 return GetFuncStringContentList<nsCachableElementsByNameNodeList>( 3526 this, MatchNameAttribute, nullptr, UseExistingNameString, aName); 3527 } 3528 Document* Open(const mozilla::dom::Optional<nsAString>& /* unused */, 3529 const mozilla::dom::Optional<nsAString>& /* unused */, 3530 mozilla::ErrorResult& aError); 3531 mozilla::dom::Nullable<mozilla::dom::WindowProxyHolder> Open( 3532 const nsACString& aURL, const nsAString& aName, 3533 const nsAString& aFeatures, mozilla::ErrorResult& rv); 3534 void Close(mozilla::ErrorResult& rv); 3535 MOZ_CAN_RUN_SCRIPT void Write( 3536 const mozilla::dom::Sequence<OwningTrustedHTMLOrString>& aText, 3537 nsIPrincipal* aSubjectPrincipal, mozilla::ErrorResult& rv); 3538 MOZ_CAN_RUN_SCRIPT void Writeln( 3539 const mozilla::dom::Sequence<OwningTrustedHTMLOrString>& aText, 3540 nsIPrincipal* aSubjectPrincipal, mozilla::ErrorResult& rv); 3541 Nullable<WindowProxyHolder> GetDefaultView() const; 3542 Element* GetActiveElement(); 3543 enum class IncludeChromeOnly : bool { No, Yes }; 3544 // TODO(emilio): Audit callers and remove the default argument, some seem like 3545 // they could want the IncludeChromeOnly::Yes version. 3546 nsIContent* GetUnretargetedFocusedContent( 3547 IncludeChromeOnly = IncludeChromeOnly::No) const; 3548 /** 3549 * Return true if this document or a subdocument has focus. 3550 */ 3551 bool HasFocus(ErrorResult& rv) const; 3552 3553 /** 3554 * Return true if this document itself has focus. 3555 */ 3556 bool ThisDocumentHasFocus() const; 3557 3558 void GetDesignMode(nsAString& aDesignMode); 3559 void SetDesignMode(const nsAString& aDesignMode, 3560 nsIPrincipal& aSubjectPrincipal, mozilla::ErrorResult& rv); 3561 void SetDesignMode(const nsAString& aDesignMode, 3562 const mozilla::Maybe<nsIPrincipal*>& aSubjectPrincipal, 3563 mozilla::ErrorResult& rv); 3564 void SetDocumentEditableFlag(bool); 3565 MOZ_CAN_RUN_SCRIPT 3566 bool ExecCommand(const nsAString& aHTMLCommandName, bool aShowUI, 3567 const TrustedHTMLOrString& aValue, 3568 nsIPrincipal& aSubjectPrincipal, mozilla::ErrorResult& aRv); 3569 MOZ_CAN_RUN_SCRIPT bool QueryCommandEnabled(const nsAString& aHTMLCommandName, 3570 nsIPrincipal& aSubjectPrincipal, 3571 mozilla::ErrorResult& aRv); 3572 MOZ_CAN_RUN_SCRIPT bool QueryCommandIndeterm( 3573 const nsAString& aHTMLCommandName, mozilla::ErrorResult& aRv); 3574 MOZ_CAN_RUN_SCRIPT bool QueryCommandState(const nsAString& aHTMLCommandName, 3575 mozilla::ErrorResult& aRv); 3576 MOZ_CAN_RUN_SCRIPT bool QueryCommandSupported( 3577 const nsAString& aHTMLCommandName, nsIPrincipal& aSubjectPrincipal, 3578 mozilla::ErrorResult& aRv); 3579 MOZ_CAN_RUN_SCRIPT void QueryCommandValue(const nsAString& aHTMLCommandName, 3580 nsAString& aValue, 3581 mozilla::ErrorResult& aRv); 3582 nsIHTMLCollection* Applets(); 3583 nsIHTMLCollection* Anchors(); 3584 TimeStamp LastFocusTime() const; 3585 void SetLastFocusTime(const TimeStamp& aFocusTime); 3586 // Event handlers are all on nsINode already 3587 bool MozSyntheticDocument() const { return IsSyntheticDocument(); } 3588 Element* GetCurrentScript(); 3589 void ReleaseCapture() const; 3590 void MozSetImageElement(const nsAString& aImageElementId, Element* aElement); 3591 nsIURI* GetDocumentURIObject() const; 3592 nsIURI* GetOnionLocationURI() const { return mOnionLocationURI; } 3593 // Not const because all the fullscreen goop is not const 3594 const char* GetFullscreenError(CallerType); 3595 bool FullscreenEnabled(CallerType aCallerType) { 3596 return !GetFullscreenError(aCallerType); 3597 } 3598 3599 void GetWireframeWithoutFlushing(bool aIncludeNodes, Nullable<Wireframe>&); 3600 3601 MOZ_CAN_RUN_SCRIPT void GetWireframe(bool aIncludeNodes, 3602 Nullable<Wireframe>&); 3603 3604 // https://html.spec.whatwg.org/#close-entire-popover-list 3605 MOZ_CAN_RUN_SCRIPT void CloseEntirePopoverList(PopoverAttributeState aMode, 3606 bool aFocusPreviousElement, 3607 bool aFireEvents); 3608 3609 // Hides all popovers until the given end point, see 3610 // https://html.spec.whatwg.org/multipage/popover.html#hide-all-popovers-until 3611 MOZ_CAN_RUN_SCRIPT void HideAllPopoversUntil(nsINode& aEndpoint, 3612 bool aFocusPreviousElement, 3613 bool aFireEvents); 3614 3615 // Hides all popovers, until the given end point, see 3616 // https://html.spec.whatwg.org/#hide-popover-stack-until 3617 MOZ_CAN_RUN_SCRIPT void HidePopoverStackUntil(PopoverAttributeState aMode, 3618 nsINode& aEndpoint, 3619 bool aFocusPreviousElement, 3620 bool aFireEvents); 3621 3622 // Hides the given popover element, see 3623 // https://html.spec.whatwg.org/multipage/popover.html#hide-popover-algorithm 3624 MOZ_CAN_RUN_SCRIPT void HidePopover(Element& popover, 3625 bool aFocusPreviousElement, 3626 bool aFireEvents, Element* aSource, 3627 ErrorResult& aRv); 3628 3629 // Returns a list of all the elements in the Document's top layer whose 3630 // popover opened in mode is in the given state. 3631 // See https://html.spec.whatwg.org/multipage/popover.html#auto-popover-list 3632 // See https://html.spec.whatwg.org/#showing-hint-popover-list 3633 nsTArray<Element*> PopoverListOf(PopoverAttributeState aMode) const; 3634 3635 // Return document's popover list's last element of a particular mode. 3636 // See 3637 // https://html.spec.whatwg.org/multipage/popover.html#topmost-auto-popover 3638 Element* GetTopmostPopoverOf(PopoverAttributeState aMode) const; 3639 3640 void AddPopoverToTopLayer(Element&); 3641 void RemovePopoverFromTopLayer(Element&); 3642 3643 Element* GetTopLayerTop(); 3644 // Return the fullscreen element in the top layer 3645 Element* GetUnretargetedFullscreenElement() const; 3646 bool Fullscreen() const { return !!GetUnretargetedFullscreenElement(); } 3647 already_AddRefed<Promise> ExitFullscreen(ErrorResult&); 3648 void ExitPointerLock() { 3649 PointerLockManager::Unlock("Document::ExitPointerLock", this); 3650 } 3651 void GetFgColor(nsAString& aFgColor); 3652 void SetFgColor(const nsAString& aFgColor); 3653 void GetLinkColor(nsAString& aLinkColor); 3654 void SetLinkColor(const nsAString& aLinkColor); 3655 void GetVlinkColor(nsAString& aAvlinkColor); 3656 void SetVlinkColor(const nsAString& aVlinkColor); 3657 void GetAlinkColor(nsAString& aAlinkColor); 3658 void SetAlinkColor(const nsAString& aAlinkColor); 3659 void GetBgColor(nsAString& aBgColor); 3660 void SetBgColor(const nsAString& aBgColor); 3661 void Clear() const { 3662 // Deprecated 3663 } 3664 void CaptureEvents(); 3665 void ReleaseEvents(); 3666 3667 mozilla::dom::HTMLAllCollection* All(); 3668 3669 static bool DocumentSupportsL10n(JSContext* aCx, JSObject* aObject); 3670 // Checks that the caller is either chrome or some addon. 3671 static bool IsCallerChromeOrAddon(JSContext* aCx, JSObject* aObject); 3672 3673 bool Hidden() const { return mVisibilityState != VisibilityState::Visible; } 3674 dom::VisibilityState VisibilityState() const { return mVisibilityState; } 3675 3676 bool RenderingSuppressedForViewTransitions() const { 3677 return mRenderingSuppressedForViewTransitions; 3678 } 3679 void SetRenderingSuppressedForViewTransitions(bool); 3680 3681 void GetSelectedStyleSheetSet(nsAString& aSheetSet); 3682 void SetSelectedStyleSheetSet(const nsAString& aSheetSet); 3683 void GetLastStyleSheetSet(nsAString& aSheetSet) { 3684 aSheetSet = mLastStyleSheetSet; 3685 } 3686 const nsString& GetCurrentStyleSheetSet() const { 3687 return mLastStyleSheetSet.IsEmpty() ? mPreferredStyleSheetSet 3688 : mLastStyleSheetSet; 3689 } 3690 void SetPreferredStyleSheetSet(const nsAString&); 3691 void GetPreferredStyleSheetSet(nsAString& aSheetSet) { 3692 aSheetSet = mPreferredStyleSheetSet; 3693 } 3694 DOMStringList* StyleSheetSets(); 3695 void EnableStyleSheetsForSet(const nsAString& aSheetSet); 3696 3697 /** 3698 * Retrieve the location of the caret position (DOM node and character 3699 * offset within that node), given a point. 3700 * 3701 * @param aX Horizontal point at which to determine the caret position, in 3702 * page coordinates. 3703 * @param aY Vertical point at which to determine the caret position, in 3704 * page coordinates. 3705 */ 3706 already_AddRefed<nsDOMCaretPosition> CaretPositionFromPoint( 3707 float aX, float aY, const CaretPositionFromPointOptions& aOptions); 3708 3709 Element* GetScrollingElement(); 3710 // A way to check whether a given element is what would get returned from 3711 // GetScrollingElement. It can be faster than comparing to the return value 3712 // of GetScrollingElement() due to being able to avoid flushes in various 3713 // cases. This method assumes that null is NOT passed. 3714 bool IsScrollingElement(Element* aElement); 3715 3716 // QuerySelector and QuerySelectorAll already defined on nsINode 3717 3718 UniquePtr<XPathExpression> CreateExpression(const nsAString& aExpression, 3719 XPathNSResolver* aResolver, 3720 ErrorResult& rv); 3721 nsINode* CreateNSResolver(nsINode& aNodeResolver); 3722 already_AddRefed<XPathResult> Evaluate( 3723 JSContext* aCx, const nsAString& aExpression, nsINode& aContextNode, 3724 XPathNSResolver* aResolver, uint16_t aType, JS::Handle<JSObject*> aResult, 3725 ErrorResult& rv); 3726 // Touch event handlers already on nsINode 3727 already_AddRefed<Touch> CreateTouch(nsGlobalWindowInner* aView, 3728 EventTarget* aTarget, int32_t aIdentifier, 3729 int32_t aPageX, int32_t aPageY, 3730 int32_t aScreenX, int32_t aScreenY, 3731 int32_t aClientX, int32_t aClientY, 3732 int32_t aRadiusX, int32_t aRadiusY, 3733 float aRotationAngle, float aForce); 3734 already_AddRefed<TouchList> CreateTouchList(); 3735 already_AddRefed<TouchList> CreateTouchList( 3736 Touch& aTouch, const Sequence<OwningNonNull<Touch>>& aTouches); 3737 already_AddRefed<TouchList> CreateTouchList( 3738 const Sequence<OwningNonNull<Touch>>& aTouches); 3739 3740 void SetStyleSheetChangeEventsEnabled(bool aValue) { 3741 mStyleSheetChangeEventsEnabled = aValue; 3742 } 3743 bool StyleSheetChangeEventsEnabled() const { 3744 return mStyleSheetChangeEventsEnabled; 3745 } 3746 void SetDevToolsAnonymousAndShadowEventsEnabled(bool aValue) { 3747 mDevToolsAnonymousAndShadowEventsEnabled = aValue; 3748 } 3749 bool DevToolsAnonymousAndShadowEventsEnabled() const { 3750 return mDevToolsAnonymousAndShadowEventsEnabled; 3751 } 3752 void SetPausedByDevTools(bool aValue) { mPausedByDevTools = aValue; } 3753 bool PausedByDevTools() const { return mPausedByDevTools; } 3754 3755 void SetForceNonNativeTheme(bool); 3756 bool ForceNonNativeTheme() const { return mForceNonNativeTheme; } 3757 3758 already_AddRefed<Promise> BlockParsing(Promise& aPromise, 3759 const BlockParsingOptions& aOptions, 3760 ErrorResult& aRv); 3761 3762 already_AddRefed<nsIURI> GetMozDocumentURIIfNotForErrorPages(); 3763 3764 Promise* GetDocumentReadyForIdle(ErrorResult& aRv); 3765 3766 void BlockUnblockOnloadForSystemOrPDFJS(bool aBlock) { 3767 if (aBlock) { 3768 BlockOnload(); 3769 } else { 3770 UnblockOnload(/* aFireSync = */ false); 3771 } 3772 } 3773 3774 nsIDOMXULCommandDispatcher* GetCommandDispatcher(); 3775 bool HasXULBroadcastManager() const { return mXULBroadcastManager; }; 3776 void InitializeXULBroadcastManager(); 3777 XULBroadcastManager* GetXULBroadcastManager() const { 3778 return mXULBroadcastManager; 3779 } 3780 nsINode* GetPopupRangeParent(ErrorResult& aRv); 3781 int32_t GetPopupRangeOffset(ErrorResult& aRv); 3782 3783 bool DevToolsWatchingDOMMutations() const { 3784 return mDevToolsWatchingDOMMutations; 3785 } 3786 void SetDevToolsWatchingDOMMutations(bool aValue); 3787 3788 // https://drafts.csswg.org/cssom-view/#evaluate-media-queries-and-report-changes 3789 void EvaluateMediaQueriesAndReportChanges(); 3790 3791 nsTHashSet<RefPtr<WakeLockSentinel>>& ActiveWakeLocks(WakeLockType aType); 3792 3793 void UnlockAllWakeLocks(WakeLockType aType); 3794 3795 // ParentNode 3796 nsIHTMLCollection* Children(); 3797 uint32_t ChildElementCount(); 3798 3799 /** 3800 * Asserts IsHTMLOrXHTML, and can't return null. 3801 * Defined inline in nsHTMLDocument.h 3802 */ 3803 inline nsHTMLDocument* AsHTMLDocument(); 3804 inline const nsHTMLDocument* AsHTMLDocument() const; 3805 3806 /** 3807 * Asserts IsSVGDocument, and can't return null. 3808 * Defined inline in SVGDocument.h 3809 */ 3810 inline SVGDocument* AsSVGDocument(); 3811 inline const SVGDocument* AsSVGDocument() const; 3812 3813 /** 3814 * Asserts IsImageDocument, and can't return null. 3815 * Defined inline in ImageDocument.h 3816 */ 3817 inline ImageDocument* AsImageDocument(); 3818 inline const ImageDocument* AsImageDocument() const; 3819 3820 gfxUserFontSet* GetUserFontSet(); 3821 void FlushUserFontSet(); 3822 void MarkUserFontSetDirty(); 3823 FontFaceSet* GetFonts() { return mFontFaceSet; } 3824 3825 // FontFaceSource 3826 FontFaceSet* GetFonts(ErrorResult&) { return Fonts(); } 3827 FontFaceSet* Fonts(); 3828 3829 bool DidFireDOMContentLoaded() const { return mDidFireDOMContentLoaded; } 3830 3831 bool IsSynthesized(); 3832 3833 // Records whether we will track use counters for this document, and if so, 3834 // which top-level document that page counters will be accumulated to. 3835 // 3836 // Informs the parent process that page use counters will be sent once the 3837 // document goes away. 3838 void InitUseCounters(); 3839 3840 // Reports document use counters via telemetry. This method only has an 3841 // effect once per document, and so is called during document destruction. 3842 void ReportDocumentUseCounters(); 3843 3844 // Report the names of the HTMLDocument properties that had 3845 // been shadowed using ID/name, and which were subsequently accessed 3846 // ("DOM clobbering"). This data is collected by the corresponding NamedGetter 3847 // method and limited to 10 unique entries. 3848 void ReportShadowedProperties(); 3849 3850 // Reports largest contentful paint via telemetry. We want the most up to 3851 // date value for LCP and so this is called during document destruction. 3852 void ReportLCP(); 3853 3854 // Report how lazyload performs for this document. 3855 void ReportDocumentLazyLoadCounters(); 3856 3857 // Sends page use counters to the parent process to accumulate against the 3858 // top-level document. Must be called while we still have access to our 3859 // WindowContext. This method has an effect each time it is called, and we 3860 // call it just before the document loses its window. 3861 void SendPageUseCounters(); 3862 3863 void SetUseCounter(UseCounter aUseCounter) { 3864 mUseCounters[aUseCounter] = true; 3865 } 3866 3867 bool HasUseCounter(UseCounter aUseCounter) const { 3868 return mUseCounters[aUseCounter]; 3869 } 3870 3871 const StyleUseCounters* GetStyleUseCounters() { 3872 return mStyleUseCounters.get(); 3873 } 3874 3875 // Propagate our use counters explicitly into the specified referencing 3876 // document. 3877 // 3878 // This is used for SVG image documents, which cannot be enumerated in the 3879 // referencing document's ReportUseCounters() like external resource documents 3880 // can. 3881 void PropagateImageUseCounters(Document* aReferencingDocument); 3882 3883 void CollectShadowedHTMLFormElementProperty(const nsAString& aName); 3884 3885 // Called to track whether this document has had any interaction. 3886 // This is used to track whether we should permit "beforeunload". 3887 // Note: These APIs are deprecated (bug 1766214), and should not be used in 3888 // new code. Please use HasBeenUserGestureActivated() or 3889 // HasValidTransientUserGestureActivation() APIs which align with the spec 3890 // (https://html.spec.whatwg.org/multipage/interaction.html#tracking-user-activation) 3891 // more and also support fission nicer. 3892 void SetUserHasInteracted(); 3893 bool UserHasInteracted() const { return mUserHasInteracted; } 3894 void ResetUserInteractionTimer(); 3895 3896 // Whether we're cloning the contents of an SVG use element. 3897 bool CloningForSVGUse() const { return mCloningForSVGUse; } 3898 3899 // If this is true, we're ignoring scrolling to a fragment. 3900 bool ForceLoadAtTop() const { return mForceLoadAtTop; } 3901 3902 /** 3903 * Return false if it's allowed to notify DevTools of node removals in this 3904 * document. 3905 */ 3906 [[nodiscard]] bool SuppressedNotifyingDevToolsOfNodeRemovals() const { 3907 return mSuppressNotifyingDevToolsOfNodeRemovals; 3908 } 3909 friend class AutoSuppressNotifyingDevToolsOfNodeRemovals; 3910 3911 // https://w3c.github.io/trusted-types/dist/spec/#require-trusted-types-for-csp-directive 3912 bool HasPolicyWithRequireTrustedTypesForDirective() const { 3913 return mHasPolicyWithRequireTrustedTypesForDirective; 3914 } 3915 void SetHasPolicyWithRequireTrustedTypesForDirective( 3916 bool aHasPolicyWithRequireTrustedTypesForDirective) { 3917 mHasPolicyWithRequireTrustedTypesForDirective = 3918 aHasPolicyWithRequireTrustedTypesForDirective; 3919 } 3920 bool IsClipboardCopyTriggered() const { return mClipboardCopyTriggered; } 3921 void ClearClipboardCopyTriggered() { mClipboardCopyTriggered = false; } 3922 void SetClipboardCopyTriggered() { mClipboardCopyTriggered = true; } 3923 3924 // This should be called when this document receives events which are likely 3925 // to be user interaction with the document, rather than the byproduct of 3926 // interaction with the browser (i.e. a keypress to scroll the view port, 3927 // keyboard shortcuts, etc). This is used to decide whether we should 3928 // permit autoplay audible media. This also gesture activates all other 3929 // content documents in this tab. 3930 void NotifyUserGestureActivation( 3931 UserActivation::Modifiers aModifiers = UserActivation::Modifiers::None()); 3932 3933 // This function is used for mochitest only. 3934 void ClearUserGestureActivation(); 3935 3936 // Return true if NotifyUserGestureActivation() has been called on any 3937 // document in the document tree. 3938 bool HasBeenUserGestureActivated(); 3939 3940 // Returns true if this document was loaded with an user interaction, 3941 // allowing a text directive to be scrolled to if the document was loaded with 3942 // a text fragment. This call consumes this flag, ie. a subsequent call will 3943 // return false. 3944 bool ConsumeTextDirectiveUserActivation(); 3945 3946 // Reture timestamp of last user gesture in milliseconds relative to 3947 // navigation start timestamp. 3948 DOMHighResTimeStamp LastUserGestureTimeStamp(); 3949 3950 // Return true if there is transient user gesture activation and it hasn't yet 3951 // timed out or hasn't been consumed. 3952 bool HasValidTransientUserGestureActivation() const; 3953 3954 // Return true if HasValidTransientUserGestureActivation() would return true, 3955 // and consume the activation. 3956 bool ConsumeTransientUserGestureActivation(); 3957 3958 bool GetTransientUserGestureActivationModifiers( 3959 UserActivation::Modifiers* aModifiers); 3960 3961 BrowsingContext* GetBrowsingContext() const; 3962 3963 // This document is a WebExtension page, it might be a background page, a 3964 // popup, a visible tab, a visible iframe ...e.t.c. 3965 bool IsExtensionPage() const; 3966 3967 bool HasScriptsBlockedBySandbox() const; 3968 3969 enum class ReportToConsole : bool { No, Yes }; 3970 void ReportHasScrollLinkedEffect( 3971 const TimeStamp& aTimeStamp, 3972 ReportToConsole aReportToConsole = ReportToConsole::Yes); 3973 bool HasScrollLinkedEffect() const; 3974 3975 #ifdef DEBUG 3976 void AssertDocGroupMatchesKey() const; 3977 #endif 3978 3979 DocGroup* GetDocGroup() const { 3980 #ifdef DEBUG 3981 AssertDocGroupMatchesKey(); 3982 #endif 3983 return mDocGroup; 3984 } 3985 3986 DocGroup* GetDocGroupOrCreate(); 3987 3988 /** 3989 * If we're a sub-document, the parent document's layout can affect our style 3990 * and layout (due to the viewport size, viewport units, media queries...). 3991 * 3992 * This function returns true if our parent document and our child document 3993 * can observe each other. If they cannot, then we don't need to synchronously 3994 * update the parent document layout every time the child document may need 3995 * up-to-date layout information. 3996 */ 3997 bool StyleOrLayoutObservablyDependsOnParentDocumentLayout() const { 3998 return GetInProcessParentDocument() && 3999 GetDocGroup() == GetInProcessParentDocument()->GetDocGroup(); 4000 } 4001 4002 void AddIntersectionObserver(DOMIntersectionObserver& aObserver) { 4003 MOZ_ASSERT(!mIntersectionObservers.Contains(&aObserver), 4004 "Intersection observer already in the list"); 4005 mIntersectionObservers.AppendElement(&aObserver); 4006 } 4007 void RemoveIntersectionObserver(DOMIntersectionObserver& aObserver) { 4008 // TODO(emilio): This can fail during unlink because Document unlink clears 4009 // the IntersectionObserver array, but it seems it wouldn't need to? 4010 // MOZ_ASSERT(mIntersectionObservers.Contains(&aObserver)); 4011 mIntersectionObservers.RemoveElement(&aObserver); 4012 } 4013 bool HasIntersectionObservers() const { 4014 return !mIntersectionObservers.IsEmpty(); 4015 } 4016 4017 // Update intersection observers in this document and all 4018 // same-process subdocuments. 4019 void UpdateIntersections(TimeStamp aNowTime); 4020 // Update the EffectsInfo of remote browsers. 4021 void UpdateRemoteFrameEffects(bool aIncludeInactive = false); 4022 MOZ_CAN_RUN_SCRIPT void NotifyIntersectionObservers(); 4023 4024 DOMIntersectionObserver* GetLazyLoadObserver() { return mLazyLoadObserver; } 4025 DOMIntersectionObserver& EnsureLazyLoadObserver(); 4026 4027 bool HasElementsWithLastRememberedSize() const { 4028 return !mElementsObservedForLastRememberedSize.IsEmpty(); 4029 } 4030 void ObserveForLastRememberedSize(Element&); 4031 void UnobserveForLastRememberedSize(Element&); 4032 void UpdateLastRememberedSizes(); 4033 4034 // Dispatch a runnable related to the document. 4035 nsresult Dispatch(already_AddRefed<nsIRunnable>&& aRunnable) const; 4036 4037 // The URLs passed to this function should match what 4038 // JS::DescribeScriptedCaller() returns, since this API is used to 4039 // determine whether some code is being called from a tracking script. 4040 void NoteScriptTrackingStatus(const nsACString& aURL, 4041 net::ClassificationFlags& aFlags); 4042 // The JSContext passed to this method represents the context that we want to 4043 // determine if it belongs to a tracker. 4044 bool IsScriptTracking(JSContext* aCx) const; 4045 4046 // Acquires the script tracking flags for the currently executing script. If 4047 // the currently executing script is not a tracker, it will return the 4048 // classification flags of the document. 4049 net::ClassificationFlags GetScriptTrackingFlags() const; 4050 4051 net::ClassificationFlags GetClassificationFlags() { 4052 return mClassificationFlags; 4053 } 4054 void SetClassificationFlags(net::ClassificationFlags aFlags) { 4055 mClassificationFlags = aFlags; 4056 } 4057 4058 // ResizeObserver usage. 4059 void AddResizeObserver(ResizeObserver& aObserver) { 4060 MOZ_ASSERT(!mResizeObservers.Contains(&aObserver)); 4061 mResizeObservers.AppendElement(&aObserver); 4062 } 4063 void RemoveResizeObserver(ResizeObserver& aObserver) { 4064 MOZ_ASSERT(mResizeObservers.Contains(&aObserver)); 4065 mResizeObservers.RemoveElement(&aObserver); 4066 } 4067 bool HasResizeObservers() const { return !mResizeObservers.IsEmpty(); } 4068 4069 void ScheduleResizeObserversNotification(); 4070 /** 4071 * Calls GatherActiveObservations(aDepth) for all ResizeObservers. 4072 * All observations in each ResizeObserver with element's depth more than 4073 * aDepth will be gathered. 4074 */ 4075 void GatherAllActiveResizeObservations(uint32_t aDepth); 4076 /** 4077 * Calls BroadcastActiveObservations() for all ResizeObservers. 4078 * It also returns the shallowest depth of observed target elements with 4079 * active observations from all ResizeObservers or 4080 * numeric_limits<uint32_t>::max() if there aren't any active observations 4081 * at all. 4082 */ 4083 MOZ_CAN_RUN_SCRIPT uint32_t BroadcastAllActiveResizeObservations(); 4084 /** 4085 * Returns whether there is any ResizeObserver that has active 4086 * observations. 4087 */ 4088 bool HasAnyActiveResizeObservations() const; 4089 /** 4090 * Returns whether there is any ResizeObserver that has skipped observations. 4091 */ 4092 bool HasAnySkippedResizeObservations() const; 4093 /** 4094 * Determine proximity to viewport for content-visibility: auto elements and 4095 * notify resize observers. 4096 */ 4097 MOZ_CAN_RUN_SCRIPT void 4098 DetermineProximityToViewportAndNotifyResizeObservers(); 4099 4100 already_AddRefed<ViewTransition> StartViewTransition( 4101 const ViewTransitionUpdateCallbackOrStartViewTransitionOptions&); 4102 ViewTransition* GetActiveViewTransition() const { 4103 return mActiveViewTransition; 4104 } 4105 void ClearActiveViewTransition(); 4106 MOZ_CAN_RUN_SCRIPT void PerformPendingViewTransitionOperations(); 4107 void EnsureViewTransitionOperationsHappen(); 4108 void MaybeSkipTransitionAfterVisibilityChange(); 4109 4110 void ScheduleViewTransitionUpdateCallback(ViewTransition* aVt); 4111 MOZ_CAN_RUN_SCRIPT void FlushViewTransitionUpdateCallbackQueue(); 4112 4113 // Getter for PermissionDelegateHandler. Performs lazy initialization. 4114 PermissionDelegateHandler* GetPermissionDelegateHandler(); 4115 4116 // Notify the document that a fetch or a XHR request has completed 4117 // succesfully in this document. This is used by the password manager to infer 4118 // whether a form is submitted. 4119 void NotifyFetchOrXHRSuccess(); 4120 4121 // Set whether NotifyFetchOrXHRSuccess should dispatch an event. 4122 void SetNotifyFetchSuccess(bool aShouldNotify); 4123 4124 // When this is set, removing a form or a password field from DOM 4125 // sends a Chrome-only event. This is now only used by the password manager 4126 // and formautofill. 4127 void SetNotifyFormOrPasswordRemoved(bool aShouldNotify); 4128 4129 // This function is used by HTMLFormElement and HTMLInputElement to determin 4130 // whether to send an event when it is removed from DOM. 4131 bool ShouldNotifyFormOrPasswordRemoved() const { 4132 return mShouldNotifyFormOrPasswordRemoved; 4133 } 4134 4135 HTMLEditor* GetHTMLEditor() const; 4136 4137 /** 4138 * Localization 4139 * 4140 * For more information on DocumentL10n see 4141 * intl/l10n/docs/fluent/tutorial.rst 4142 */ 4143 4144 public: 4145 /** 4146 * This is a public method exposed on Document WebIDL 4147 * to chrome only documents. 4148 */ 4149 DocumentL10n* GetL10n() const { return mDocumentL10n.get(); } 4150 4151 /** 4152 * Whether there's any async l10n mutation work pending. 4153 * 4154 * When this turns false, we fire the L10nMutationsFinished event. 4155 */ 4156 bool HasPendingL10nMutations() const; 4157 4158 /** 4159 * This method should be called when the container 4160 * of l10n resources parsing is completed. 4161 * 4162 * It triggers initial async fetch of the resources 4163 * as early as possible. 4164 * 4165 * In HTML case this is </head>. 4166 * In XUL case this is </linkset>. 4167 */ 4168 void OnL10nResourceContainerParsed(); 4169 4170 /** 4171 * This method should be called when a link element 4172 * with rel="localization" is being added to the 4173 * l10n resource container element. 4174 */ 4175 void LocalizationLinkAdded(Element* aLinkElement); 4176 4177 /** 4178 * This method should be called when a link element 4179 * with rel="localization" is being removed. 4180 */ 4181 void LocalizationLinkRemoved(Element* aLinkElement); 4182 4183 /** 4184 * This method should be called as soon as the 4185 * parsing of the document is completed. 4186 * 4187 * In HTML/XHTML this happens when we finish parsing 4188 * the document element. 4189 * In XUL it happens at `DoneWalking`, during 4190 * `MozBeforeInitialXULLayout`. 4191 */ 4192 void OnParsingCompleted(); 4193 4194 /** 4195 * This method is called when the initial translation 4196 * of the document is completed. 4197 * 4198 * It unblocks the load event if translation was blocking it. 4199 * 4200 * If the `aL10nCached` is set to `true`, and the document has 4201 * a prototype, it will set the `isL10nCached` flag on it. 4202 */ 4203 void InitialTranslationCompleted(bool aL10nCached); 4204 4205 /** 4206 * Returns whether the document allows localization. 4207 */ 4208 bool AllowsL10n() const; 4209 4210 void SetAllowDeclarativeShadowRoots(bool aAllowDeclarativeShadowRoots); 4211 bool AllowsDeclarativeShadowRoots() const; 4212 4213 void SuspendDOMNotifications() { 4214 MOZ_ASSERT(IsHTMLDocument(), 4215 "Currently suspending DOM notifications is supported only on " 4216 "HTML documents."); 4217 mSuspendDOMNotifications = true; 4218 } 4219 4220 void ResumeDOMNotifications() { mSuspendDOMNotifications = false; } 4221 4222 bool DOMNotificationsSuspended() const { return mSuspendDOMNotifications; } 4223 4224 bool IsExpectingEndLoad() { return mDidCallBeginLoad; } 4225 4226 protected: 4227 RefPtr<DocumentL10n> mDocumentL10n; 4228 4229 /** 4230 * Return true when you want a document without explicitly specified viewport 4231 * dimensions/scale to be treated as if "width=device-width" had in fact been 4232 * specified. 4233 */ 4234 virtual bool UseWidthDeviceWidthFallbackViewport() const; 4235 4236 private: 4237 bool IsErrorPage() const; 4238 4239 // Notifies the pres context that an image we track may have started or 4240 // stopped animating. 4241 void AnimatedImageStateMaybeChanged(bool aAnimating); 4242 4243 // Takes the bits from mStyleUseCounters if appropriate, and sets them in 4244 // mUseCounters. 4245 void SetCssUseCounterBits(); 4246 4247 void ParseWidthAndHeightInMetaViewport(const nsAString& aWidthString, 4248 const nsAString& aHeightString, 4249 bool aIsAutoScale); 4250 4251 // Parse scale values in viewport meta tag for a given |aHeaderField| which 4252 // represents the scale property and returns the scale value if it's valid. 4253 Maybe<LayoutDeviceToScreenScale> ParseScaleInHeader(nsAtom* aHeaderField); 4254 4255 // Parse scale values in |aViewportMetaData| and set the values in 4256 // mScaleMinFloat, mScaleMaxFloat and mScaleFloat respectively. 4257 void ParseScalesInViewportMetaData(const ViewportMetaData& aViewportMetaData); 4258 4259 // Get parent FeaturePolicy from container. The parent FeaturePolicy is 4260 // stored in parent iframe or container's browsingContext (cross process) 4261 already_AddRefed<mozilla::dom::FeaturePolicy> GetParentFeaturePolicy(); 4262 4263 public: 4264 const OriginTrials& Trials() const { return mTrials; } 4265 4266 dom::InteractiveWidget InteractiveWidget() const { 4267 return mInteractiveWidgetMode; 4268 } 4269 4270 private: 4271 void DoCacheAllKnownLangPrefs(); 4272 void RecomputeLanguageFromCharset(); 4273 bool GetSHEntryHasUserInteraction(); 4274 4275 void AppendAutoFocusCandidateToTopDocument(Element* aAutoFocusCandidate); 4276 4277 public: 4278 void SetMayNeedFontPrefsUpdate() { mMayNeedFontPrefsUpdate = true; } 4279 4280 bool MayNeedFontPrefsUpdate() { return mMayNeedFontPrefsUpdate; } 4281 4282 void SetSHEntryHasUserInteraction(bool aHasInteraction); 4283 4284 nsAtom* GetContentLanguageAsAtomForStyle() const; 4285 nsAtom* GetLanguageForStyle() const; 4286 4287 /** 4288 * Fetch the user's font preferences for the given aLanguage's 4289 * language group. 4290 */ 4291 const LangGroupFontPrefs* GetFontPrefsForLang( 4292 nsAtom* aLanguage, bool* aNeedsToCache = nullptr) const; 4293 4294 void ForceCacheLang(nsAtom* aLanguage) { 4295 if (!mLanguagesUsed.EnsureInserted(aLanguage)) { 4296 return; 4297 } 4298 GetFontPrefsForLang(aLanguage); 4299 } 4300 4301 void CacheAllKnownLangPrefs() { 4302 if (!mMayNeedFontPrefsUpdate) { 4303 return; 4304 } 4305 DoCacheAllKnownLangPrefs(); 4306 } 4307 4308 nsINode* GetServoRestyleRoot() const { return mServoRestyleRoot; } 4309 4310 uint32_t GetServoRestyleRootDirtyBits() const { 4311 MOZ_ASSERT(mServoRestyleRoot); 4312 MOZ_ASSERT(mServoRestyleRootDirtyBits); 4313 return mServoRestyleRootDirtyBits; 4314 } 4315 4316 void ClearServoRestyleRoot() { 4317 mServoRestyleRoot = nullptr; 4318 mServoRestyleRootDirtyBits = 0; 4319 } 4320 4321 inline void SetServoRestyleRoot(nsINode* aRoot, uint32_t aDirtyBits); 4322 inline void SetServoRestyleRootDirtyBits(uint32_t aDirtyBits); 4323 4324 bool ShouldThrowOnDynamicMarkupInsertion() { 4325 return mThrowOnDynamicMarkupInsertionCounter; 4326 } 4327 4328 void IncrementThrowOnDynamicMarkupInsertionCounter() { 4329 ++mThrowOnDynamicMarkupInsertionCounter; 4330 } 4331 4332 void DecrementThrowOnDynamicMarkupInsertionCounter() { 4333 MOZ_ASSERT(mThrowOnDynamicMarkupInsertionCounter); 4334 --mThrowOnDynamicMarkupInsertionCounter; 4335 } 4336 4337 // https://html.spec.whatwg.org/#unload-counter 4338 bool ShouldIgnoreOpens() const { return mIgnoreOpensDuringUnloadCounter; } 4339 4340 // https://html.spec.whatwg.org/#unload-counter 4341 void IncrementIgnoreOpensDuringUnloadCounter() { 4342 ++mIgnoreOpensDuringUnloadCounter; 4343 } 4344 4345 // https://html.spec.whatwg.org/#unload-counter 4346 void DecrementIgnoreOpensDuringUnloadCounter() { 4347 MOZ_ASSERT(mIgnoreOpensDuringUnloadCounter); 4348 --mIgnoreOpensDuringUnloadCounter; 4349 } 4350 4351 mozilla::dom::FeaturePolicy* FeaturePolicy() const; 4352 4353 /** 4354 * Find the (non-anonymous) content in this document for aFrame. It will 4355 * be aFrame's content node if that content is in this document and not 4356 * anonymous. Otherwise, when aFrame is in a subdocument, we use the frame 4357 * element containing the subdocument containing aFrame, and/or find the 4358 * nearest non-anonymous ancestor in this document. 4359 * Returns null if there is no such element. 4360 */ 4361 nsIContent* GetContentInThisDocument(nsIFrame* aFrame) const; 4362 4363 void ReportShadowDOMUsage(); 4364 4365 // Sets flags for media telemetry. 4366 void SetDocTreeHadMedia(); 4367 4368 dom::XPathEvaluator* XPathEvaluator(); 4369 4370 void MaybeInitializeFinalizeFrameLoaders(); 4371 4372 void SetDelayFrameLoaderInitialization(bool aDelayFrameLoaderInitialization) { 4373 mDelayFrameLoaderInitialization = aDelayFrameLoaderInitialization; 4374 } 4375 4376 void SetPrototypeDocument(nsXULPrototypeDocument* aPrototype); 4377 4378 nsIPermissionDelegateHandler* PermDelegateHandler(); 4379 4380 // Returns whether this is a top-level about:blank page without an opener (and 4381 // thus likely not accessible by content). Likely because it shouldn't be used 4382 // for security checks for example, see bug 1860098. 4383 bool IsLikelyContentInaccessibleTopLevelAboutBlank() const; 4384 4385 // CSS prefers-color-scheme media feature for this document. 4386 enum class IgnoreRFP { No, Yes }; 4387 ColorScheme PreferredColorScheme(IgnoreRFP = IgnoreRFP::No) const; 4388 // Returns the initial color-scheme used for this document based on the 4389 // color-scheme meta tag. 4390 ColorScheme DefaultColorScheme() const; 4391 4392 static bool HasRecentlyStartedForegroundLoads(); 4393 4394 static bool AutomaticStorageAccessPermissionCanBeGranted( 4395 nsIPrincipal* aPrincipal); 4396 4397 already_AddRefed<Promise> AddCertException(bool aIsTemporary, 4398 ErrorResult& aError); 4399 4400 void ReloadWithHttpsOnlyException(); 4401 4402 // Subframes need to be static cloned after the main document has been 4403 // embedded within a script global. A `PendingFrameStaticClone` is a static 4404 // clone which has not yet been performed. 4405 // 4406 // The getter returns a direct reference to an internal array which is 4407 // manipulated from within printing code. 4408 struct PendingFrameStaticClone { 4409 PendingFrameStaticClone() = default; 4410 PendingFrameStaticClone(PendingFrameStaticClone&&) = default; 4411 PendingFrameStaticClone& operator=(PendingFrameStaticClone&&) = default; 4412 ~PendingFrameStaticClone(); 4413 4414 RefPtr<nsFrameLoaderOwner> mElement; 4415 RefPtr<nsFrameLoader> mStaticCloneOf; 4416 }; 4417 void AddPendingFrameStaticClone(nsFrameLoaderOwner* aElement, 4418 nsFrameLoader* aStaticCloneOf); 4419 4420 bool ShouldAvoidNativeTheme() const; 4421 4422 static bool IsValidDomain(nsIURI* aOrigHost, nsIURI* aNewURI); 4423 4424 // Inform a parent document that a BrowserBridgeChild has been created for 4425 // an OOP sub-document. 4426 // (This is the OOP counterpart to nsDocLoader::ChildEnteringOnload) 4427 void OOPChildLoadStarted(BrowserBridgeChild* aChild); 4428 4429 // Inform a parent document that the BrowserBridgeChild for one of its 4430 // OOP sub-documents is done calling its onload handler. 4431 // (This is the OOP counterpart to nsDocLoader::ChildDoneWithOnload) 4432 void OOPChildLoadDone(BrowserBridgeChild* aChild); 4433 4434 void ClearOOPChildrenLoading(); 4435 4436 bool HasOOPChildrenLoading() { return !mOOPChildrenLoading.IsEmpty(); } 4437 4438 void SetDidHitCompleteSheetCache() { mDidHitCompleteSheetCache = true; } 4439 4440 bool DidHitCompleteSheetCache() const { return mDidHitCompleteSheetCache; } 4441 4442 /** 4443 * Get the `HighlightRegistry` which contains all highlights associated 4444 * with this document. 4445 */ 4446 class HighlightRegistry& HighlightRegistry(); 4447 4448 /** 4449 * @brief Returns the `FragmentDirective` object which contains information 4450 * and functionality to extract or create text directives. 4451 * Guaranteed to be non-null. 4452 */ 4453 class FragmentDirective* FragmentDirective(); 4454 4455 bool ShouldResistFingerprinting(RFPTarget aTarget) const; 4456 bool IsInPrivateBrowsing() const; 4457 4458 const Maybe<RFPTargetSet>& GetOverriddenFingerprintingSettings() const { 4459 return mOverriddenFingerprintingSettings; 4460 } 4461 4462 // Recompute the current resist fingerprinting state. Returns true when 4463 // the state was changed. 4464 bool RecomputeResistFingerprinting(bool aForceRefreshRTPCallerType = false); 4465 4466 // Recompute the partitionKey for this document if needed. This is for 4467 // handling the case where the principal of the document is changed during the 4468 // loading, e.g. a sandboxed document. We only need to recompute for the 4469 // top-level content document. 4470 void MaybeRecomputePartitionKey(); 4471 4472 void RecordCanvasUsage(CanvasUsage& aUsage); 4473 void RecordFontFingerprinting(); 4474 4475 bool MayHaveDOMActivateListeners() const; 4476 4477 void DropStyleSet(); 4478 4479 // Get a list of all Document objects which are present in the current 4480 // process. This should not be used in hot code paths. 4481 // 4482 // NOTE: This includes both primary and data documents, as well as documents 4483 // which have not yet been fully initialized. 4484 static void GetAllInProcessDocuments( 4485 nsTArray<RefPtr<Document>>& aAllDocuments); 4486 4487 protected: 4488 // Returns the WindowContext for the document that we will contribute 4489 // page use counters to. 4490 WindowContext* GetWindowContextForPageUseCounters() const; 4491 4492 void DoUpdateSVGUseElementShadowTrees(); 4493 4494 already_AddRefed<nsIPrincipal> MaybeDowngradePrincipal( 4495 nsIPrincipal* aPrincipal); 4496 4497 void EnsureOnloadBlocker(); 4498 4499 void SendToConsole(nsCOMArray<nsISecurityConsoleMessage>& aMessages); 4500 4501 // Returns true if the scheme for the url for this document is "about". 4502 bool IsAboutPage() const; 4503 4504 bool ContainsEMEContent(); 4505 bool ContainsMSEContent(); 4506 4507 /** 4508 * Returns the title element of the document as defined by the HTML 4509 * specification, or null if there isn't one. For documents whose root 4510 * element is an <svg:svg>, this is the first <svg:title> element that's a 4511 * child of the root. For other documents, it's the first HTML title element 4512 * in the document. 4513 */ 4514 Element* GetTitleElement(); 4515 4516 void RecordNavigationTiming(ReadyState aReadyState); 4517 4518 // Recomputes the visibility state but doesn't set the new value. 4519 dom::VisibilityState ComputeVisibilityState() const; 4520 4521 // Since we wouldn't automatically play media from non-visited page, we need 4522 // to notify window when the page was first visited. 4523 void MaybeActiveMediaComponents(); 4524 4525 // Apply the fullscreen state to the document, and trigger related 4526 // events. It returns false if the fullscreen element ready check 4527 // fails and nothing gets changed. 4528 MOZ_CAN_RUN_SCRIPT_BOUNDARY bool ApplyFullscreen( 4529 UniquePtr<FullscreenRequest>); 4530 4531 void RemoveDocStyleSheetsFromStyleSets(); 4532 void ResetStylesheetsToURI(nsIURI* aURI); 4533 void FillStyleSet(); 4534 void FillStyleSetUserAndUASheets(); 4535 void FillStyleSetDocumentSheets(); 4536 void CompatibilityModeChanged(); 4537 bool NeedsQuirksSheet() const { 4538 // SVG documents never load quirk.css. 4539 // FIXME(emilio): Can SVG documents be in quirks mode anyway? 4540 return mCompatMode == eCompatibility_NavQuirks && !IsSVGDocument(); 4541 } 4542 void AddStyleSheetToStyleSets(StyleSheet&); 4543 void RemoveStyleSheetFromStyleSets(StyleSheet&); 4544 void NotifyStyleSheetApplicableStateChanged(); 4545 // Just like EnableStyleSheetsForSet, but doesn't check whether 4546 // aSheetSet is null and allows the caller to control whether to set 4547 // aSheetSet as the preferred set in the CSSLoader. 4548 void EnableStyleSheetsForSetInternal(const nsAString& aSheetSet, 4549 bool aUpdateCSSLoader); 4550 4551 already_AddRefed<nsIURI> GetDomainURI(); 4552 already_AddRefed<nsIURI> CreateInheritingURIForHost( 4553 const nsACString& aHostString); 4554 already_AddRefed<nsIURI> RegistrableDomainSuffixOfInternal( 4555 const nsAString& aHostSuffixString, nsIURI* aOrigHost); 4556 4557 MOZ_CAN_RUN_SCRIPT void WriteCommon(const nsAString& aText, 4558 bool aNewlineTerminate, bool aIsTrusted, 4559 nsIPrincipal* aSubjectPrincipal, 4560 mozilla::ErrorResult& aRv); 4561 // A version of WriteCommon used by WebIDL bindings 4562 MOZ_CAN_RUN_SCRIPT void WriteCommon( 4563 const mozilla::dom::Sequence<OwningTrustedHTMLOrString>& aText, 4564 bool aNewlineTerminate, nsIPrincipal* aSubjectPrincipal, 4565 mozilla::ErrorResult& rv); 4566 4567 void* GenerateParserKey(void); 4568 4569 private: 4570 // ExecCommandParam indicates how HTMLDocument.execCommand() treats given the 4571 // parameter. 4572 enum class ExecCommandParam : uint8_t { 4573 // Always ignore it. 4574 Ignore, 4575 // Treat the given parameter as-is. If the command requires it, use it. 4576 // Otherwise, ignore it. 4577 String, 4578 // Always treat it as boolean parameter. 4579 Boolean, 4580 // Always treat it as boolean, but inverted. 4581 InvertedBoolean, 4582 }; 4583 4584 using GetEditorCommandFunc = mozilla::EditorCommand*(); 4585 4586 struct InternalCommandData { 4587 const char* mXULCommandName; 4588 mozilla::Command mCommand; // uint8_t 4589 // How ConvertToInternalCommand() to treats aValue. 4590 // Its callers don't need to check this. 4591 ExecCommandParam mExecCommandParam; // uint8_t 4592 GetEditorCommandFunc* mGetEditorCommandFunc; 4593 enum class CommandOnTextEditor : uint8_t { 4594 Disabled, 4595 Enabled, 4596 FallThrough, // Not disabled, but handled by HTMLEditor if there is one 4597 }; 4598 CommandOnTextEditor mCommandOnTextEditor; 4599 4600 InternalCommandData() 4601 : mXULCommandName(nullptr), 4602 mCommand(mozilla::Command::DoNothing), 4603 mExecCommandParam(ExecCommandParam::Ignore), 4604 mGetEditorCommandFunc(nullptr), 4605 mCommandOnTextEditor(CommandOnTextEditor::Disabled) {} 4606 InternalCommandData(const char* aXULCommandName, mozilla::Command aCommand, 4607 ExecCommandParam aExecCommandParam, 4608 GetEditorCommandFunc aGetEditorCommandFunc, 4609 CommandOnTextEditor aCommandOnTextEditor) 4610 : mXULCommandName(aXULCommandName), 4611 mCommand(aCommand), 4612 mExecCommandParam(aExecCommandParam), 4613 mGetEditorCommandFunc(aGetEditorCommandFunc), 4614 mCommandOnTextEditor(aCommandOnTextEditor) {} 4615 4616 bool IsAvailableOnlyWhenEditable() const { 4617 return mCommand != mozilla::Command::Cut && 4618 mCommand != mozilla::Command::Copy && 4619 mCommand != mozilla::Command::Paste && 4620 mCommand != mozilla::Command::SetDocumentReadOnly && 4621 mCommand != mozilla::Command::SelectAll; 4622 } 4623 bool IsCutOrCopyCommand() const { 4624 return mCommand == mozilla::Command::Cut || 4625 mCommand == mozilla::Command::Copy; 4626 } 4627 bool IsPasteCommand() const { return mCommand == mozilla::Command::Paste; } 4628 }; 4629 4630 /** 4631 * AutoEditorCommandTarget considers which editor or global command manager 4632 * handles given command. 4633 */ 4634 class MOZ_RAII AutoEditorCommandTarget { 4635 public: 4636 MOZ_CAN_RUN_SCRIPT AutoEditorCommandTarget( 4637 Document& aDocument, const InternalCommandData& aCommandData); 4638 AutoEditorCommandTarget() = delete; 4639 explicit AutoEditorCommandTarget(const AutoEditorCommandTarget& aOther) = 4640 delete; 4641 4642 bool DoNothing() const { return mDoNothing; } 4643 MOZ_CAN_RUN_SCRIPT bool IsEditable(Document* aDocument) const; 4644 bool IsEditor() const { 4645 MOZ_ASSERT_IF(mEditorCommand, mActiveEditor || mHTMLEditor); 4646 return !!mEditorCommand; 4647 } 4648 4649 MOZ_CAN_RUN_SCRIPT bool IsCommandEnabled() const; 4650 MOZ_CAN_RUN_SCRIPT nsresult DoCommand(nsIPrincipal* aPrincipal) const; 4651 template <typename ParamType> 4652 MOZ_CAN_RUN_SCRIPT nsresult DoCommandParam(const ParamType& aParam, 4653 nsIPrincipal* aPrincipal) const; 4654 MOZ_CAN_RUN_SCRIPT nsresult 4655 GetCommandStateParams(nsCommandParams& aParams) const; 4656 4657 // The returned editor's life is guaranteed while this instance is alive. 4658 EditorBase* GetTargetEditor() const; 4659 4660 private: 4661 RefPtr<EditorBase> mActiveEditor; 4662 RefPtr<HTMLEditor> mHTMLEditor; 4663 RefPtr<EditorCommand> mEditorCommand; 4664 const InternalCommandData& mCommandData; 4665 bool mDoNothing = false; 4666 }; 4667 4668 /** 4669 * Helper method to initialize sInternalCommandDataHashtable. 4670 */ 4671 static void EnsureInitializeInternalCommandDataHashtable(); 4672 4673 /** 4674 * ConvertToInternalCommand() returns a copy of InternalCommandData instance. 4675 * Note that if aAdjustedValue is non-nullptr, this method checks whether 4676 * aValue is proper value or not unless InternalCommandData::mExecCommandParam 4677 * is ExecCommandParam::Ignore. For example, if aHTMLCommandName is 4678 * "defaultParagraphSeparator", the value has to be one of "div", "p" or 4679 * "br". If aValue is invalid value for InternalCommandData::mCommand, this 4680 * returns a copy of instance created with default constructor. I.e., its 4681 * mCommand is set to Command::DoNothing. So, this treats aHTMLCommandName 4682 * is unsupported in such case. 4683 * 4684 * @param aHTMLCommandName Command name in HTML, e.g., used by 4685 * execCommand(). 4686 * @param aValue The value which is set to the 3rd parameter 4687 * of execCommand(). 4688 * @param aSubjectPrincipal Principal used for execCommand(). 4689 * @param aRv ErrorResult used for Trusted Type conversion. 4690 * @param aAdjustedValue [out] Must be empty string if set non-nullptr. 4691 * Will be set to adjusted value for executing 4692 * the internal command. 4693 * @return Returns a copy of instance created with the 4694 * default constructor if there is no 4695 * corresponding internal command for 4696 * aHTMLCommandName or aValue is invalid for 4697 * found internal command when aAdjustedValue 4698 * is not nullptr. Otherwise, returns a copy of 4699 * instance registered in 4700 * sInternalCommandDataHashtable. 4701 */ 4702 MOZ_CAN_RUN_SCRIPT InternalCommandData ConvertToInternalCommand( 4703 const nsAString& aHTMLCommandName, 4704 const TrustedHTMLOrString* aValue = nullptr, 4705 nsIPrincipal* aSubjectPrincipal = nullptr, ErrorResult* aRv = nullptr, 4706 nsAString* aAdjustedValue = nullptr); 4707 4708 /** 4709 * AutoRunningExecCommandMarker is AutoRestorer for mIsRunningExecCommand. 4710 * Since it's a bit field, not a bool member, therefore, we cannot use 4711 * AutoRestorer for it. 4712 */ 4713 class MOZ_STACK_CLASS AutoRunningExecCommandMarker final { 4714 public: 4715 AutoRunningExecCommandMarker() = delete; 4716 explicit AutoRunningExecCommandMarker(const AutoRunningExecCommandMarker&) = 4717 delete; 4718 // Guaranteeing the document's lifetime with `MOZ_CAN_RUN_SCRIPT`. 4719 MOZ_CAN_RUN_SCRIPT AutoRunningExecCommandMarker(Document& aDocument, 4720 nsIPrincipal* aPrincipal); 4721 ~AutoRunningExecCommandMarker() { 4722 if (mTreatAsUserInput) { 4723 mDocument.mIsRunningExecCommandByChromeOrAddon = 4724 mHasBeenRunningByChromeOrAddon; 4725 } else { 4726 mDocument.mIsRunningExecCommandByContent = mHasBeenRunningByContent; 4727 } 4728 } 4729 4730 [[nodiscard]] bool IsSafeToRun() const { 4731 // We don't allow nested calls of execCommand even if the caller is chrome 4732 // script. 4733 if (mTreatAsUserInput) { 4734 return !mHasBeenRunningByChromeOrAddon && !mHasBeenRunningByContent; 4735 } 4736 // If current call is by content, we should ignore whether nested with a 4737 // call by addon (or chrome script) because the caller wants to emulate 4738 // user input for making it undoable. So, we should treat the first 4739 // call as user input. 4740 return !mHasBeenRunningByContent; 4741 } 4742 4743 private: 4744 Document& mDocument; 4745 bool mTreatAsUserInput; 4746 bool mHasBeenRunningByContent; 4747 bool mHasBeenRunningByChromeOrAddon; 4748 }; 4749 4750 // Mapping table from HTML command name to internal command. 4751 using InternalCommandDataHashtable = 4752 nsTHashMap<nsStringCaseInsensitiveHashKey, InternalCommandData>; 4753 static InternalCommandDataHashtable* sInternalCommandDataHashtable; 4754 4755 mutable std::bitset<static_cast<size_t>( 4756 DeprecatedOperations::eDeprecatedOperationCount)> 4757 mDeprecationWarnedAbout; 4758 mutable std::bitset<eDocumentWarningCount> mDocWarningWarnedAbout; 4759 4760 // Lazy-initialization to have mDocGroup initialized in prior to the 4761 UniquePtr<ServoStyleSet> mStyleSet; 4762 4763 protected: 4764 // Never ever call this. Only call GetWindow! 4765 nsPIDOMWindowOuter* GetWindowInternal() const; 4766 4767 // Never ever call this. Only call GetScriptHandlingObject! 4768 nsIScriptGlobalObject* GetScriptHandlingObjectInternal() const; 4769 4770 // Never ever call this. Only call AllowXULXBL! 4771 bool InternalAllowXULXBL(); 4772 4773 virtual Element* GetNameSpaceElement() override { return GetRootElement(); } 4774 4775 nsCString GetContentTypeInternal() const { return mContentType; } 4776 4777 // Helper for GetScrollingElement/IsScrollingElement. 4778 bool IsPotentiallyScrollable(HTMLBodyElement* aBody); 4779 4780 void MaybeAllowStorageForOpenerAfterUserInteraction(); 4781 4782 void MaybeStoreUserInteractionAsPermission(); 4783 4784 // Helpers for GetElementsByName. 4785 static bool MatchNameAttribute(Element* aElement, int32_t aNamespaceID, 4786 nsAtom* aAtom, void* aData); 4787 static void* UseExistingNameString(nsINode* aRootNode, const nsString* aName); 4788 4789 void MaybeResolveReadyForIdle(); 4790 4791 using AutomaticStorageAccessPermissionGrantPromise = 4792 MozPromise<bool, bool, true>; 4793 [[nodiscard]] RefPtr<AutomaticStorageAccessPermissionGrantPromise> 4794 AutomaticStorageAccessPermissionCanBeGranted(bool hasUserActivation, 4795 bool aIsThirdPartyTracker); 4796 4797 static void AddToplevelLoadingDocument(Document* aDoc); 4798 static void RemoveToplevelLoadingDocument(Document* aDoc); 4799 static AutoTArray<Document*, 8>* sLoadingForegroundTopLevelContentDocument; 4800 friend class cycleCollection; 4801 4802 nsCOMPtr<nsIReferrerInfo> mPreloadReferrerInfo; 4803 nsCOMPtr<nsIReferrerInfo> mReferrerInfo; 4804 // A request referrer policy, which is a referrer policy, initially the 4805 // default referrer policy. 4806 ReferrerPolicyEnum mRequestReferrerPolicy = 4807 ReferrerPolicyEnum::Strict_origin_when_cross_origin; 4808 4809 nsString mLastModified; 4810 4811 nsCOMPtr<nsIURI> mDocumentURI; 4812 nsCOMPtr<nsIURI> mOriginalURI; 4813 nsCOMPtr<nsIURI> mChromeXHRDocURI; 4814 nsCOMPtr<nsIURI> mDocumentBaseURI; 4815 nsCOMPtr<nsIURI> mChromeXHRDocBaseURI; 4816 nsCOMPtr<nsIURI> mOnionLocationURI; 4817 4818 // A lazily-constructed URL data for style system to resolve URL values. 4819 RefPtr<URLExtraData> mCachedURLData; 4820 nsCOMPtr<nsIReferrerInfo> mCachedReferrerInfoForInternalCSSAndSVGResources; 4821 4822 nsWeakPtr mDocumentLoadGroup; 4823 4824 WeakPtr<nsDocShell> mDocumentContainer; 4825 4826 NotNull<const Encoding*> mCharacterSet; 4827 int32_t mCharacterSetSource; 4828 4829 OriginTrials mTrials; 4830 4831 // This is just a weak pointer; the parent document owns its children. 4832 Document* mParentDocument; 4833 4834 // A reference to the element last returned from GetRootElement(). 4835 Element* mCachedRootElement; 4836 4837 // This is maintained by AutoSetRestoreSVGContextPaint. 4838 const SVGContextPaint* mCurrentContextPaint = nullptr; 4839 4840 // This is a weak reference, but we hold a strong reference to mNodeInfo, 4841 // which in turn holds a strong reference to this mNodeInfoManager. 4842 nsNodeInfoManager* mNodeInfoManager; 4843 RefPtr<css::Loader> mCSSLoader; 4844 RefPtr<css::ImageLoader> mStyleImageLoader; 4845 4846 // The object that contains link color declarations (from the <body> mapped 4847 // attributes), mapped attribute caches, and inline style attribute caches. 4848 RefPtr<AttributeStyles> mAttributeStyles; 4849 4850 // Tracking for images in the document. 4851 nsTHashMap<nsPtrHashKey<imgIRequest>, uint32_t> mTrackedImages; 4852 4853 // A hashtable of ShadowRoots belonging to the composed doc. 4854 // 4855 // See ShadowRoot::Bind and ShadowRoot::Unbind. 4856 ShadowRootSet mComposedShadowRoots; 4857 4858 using SVGUseElementSet = nsTHashSet<SVGUseElement*>; 4859 4860 // The set of <svg:use> elements that need a shadow tree reclone because the 4861 // tree they map to has changed. 4862 SVGUseElementSet mSVGUseElementsNeedingShadowTreeUpdate; 4863 4864 // The set of all object, embed, video/audio elements or 4865 // nsIObjectLoadingContent or DocumentActivity for which this is 4866 // the owner document. (They might not be in the document.) 4867 // 4868 // These are non-owning pointers, the elements are responsible for removing 4869 // themselves when they go away. 4870 UniquePtr<nsTHashSet<nsISupports*>> mActivityObservers; 4871 4872 // A hashtable of styled links keyed by address pointer. 4873 nsTHashSet<Link*> mStyledLinks; 4874 #ifdef DEBUG 4875 // Indicates whether mStyledLinks was cleared or not. This is used to track 4876 // state so we can provide useful assertions to consumers of ForgetLink and 4877 // AddStyleRelevantLink. 4878 bool mStyledLinksCleared; 4879 #endif 4880 4881 // The array of all links that need their status resolved. Links must add 4882 // themselves to this set by calling RegisterPendingLinkUpdate when added to a 4883 // document. 4884 static const size_t kSegmentSize = 128; 4885 4886 using LinksToUpdateList = 4887 SegmentedVector<nsCOMPtr<Link>, kSegmentSize, InfallibleAllocPolicy>; 4888 4889 LinksToUpdateList mLinksToUpdate; 4890 4891 // SMIL Animation Controller, lazily-initialized in GetAnimationController 4892 RefPtr<SMILAnimationController> mAnimationController; 4893 4894 // Table of element properties for this document. 4895 nsPropertyTable mPropertyTable; 4896 4897 // Our cached .children collection 4898 nsCOMPtr<nsIHTMLCollection> mChildrenCollection; 4899 4900 // Various DOM lists 4901 RefPtr<nsContentList> mImages; 4902 RefPtr<nsContentList> mEmbeds; 4903 RefPtr<nsContentList> mLinks; 4904 RefPtr<nsContentList> mForms; 4905 RefPtr<nsContentList> mScripts; 4906 nsCOMPtr<nsIHTMLCollection> mApplets; 4907 RefPtr<nsContentList> mAnchors; 4908 4909 // container for per-context fonts (downloadable, SVG, etc.) 4910 RefPtr<FontFaceSet> mFontFaceSet; 4911 4912 // Last time this document or a one of its sub-documents was focused. If 4913 // focus has never occurred then mLastFocusTime.IsNull() will be true. 4914 TimeStamp mLastFocusTime; 4915 4916 // Last time we found any scroll linked effect in this document. 4917 TimeStamp mLastScrollLinkedEffectDetectionTime; 4918 4919 DocumentState mState{DocumentState::LTR_LOCALE}; 4920 4921 RefPtr<Promise> mReadyForIdle; 4922 4923 RefPtr<mozilla::dom::FeaturePolicy> mFeaturePolicy; 4924 4925 // Permission Delegate Handler, lazily-initialized in 4926 // GetPermissionDelegateHandler 4927 RefPtr<PermissionDelegateHandler> mPermissionDelegateHandler; 4928 4929 // https://html.spec.whatwg.org/#is-initial-about:blank 4930 // Track the initial about:blank status of this document. 4931 // We track both whether the document was previously initial, 4932 // and whether it is an initial about:blank which has had document.open called 4933 // on it (see bug 1995397). 4934 InitialStatus mInitialStatus; 4935 4936 bool mCachedStateObjectValid : 1; 4937 bool mBlockAllMixedContent : 1; 4938 bool mBlockAllMixedContentPreloads : 1; 4939 bool mUpgradeInsecureRequests : 1; 4940 bool mUpgradeInsecurePreloads : 1; 4941 bool mDevToolsWatchingDOMMutations : 1; 4942 4943 // Indicates whether this document is normal as in navigation or loaded as 4944 // data as in XHR or DOMParser. 4945 bool mLoadedAsData : 1; 4946 4947 // https://drafts.csswg.org/css-view-transitions-1/#document-rendering-suppression-for-view-transitions 4948 bool mRenderingSuppressedForViewTransitions : 1; 4949 4950 // True if BIDI is enabled. 4951 bool mBidiEnabled : 1; 4952 // True if we may need to recompute the language prefs for this document. 4953 bool mMayNeedFontPrefsUpdate : 1; 4954 4955 // True if we are trying to fire the load event for the initial about:blank. 4956 // Since the initial about:blank is already in READYSTATE_COMPLETE when 4957 // firing the load event, a different indicator is needed. 4958 // IsInitialDocument() isn't a sufficient indicator, because it 4959 // remains set, when navigating back in history. 4960 bool mInitialAboutBlankLoadCompleting : 1; 4961 4962 bool mIgnoreDocGroupMismatches : 1; 4963 4964 // True if the document is considered for memory reporting as a 4965 // data document 4966 bool mAddedToMemoryReportingAsDataDocument : 1; 4967 4968 // If true, whoever is creating the document has gotten it to the 4969 // point where it's safe to start layout on it. 4970 bool mMayStartLayout : 1; 4971 4972 // True iff we've ever fired a DOMTitleChanged event for this document 4973 bool mHaveFiredTitleChange : 1; 4974 4975 // State for IsShowing(). mIsShowing starts off false. It becomes true when 4976 // OnPageShow happens and becomes false when OnPageHide happens. So it's false 4977 // before the initial load completes and when we're in bfcache or unloaded, 4978 // true otherwise. 4979 bool mIsShowing : 1; 4980 4981 // State for IsVisible(). mVisible starts off true. It becomes false when 4982 // OnPageHide happens, and becomes true again when OnPageShow happens. So 4983 // it's false only when we're in bfcache or unloaded. 4984 bool mVisible : 1; 4985 4986 // State for IsCompletelyLoaded. Starts off false and becomes true after 4987 // pageshow has fired. Doesn't reset after that. 4988 bool mIsCompletelyLoaded : 1; 4989 4990 // True if our content viewer has been removed from the docshell 4991 // (it may still be displayed, but in zombie state). Form control data 4992 // has been saved. 4993 bool mRemovedFromDocShell : 1; 4994 4995 // True iff DNS prefetch is allowed for this document. Note that if the 4996 // document has no window, DNS prefetch won't be performed no matter what. 4997 bool mAllowDNSPrefetch : 1; 4998 4999 // True when this document is a static clone of a normal document 5000 bool mIsStaticDocument : 1; 5001 5002 // True while this document is being cloned to a static document. 5003 bool mCreatingStaticClone : 1; 5004 5005 // True if this static document has any <canvas> element with a 5006 // mozPrintCallback property at the time of the clone. 5007 bool mHasPrintCallbacks : 1; 5008 5009 // True iff the document is being unlinked or deleted. 5010 bool mInUnlinkOrDeletion : 1; 5011 5012 // True if document has ever had script handling object. 5013 bool mHasHadScriptHandlingObject : 1; 5014 5015 // True if we're an SVG document being used as an image. 5016 bool mIsBeingUsedAsImage : 1; 5017 5018 // True if our current document URI's scheme enables privileged CSS rules. 5019 bool mChromeRulesEnabled : 1; 5020 5021 // True if we're loaded in a chrome docshell. 5022 bool mInChromeDocShell : 1; 5023 5024 // True is this document is synthetic : stand alone image, video, audio 5025 // file, etc. 5026 bool mIsSyntheticDocument : 1; 5027 5028 // True is there is a pending runnable which will call 5029 // FlushPendingLinkUpdates(). 5030 bool mHasLinksToUpdateRunnable : 1; 5031 5032 // True if we're flushing pending link updates. 5033 bool mFlushingPendingLinkUpdates : 1; 5034 5035 // True if a DOMMutationObserver is perhaps attached to a node in the 5036 // document. 5037 bool mMayHaveDOMMutationObservers : 1; 5038 5039 // True if an nsIAnimationObserver is perhaps attached to a node in the 5040 // document. 5041 bool mMayHaveAnimationObservers : 1; 5042 5043 // True if the document has a CSP delivered throuh a header 5044 bool mHasCSPDeliveredThroughHeader : 1; 5045 5046 // True if DisallowBFCaching has been called on this document. 5047 bool mBFCacheDisallowed : 1; 5048 5049 bool mHasHadDefaultView : 1; 5050 5051 // Whether style sheet change events will be dispatched for this document 5052 bool mStyleSheetChangeEventsEnabled : 1; 5053 5054 // Whether shadowrootattached/anonymousnodecreated/anonymousnoderemoved events 5055 // will be dispatched for this document. 5056 bool mDevToolsAnonymousAndShadowEventsEnabled : 1; 5057 5058 // Whether DevTools is pausing the page (in which case we don't really want to 5059 // stop rendering). 5060 bool mPausedByDevTools : 1; 5061 // If true, (-moz-native-theme) media query always evaluates to false. 5062 bool mForceNonNativeTheme : 1; 5063 // Whether the document was created by a srcdoc iframe. 5064 bool mIsSrcdocDocument : 1; 5065 5066 // Whether this document has a display document and thus is considered to 5067 // be a resource document. Normally this is the same as !!mDisplayDocument, 5068 // but mDisplayDocument is cleared during Unlink. mHasDisplayDocument is 5069 // valid in the document's destructor. 5070 bool mHasDisplayDocument : 1; 5071 5072 // Is the current mFontFaceSet valid? 5073 bool mFontFaceSetDirty : 1; 5074 5075 // True if we have fired the DOMContentLoaded event, or don't plan to fire one 5076 // (e.g. we're not being parsed at all). 5077 bool mDidFireDOMContentLoaded : 1; 5078 5079 bool mIsTopLevelContentDocument : 1; 5080 5081 bool mIsContentDocument : 1; 5082 5083 // True if we have called BeginLoad and are expecting a paired EndLoad call. 5084 bool mDidCallBeginLoad : 1; 5085 5086 // True if the encoding menu should be disabled. 5087 bool mEncodingMenuDisabled : 1; 5088 5089 // False if we've disabled link handling for elements inside this document, 5090 // true otherwise. 5091 bool mLinksEnabled : 1; 5092 5093 // True if this document is for an SVG-in-OpenType font. 5094 bool mIsSVGGlyphsDocument : 1; 5095 5096 // True if the document is being destroyed. 5097 bool mInDestructor : 1; 5098 5099 // True if the document has been detached from its content viewer. 5100 bool mIsGoingAway : 1; 5101 5102 // Whether we have filled our style set with all the stylesheets. 5103 bool mStyleSetFilled : 1; 5104 5105 // Whether we have a quirks mode stylesheet in the style set. 5106 bool mQuirkSheetAdded : 1; 5107 5108 // True if this document has ever had an HTML or SVG <title> element 5109 // bound to it 5110 bool mMayHaveTitleElement : 1; 5111 5112 bool mDOMLoadingSet : 1; 5113 bool mDOMInteractiveSet : 1; 5114 bool mDOMCompleteSet : 1; 5115 bool mAutoFocusFired : 1; 5116 5117 bool mScrolledToRefAlready : 1; 5118 bool mChangeScrollPosWhenScrollingToRef : 1; 5119 5120 bool mDelayFrameLoaderInitialization : 1; 5121 5122 // True if we should fire load events synchronously 5123 bool mSynchronousDOMContentLoaded : 1; 5124 5125 // Set to true when the document is possibly controlled by the ServiceWorker. 5126 // Used to prevent multiple requests to ServiceWorkerManager. 5127 bool mMaybeServiceWorkerControlled : 1; 5128 5129 // These member variables cache information about the viewport so we don't 5130 // have to recalculate it each time. 5131 bool mAllowZoom : 1; 5132 bool mValidScaleFloat : 1; 5133 bool mValidMinScale : 1; 5134 bool mValidMaxScale : 1; 5135 bool mWidthStrEmpty : 1; 5136 5137 bool mLockingImages : 1; 5138 bool mAnimatingImages : 1; 5139 5140 // Parser aborted. True if the parser of this document was forcibly 5141 // terminated instead of letting it finish at its own pace. 5142 bool mParserAborted : 1; 5143 5144 // Whether we have reported document use counters for this document with 5145 // Telemetry yet. Normally this is only done at document destruction time, 5146 // but for image documents (SVG documents) that are not guaranteed to be 5147 // destroyed, we report use counters when the image cache no longer has any 5148 // imgRequestProxys pointing to them. We track whether we ever reported use 5149 // counters so that we only report them once for the document. 5150 bool mReportedDocumentUseCounters : 1; 5151 5152 bool mHasReportedShadowDOMUsage : 1; 5153 5154 // The HTML spec has a "iframe load in progress" flag, but that doesn't seem 5155 // to have the right semantics. See 5156 // <https://github.com/whatwg/html/issues/4292>. What we have instead is a 5157 // flag that is set while the window's 'load' event is firing if this document 5158 // is the window's document. 5159 bool mLoadEventFiring : 1; 5160 5161 // The HTML spec has a "mute iframe load" flag, but that doesn't seem to have 5162 // the right semantics. See <https://github.com/whatwg/html/issues/4292>. 5163 // What we have instead is a flag that is set if completion of our document 5164 // via document.close() should skip firing the load event. Note that this 5165 // flag is only relevant for HTML documents, but lives here for reasons that 5166 // are documented above on SkipLoadEventAfterClose(). 5167 bool mSkipLoadEventAfterClose : 1; 5168 5169 // When false, the .cookies property is completely disabled 5170 bool mDisableCookieAccess : 1; 5171 5172 // When false, the document.write() API is disabled. 5173 bool mDisableDocWrite : 1; 5174 5175 // Has document.write() been called with a recursion depth higher than 5176 // allowed? 5177 bool mTooDeepWriteRecursion : 1; 5178 5179 /** 5180 * Temporary flag that is set in EndUpdate() to ignore 5181 * MaybeEditingStateChanged() script runners from a nested scope. 5182 */ 5183 bool mPendingMaybeEditingStateChanged : 1; 5184 5185 // mHasBeenEditable is set to true when mEditingState is firstly set to 5186 // eDesignMode or eContentEditable. 5187 bool mHasBeenEditable : 1; 5188 5189 // While we're handling an execCommand call by web app, set 5190 // to true. 5191 bool mIsRunningExecCommandByContent : 1; 5192 // While we're handling an execCommand call by an addon (or chrome script), 5193 // set to true. 5194 bool mIsRunningExecCommandByChromeOrAddon : 1; 5195 5196 // True if we should change the readystate to complete after we fire 5197 // DOMContentLoaded. This happens when we abort a load and 5198 // nsDocumentViewer::EndLoad runs while we still have things blocking 5199 // DOMContentLoaded. We wait for those to complete, and then update the 5200 // readystate when they finish. 5201 bool mSetCompleteAfterDOMContentLoaded : 1; 5202 5203 // Set the true if a completed cached stylesheet was created for the document. 5204 bool mDidHitCompleteSheetCache : 1; 5205 5206 // Whether we have initialized mShouldReportUseCounters and 5207 // mShouldSendPageUseCounters, and sent any needed message to the parent 5208 // process to indicate that use counter data will be sent at some later point. 5209 bool mUseCountersInitialized : 1; 5210 5211 // Whether this document should report use counters. 5212 bool mShouldReportUseCounters : 1; 5213 5214 // Whether this document should send page use counters. Set to true after 5215 // we've called SendExpectPageUseCounters on the top-level WindowGlobal. 5216 bool mShouldSendPageUseCounters : 1; 5217 5218 // Whether the user has interacted with the document or not: 5219 bool mUserHasInteracted : 1; 5220 5221 // We constantly update the user-interaction anti-tracking permission at any 5222 // user-interaction using a timer. This boolean value is set to true when this 5223 // timer is scheduled. 5224 bool mHasUserInteractionTimerScheduled : 1; 5225 5226 // Whether we should resist fingerprinting. 5227 bool mShouldResistFingerprinting : 1; 5228 5229 // Whether we are in private browsing mode. 5230 bool mIsInPrivateBrowsing : 1; 5231 5232 // Whether we're cloning the contents of an SVG use element. 5233 bool mCloningForSVGUse : 1; 5234 5235 bool mAllowDeclarativeShadowRoots : 1; 5236 5237 bool mSuspendDOMNotifications : 1; 5238 5239 bool mForceLoadAtTop : 1; 5240 5241 bool mSuppressNotifyingDevToolsOfNodeRemovals : 1; 5242 5243 // Whether the document's CSP contains a require-trusted-types-for directive. 5244 bool mHasPolicyWithRequireTrustedTypesForDirective : 1; 5245 5246 // Whether a copy event happened. Used to detect when this happens 5247 // while a paste event is being handled in JS. 5248 bool mClipboardCopyTriggered : 1; 5249 5250 // The fingerprinting protections overrides for this document. The value will 5251 // override the default enabled fingerprinting protections for this document. 5252 // This will only get populated if these is one that comes from the local 5253 // fingerprinting protection override pref or WebCompat. Otherwise, a value of 5254 // Nothing() indicates no overrides are present for this document. 5255 Maybe<RFPTargetSet> mOverriddenFingerprintingSettings; 5256 5257 uint8_t mXMLDeclarationBits; 5258 5259 // NOTE(emilio): Technically, this should be a StyleColorSchemeFlags, but we 5260 // use uint8_t to avoid having to include a bunch of style system headers 5261 // everywhere. 5262 uint8_t mColorSchemeBits = 0; 5263 5264 // Currently active onload blockers. 5265 uint32_t mOnloadBlockCount; 5266 5267 // Tracks if we are currently processing any document.write calls (either 5268 // implicit or explicit). Note that if a write call writes out something which 5269 // would block the parser, then mWriteLevel will be incorrect until the parser 5270 // finishes processing that script. 5271 uint32_t mWriteLevel; 5272 5273 uint32_t mContentEditableCount; 5274 EditingState mEditingState; 5275 5276 // Compatibility mode 5277 nsCompatibility mCompatMode; 5278 5279 // Our readyState 5280 ReadyState mReadyState; 5281 5282 // Ancestor's loading state 5283 bool mAncestorIsLoading; 5284 5285 // Our visibility state 5286 dom::VisibilityState mVisibilityState; 5287 5288 enum Type { 5289 eUnknown, // should never be used 5290 eHTML, 5291 eXHTML, 5292 eGenericXML, 5293 eSVG 5294 }; 5295 5296 Type mType; 5297 5298 uint8_t mDefaultElementType; 5299 5300 enum Tri { eTriUnset = 0, eTriFalse, eTriTrue }; 5301 5302 Tri mAllowXULXBL; 5303 5304 bool mSkipDTDSecurityChecks; 5305 5306 // The document's script global object, the object from which the 5307 // document can get its script context and scope. This is the 5308 // *inner* window object. 5309 nsCOMPtr<nsIScriptGlobalObject> mScriptGlobalObject; 5310 5311 // If mIsStaticDocument is true, mOriginalDocument points to the original 5312 // document. 5313 RefPtr<Document> mOriginalDocument; 5314 5315 // The bidi options for this document. What this bitfield means is 5316 // defined in nsBidiUtils.h 5317 uint32_t mBidiOptions; 5318 5319 // The sandbox flags on the document. These reflect the value of the sandbox 5320 // attribute of the associated IFRAME or CSP-protectable content, if existent. 5321 // These are set at load time and are immutable - see nsSandboxFlags.h for the 5322 // possible flags. 5323 uint32_t mSandboxFlags; 5324 5325 // The embedder policy obtained from parsing the HTTP response header or from 5326 // our opener if this is the initial about:blank document. 5327 Maybe<nsILoadInfo::CrossOriginEmbedderPolicy> mEmbedderPolicy; 5328 5329 RefPtr<nsAtom> mContentLanguage; 5330 5331 // The channel that got passed to Document::StartDocumentLoad(), if any. 5332 nsCOMPtr<nsIChannel> mChannel; 5333 5334 nsCOMPtr<nsIContentSecurityPolicy> mPreloadCSP; 5335 RefPtr<PolicyContainer> mPolicyContainer; 5336 5337 private: 5338 nsCString mContentType; 5339 5340 nsTArray<nsString> mAncestorOriginsList; 5341 5342 protected: 5343 // The document's security info 5344 nsCOMPtr<nsITransportSecurityInfo> mSecurityInfo; 5345 5346 // The channel that failed to load and resulted in an error page. 5347 // This only applies to error pages. Might be null. 5348 nsCOMPtr<nsIChannel> mFailedChannel; 5349 5350 // if this document is part of a multipart document, 5351 // the ID can be used to distinguish it from the other parts. 5352 uint32_t mPartID; 5353 5354 // Cycle collector generation in which we're certain that this document 5355 // won't be collected 5356 uint32_t mMarkedCCGeneration; 5357 5358 PresShell* mPresShell; 5359 5360 // All images in process of being preloaded. This is a hashtable so 5361 // we can remove them as the real image loads start; that way we 5362 // make sure to not keep the image load going when no one cares 5363 // about it anymore. 5364 nsRefPtrHashtable<nsURIHashKey, imgIRequest> mPreloadingImages; 5365 5366 // A list of preconnects initiated by the preloader. This prevents 5367 // the same uri from being used more than once, and allows the dom 5368 // builder to not repeat the work of the preloader. 5369 nsTHashMap<nsURIHashKey, bool> mPreloadedPreconnects; 5370 5371 // Current depth of picture elements from parser 5372 uint32_t mPreloadPictureDepth; 5373 5374 // Set if we've found a URL for the current picture 5375 nsString mPreloadPictureFoundSource; 5376 5377 // If we're an external resource document, this will be non-null and will 5378 // point to our "display document": the one that all resource lookups should 5379 // go to. 5380 RefPtr<Document> mDisplayDocument; 5381 5382 uint32_t mEventsSuppressed; 5383 5384 // Any XHR ChannelEventQueues that were suspended on this document while 5385 // events were suppressed. 5386 nsTArray<RefPtr<net::ChannelEventQueue>> mSuspendedQueues; 5387 5388 // Any postMessage events that were suspended on this document while events 5389 // were suppressed. 5390 nsTArray<RefPtr<PostMessageEvent>> mSuspendedPostMessageEvents; 5391 5392 RefPtr<EventListener> mSuppressedEventListener; 5393 5394 /** 5395 * https://html.spec.whatwg.org/#ignore-destructive-writes-counter 5396 */ 5397 uint32_t mIgnoreDestructiveWritesCounter; 5398 5399 // Count of live static clones of this document. 5400 uint32_t mStaticCloneCount; 5401 5402 // If the document is currently printing (or in print preview) this will point 5403 // to the current static clone of this document. This is weak since the clone 5404 // also has a reference to this document. 5405 WeakPtr<Document> mLatestStaticClone; 5406 5407 // Array of nodes that have been blocked to prevent user tracking. 5408 // They most likely have had their nsIChannel canceled by the URL 5409 // classifier. (Safebrowsing) 5410 // 5411 // Weak nsINode pointers are used to allow nodes to disappear. 5412 nsTArray<nsWeakPtr> mBlockedNodesByClassifier; 5413 5414 // Weak reference to mScriptGlobalObject QI:d to nsPIDOMWindow, 5415 // updated on every set of mScriptGlobalObject. 5416 nsPIDOMWindowInner* mWindow; 5417 5418 nsCOMPtr<nsIDocumentEncoder> mCachedEncoder; 5419 5420 dom::FrameRequestManager mFrameRequestManager; 5421 5422 // This object allows us to evict ourself from the back/forward cache. The 5423 // pointer is non-null iff we're currently in the bfcache. 5424 nsIBFCacheEntry* mBFCacheEntry; 5425 5426 // Our base target. 5427 nsString mBaseTarget; 5428 5429 nsCOMPtr<nsIStructuredCloneContainer> mStateObjectContainer; 5430 JS::Heap<JS::Value> mCachedStateObject; 5431 5432 uint32_t mInSyncOperationCount; 5433 5434 UniquePtr<dom::XPathEvaluator> mXPathEvaluator; 5435 5436 nsTArray<RefPtr<AnonymousContent>> mAnonymousContents; 5437 5438 // The <div class="moz-custom-content-container"> that we use to wrap all the 5439 // mAnonymousContents roots. It's a NAC root, child of the root element. 5440 RefPtr<Element> mCustomContentContainer; 5441 5442 uint32_t mBlockDOMContentLoaded; 5443 5444 // Our live MediaQueryLists 5445 LinkedList<MediaQueryList> mDOMMediaQueryLists; 5446 5447 // A hashmap to keep track of which {element, imgRequestProxy} 5448 // combination has been processed to avoid considering the same 5449 // element twice for LargestContentfulPaint. 5450 ContentIdentifiersForLCPType mContentIdentifiersForLCP; 5451 5452 // Array of observers 5453 nsTObserverArray<nsIDocumentObserver*> mObservers; 5454 5455 // Flags for use counters used directly by this document. 5456 UseCounters mUseCounters; 5457 // Flags for use counters from resource documents, static clones, 5458 // and SVG images referenced by this document. Those documents propagate 5459 // their use counters up to here, which then count towards the top-level 5460 // document's page use counters. 5461 UseCounters mChildDocumentUseCounters; 5462 5463 // The CSS property use counters. 5464 UniquePtr<StyleUseCounters> mStyleUseCounters; 5465 5466 TimeStamp mPageUnloadingEventTimeStamp; 5467 5468 RefPtr<DocGroup> mDocGroup; 5469 5470 RefPtr<nsCommandManager> mMidasCommandManager; 5471 5472 // The hashmap of all the tracking script URLs. URLs are added to this map by 5473 // calling NoteScriptTrackingStatus(). Currently we assume that a URL not 5474 // existing in the map means the corresponding script isn't a tracking script. 5475 nsTHashMap<nsCStringHashKey, net::ClassificationFlags> mTrackingScripts; 5476 5477 // Pointer to our parser if we're currently in the process of being 5478 // parsed into. 5479 nsCOMPtr<nsIParser> mParser; 5480 5481 // If the document was created from the the prototype cache there will be a 5482 // reference to the prototype document to allow tracing. 5483 RefPtr<nsXULPrototypeDocument> mPrototypeDocument; 5484 5485 // Weak reference to our sink for in case we no longer have a parser. This 5486 // will allow us to flush out any pending stuff from the sink even if 5487 // EndLoad() has already happened. 5488 nsWeakPtr mWeakSink; 5489 5490 // Our update nesting level 5491 uint32_t mUpdateNestLevel; 5492 5493 // HTTPS-Only Mode Status 5494 // Constants are defined at nsILoadInfo::HTTPS_ONLY_* 5495 uint32_t mHttpsOnlyStatus; 5496 5497 enum ViewportType : uint8_t { 5498 DisplayWidthHeight, 5499 Specified, 5500 Unknown, 5501 }; 5502 5503 ViewportType mViewportType; 5504 5505 // viewport-fit described by 5506 // https://drafts.csswg.org/css-round-display/#viewport-fit-descriptor 5507 ViewportFitType mViewportFit; 5508 5509 // https://drafts.csswg.org/css-viewport/#interactive-widget-section 5510 dom::InteractiveWidget mInteractiveWidgetMode; 5511 5512 // XXXdholbert This should really be modernized to a nsTHashMap or similar, 5513 // though note that the modernization will need to take care to also convert 5514 // the special hash_table_ops logic (e.g. how SubDocClearEntry clears the 5515 // parent document as part of cleaning up an entry in this table). 5516 UniquePtr<PLDHashTable> mSubDocuments; 5517 5518 class HeaderData; 5519 UniquePtr<HeaderData> mHeaderData; 5520 5521 nsTArray<net::EarlyHintConnectArgs> mEarlyHints; 5522 5523 class TitleChangeEvent; 5524 nsRevocableEventPtr<TitleChangeEvent> mPendingTitleChangeEvent; 5525 5526 RefPtr<nsDOMNavigationTiming> mTiming; 5527 5528 // Recorded time of change to 'loading' state 5529 // or time of the page gets restored from BFCache. 5530 TimeStamp mLoadingOrRestoredFromBFCacheTimeStamp; 5531 5532 // Decided to use nsTObserverArray because it allows us to 5533 // remove candidates while iterating them and this is what 5534 // the spec defines. We could implement the spec without 5535 // using nsTObserverArray, however using nsTObserverArray is more clear. 5536 nsTObserverArray<nsWeakPtr> mAutoFocusCandidates; 5537 5538 nsCString mScrollToRef; 5539 5540 // Weak reference to the scope object (aka the script global object) 5541 // that, unlike mScriptGlobalObject, is never unset once set. This 5542 // is a weak reference to avoid leaks due to circular references. 5543 nsWeakPtr mScopeObject; 5544 5545 // Array of intersection observers with active observations. 5546 nsTArray<DOMIntersectionObserver*> mIntersectionObservers; 5547 // Array of resize observers with active observations. 5548 nsTArray<ResizeObserver*> mResizeObservers; 5549 5550 RefPtr<DOMIntersectionObserver> mLazyLoadObserver; 5551 5552 // Elements observed for a last remembered size. 5553 // @see {@link https://drafts.csswg.org/css-sizing-4/#last-remembered} 5554 nsTHashSet<RefPtr<Element>> mElementsObservedForLastRememberedSize; 5555 5556 // Stack of top layer elements. 5557 nsTArray<nsWeakPtr> mTopLayer; 5558 5559 // Stack of open dialogs 5560 // https://html.spec.whatwg.org/#open-dialogs-list 5561 nsTArray<HTMLDialogElement*> mOpenDialogs; 5562 5563 // The last dialog pointer-down target 5564 // https://html.spec.whatwg.org/#dialog-pointerdown-target 5565 nsWeakPtr mLastDialogPointerdownTarget; 5566 5567 // The root of the doc tree in which this document is in. This is only 5568 // non-null when this document is in fullscreen mode. 5569 WeakPtr<Document> mFullscreenRoot; 5570 5571 RefPtr<DOMImplementation> mDOMImplementation; 5572 5573 RefPtr<nsContentList> mImageMaps; 5574 5575 // A set of responsive images keyed by address pointer. 5576 nsTHashSet<HTMLImageElement*> mResponsiveContent; 5577 5578 // The default document timeline associated to this document. 5579 RefPtr<DocumentTimeline> mDocumentTimeline; 5580 // The timeline controller which holds the timelines attached to this 5581 // document. 5582 AnimationTimelinesController mTimelinesController; 5583 5584 RefPtr<dom::ScriptLoader> mScriptLoader; 5585 5586 // Tracker for scroll-driven animations that are waiting to start. 5587 // nullptr until GetOrCreateScrollTimelineAnimationTracker is called. 5588 RefPtr<ScrollTimelineAnimationTracker> mScrollTimelineAnimationTracker; 5589 5590 // A document "without a browsing context" that owns the content of 5591 // HTMLTemplateElement. 5592 RefPtr<Document> mTemplateContentsOwner; 5593 5594 dom::ExternalResourceMap mExternalResourceMap; 5595 5596 // ScreenOrientation "pending promise" as described by 5597 // http://www.w3.org/TR/screen-orientation/ 5598 RefPtr<Promise> mOrientationPendingPromise; 5599 5600 nsTArray<RefPtr<nsFrameLoader>> mInitializableFrameLoaders; 5601 nsTArray<nsCOMPtr<nsIRunnable>> mFrameLoaderFinalizers; 5602 RefPtr<nsRunnableMethod<Document>> mFrameLoaderRunner; 5603 5604 nsTArray<PendingFrameStaticClone> mPendingFrameStaticClones; 5605 5606 // The layout history state that should be used by nodes in this 5607 // document. We only actually store a pointer to it when: 5608 // 1) We have no script global object. 5609 // 2) We haven't had Destroy() called on us yet. 5610 nsCOMPtr<nsILayoutHistoryState> mLayoutHistoryState; 5611 5612 // Mapping of wake lock types to sets of wake locks sentinels 5613 // https://w3c.github.io/screen-wake-lock/#internal-slots 5614 nsTHashMap<WakeLockType, nsTHashSet<RefPtr<WakeLockSentinel>>> mActiveLocks; 5615 5616 // The parsed viewport metadata of the last modified <meta name=viewport> 5617 // element. 5618 UniquePtr<ViewportMetaData> mLastModifiedViewportMetaData; 5619 5620 // A tree ordered list of all color-scheme meta tags in this document. 5621 // 5622 // TODO(emilio): There are other meta tags in the spec that have a similar 5623 // processing model to color-scheme. We could store all in-document meta tags 5624 // here to get sane and fast <meta> element processing. 5625 TreeOrderedArray<HTMLMetaElement*> mColorSchemeMetaTags; 5626 5627 // These member variables cache information about the viewport so we don't 5628 // have to recalculate it each time. 5629 LayoutDeviceToScreenScale mScaleMinFloat; 5630 LayoutDeviceToScreenScale mScaleMaxFloat; 5631 LayoutDeviceToScreenScale mScaleFloat; 5632 CSSToLayoutDeviceScale mPixelRatio; 5633 5634 CSSCoord mMinWidth; 5635 CSSCoord mMaxWidth; 5636 CSSCoord mMinHeight; 5637 CSSCoord mMaxHeight; 5638 5639 RefPtr<EventListenerManager> mListenerManager; 5640 5641 nsCOMPtr<nsIRequest> mOnloadBlocker; 5642 5643 // Gecko-internal sheets used for extensions and such. 5644 // Exposed to privileged script via nsIDOMWindowUtils.loadSheet. 5645 nsTArray<RefPtr<StyleSheet>> mAdditionalSheets[AdditionalSheetTypeCount]; 5646 5647 // Member to store out last-selected stylesheet set. 5648 nsString mLastStyleSheetSet; 5649 nsString mPreferredStyleSheetSet; 5650 5651 RefPtr<DOMStyleSheetSetList> mStyleSheetSetList; 5652 5653 // We lazily calculate declaration blocks for elements with mapped 5654 // attributes. This set contains all elements which need lazy resolution. 5655 nsTHashSet<Element*> mLazyPresElements; 5656 5657 nsTHashSet<RefPtr<nsAtom>> mLanguagesUsed; 5658 5659 // TODO(emilio): Is this hot enough to warrant to be cached? 5660 // EncodingToLang.cpp keeps the atom alive until shutdown, so 5661 // no need for a RefPtr. 5662 nsAtom* mLanguageFromCharset; 5663 5664 // Restyle root for servo's style system. 5665 // 5666 // We store this as an nsINode, rather than as an Element, so that we can 5667 // store the Document node as the restyle root if the entire document (along 5668 // with all document-level native-anonymous content) needs to be restyled. 5669 // 5670 // We also track which "descendant" bits (normal/animation-only/lazy-fc) the 5671 // root corresponds to. 5672 nsCOMPtr<nsINode> mServoRestyleRoot; 5673 uint32_t mServoRestyleRootDirtyBits; 5674 5675 // Used in conjunction with the create-an-element-for-the-token algorithm to 5676 // prevent custom element constructors from being able to use document.open(), 5677 // document.close(), and document.write() when they are invoked by the parser. 5678 uint32_t mThrowOnDynamicMarkupInsertionCounter; 5679 5680 // Count of unload/beforeunload/pagehide operations in progress. 5681 uint32_t mIgnoreOpensDuringUnloadCounter; 5682 5683 nsCOMPtr<nsIDOMXULCommandDispatcher> 5684 mCommandDispatcher; // [OWNER] of the focus tracker 5685 5686 RefPtr<XULBroadcastManager> mXULBroadcastManager; 5687 RefPtr<XULPersist> mXULPersist; 5688 RefPtr<ChromeObserver> mChromeObserver; 5689 5690 RefPtr<HTMLAllCollection> mAll; 5691 5692 // The active view transition. 5693 // https://drafts.csswg.org/css-view-transitions-1/#document-active-view-transition 5694 RefPtr<ViewTransition> mActiveViewTransition; 5695 // The update callback queue. 5696 // https://drafts.csswg.org/css-view-transitions-1/#document-update-callback-queue 5697 nsTArray<RefPtr<ViewTransition>> mViewTransitionUpdateCallbacks; 5698 5699 nsTHashSet<RefPtr<WorkerDocumentListener>> mWorkerListeners; 5700 5701 // Pres shell resolution saved before entering fullscreen mode. 5702 float mSavedResolution; 5703 5704 nsCOMPtr<nsICookieJarSettings> mCookieJarSettings; 5705 5706 bool mHasStoragePermission; 5707 5708 net::ClassificationFlags mClassificationFlags; 5709 5710 // Document generation. Gets incremented everytime it changes. 5711 int32_t mGeneration; 5712 5713 // Cached TabSizes values for the document. 5714 int32_t mCachedTabSizeGeneration; 5715 nsTabSizes mCachedTabSizes; 5716 5717 // This is equal to document's principal but with an isolation key. See 5718 // StoragePrincipalHelper.h to know more. 5719 nsCOMPtr<nsIPrincipal> mPartitionedPrincipal; 5720 5721 // The cached storage principal for this document. 5722 // This is mutable so that we can keep EffectiveStoragePrincipal() const 5723 // which is required due to its CloneDocHelper() call site. :-( 5724 mutable nsCOMPtr<nsIPrincipal> mActiveStoragePrincipal; 5725 5726 // The cached cookie principal for this document. 5727 // This is mutable so that we can keep EffectiveCookiePrincipal() const 5728 // which is required due to its CloneDocHelper() call site. :-( 5729 mutable nsCOMPtr<nsIPrincipal> mActiveCookiePrincipal; 5730 5731 // https://fullscreen.spec.whatwg.org/#list-of-pending-fullscreen-events 5732 nsTArray<UniquePtr<PendingFullscreenEvent>> mPendingFullscreenEvents; 5733 5734 // See GetNextFormNumber and GetNextControlNumber. 5735 int32_t mNextFormNumber; 5736 int32_t mNextControlNumber; 5737 5738 uint32_t mMediaElementWithMSECount = 0; 5739 5740 // Scope preloads per document. This is used by speculative loading as well. 5741 PreloadService mPreloadService; 5742 5743 // See NotifyFetchOrXHRSuccess and SetNotifyFetchSuccess. 5744 bool mShouldNotifyFetchSuccess; 5745 5746 // See SetNotifyFormOrPasswordRemoved and ShouldNotifyFormOrPasswordRemoved. 5747 bool mShouldNotifyFormOrPasswordRemoved; 5748 5749 // Used by the shadowed_html_document_property_access telemetry probe to 5750 // collected shadowed HTMLDocument properties. (Limited to 10 entries) 5751 nsTArray<nsString> mShadowedHTMLDocumentProperties; 5752 5753 // Collection of data used by the pageload event. 5754 PageloadEventData mPageloadEventData; 5755 5756 // Record page load telemetry 5757 void RecordPageLoadEventTelemetry(); 5758 5759 // Accumulate JS telemetry collected 5760 void AccumulateJSTelemetry(); 5761 5762 // Accumulate page load metrics 5763 void AccumulatePageLoadTelemetry(); 5764 5765 // The OOP counterpart to nsDocLoader::mChildrenInOnload. 5766 // Not holding strong refs here since we don't actually use the BBCs. 5767 nsTArray<const BrowserBridgeChild*> mOOPChildrenLoading; 5768 5769 // Registry of custom highlight definitions associated with this document. 5770 RefPtr<class HighlightRegistry> mHighlightRegistry; 5771 5772 // Used for tracking a number of recent canvas extractions (e.g. toDataURL), 5773 // this is used for a canvas fingerprinter detection heuristic. 5774 // Store all recent usages in a single nsTArray instead of a hash map. 5775 nsTArray<CanvasUsage> mCanvasUsageData; 5776 // Timestamp (PR_Now microseconds) of the last update to mCanvasUsageData. 5777 uint64_t mCanvasUsageLastTimestamp = 0; 5778 5779 RefPtr<class FragmentDirective> mFragmentDirective; 5780 UniquePtr<RadioGroupContainer> mRadioGroupContainer; 5781 5782 nsCOMPtr<nsIURI> mTLSCertificateBindingURI; 5783 5784 public: 5785 // Needs to be public because the bindings code pokes at it. 5786 JS::ExpandoAndGeneration mExpandoAndGeneration; 5787 5788 bool HasPendingInitialTranslation(); 5789 5790 nsRefPtrHashtable<nsRefPtrHashKey<Element>, nsXULPrototypeElement> 5791 mL10nProtoElements; 5792 5793 void LoadEventFired(); 5794 5795 RadioGroupContainer& OwnedRadioGroupContainer(); 5796 5797 MOZ_CAN_RUN_SCRIPT static already_AddRefed<Document> ParseHTMLUnsafe( 5798 GlobalObject& aGlobal, const TrustedHTMLOrString& aHTML, 5799 const SetHTMLUnsafeOptions& aOptions, nsIPrincipal* aSubjectPrincipal, 5800 ErrorResult& aError); 5801 5802 static already_AddRefed<Document> ParseHTML(GlobalObject& aGlobal, 5803 const nsAString& aHTML, 5804 const SetHTMLOptions& aOptions, 5805 ErrorResult& aError); 5806 5807 nsIURI* GetTlsCertificateBindingURI() const { 5808 return mTLSCertificateBindingURI; 5809 } 5810 }; 5811 5812 enum class SyncOperationBehavior { eSuspendInput, eAllowInput }; 5813 5814 class AutoWalkBrowsingContextGroup { 5815 public: 5816 virtual ~AutoWalkBrowsingContextGroup() = default; 5817 5818 protected: 5819 void SuppressBrowsingContext(BrowsingContext* aContext); 5820 void SuppressBrowsingContextGroup(BrowsingContextGroup* aGroup); 5821 void UnsuppressDocuments() { 5822 for (const auto& doc : mDocuments) { 5823 UnsuppressDocument(doc); 5824 } 5825 } 5826 virtual void SuppressDocument(Document* aDocument) = 0; 5827 virtual void UnsuppressDocument(Document* aDocument) = 0; 5828 AutoTArray<RefPtr<Document>, 16> mDocuments; 5829 }; 5830 5831 class MOZ_RAII nsAutoSyncOperation : private AutoWalkBrowsingContextGroup { 5832 public: 5833 explicit nsAutoSyncOperation(Document* aDocument, 5834 SyncOperationBehavior aSyncBehavior); 5835 ~nsAutoSyncOperation(); 5836 5837 protected: 5838 void SuppressDocument(Document* aDocument) override; 5839 void UnsuppressDocument(Document* aDocument) override; 5840 5841 private: 5842 uint32_t mMicroTaskLevel; 5843 const SyncOperationBehavior mSyncBehavior; 5844 RefPtr<BrowsingContext> mBrowsingContext; 5845 }; 5846 5847 class MOZ_RAII AutoSetThrowOnDynamicMarkupInsertionCounter final { 5848 public: 5849 explicit AutoSetThrowOnDynamicMarkupInsertionCounter(Document* aDocument) 5850 : mDocument(aDocument) { 5851 mDocument->IncrementThrowOnDynamicMarkupInsertionCounter(); 5852 } 5853 5854 ~AutoSetThrowOnDynamicMarkupInsertionCounter() { 5855 mDocument->DecrementThrowOnDynamicMarkupInsertionCounter(); 5856 } 5857 5858 private: 5859 Document* mDocument; 5860 }; 5861 5862 class MOZ_RAII IgnoreOpensDuringUnload final { 5863 public: 5864 explicit IgnoreOpensDuringUnload(Document* aDoc) : mDoc(aDoc) { 5865 mDoc->IncrementIgnoreOpensDuringUnloadCounter(); 5866 } 5867 5868 ~IgnoreOpensDuringUnload() { 5869 mDoc->DecrementIgnoreOpensDuringUnloadCounter(); 5870 } 5871 5872 private: 5873 Document* mDoc; 5874 }; 5875 5876 /** 5877 * Suppress notifying DevTools of node removals in the given document even if 5878 * DevTools wants to know that. This guarantees the lifetime of the given 5879 * document while the instance is alive. 5880 */ 5881 class MOZ_RAII AutoSuppressNotifyingDevToolsOfNodeRemovals final { 5882 public: 5883 explicit AutoSuppressNotifyingDevToolsOfNodeRemovals(Document& aDoc) 5884 : mDoc(aDoc), 5885 mDidSuppress( 5886 static_cast<bool>(aDoc.mSuppressNotifyingDevToolsOfNodeRemovals)) { 5887 mDoc->mSuppressNotifyingDevToolsOfNodeRemovals = true; 5888 } 5889 ~AutoSuppressNotifyingDevToolsOfNodeRemovals() { 5890 MOZ_ASSERT(mDoc->mSuppressNotifyingDevToolsOfNodeRemovals); 5891 mDoc->mSuppressNotifyingDevToolsOfNodeRemovals = mDidSuppress; 5892 } 5893 5894 Document& Doc() const { return mDoc; } 5895 5896 private: 5897 const OwningNonNull<Document> mDoc; 5898 bool mDidSuppress; 5899 }; 5900 5901 bool IsInFocusedTab(Document* aDoc); 5902 5903 // This covers all cases covered by IsInFocusedTab, but also ensures that 5904 // focused tab is "active" meaning not occluded. 5905 bool IsInActiveTab(Document* aDoc); 5906 5907 } // namespace mozilla::dom 5908 5909 NON_VIRTUAL_ADDREF_RELEASE(mozilla::dom::Document) 5910 5911 // XXX These belong somewhere else 5912 nsresult NS_NewHTMLDocument( 5913 mozilla::dom::Document** aInstancePtrResult, nsIPrincipal* aPrincipal, 5914 nsIPrincipal* aPartitionedPrincipal, 5915 mozilla::dom::LoadedAsData aLoadedAsData = mozilla::dom::LoadedAsData::No); 5916 5917 nsresult NS_NewXMLDocument( 5918 mozilla::dom::Document** aInstancePtrResult, nsIPrincipal* aPrincipal, 5919 nsIPrincipal* aPartitionedPrincipal, 5920 mozilla::dom::LoadedAsData aLoadedAsData = mozilla::dom::LoadedAsData::No, 5921 bool aIsPlainDocument = false); 5922 5923 nsresult NS_NewSVGDocument( 5924 mozilla::dom::Document** aInstancePtrResult, nsIPrincipal* aPrincipal, 5925 nsIPrincipal* aPartitionedPrincipal, 5926 mozilla::dom::LoadedAsData aLoadedAsData = mozilla::dom::LoadedAsData::No); 5927 5928 nsresult NS_NewImageDocument(mozilla::dom::Document** aInstancePtrResult, 5929 nsIPrincipal* aPrincipal, 5930 nsIPrincipal* aPartitionedPrincipal); 5931 5932 nsresult NS_NewVideoDocument(mozilla::dom::Document** aInstancePtrResult, 5933 nsIPrincipal* aPrincipal, 5934 nsIPrincipal* aPartitionedPrincipal); 5935 5936 // Enum for requesting a particular type of document when creating a doc 5937 enum class DocumentFlavor : uint8_t { 5938 LegacyGuess, // compat with old code until made HTML5-compliant 5939 HTML, // HTMLDocument with HTMLness bit set to true 5940 SVG, // SVGDocument 5941 XML, // XMLDocument 5942 Plain, // Just a Document 5943 }; 5944 5945 // Note: it's the caller's responsibility to create or get aPrincipal as needed 5946 // -- this method will not attempt to get a principal based on aDocumentURI. 5947 // Also, both aDocumentURI and aBaseURI must not be null. 5948 nsresult NS_NewDOMDocument( 5949 mozilla::dom::Document** aInstancePtrResult, const nsAString& aNamespaceURI, 5950 const nsAString& aQualifiedName, mozilla::dom::DocumentType* aDoctype, 5951 nsIURI* aDocumentURI, nsIURI* aBaseURI, nsIPrincipal* aPrincipal, 5952 mozilla::dom::LoadedAsData aLoadedAsData, nsIGlobalObject* aEventObject, 5953 DocumentFlavor aFlavor); 5954 5955 inline mozilla::dom::Document* nsINode::GetOwnerDocument() const { 5956 mozilla::dom::Document* ownerDoc = OwnerDoc(); 5957 5958 return ownerDoc != this ? ownerDoc : nullptr; 5959 } 5960 5961 inline nsINode* nsINode::OwnerDocAsNode() const { return OwnerDoc(); } 5962 5963 inline mozilla::dom::Document* nsINode::AsDocument() { 5964 MOZ_ASSERT(IsDocument()); 5965 return static_cast<mozilla::dom::Document*>(this); 5966 } 5967 5968 inline const mozilla::dom::Document* nsINode::AsDocument() const { 5969 MOZ_ASSERT(IsDocument()); 5970 return static_cast<const mozilla::dom::Document*>(this); 5971 } 5972 5973 inline nsISupports* ToSupports(mozilla::dom::Document* aDoc) { 5974 return static_cast<nsINode*>(aDoc); 5975 } 5976 5977 #endif /* mozilla_dom_Document_h___ */