Bug 1842773 - Part 5: Add ArrayBuffer.prototype.{maxByteLength,resizable} getters...
[gecko.git] / dom / base / nsContentSink.h
blobe9a2166dcdb39df5f817062abb0f1337a151fa3e
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/. */
7 /*
8 * Base class for the XML and HTML content sinks, which construct a
9 * DOM based on information from the parser.
12 #ifndef _nsContentSink_h_
13 #define _nsContentSink_h_
15 // Base class for contentsink implementations.
17 #include "mozilla/Attributes.h"
18 #include "nsICSSLoaderObserver.h"
19 #include "nsWeakReference.h"
20 #include "nsCOMPtr.h"
21 #include "nsString.h"
22 #include "nsGkAtoms.h"
23 #include "nsITimer.h"
24 #include "nsStubDocumentObserver.h"
25 #include "nsIContentSink.h"
26 #include "mozilla/Logging.h"
27 #include "nsCycleCollectionParticipant.h"
28 #include "nsThreadUtils.h"
29 #include "mozilla/StaticPrefs_content.h"
31 class nsIURI;
32 class nsIChannel;
33 class nsIDocShell;
34 class nsAtom;
35 class nsIChannel;
36 class nsIContent;
37 class nsNodeInfoManager;
39 namespace mozilla {
40 namespace css {
41 class Loader;
42 } // namespace css
44 namespace dom {
45 class Document;
46 class ScriptLoader;
47 } // namespace dom
49 namespace net {
50 struct LinkHeader;
52 } // namespace mozilla
54 #ifdef DEBUG
56 extern mozilla::LazyLogModule gContentSinkLogModuleInfo;
58 # define SINK_TRACE_CALLS 0x1
59 # define SINK_TRACE_REFLOW 0x2
60 # define SINK_ALWAYS_REFLOW 0x4
62 # define SINK_LOG_TEST(_lm, _bit) (int((_lm)->Level()) & (_bit))
64 # define SINK_TRACE(_lm, _bit, _args) \
65 do { \
66 if (SINK_LOG_TEST(_lm, _bit)) { \
67 printf_stderr _args; \
68 } \
69 } while (0)
71 #else
72 # define SINK_TRACE(_lm, _bit, _args)
73 #endif
75 #undef SINK_NO_INCREMENTAL
77 //----------------------------------------------------------------------
79 class nsContentSink : public nsICSSLoaderObserver,
80 public nsSupportsWeakReference,
81 public nsStubDocumentObserver,
82 public nsITimerCallback,
83 public nsINamed {
84 protected:
85 using Document = mozilla::dom::Document;
87 private:
88 NS_DECL_CYCLE_COLLECTING_ISUPPORTS
89 NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsContentSink, nsICSSLoaderObserver)
90 // nsITimerCallback
91 NS_DECL_NSITIMERCALLBACK
93 NS_DECL_NSINAMED
95 // nsICSSLoaderObserver
96 NS_IMETHOD StyleSheetLoaded(mozilla::StyleSheet* aSheet, bool aWasDeferred,
97 nsresult aStatus) override;
99 // nsIContentSink implementation helpers
100 nsresult WillParseImpl(void);
101 nsresult WillInterruptImpl(void);
102 void WillResumeImpl();
103 nsresult DidProcessATokenImpl(void);
104 void WillBuildModelImpl(void);
105 void DidBuildModelImpl(bool aTerminated);
106 void DropParserAndPerfHint(void);
107 bool IsScriptExecutingImpl();
109 void NotifyAppend(nsIContent* aContent, uint32_t aStartIndex);
111 // nsIDocumentObserver
112 NS_DECL_NSIDOCUMENTOBSERVER_BEGINUPDATE
113 NS_DECL_NSIDOCUMENTOBSERVER_ENDUPDATE
115 virtual void UpdateChildCounts() = 0;
117 bool IsTimeToNotify();
119 protected:
120 nsContentSink();
121 virtual ~nsContentSink();
123 nsresult Init(Document* aDoc, nsIURI* aURI, nsISupports* aContainer,
124 nsIChannel* aChannel);
126 nsresult ProcessHTTPHeaders(nsIChannel* aChannel);
127 // aEarlyHintPreloaderId zero means no early hint channel to connect back
128 nsresult ProcessLinkFromHeader(const mozilla::net::LinkHeader& aHeader,
129 uint64_t aEarlyHintPreloaderId);
131 // @param aFetchPriority Accepts a case-insensitive fetch priority keyword and
132 // other values too, see
133 // <https://html.spec.whatwg.org/#fetch-priority-attribute>.
134 virtual nsresult ProcessStyleLinkFromHeader(
135 const nsAString& aHref, bool aAlternate, const nsAString& aTitle,
136 const nsAString& aIntegrity, const nsAString& aType,
137 const nsAString& aMedia, const nsAString& aReferrerPolicy,
138 const nsAString& aFetchPriority);
140 void PrefetchHref(const nsAString& aHref, const nsAString& aAs,
141 const nsAString& aType, const nsAString& aMedia);
142 void PreloadHref(const nsAString& aHref, const nsAString& aAs,
143 const nsAString& aType, const nsAString& aMedia,
144 const nsAString& aNonce, const nsAString& aIntegrity,
145 const nsAString& aSrcset, const nsAString& aSizes,
146 const nsAString& aCORS, const nsAString& aReferrerPolicy,
147 uint64_t aEarlyHintPreloaderId,
148 const nsAString& aFetchPriority);
150 void PreloadModule(const nsAString& aHref, const nsAString& aAs,
151 const nsAString& aMedia, const nsAString& aNonce,
152 const nsAString& aIntegrity, const nsAString& aCORS,
153 const nsAString& aReferrerPolicy,
154 uint64_t aEarlyHintPreloaderId,
155 const nsAString& aFetchPriority);
157 // For PrefetchDNS() aHref can either be the usual
158 // URI format or of the form "//www.hostname.com" without a scheme.
159 void PrefetchDNS(const nsAString& aHref);
161 // Gets the cache key (used to identify items in a cache) of the channel.
162 nsresult GetChannelCacheKey(nsIChannel* aChannel, nsACString& aCacheKey);
164 public:
165 // For Preconnect() aHref can either be the usual
166 // URI format or of the form "//www.hostname.com" without a scheme.
167 void Preconnect(const nsAString& aHref, const nsAString& aCrossOrigin);
169 protected:
170 // Tries to scroll to the URI's named anchor. Once we've successfully
171 // done that, further calls to this method will be ignored.
172 MOZ_CAN_RUN_SCRIPT_BOUNDARY void ScrollToRef();
174 // Start layout. If aIgnorePendingSheets is true, this will happen even if
175 // we still have stylesheet loads pending. Otherwise, we'll wait until the
176 // stylesheets are all done loading.
177 public:
178 void StartLayout(bool aIgnorePendingSheets);
180 static void NotifyDocElementCreated(Document* aDoc);
182 Document* GetDocument() { return mDocument; }
184 // Later on we might want to make this more involved somehow
185 // (e.g. stop waiting after some timeout or whatnot).
186 bool WaitForPendingSheets() { return mPendingSheetCount > 0; }
188 protected:
189 inline int32_t GetNotificationInterval() {
190 if (mDynamicLowerValue) {
191 return 1000;
194 return mozilla::StaticPrefs::content_notify_interval();
197 virtual nsresult FlushTags() = 0;
199 void DoProcessLinkHeader();
201 void StopDeflecting() {
202 mDeflectedCount = mozilla::StaticPrefs::content_sink_perf_deflect_count();
205 protected:
206 RefPtr<Document> mDocument;
207 RefPtr<nsParserBase> mParser;
208 nsCOMPtr<nsIURI> mDocumentURI;
209 nsCOMPtr<nsIDocShell> mDocShell;
210 RefPtr<mozilla::css::Loader> mCSSLoader;
211 RefPtr<nsNodeInfoManager> mNodeInfoManager;
212 RefPtr<mozilla::dom::ScriptLoader> mScriptLoader;
214 // back off timer notification after count
215 int32_t mBackoffCount;
217 // Time of last notification
218 // Note: mLastNotificationTime is only valid once mLayoutStarted is true.
219 PRTime mLastNotificationTime;
221 // Timer used for notification
222 nsCOMPtr<nsITimer> mNotificationTimer;
224 uint8_t mLayoutStarted : 1;
225 uint8_t mDynamicLowerValue : 1;
226 uint8_t mParsing : 1;
227 uint8_t mDroppedTimer : 1;
228 // If true, we deferred starting layout until sheets load
229 uint8_t mDeferredLayoutStart : 1;
230 // If true, we deferred notifications until sheets load
231 uint8_t mDeferredFlushTags : 1;
232 // If false, we're not ourselves a document observer; that means we
233 // shouldn't be performing any more content model notifications,
234 // since we're not longer updating our child counts.
235 uint8_t mIsDocumentObserver : 1;
236 // True if this is parser is a fragment parser or an HTML DOMParser.
237 // XML DOMParser leaves this to false for now!
238 uint8_t mRunsToCompletion : 1;
239 // True if we are blocking load event.
240 bool mIsBlockingOnload : 1;
243 // -- Can interrupt parsing members --
246 // The number of tokens that have been processed since we measured
247 // if it's time to return to the main event loop.
248 uint32_t mDeflectedCount;
250 // Is there currently a pending event?
251 bool mHasPendingEvent;
253 // When to return to the main event loop
254 uint32_t mCurrentParseEndTime;
256 int32_t mBeginLoadTime;
258 // Last mouse event or keyboard event time sampled by the content
259 // sink
260 uint32_t mLastSampledUserEventTime;
262 int32_t mInMonolithicContainer;
264 int32_t mInNotification;
265 uint32_t mUpdatesInNotification;
267 uint32_t mPendingSheetCount;
269 nsRevocableEventPtr<nsRunnableMethod<nsContentSink, void, false> >
270 mProcessLinkHeaderEvent;
273 #endif // _nsContentSink_h_