Source code

Revision control

Other Tools

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 nsDocShell_h__
8
#define nsDocShell_h__
9
10
#include <utility>
11
12
#include "GeckoProfiler.h"
13
#include "Units.h"
14
#include "jsapi.h"
15
#include "mozilla/BasePrincipal.h"
16
#include "mozilla/HalScreenConfiguration.h"
17
#include "mozilla/LinkedList.h"
18
#include "mozilla/Maybe.h"
19
#include "mozilla/ObservedDocShell.h"
20
#include "mozilla/ScrollbarPreferences.h"
21
#include "mozilla/StaticPrefs_browser.h"
22
#include "mozilla/TimeStamp.h"
23
#include "mozilla/TimelineConsumers.h"
24
#include "mozilla/TimelineMarker.h"
25
#include "mozilla/UniquePtr.h"
26
#include "mozilla/WeakPtr.h"
27
#include "mozilla/dom/BrowsingContext.h"
28
#include "mozilla/dom/ChildSHistory.h"
29
#include "mozilla/dom/ProfileTimelineMarkerBinding.h"
30
#include "mozilla/dom/WindowProxyHolder.h"
31
#include "mozilla/gfx/Matrix.h"
32
#include "nsCOMPtr.h"
33
#include "nsCRT.h"
34
#include "nsCharsetSource.h"
35
#include "nsContentPolicyUtils.h"
36
#include "nsContentUtils.h"
37
#include "nsDocLoader.h"
38
#include "nsIAuthPromptProvider.h"
39
#include "nsIBaseWindow.h"
40
#include "nsIDeprecationWarner.h"
41
#include "nsIDocShell.h"
42
#include "nsIDocShellTreeItem.h"
43
#include "nsIInterfaceRequestor.h"
44
#include "nsILoadContext.h"
45
#include "nsILoadURIDelegate.h"
46
#include "nsINetworkInterceptController.h"
47
#include "nsIRefreshURI.h"
48
#include "nsIWebNavigation.h"
49
#include "nsIWebPageDescriptor.h"
50
#include "nsIWebProgressListener.h"
51
#include "nsPoint.h" // mCurrent/mDefaultScrollbarPreferences
52
#include "nsRect.h"
53
#include "nsString.h"
54
#include "nsThreadUtils.h"
55
#include "prtime.h"
56
57
// Interfaces Needed
58
59
namespace mozilla {
60
class Encoding;
61
class HTMLEditor;
62
enum class TaskCategory;
63
namespace dom {
64
class ClientInfo;
65
class ClientSource;
66
class EventTarget;
67
} // namespace dom
68
namespace net {
69
class LoadInfo;
70
class DocumentChannelRedirect;
71
} // namespace net
72
} // namespace mozilla
73
74
class nsIContentViewer;
75
class nsIController;
76
class nsIDocShellTreeOwner;
77
class nsIHttpChannel;
78
class nsIMutableArray;
79
class nsIPrompt;
80
class nsIScrollableFrame;
81
class nsISecureBrowserUI;
82
class nsISHistory;
83
class nsIStringBundle;
84
class nsIURIFixup;
85
class nsIURILoader;
86
class nsIWebBrowserFind;
87
class nsIWidget;
88
class nsIReferrerInfo;
89
90
class nsCommandManager;
91
class nsDocShell;
92
class nsDocShellEditorData;
93
class nsDOMNavigationTiming;
94
class nsDSURIContentListener;
95
class nsGlobalWindowInner;
96
class nsGlobalWindowOuter;
97
98
class FramingChecker;
99
class OnLinkClickEvent;
100
101
/* internally used ViewMode types */
102
enum ViewMode { viewNormal = 0x0, viewSource = 0x1 };
103
104
enum eCharsetReloadState {
105
eCharsetReloadInit,
106
eCharsetReloadRequested,
107
eCharsetReloadStopOrigional
108
};
109
110
class nsDocShell final : public nsDocLoader,
111
public nsIDocShell,
112
public nsIWebNavigation,
113
public nsIBaseWindow,
114
public nsIRefreshURI,
115
public nsIWebProgressListener,
116
public nsIWebPageDescriptor,
117
public nsIAuthPromptProvider,
118
public nsILoadContext,
119
public nsINetworkInterceptController,
120
public nsIDeprecationWarner,
121
public mozilla::SupportsWeakPtr<nsDocShell> {
122
public:
123
enum InternalLoad : uint32_t {
124
INTERNAL_LOAD_FLAGS_NONE = 0x0,
125
INTERNAL_LOAD_FLAGS_INHERIT_PRINCIPAL = 0x1,
126
INTERNAL_LOAD_FLAGS_DONT_SEND_REFERRER = 0x2,
127
INTERNAL_LOAD_FLAGS_ALLOW_THIRD_PARTY_FIXUP = 0x4,
128
129
// This flag marks the first load in this object
130
// @see nsIWebNavigation::LOAD_FLAGS_FIRST_LOAD
131
INTERNAL_LOAD_FLAGS_FIRST_LOAD = 0x8,
132
133
// The set of flags that should not be set before calling into
134
// nsDocShell::LoadURI and other nsDocShell loading functions.
135
INTERNAL_LOAD_FLAGS_LOADURI_SETUP_FLAGS = 0xf,
136
137
INTERNAL_LOAD_FLAGS_BYPASS_CLASSIFIER = 0x10,
138
INTERNAL_LOAD_FLAGS_FORCE_ALLOW_COOKIES = 0x20,
139
140
// Whether the load should be treated as srcdoc load, rather than a URI one.
141
INTERNAL_LOAD_FLAGS_IS_SRCDOC = 0x40,
142
143
// Whether this is the load of a frame's original src attribute
144
INTERNAL_LOAD_FLAGS_ORIGINAL_FRAME_SRC = 0x80,
145
146
INTERNAL_LOAD_FLAGS_NO_OPENER = 0x100,
147
148
// Whether a top-level data URI navigation is allowed for that load
149
INTERNAL_LOAD_FLAGS_FORCE_ALLOW_DATA_URI = 0x200,
150
151
// Whether the load should go through LoadURIDelegate.
152
INTERNAL_LOAD_FLAGS_BYPASS_LOAD_URI_DELEGATE = 0x2000,
153
};
154
155
// Event type dispatched by RestorePresentation
156
class RestorePresentationEvent : public mozilla::Runnable {
157
public:
158
NS_DECL_NSIRUNNABLE
159
explicit RestorePresentationEvent(nsDocShell* aDs)
160
: mozilla::Runnable("nsDocShell::RestorePresentationEvent"),
161
mDocShell(aDs) {}
162
void Revoke() { mDocShell = nullptr; }
163
164
private:
165
RefPtr<nsDocShell> mDocShell;
166
};
167
168
class InterfaceRequestorProxy : public nsIInterfaceRequestor {
169
public:
170
explicit InterfaceRequestorProxy(nsIInterfaceRequestor* aRequestor);
171
NS_DECL_THREADSAFE_ISUPPORTS
172
NS_DECL_NSIINTERFACEREQUESTOR
173
174
private:
175
virtual ~InterfaceRequestorProxy();
176
InterfaceRequestorProxy() = default;
177
nsWeakPtr mWeakPtr;
178
};
179
180
MOZ_DECLARE_WEAKREFERENCE_TYPENAME(nsDocShell)
181
NS_DECL_ISUPPORTS_INHERITED
182
NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(nsDocShell, nsDocLoader)
183
NS_DECL_NSIDOCSHELL
184
NS_DECL_NSIDOCSHELLTREEITEM
185
NS_DECL_NSIWEBNAVIGATION
186
NS_DECL_NSIBASEWINDOW
187
NS_DECL_NSIINTERFACEREQUESTOR
188
NS_DECL_NSIWEBPROGRESSLISTENER
189
NS_DECL_NSIREFRESHURI
190
NS_DECL_NSIWEBPAGEDESCRIPTOR
191
NS_DECL_NSIAUTHPROMPTPROVIDER
192
NS_DECL_NSINETWORKINTERCEPTCONTROLLER
193
NS_DECL_NSIDEPRECATIONWARNER
194
195
// Create a new nsDocShell object, initializing it.
196
static already_AddRefed<nsDocShell> Create(
197
mozilla::dom::BrowsingContext* aBrowsingContext,
198
uint64_t aContentWindowID = 0);
199
200
NS_IMETHOD Stop() override {
201
// Need this here because otherwise nsIWebNavigation::Stop
202
// overrides the docloader's Stop()
203
return nsDocLoader::Stop();
204
}
205
206
mozilla::ScrollbarPreference ScrollbarPreference() const {
207
return mScrollbarPref;
208
}
209
void SetScrollbarPreference(mozilla::ScrollbarPreference);
210
211
/*
212
* The size, in CSS pixels, of the margins for the <body> of an HTML document
213
* in this docshell; used to implement the marginwidth attribute on HTML
214
* <frame>/<iframe> elements. A value smaller than zero indicates that the
215
* attribute was not set.
216
*/
217
const mozilla::CSSIntSize& GetFrameMargins() const { return mFrameMargins; }
218
219
bool UpdateFrameMargins(const mozilla::CSSIntSize& aMargins) {
220
if (mFrameMargins == aMargins) {
221
return false;
222
}
223
mFrameMargins = aMargins;
224
return true;
225
}
226
227
/**
228
* Process a click on a link.
229
*
230
* @param aContent the content object used for triggering the link.
231
* @param aURI a URI object that defines the destination for the link
232
* @param aTargetSpec indicates where the link is targeted (may be an empty
233
* string)
234
* @param aFileName non-null when the link should be downloaded as the given
235
* file
236
* @param aPostDataStream the POST data to send
237
* @param aHeadersDataStream ??? (only used for plugins)
238
* @param aIsTrusted false if the triggerer is an untrusted DOM event.
239
* @param aTriggeringPrincipal, if not passed explicitly we fall back to
240
* the document's principal.
241
* @param aCsp, the CSP to be used for the load, that is the CSP of the
242
* entity responsible for causing the load to occur. Most likely
243
* this is the CSP of the document that started the load. In case
244
* aCsp was not passed explicitly we fall back to using
245
* aContent's document's CSP if that document holds any.
246
*/
247
nsresult OnLinkClick(nsIContent* aContent, nsIURI* aURI,
248
const nsAString& aTargetSpec, const nsAString& aFileName,
249
nsIInputStream* aPostDataStream,
250
nsIInputStream* aHeadersDataStream,
251
bool aIsUserTriggered, bool aIsTrusted,
252
nsIPrincipal* aTriggeringPrincipal,
253
nsIContentSecurityPolicy* aCsp);
254
/**
255
* Process a click on a link.
256
*
257
* Works the same as OnLinkClick() except it happens immediately rather than
258
* through an event.
259
*
260
* @param aContent the content object used for triggering the link.
261
* @param aURI a URI obect that defines the destination for the link
262
* @param aTargetSpec indicates where the link is targeted (may be an empty
263
* string)
264
* @param aFileName non-null when the link should be downloaded as the given
265
* file
266
* @param aPostDataStream the POST data to send
267
* @param aHeadersDataStream ??? (only used for plugins)
268
* @param aNoOpenerImplied if the link implies "noopener"
269
* @param aDocShell (out-param) the DocShell that the request was opened on
270
* @param aRequest the request that was opened
271
* @param aTriggeringPrincipal, if not passed explicitly we fall back to
272
* the document's principal.
273
* @param aCsp, the CSP to be used for the load, that is the CSP of the
274
* entity responsible for causing the load to occur. Most likely
275
* this is the CSP of the document that started the load. In case
276
* aCsp was not passed explicitly we fall back to using
277
* aContent's document's CSP if that document holds any.
278
*/
279
nsresult OnLinkClickSync(
280
nsIContent* aContent, nsIURI* aURI, const nsAString& aTargetSpec,
281
const nsAString& aFileName, nsIInputStream* aPostDataStream = nullptr,
282
nsIInputStream* aHeadersDataStream = nullptr,
283
bool aNoOpenerImplied = false, nsIDocShell** aDocShell = nullptr,
284
nsIRequest** aRequest = nullptr, bool aIsUserTriggered = false,
285
nsIPrincipal* aTriggeringPrincipal = nullptr,
286
nsIContentSecurityPolicy* aCsp = nullptr);
287
/**
288
* Process a mouse-over a link.
289
*
290
* @param aContent the linked content.
291
* @param aURI an URI object that defines the destination for the link
292
* @param aTargetSpec indicates where the link is targeted (it may be an empty
293
* string)
294
*/
295
nsresult OnOverLink(nsIContent* aContent, nsIURI* aURI,
296
const nsAString& aTargetSpec);
297
/**
298
* Process the mouse leaving a link.
299
*/
300
nsresult OnLeaveLink();
301
302
// Don't use NS_DECL_NSILOADCONTEXT because some of nsILoadContext's methods
303
// are shared with nsIDocShell and can't be declared twice.
304
NS_IMETHOD GetAssociatedWindow(mozIDOMWindowProxy**) override;
305
NS_IMETHOD GetTopWindow(mozIDOMWindowProxy**) override;
306
NS_IMETHOD GetTopFrameElement(mozilla::dom::Element**) override;
307
NS_IMETHOD GetNestedFrameId(uint64_t*) override;
308
NS_IMETHOD GetIsContent(bool*) override;
309
NS_IMETHOD GetUsePrivateBrowsing(bool*) override;
310
NS_IMETHOD SetUsePrivateBrowsing(bool) override;
311
NS_IMETHOD SetPrivateBrowsing(bool) override;
312
NS_IMETHOD GetUseRemoteTabs(bool*) override;
313
NS_IMETHOD SetRemoteTabs(bool) override;
314
NS_IMETHOD GetUseRemoteSubframes(bool*) override;
315
NS_IMETHOD SetRemoteSubframes(bool) override;
316
NS_IMETHOD GetScriptableOriginAttributes(
317
JSContext*, JS::MutableHandle<JS::Value>) override;
318
NS_IMETHOD_(void)
319
GetOriginAttributes(mozilla::OriginAttributes& aAttrs) override;
320
321
// Restores a cached presentation from history (mLSHE).
322
// This method swaps out the content viewer and simulates loads for
323
// subframes. It then simulates the completion of the toplevel load.
324
nsresult RestoreFromHistory();
325
326
// Perform a URI load from a refresh timer. This is just like the
327
// ForceRefreshURI method on nsIRefreshURI, but makes sure to take
328
// the timer involved out of mRefreshURIList if it's there.
329
// aTimer must not be null.
330
nsresult ForceRefreshURIFromTimer(nsIURI* aURI, nsIPrincipal* aPrincipal,
331
int32_t aDelay, bool aMetaRefresh,
332
nsITimer* aTimer);
333
334
// We need dummy OnLocationChange in some cases to update the UI without
335
// updating security info.
336
void FireDummyOnLocationChange() {
337
FireOnLocationChange(this, nullptr, mCurrentURI,
338
LOCATION_CHANGE_SAME_DOCUMENT);
339
}
340
341
// This function is created exclusively for dom.background_loading_iframe is
342
// set. As soon as the current DocShell knows itself can be treated as
343
// background loading, it triggers the parent docshell to see if the parent
344
// document can fire load event earlier.
345
void TriggerParentCheckDocShellIsEmpty();
346
347
nsresult HistoryEntryRemoved(int32_t aIndex);
348
349
// Notify Scroll observers when an async panning/zooming transform
350
// has started being applied
351
MOZ_CAN_RUN_SCRIPT_BOUNDARY
352
void NotifyAsyncPanZoomStarted();
353
354
// Notify Scroll observers when an async panning/zooming transform
355
// is no longer applied
356
MOZ_CAN_RUN_SCRIPT_BOUNDARY
357
void NotifyAsyncPanZoomStopped();
358
359
void SetInFrameSwap(bool aInSwap) { mInFrameSwap = aInSwap; }
360
bool InFrameSwap();
361
362
void SetIsFrame() { mIsFrame = true; };
363
364
const mozilla::Encoding* GetForcedCharset() { return mForcedCharset; }
365
366
mozilla::HTMLEditor* GetHTMLEditorInternal();
367
nsresult SetHTMLEditorInternal(mozilla::HTMLEditor* aHTMLEditor);
368
369
// Handle page navigation due to charset changes
370
nsresult CharsetChangeReloadDocument(const char* aCharset = nullptr,
371
int32_t aSource = kCharsetUninitialized);
372
nsresult CharsetChangeStopDocumentLoad();
373
374
nsDOMNavigationTiming* GetNavigationTiming() const;
375
376
nsresult SetOriginAttributes(const mozilla::OriginAttributes& aAttrs);
377
378
/**
379
* Get the list of ancestor principals for this docshell. The list is meant
380
* to be the list of principals of the documents this docshell is "nested
381
* through" in the sense of
383
* In practice, it is defined as follows:
384
*
385
* If this is an <iframe mozbrowser> or a toplevel content docshell
386
* (i.e. toplevel document in spec terms), the list is empty.
387
*
388
* Otherwise the list is the list for the document we're nested through (again
389
* in the spec sense), with the principal of that document prepended. Note
390
* that this matches the ordering specified for Location.ancestorOrigins.
391
*/
392
const nsTArray<nsCOMPtr<nsIPrincipal>>& AncestorPrincipals() const {
393
return mAncestorPrincipals;
394
}
395
396
/**
397
* Set the list of ancestor principals for this docshell. This is really only
398
* needed for use by the frameloader. We can't do this ourselves, inside
399
* docshell, because there's a bunch of state setup that frameloader does
400
* (like telling us whether we're a mozbrowser), some of which comes after the
401
* docshell is added to the docshell tree, which can affect what the ancestor
402
* principals should look like.
403
*
404
* This method steals the data from the passed-in array.
405
*/
406
void SetAncestorPrincipals(
407
nsTArray<nsCOMPtr<nsIPrincipal>>&& aAncestorPrincipals) {
408
mAncestorPrincipals = std::move(aAncestorPrincipals);
409
}
410
411
/**
412
* Get the list of ancestor outerWindowIDs for this docshell. The list is
413
* meant to be the list of outer window IDs that correspond to the
414
* ancestorPrincipals above. For each ancestor principal, we store the
415
* parent window ID.
416
*/
417
const nsTArray<uint64_t>& AncestorOuterWindowIDs() const {
418
return mAncestorOuterWindowIDs;
419
}
420
421
/**
422
* Set the list of ancestor outer window IDs for this docshell. We call this
423
* from frameloader as well in order to keep the array matched with the
424
* ancestor principals.
425
*
426
* This method steals the data from the passed-in array.
427
*/
428
void SetAncestorOuterWindowIDs(nsTArray<uint64_t>&& aAncestorOuterWindowIDs) {
429
mAncestorOuterWindowIDs = std::move(aAncestorOuterWindowIDs);
430
}
431
432
const mozilla::OriginAttributes& GetOriginAttributes() {
433
return mOriginAttributes;
434
}
435
436
// Determine whether this docshell corresponds to the given history entry,
437
// via having a pointer to it in mOSHE or mLSHE.
438
bool HasHistoryEntry(nsISHEntry* aEntry) const {
439
return aEntry && (aEntry == mOSHE || aEntry == mLSHE);
440
}
441
442
// Update any pointers (mOSHE or mLSHE) to aOldEntry to point to aNewEntry
443
void SwapHistoryEntries(nsISHEntry* aOldEntry, nsISHEntry* aNewEntry);
444
445
mozilla::gfx::Matrix5x4* GetColorMatrix() { return mColorMatrix.get(); }
446
447
static bool SandboxFlagsImplyCookies(const uint32_t& aSandboxFlags);
448
449
// Tell the favicon service that aNewURI has the same favicon as aOldURI.
450
static void CopyFavicon(nsIURI* aOldURI, nsIURI* aNewURI,
451
nsIPrincipal* aLoadingPrincipal,
452
bool aInPrivateBrowsing);
453
454
static nsDocShell* Cast(nsIDocShell* aDocShell) {
455
return static_cast<nsDocShell*>(aDocShell);
456
}
457
458
// Returns true if the current load is a force reload (started by holding
459
// shift while triggering reload)
460
bool IsForceReloading();
461
462
mozilla::dom::WindowProxyHolder GetWindowProxy() {
463
EnsureScriptEnvironment();
464
return mozilla::dom::WindowProxyHolder(mBrowsingContext);
465
}
466
467
/**
468
* Loads the given URI. See comments on nsDocShellLoadState members for more
469
* information on information used. aDocShell and aRequest come from
470
* onLinkClickSync, which is triggered during form submission.
471
*/
472
MOZ_CAN_RUN_SCRIPT_BOUNDARY
473
nsresult InternalLoad(nsDocShellLoadState* aLoadState,
474
nsIDocShell** aDocShell, nsIRequest** aRequest);
475
476
// Clear the document's storage access flag if needed.
477
void MaybeClearStorageAccessFlag();
478
479
void SetWillChangeProcess() { mWillChangeProcess = true; }
480
481
// Create a content viewer within this nsDocShell for the given
482
// `WindowGlobalChild` actor.
483
nsresult CreateContentViewerForActor(
484
mozilla::dom::WindowGlobalChild* aWindowActor);
485
486
// Creates a real network channel (not a DocumentChannel) using the specified
487
// parameters.
488
// Used by nsDocShell when not using DocumentChannel, by DocumentLoadListener
489
// (parent-process DocumentChannel), and by DocumentChannelChild/ContentChild
490
// to transfer the resulting channel into the final process.
491
static nsresult CreateRealChannelForDocument(
492
nsIChannel** aChannel, nsIURI* aURI, nsILoadInfo* aLoadInfo,
493
nsIInterfaceRequestor* aCallbacks, nsLoadFlags aLoadFlags,
494
const nsAString& aSrcdoc, nsIURI* aBaseURI);
495
496
// Creates a real (not DocumentChannel) channel, and configures it using the
497
// supplied nsDocShellLoadState.
498
// Configuration options here are ones that should be applied to only the
499
// real channel, especially ones that need to QI to channel subclasses.
500
static bool CreateAndConfigureRealChannelForLoadState(
501
mozilla::dom::BrowsingContext* aBrowsingContext,
502
nsDocShellLoadState* aLoadState, mozilla::net::LoadInfo* aLoadInfo,
503
nsIInterfaceRequestor* aCallbacks, nsDocShell* aDocShell,
504
const mozilla::OriginAttributes& aOriginAttributes,
505
nsLoadFlags aLoadFlags, uint32_t aCacheKey, nsresult& rv,
506
nsIChannel** aChannel);
507
508
// Notify consumers of a search being loaded through the observer service:
509
static void MaybeNotifyKeywordSearchLoading(const nsString& aProvider,
510
const nsString& aKeyword);
511
512
nsDocShell* GetInProcessChildAt(int32_t aIndex);
513
514
/**
515
* Helper function that finds the last URI and its transition flags for a
516
* channel.
517
*
518
* This method first checks the channel's property bag to see if previous
519
* info has been saved. If not, it gives back the referrer of the channel.
520
*
521
* @param aChannel
522
* The channel we are transitioning to
523
* @param aURI
524
* Output parameter with the previous URI, not addref'd
525
* @param aChannelRedirectFlags
526
* If a redirect, output parameter with the previous redirect flags
527
* from nsIChannelEventSink
528
*/
529
static void ExtractLastVisit(nsIChannel* aChannel, nsIURI** aURI,
530
uint32_t* aChannelRedirectFlags);
531
532
static uint32_t ComputeURILoaderFlags(
533
mozilla::dom::BrowsingContext* aBrowsingContext, uint32_t aLoadType);
534
535
private: // member functions
536
friend class nsDSURIContentListener;
537
friend class FramingChecker;
538
friend class OnLinkClickEvent;
539
friend class nsIDocShell;
540
friend class mozilla::dom::BrowsingContext;
541
542
// It is necessary to allow adding a timeline marker wherever a docshell
543
// instance is available. This operation happens frequently and needs to
544
// be very fast, so instead of using a Map or having to search for some
545
// docshell-specific markers storage, a pointer to an `ObservedDocShell` is
546
// is stored on docshells directly.
547
friend void mozilla::TimelineConsumers::AddConsumer(nsDocShell*);
548
friend void mozilla::TimelineConsumers::RemoveConsumer(nsDocShell*);
549
friend void mozilla::TimelineConsumers::AddMarkerForDocShell(
550
nsDocShell*, const char*, MarkerTracingType, MarkerStackRequest);
551
friend void mozilla::TimelineConsumers::AddMarkerForDocShell(
552
nsDocShell*, const char*, const TimeStamp&, MarkerTracingType,
553
MarkerStackRequest);
554
friend void mozilla::TimelineConsumers::AddMarkerForDocShell(
555
nsDocShell*, UniquePtr<AbstractTimelineMarker>&&);
556
friend void mozilla::TimelineConsumers::PopMarkers(
557
nsDocShell*, JSContext*, nsTArray<dom::ProfileTimelineMarker>&);
558
559
nsDocShell(mozilla::dom::BrowsingContext* aBrowsingContext,
560
uint64_t aContentWindowID);
561
562
// Security check to prevent frameset spoofing. See comments at
563
// implementation site.
564
static bool ValidateOrigin(mozilla::dom::BrowsingContext* aOrigin,
565
mozilla::dom::BrowsingContext* aTarget);
566
567
static inline uint32_t PRTimeToSeconds(PRTime aTimeUsec) {
568
return uint32_t(aTimeUsec / PR_USEC_PER_SEC);
569
}
570
571
static const nsCString FrameTypeToString(uint32_t aFrameType) {
572
switch (aFrameType) {
573
case FRAME_TYPE_BROWSER:
574
return NS_LITERAL_CSTRING("browser");
575
case FRAME_TYPE_REGULAR:
576
return NS_LITERAL_CSTRING("regular");
577
default:
578
NS_ERROR("Unknown frame type");
579
return EmptyCString();
580
}
581
}
582
583
virtual ~nsDocShell();
584
585
//
586
// nsDocLoader
587
//
588
589
virtual void DestroyChildren() override;
590
591
// Overridden from nsDocLoader, this provides more information than the
592
// normal OnStateChange with flags STATE_REDIRECTING
593
virtual void OnRedirectStateChange(nsIChannel* aOldChannel,
594
nsIChannel* aNewChannel,
595
uint32_t aRedirectFlags,
596
uint32_t aStateFlags) override;
597
598
// Override the parent setter from nsDocLoader
599
virtual nsresult SetDocLoaderParent(nsDocLoader* aLoader) override;
600
601
//
602
// Content Viewer Management
603
//
604
605
nsresult EnsureContentViewer();
606
607
// aPrincipal can be passed in if the caller wants. If null is
608
// passed in, the about:blank principal will end up being used.
609
// aCSP, if any, will be used for the new about:blank load.
610
nsresult CreateAboutBlankContentViewer(
611
nsIPrincipal* aPrincipal, nsIPrincipal* aStoragePrincipal,
612
nsIContentSecurityPolicy* aCSP, nsIURI* aBaseURI,
613
bool aTryToSaveOldPresentation = true, bool aCheckPermitUnload = true,
614
mozilla::dom::WindowGlobalChild* aActor = nullptr);
615
616
nsresult CreateContentViewer(const nsACString& aContentType,
617
nsIRequest* aRequest,
618
nsIStreamListener** aContentHandler);
619
620
nsresult NewContentViewerObj(const nsACString& aContentType,
621
nsIRequest* aRequest, nsILoadGroup* aLoadGroup,
622
nsIStreamListener** aContentHandler,
623
nsIContentViewer** aViewer);
624
625
already_AddRefed<nsILoadURIDelegate> GetLoadURIDelegate();
626
627
nsresult SetupNewViewer(
628
nsIContentViewer* aNewViewer,
629
mozilla::dom::WindowGlobalChild* aWindowActor = nullptr);
630
631
//
632
// Session History
633
//
634
635
bool ShouldAddToSessionHistory(nsIURI* aURI, nsIChannel* aChannel);
636
637
// Either aChannel or aOwner must be null. If aChannel is
638
// present, the owner should be gotten from it.
639
// If aCloneChildren is true, then our current session history's
640
// children will be cloned onto the new entry. This should be
641
// used when we aren't actually changing the document while adding
642
// the new session history entry.
643
// aCsp is the CSP to be used for the load. That is *not* the CSP
644
// that will be applied to subresource loads within that document
645
// but the CSP for the document load itself. E.g. if that CSP
646
// includes upgrade-insecure-requests, then the new top-level load
647
// will be upgraded to HTTPS.
648
nsresult AddToSessionHistory(nsIURI* aURI, nsIChannel* aChannel,
649
nsIPrincipal* aTriggeringPrincipal,
650
nsIPrincipal* aPrincipalToInherit,
651
nsIPrincipal* aStoragePrincipalToInherit,
652
nsIContentSecurityPolicy* aCsp,
653
bool aCloneChildren, nsISHEntry** aNewEntry);
654
655
nsresult AddChildSHEntryToParent(nsISHEntry* aNewEntry, int32_t aChildOffset,
656
bool aCloneChildren);
657
658
nsresult AddChildSHEntryInternal(nsISHEntry* aCloneRef, nsISHEntry* aNewEntry,
659
int32_t aChildOffset, uint32_t aLoadType,
660
bool aCloneChildren);
661
662
// Call this method to swap in a new history entry to m[OL]SHE, rather than
663
// setting it directly. This completes the navigation in all docshells
664
// in the case of a subframe navigation.
665
// Returns old mOSHE/mLSHE.
666
already_AddRefed<nsISHEntry> SetHistoryEntry(nsCOMPtr<nsISHEntry>* aPtr,
667
nsISHEntry* aEntry);
668
669
// This method calls SetHistoryEntry and updates mOSHE and mLSHE in BC to be
670
// the same as in docshell
671
void SetHistoryEntryAndUpdateBC(const Maybe<nsISHEntry*>& aLSHE,
672
const Maybe<nsISHEntry*>& aOSHE);
673
674
//
675
// URI Load
676
//
677
678
// Actually open a channel and perform a URI load. Callers need to pass a
679
// non-null aLoadState->TriggeringPrincipal() which initiated the URI load.
680
// Please note that the TriggeringPrincipal will be used for performing
681
// security checks. If aLoadState->URI() is provided by the web, then please
682
// do not pass a SystemPrincipal as the triggeringPrincipal. If
683
// aLoadState()->PrincipalToInherit is null, then no inheritance of any sort
684
// will happen and the load will get a principal based on the URI being
685
// loaded. If the Srcdoc flag is set (INTERNAL_LOAD_FLAGS_IS_SRCDOC), the load
686
// will be considered as a srcdoc load, and the contents of Srcdoc will be
687
// loaded instead of the URI. aLoadState->OriginalURI() will be set as the
688
// originalURI on the channel that does the load. If OriginalURI is null, URI
689
// will be set as the originalURI. If LoadReplace is true, LOAD_REPLACE flag
690
// will be set on the nsIChannel.
691
nsresult DoURILoad(nsDocShellLoadState* aLoadState, nsIDocShell** aDocShell,
692
nsIRequest** aRequest);
693
694
static nsresult AddHeadersToChannel(nsIInputStream* aHeadersData,
695
nsIChannel* aChannel);
696
697
nsresult DoChannelLoad(nsIChannel* aChannel, nsIURILoader* aURILoader,
698
bool aBypassClassifier);
699
700
nsresult OpenInitializedChannel(nsIChannel* aChannel,
701
nsIURILoader* aURILoader,
702
uint32_t aOpenFlags);
703
704
MOZ_CAN_RUN_SCRIPT
705
nsresult ScrollToAnchor(bool aCurHasRef, bool aNewHasRef,
706
nsACString& aNewHash, uint32_t aLoadType);
707
708
// Returns true if would have called FireOnLocationChange,
709
// but did not because aFireOnLocationChange was false on entry.
710
// In this case it is the caller's responsibility to ensure
711
// FireOnLocationChange is called.
712
// In all other cases false is returned.
713
bool OnLoadingSite(nsIChannel* aChannel, bool aFireOnLocationChange,
714
bool aAddToGlobalHistory = true);
715
716
// Returns true if would have called FireOnLocationChange,
717
// but did not because aFireOnLocationChange was false on entry.
718
// In this case it is the caller's responsibility to ensure
719
// FireOnLocationChange is called.
720
// In all other cases false is returned.
721
// Either aChannel or aTriggeringPrincipal must be null. If aChannel is
722
// present, the owner should be gotten from it.
723
// If OnNewURI calls AddToSessionHistory, it will pass its
724
// aCloneSHChildren argument as aCloneChildren.
725
// aCsp is the CSP to be used for the load. That is *not* the CSP
726
// that will be applied to subresource loads within that document
727
// but the CSP for the document load itself. E.g. if that CSP
728
// includes upgrade-insecure-requests, then the new top-level load
729
// will be upgraded to HTTPS.
730
bool OnNewURI(nsIURI* aURI, nsIChannel* aChannel,
731
nsIPrincipal* aTriggeringPrincipal,
732
nsIPrincipal* aPrincipalToInherit,
733
nsIPrincipal* aStoragePrincipalToInehrit, uint32_t aLoadType,
734
nsIContentSecurityPolicy* aCsp, bool aFireOnLocationChange,
735
bool aAddToGlobalHistory, bool aCloneSHChildren);
736
737
// Helper method that is called when a new document (including any
738
// sub-documents - ie. frames) has been completely loaded.
739
MOZ_CAN_RUN_SCRIPT_BOUNDARY
740
nsresult EndPageLoad(nsIWebProgress* aProgress, nsIChannel* aChannel,
741
nsresult aResult);
742
743
// Builds an error page URI (e.g. about:neterror?etc) for the given aURI
744
// and displays it via the LoadErrorPage() overload below.
745
nsresult LoadErrorPage(nsIURI* aURI, const char16_t* aURL,
746
const char* aErrorPage, const char* aErrorType,
747
const char16_t* aDescription, const char* aCSSClass,
748
nsIChannel* aFailedChannel);
749
750
// This method directly loads aErrorURI as an error page. aFailedURI and
751
// aFailedChannel come from DisplayLoadError() or the LoadErrorPage() overload
752
// above.
753
nsresult LoadErrorPage(nsIURI* aErrorURI, nsIURI* aFailedURI,
754
nsIChannel* aFailedChannel);
755
756
bool DisplayLoadError(nsresult aError, nsIURI* aURI, const char16_t* aURL,
757
nsIChannel* aFailedChannel) {
758
bool didDisplayLoadError = false;
759
DisplayLoadError(aError, aURI, aURL, aFailedChannel, &didDisplayLoadError);
760
return didDisplayLoadError;
761
}
762
763
//
764
// Uncategorized
765
//
766
767
// Get the principal that we'll set on the channel if we're inheriting. If
768
// aConsiderCurrentDocument is true, we try to use the current document if
769
// at all possible. If that fails, we fall back on the parent document.
770
// If that fails too, we force creation of a content viewer and use the
771
// resulting principal. If aConsiderCurrentDocument is false, we just look
772
// at the parent.
773
// If aConsiderStoragePrincipal is true, we consider the storage principal
774
// instead of the node principal.
775
nsIPrincipal* GetInheritedPrincipal(bool aConsiderCurrentDocument,
776
bool aConsiderStoragePrincipal = false);
777
778
/**
779
* Helper function that caches a URI and a transition for saving later.
780
*
781
* @param aChannel
782
* Channel that will have these properties saved
783
* @param aURI
784
* The URI to save for later
785
* @param aChannelRedirectFlags
786
* The nsIChannelEventSink redirect flags to save for later
787
*/
788
void SaveLastVisit(nsIChannel* aChannel, nsIURI* aURI,
789
uint32_t aChannelRedirectFlags);
790
791
/**
792
* Helper function for adding a URI visit using IHistory.
793
*
794
* The IHistory API maintains chains of visits, tracking both HTTP referrers
795
* and redirects for a user session. VisitURI requires the current URI and
796
* the previous URI in the chain.
797
*
798
* Visits can be saved either during a redirect or when the request has
799
* reached its final destination. The previous URI in the visit may be
800
* from another redirect.
801
*
802
* @pre aURI is not null.
803
*
804
* @param aURI
805
* The URI that was just visited
806
* @param aPreviousURI
807
* The previous URI of this visit
808
* @param aChannelRedirectFlags
809
* For redirects, the redirect flags from nsIChannelEventSink
810
* (0 otherwise)
811
* @param aResponseStatus
812
* For HTTP channels, the response code (0 otherwise).
813
*/
814
void AddURIVisit(nsIURI* aURI, nsIURI* aPreviousURI,
815
uint32_t aChannelRedirectFlags,
816
uint32_t aResponseStatus = 0);
817
818
/**
819
* Helper function that will add the redirect chain found in aRedirects using
820
* IHistory (see AddURI and SaveLastVisit above for details)
821
*
822
* @param aChannel
823
* Channel that will have these properties saved
824
* @param aURI
825
* The URI that was just visited
826
* @param aChannelRedirectFlags
827
* For redirects, the redirect flags from nsIChannelEventSink
828
* (0 otherwise)
829
* @param aRedirects
830
* The redirect chain collected by the DocumentChannelParent
831
*/
832
void SavePreviousRedirectsAndLastVisit(
833
nsIChannel* aChannel, nsIURI* aURI, uint32_t aChannelRedirectFlags,
834
const nsTArray<mozilla::net::DocumentChannelRedirect>& aRedirects);
835
836
// Sets the current document's current state object to the given SHEntry's
837
// state object. The current state object is eventually given to the page
838
// in the PopState event.
839
nsresult SetDocCurrentStateObj(nsISHEntry* aShEntry);
840
841
// Returns true if would have called FireOnLocationChange,
842
// but did not because aFireOnLocationChange was false on entry.
843
// In this case it is the caller's responsibility to ensure
844
// FireOnLocationChange is called.
845
// In all other cases false is returned.
846
bool SetCurrentURI(nsIURI* aURI, nsIRequest* aRequest,
847
bool aFireOnLocationChange, uint32_t aLocationFlags);
848
849
// The following methods deal with saving and restoring content viewers
850
// in session history.
851
852
// mContentViewer points to the current content viewer associated with
853
// this docshell. When loading a new document, the content viewer is
854
// either destroyed or stored into a session history entry. To make sure
855
// that destruction happens in a controlled fashion, a given content viewer
856
// is always owned in exactly one of these ways:
857
// 1) The content viewer is active and owned by a docshell's
858
// mContentViewer.
859
// 2) The content viewer is still being displayed while we begin loading
860
// a new document. The content viewer is owned by the _new_
861
// content viewer's mPreviousViewer, and has a pointer to the
862
// nsISHEntry where it will eventually be stored. The content viewer
863
// has been close()d by the docshell, which detaches the document from
864
// the window object.
865
// 3) The content viewer is cached in session history. The nsISHEntry
866
// has the only owning reference to the content viewer. The viewer
867
// has released its nsISHEntry pointer to prevent circular ownership.
868
//
869
// When restoring a content viewer from session history, open() is called
870
// to reattach the document to the window object. The content viewer is
871
// then placed into mContentViewer and removed from the history entry.
872
// (mContentViewer is put into session history as described above, if
873
// applicable).
874
875
// Determines whether we can safely cache the current mContentViewer in
876
// session history. This checks a number of factors such as cache policy,
877
// pending requests, and unload handlers.
878
// |aLoadType| should be the load type that will replace the current
879
// presentation. |aNewRequest| should be the request for the document to
880
// be loaded in place of the current document, or null if such a request
881
// has not been created yet. |aNewDocument| should be the document that will
882
// replace the current document.
883
bool CanSavePresentation(uint32_t aLoadType, nsIRequest* aNewRequest,
884
mozilla::dom::Document* aNewDocument);
885
886
// There are 11 possible reasons to make a request fails to use BFCache
887
// (see BFCacheStatus in dom/base/Document.h), and we'd like to record
888
// the common combinations for reasons which make requests fail to use
889
// BFCache. These combinations are generated based on some local browsings,
890
// we need to adjust them when necessary.
891
enum BFCacheStatusCombo : uint16_t {
892
BFCACHE_SUCCESS,
893
SUCCESS_NOT_ONLY_TOPLEVEL =
894
mozilla::dom::BFCacheStatus::NOT_ONLY_TOPLEVEL_IN_BCG,
895
UNLOAD = mozilla::dom::BFCacheStatus::UNLOAD_LISTENER,
896
UNLOAD_REQUEST = mozilla::dom::BFCacheStatus::UNLOAD_LISTENER |
897
mozilla::dom::BFCacheStatus::REQUEST,
898
REQUEST = mozilla::dom::BFCacheStatus::REQUEST,
899
UNLOAD_REQUEST_PEER = mozilla::dom::BFCacheStatus::UNLOAD_LISTENER |
900
mozilla::dom::BFCacheStatus::REQUEST |
901
mozilla::dom::BFCacheStatus::ACTIVE_PEER_CONNECTION,
902
UNLOAD_REQUEST_PEER_MSE =
903
mozilla::dom::BFCacheStatus::UNLOAD_LISTENER |
904
mozilla::dom::BFCacheStatus::REQUEST |
905
mozilla::dom::BFCacheStatus::ACTIVE_PEER_CONNECTION |
906
mozilla::dom::BFCacheStatus::CONTAINS_MSE_CONTENT,
907
UNLOAD_REQUEST_MSE = mozilla::dom::BFCacheStatus::UNLOAD_LISTENER |
908
mozilla::dom::BFCacheStatus::REQUEST |
909
mozilla::dom::BFCacheStatus::CONTAINS_MSE_CONTENT,
910
SUSPENDED_UNLOAD_REQUEST_PEER =
911
mozilla::dom::BFCacheStatus::SUSPENDED |
912
mozilla::dom::BFCacheStatus::UNLOAD_LISTENER |
913
mozilla::dom::BFCacheStatus::REQUEST |
914
mozilla::dom::BFCacheStatus::ACTIVE_PEER_CONNECTION,
915
REMOTE_SUBFRAMES = mozilla::dom::BFCacheStatus::CONTAINS_REMOTE_SUBFRAMES
916
};
917
918
void ReportBFCacheComboTelemetry(uint16_t aCombo);
919
920
// Captures the state of the supporting elements of the presentation
921
// (the "window" object, docshell tree, meta-refresh loads, and security
922
// state) and stores them on |mOSHE|.
923
nsresult CaptureState();
924
925
// Begin the toplevel restore process for |aSHEntry|.
926
// This simulates a channel open, and defers the real work until
927
// RestoreFromHistory is called from a PLEvent.
928
nsresult RestorePresentation(nsISHEntry* aSHEntry, bool* aRestoring);
929
930
// Call BeginRestore(nullptr, false) for each child of this shell.
931
nsresult BeginRestoreChildren();
932
933
// Method to get our current position and size without flushing
934
void DoGetPositionAndSize(int32_t* aX, int32_t* aY, int32_t* aWidth,
935
int32_t* aHeight);
936
937
// Call this when a URI load is handed to us (via OnLinkClick or
938
// InternalLoad). This makes sure that we're not inside unload, or that if
939
// we are it's still OK to load this URI.
940
bool IsOKToLoadURI(nsIURI* aURI);
941
942
// helpers for executing commands
943
nsresult GetControllerForCommand(const char* aCommand,
944
nsIController** aResult);
945
946
// Possibly create a ClientSource object to represent an initial about:blank
947
// window that has not been allocated yet. Normally we try not to create
948
// this about:blank window until something calls GetDocument(). We still need
949
// the ClientSource to exist for this conceptual window, though.
950
//
951
// The ClientSource is created with the given principal if specified. If
952
// the principal is not provided we will attempt to inherit it when we
953
// are sure it will match what the real about:blank window principal
954
// would have been. There are some corner cases where we cannot easily
955
// determine the correct principal and will not create the ClientSource.
956
// In these cases the initial about:blank will appear to not exist until
957
// its real document and window are created.
958
void MaybeCreateInitialClientSource(nsIPrincipal* aPrincipal = nullptr);
959
960
// Determine if a service worker is allowed to control a window in this
961
// docshell with the given URL. If there are any reasons it should not,
962
// this will return false. If true is returned then the window *may* be
963
// controlled. The caller must still consult either the parent controller
964
// or the ServiceWorkerManager to determine if a service worker should
965
// actually control the window.
966
bool ServiceWorkerAllowedToControlWindow(nsIPrincipal* aPrincipal,
967
nsIURI* aURI);
968
969
// Return the ClientInfo for the initial about:blank window, if it exists
970
// or we have speculatively created a ClientSource in
971
// MaybeCreateInitialClientSource(). This can return a ClientInfo object
972
// even if GetExtantDoc() returns nullptr.
973
mozilla::Maybe<mozilla::dom::ClientInfo> GetInitialClientInfo() const;
974
975
/**
976
* Initializes mTiming if it isn't yet.
977
* After calling this, mTiming is non-null. This method returns true if the
978
* initialization of the Timing can be reset (basically this is true if a new
979
* Timing object is created).
980
* In case the loading is aborted, MaybeResetInitTiming() can be called
981
* passing the return value of MaybeInitTiming(): if it's possible to reset
982
* the Timing, this method will do it.
983
*/
984
MOZ_MUST_USE bool MaybeInitTiming();
985
void MaybeResetInitTiming(bool aReset);
986
987
// Convenience method for getting our parent docshell. Can return null
988
already_AddRefed<nsDocShell> GetInProcessParentDocshell();
989
990
// Helper assertion to enforce that mInPrivateBrowsing is in sync with
991
// OriginAttributes.mPrivateBrowsingId
992
void AssertOriginAttributesMatchPrivateBrowsing();
993
994
// Internal implementation of nsIDocShell::FirePageHideNotification.
995
// If aSkipCheckingDynEntries is true, it will not try to remove dynamic
996
// subframe entries. This is to avoid redundant RemoveDynEntries calls in all
997
// children docshells.
998
void FirePageHideNotificationInternal(bool aIsUnload,
999
bool aSkipCheckingDynEntries);
1000
1001
// Dispatch a runnable to the TabGroup associated to this docshell.
1002
nsresult DispatchToTabGroup(mozilla::TaskCategory aCategory,
1003
already_AddRefed<nsIRunnable>&& aRunnable);
1004
1005
void SetupReferrerInfoFromChannel(nsIChannel* aChannel);
1006
void SetReferrerInfo(nsIReferrerInfo* aReferrerInfo);
1007
void ReattachEditorToWindow(nsISHEntry* aSHEntry);
1008
void RecomputeCanExecuteScripts();
1009
void ClearFrameHistory(nsISHEntry* aEntry);
1010
void UpdateGlobalHistoryTitle(nsIURI* aURI);
1011
bool IsFrame();
1012
bool CanSetOriginAttributes();
1013
bool ShouldBlockLoadingForBackButton();
1014
bool ShouldDiscardLayoutState(nsIHttpChannel* aChannel);
1015
bool HasUnloadedParent();
1016
bool JustStartedNetworkLoad();
1017
bool IsPrintingOrPP(bool aDisplayErrorDialog = true);
1018
bool IsNavigationAllowed(bool aDisplayPrintErrorDialog = true,
1019
bool aCheckIfUnloadFired = true);
1020
uint32_t GetInheritedFrameType();
1021
nsIScrollableFrame* GetRootScrollFrame();
1022
nsIChannel* GetCurrentDocChannel();
1023
nsresult EnsureScriptEnvironment();
1024
nsresult EnsureEditorData();
1025
nsresult EnsureTransferableHookData();
1026
nsresult EnsureFind();
1027
nsresult EnsureCommandHandler();
1028
nsresult RefreshURIFromQueue();
1029
nsresult Embed(nsIContentViewer* aContentViewer,
1030
mozilla::dom::WindowGlobalChild* aWindowActor = nullptr);
1031
nsPresContext* GetEldestPresContext();
1032
nsresult CheckLoadingPermissions();
1033
nsresult PersistLayoutHistoryState();
1034
nsresult LoadHistoryEntry(nsISHEntry* aEntry, uint32_t aLoadType);
1035
nsresult GetHttpChannel(nsIChannel* aChannel, nsIHttpChannel** aReturn);
1036
nsresult ConfirmRepost(bool* aRepost);
1037
nsresult GetPromptAndStringBundle(nsIPrompt** aPrompt,
1038
nsIStringBundle** aStringBundle);
1039
nsresult SetCurScrollPosEx(int32_t aCurHorizontalPos,
1040
int32_t aCurVerticalPos);
1041
nsPoint GetCurScrollPos();
1042
1043
already_AddRefed<mozilla::dom::ChildSHistory> GetRootSessionHistory();
1044
1045
inline bool UseErrorPages() {
1046
return (mObserveErrorPages
1047
? mozilla::StaticPrefs::browser_xul_error_pages_enabled()
1048
: mUseErrorPages);
1049
}
1050
1051
bool CSSErrorReportingEnabled() const { return mCSSErrorReportingEnabled; }
1052
1053
// Handles retrieval of subframe session history for nsDocShell::LoadURI. If a
1054
// load is requested in a subframe of the current DocShell, the subframe
1055
// loadType may need to reflect the loadType of the parent document, or in
1056
// some cases (like reloads), the history load may need to be cancelled. See
1057
// function comments for in-depth logic descriptions.
1058
void MaybeHandleSubframeHistory(nsDocShellLoadState* aLoadState);
1059
1060
// If we are passed a named target during InternalLoad, this method handles
1061
// moving the load to the browsing context the target name resolves to.
1062
nsresult PerformRetargeting(nsDocShellLoadState* aLoadState,
1063
nsIDocShell** aDocShell, nsIRequest** aRequest);
1064
1065
// Returns one of nsIContentPolicy::TYPE_DOCUMENT,
1066
// nsIContentPolicy::TYPE_INTERNAL_IFRAME, or
1067
// nsIContentPolicy::TYPE_INTERNAL_FRAME depending on who is responsible for
1068
// this docshell.
1069
uint32_t DetermineContentType();
1070
1071
// In cases where we have a LoadURIDelegate (loading external links via
1072
// GeckoView), a load may need to be handled through the delegate. aWindowType
1073
// is either nsIBrowserDOMWindow::OPEN_CURRENTWINDOW or
1074
// nsIBrowserDOMWindow::OPEN_NEWWINDOW.
1075
nsresult MaybeHandleLoadDelegate(nsDocShellLoadState* aLoadState,
1076
uint32_t aWindowType, bool* aDidHandleLoad);
1077
1078
struct SameDocumentNavigationState {
1079
nsAutoCString mCurrentHash;
1080
nsAutoCString mNewHash;
1081
bool mCurrentURIHasRef = false;
1082
bool mNewURIHasRef = false;
1083
bool mSameExceptHashes = false;
1084
bool mHistoryNavBetweenSameDoc = false;
1085
};
1086
1087
// Check to see if we're loading a prior history entry or doing a fragment
1088
// navigation in the same document.
1089
bool IsSameDocumentNavigation(nsDocShellLoadState* aLoadState,
1090
SameDocumentNavigationState& aState);
1091
1092
// ... If so, handle the scrolling or other action required instead of
1093
// continuing with new document navigation.
1094
MOZ_CAN_RUN_SCRIPT
1095
nsresult HandleSameDocumentNavigation(nsDocShellLoadState* aLoadState,
1096
SameDocumentNavigationState& aState);
1097
1098
private: // data members
1099
static nsIURIFixup* sURIFixup;
1100
1101
#ifdef DEBUG
1102
// We're counting the number of |nsDocShells| to help find leaks
1103
static unsigned long gNumberOfDocShells;
1104
#endif /* DEBUG */
1105
1106
nsID mHistoryID;
1107
nsString mTitle;
1108
nsCString mOriginalUriString;
1109
nsWeakPtr mOpener;
1110
nsTObserverArray<nsWeakPtr> mPrivacyObservers;
1111
nsTObserverArray<nsWeakPtr> mReflowObservers;
1112
nsTObserverArray<nsWeakPtr> mScrollObservers;
1113
mozilla::OriginAttributes mOriginAttributes;
1114
mozilla::UniquePtr<mozilla::dom::ClientSource> mInitialClientSource;
1115
nsCOMPtr<nsINetworkInterceptController> mInterceptController;
1116
RefPtr<nsDOMNavigationTiming> mTiming;
1117
RefPtr<nsDSURIContentListener> mContentListener;
1118
RefPtr<nsGlobalWindowOuter> mScriptGlobal;
1119
nsCOMPtr<nsIPrincipal> mParentCharsetPrincipal;
1120
nsCOMPtr<nsIMutableArray> mRefreshURIList;
1121
nsCOMPtr<nsIMutableArray> mSavedRefreshURIList;
1122
uint64_t mContentWindowID;
1123
nsCOMPtr<nsIContentViewer> mContentViewer;
1124
nsCOMPtr<nsIWidget> mParentWidget;
1125
RefPtr<mozilla::dom::ChildSHistory> mSessionHistory;
1126
nsCOMPtr<nsIWebBrowserFind> mFind;
1127
RefPtr<nsCommandManager> mCommandManager;
1128
RefPtr<mozilla::dom::BrowsingContext> mBrowsingContext;
1129
1130
// Weak reference to our BrowserChild actor.
1131
nsWeakPtr mBrowserChild;
1132
1133
// Dimensions of the docshell
1134
nsIntRect mBounds;
1135
1136
/**
1137
* Content-Type Hint of the most-recently initiated load. Used for
1138
* session history entries.
1139
*/
1140
nsCString mContentTypeHint;
1141
1142
// An observed docshell wrapper is created when recording markers is enabled.
1143
mozilla::UniquePtr<mozilla::ObservedDocShell> mObserved;
1144
1145
// mCurrentURI should be marked immutable on set if possible.
1146
nsCOMPtr<nsIURI> mCurrentURI;
1147
nsCOMPtr<nsIReferrerInfo> mReferrerInfo;
1148
1149
#ifdef DEBUG
1150
nsCOMPtr<nsIURI> mLastOpenedURI;
1151
#endif
1152
1153
// Reference to the SHEntry for this docshell until the page is destroyed.
1154
// Somebody give me better name
1155
nsCOMPtr<nsISHEntry> mOSHE;
1156
1157
// Reference to the SHEntry for this docshell until the page is loaded
1158
// Somebody give me better name.
1159
// If mLSHE is non-null, non-pushState subframe loads don't create separate
1160
// root history entries. That is, frames loaded during the parent page
1161
// load don't generate history entries the way frame navigation after the
1162
// parent has loaded does. (This isn't the only purpose of mLSHE.)
1163
nsCOMPtr<nsISHEntry> mLSHE;
1164
1165
// Holds a weak pointer to a RestorePresentationEvent object if any that
1166
// holds a weak pointer back to us. We use this pointer to possibly revoke
1167
// the event whenever necessary.
1168
nsRevocableEventPtr<RestorePresentationEvent> mRestorePresentationEvent;
1169
1170
// Editor data, if this document is designMode or contentEditable.
1171
mozilla::UniquePtr<nsDocShellEditorData> mEditorData;
1172
1173
// Secure browser UI object
1174
nsCOMPtr<nsISecureBrowserUI> mSecurityUI;
1175
1176
// The URI we're currently loading. This is only relevant during the
1177
// firing of a pagehide/unload. The caller of FirePageHideNotification()
1178
// is responsible for setting it and unsetting it. It may be null if the
1179
// pagehide/unload is happening for some reason other than just loading a
1180
// new URI.
1181
nsCOMPtr<nsIURI> mLoadingURI;
1182
1183
// Our list of ancestor principals.
1184
nsTArray<nsCOMPtr<nsIPrincipal>> mAncestorPrincipals;
1185
1186
// Our list of ancestor outerWindowIDs.
1187
nsTArray<uint64_t> mAncestorOuterWindowIDs;
1188
1189
// Set in LoadErrorPage from the method argument and used later
1190
// in CreateContentViewer. We have to delay an shistory entry creation
1191
// for which these objects are needed.
1192
nsCOMPtr<nsIURI> mFailedURI;
1193
nsCOMPtr<nsIChannel> mFailedChannel;
1194
1195
// Set in DoURILoad when either the LOAD_RELOAD_ALLOW_MIXED_CONTENT flag or
1196
// the LOAD_NORMAL_ALLOW_MIXED_CONTENT flag is set.
1197
// Checked in nsMixedContentBlocker, to see if the channels match.
1198
nsCOMPtr<nsIChannel> mMixedContentChannel;
1199
1200
mozilla::UniquePtr<mozilla::gfx::Matrix5x4> mColorMatrix;
1201
1202
const mozilla::Encoding* mForcedCharset;
1203
const mozilla::Encoding* mParentCharset;
1204
1205
// WEAK REFERENCES BELOW HERE.
1206
// Note these are intentionally not addrefd. Doing so will create a cycle.
1207
// For that reasons don't use nsCOMPtr.
1208
1209
nsIDocShellTreeOwner* mTreeOwner; // Weak Reference
1210
1211
RefPtr<mozilla::dom::EventTarget> mChromeEventHandler;
1212
1213
mozilla::ScrollbarPreference mScrollbarPref; // persistent across doc loads
1214
1215
eCharsetReloadState mCharsetReloadState;
1216
1217
mozilla::hal::ScreenOrientation mOrientationLock;
1218
1219
int32_t mParentCharsetSource;
1220
mozilla::CSSIntSize mFrameMargins;
1221
1222
// This can either be a content docshell or a chrome docshell.
1223
const int32_t mItemType;
1224
1225
// Index into the nsISHEntry array, indicating the previous and current
1226
// entry at the time that this DocShell begins to load. Consequently
1227
// root docshell's indices can differ from child docshells'.
1228
int32_t mPreviousEntryIndex;
1229
int32_t mLoadedEntryIndex;
1230
1231
// Offset in the parent's child list.
1232
// -1 if the docshell is added dynamically to the parent shell.
1233
int32_t mChildOffset;
1234
1235
BusyFlags mBusyFlags;
1236
AppType mAppType;
1237
uint32_t mLoadType;
1238
uint32_t mDefaultLoadFlags;
1239
uint32_t mFailedLoadType;
1240
1241
// Are we a regular frame, a browser frame, or an app frame?
1242
FrameType mFrameType;
1243
1244
// This represents the state of private browsing in the docshell.
1245
// Currently treated as a binary value: 1 - in private mode, 0 - not private
1246
// mode On content docshells mPrivateBrowsingId ==
1247
// mOriginAttributes.mPrivateBrowsingId On chrome docshells this value will be
1248
// set, but not have the corresponding origin attribute set.
1249
uint32_t mPrivateBrowsingId;
1250
1251
// This represents the CSS display-mode we are currently using. This is mostly
1252
// used for media queries.
1253
DisplayMode mDisplayMode;
1254
1255
// A depth count of how many times NotifyRunToCompletionStart
1256
// has been called without a matching NotifyRunToCompletionStop.
1257
uint32_t mJSRunToCompletionDepth;
1258
1259
// Whether or not touch events are overridden. Possible values are defined
1260
// as constants in the nsIDocShell.idl file.
1261
TouchEventsOverride mTouchEventsOverride;
1262
1263
// Whether or not handling of the <meta name="viewport"> tag is overridden.
1264
// Possible values are defined as constants in nsIDocShell.idl.
1265
MetaViewportOverride mMetaViewportOverride;
1266
1267
// mFullscreenAllowed stores how we determine whether fullscreen is allowed
1268
// when GetFullscreenAllowed() is called. Fullscreen is allowed in a
1269
// docshell when all containing iframes have the allowfullscreen
1270
// attribute set to true. When mFullscreenAllowed is CHECK_ATTRIBUTES
1271
// we check this docshell's containing frame for the allowfullscreen
1272
// attribute, and recurse onto the parent docshell to ensure all containing
1273
// frames also have the allowfullscreen attribute. If we find an ancestor
1274
// docshell with mFullscreenAllowed not equal to CHECK_ATTRIBUTES, we've
1275
// reached a content boundary, and mFullscreenAllowed denotes whether the
1276
// parent across the content boundary has allowfullscreen=true in all its
1277
// containing iframes. mFullscreenAllowed defaults to CHECK_ATTRIBUTES and
1278
// is set otherwise when docshells which are content boundaries are created.
1279
enum FullscreenAllowedState : uint8_t {
1280
CHECK_ATTRIBUTES,
1281
PARENT_ALLOWS,
1282
PARENT_PROHIBITS
1283
};
1284
FullscreenAllowedState mFullscreenAllowed;
1285
1286
// The following two fields cannot be declared as bit fields
1287
// because of uses with AutoRestore.
1288
bool mCreatingDocument; // (should be) debugging only
1289
#ifdef DEBUG
1290
bool mInEnsureScriptEnv;
1291
#endif
1292
1293
bool mCreated : 1;
1294
bool mAllowSubframes : 1;
1295
bool mAllowJavascript : 1;
1296
bool mAllowMetaRedirects : 1;
1297
bool mAllowImages : 1;
1298
bool mAllowMedia : 1;
1299
bool mAllowDNSPrefetch : 1;
1300
bool mAllowWindowControl : 1;
1301
bool mUseErrorPages : 1;
1302
bool mObserveErrorPages : 1;
1303
bool mCSSErrorReportingEnabled : 1;
1304
bool mAllowAuth : 1;
1305
bool mAllowKeywordFixup : 1;
1306
bool mIsOffScreenBrowser : 1;
1307
bool mDisableMetaRefreshWhenInactive : 1;
1308
bool mIsAppTab : 1;
1309
bool mUseGlobalHistory : 1;
1310
bool mUseRemoteTabs : 1;
1311
bool mUseRemoteSubframes : 1;
1312
bool mUseTrackingProtection : 1;
1313
bool mDeviceSizeIsPageSize : 1;
1314
bool mWindowDraggingAllowed : 1;
1315
bool mInFrameSwap : 1;
1316
bool mInheritPrivateBrowsingId : 1;
1317
1318
// Because scriptability depends on the mAllowJavascript values of our
1319
// ancestors, we cache the effective scriptability and recompute it when
1320
// it might have changed;
1321
bool mCanExecuteScripts : 1;
1322
1323
// This boolean is set to true right before we fire pagehide and generally
1324
// unset when we embed a new content viewer. While it's true no navigation
1325
// is allowed in this docshell.
1326
bool mFiredUnloadEvent : 1;
1327
1328
// this flag is for bug #21358. a docshell may load many urls
1329
// which don't result in new documents being created (i.e. a new
1330
// content viewer) we want to make sure we don't call a on load
1331
// event more than once for a given content viewer.
1332
bool mEODForCurrentDocument : 1;
1333
bool mURIResultedInDocument : 1;
1334
1335
bool mIsBeingDestroyed : 1;
1336
1337
bool mIsExecutingOnLoadHandler : 1;
1338
1339
// Indicates that a DocShell in this "docshell tree" is printing
1340
bool mIsPrintingOrPP : 1;
1341
1342
// Indicates to CreateContentViewer() that it is safe to cache the old
1343
// presentation of the page, and to SetupNewViewer() that the old viewer
1344
// should be passed a SHEntry to save itself into.
1345
bool mSavingOldViewer : 1;
1346
1347
// @see nsIDocShellHistory::createdDynamically
1348
bool mDynamicallyCreated : 1;
1349
bool mAffectPrivateSessionLifetime : 1;
1350
bool mInvisible : 1;
1351
bool mHasLoadedNonBlankURI : 1;
1352
1353
// This flag means that mTiming has been initialized but nulled out.
1354
// We will check the innerWin's timing before creating a new one
1355
// in MaybeInitTiming()
1356
bool mBlankTiming : 1;
1357
1358
// This flag indicates when the title is valid for the current URI.
1359
bool mTitleValidForCurrentURI : 1;
1360
1361
bool mIsFrame : 1;
1362
1363
// If mWillChangeProcess is set to true, then when the docshell is destroyed,
1364
// we prepare the browsing context to change process.
1365
bool mWillChangeProcess : 1;
1366
1367
// Set when activity in this docshell is being watched by the developer tools.
1368
bool mWatchedByDevtools : 1;
1369
1370
// This flag indicates whether or not the DocShell is currently executing an
1371
// nsIWebNavigation navigation method.
1372
bool mIsNavigating : 1;
1373
};
1374
1375
#endif /* nsDocShell_h__ */