tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

WindowGlobalParent.h (17477B)


      1 /* -*- Mode: C++; c-basic-offset: 2; indent-tabs-mode: nil; tab-width: 8 -*- */
      2 /* vim: set sw=2 ts=8 et tw=80 ft=cpp : */
      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_WindowGlobalParent_h
      8 #define mozilla_dom_WindowGlobalParent_h
      9 
     10 #include "mozilla/ContentBlockingLog.h"
     11 #include "mozilla/ContentBlockingNotifier.h"
     12 #include "mozilla/Maybe.h"
     13 #include "mozilla/RefPtr.h"
     14 #include "mozilla/UniquePtr.h"
     15 #include "mozilla/dom/CanonicalBrowsingContext.h"
     16 #include "mozilla/dom/ClientIPCTypes.h"
     17 #include "mozilla/dom/ClientInfo.h"
     18 #include "mozilla/dom/DOMRect.h"
     19 #include "mozilla/dom/PWindowGlobalParent.h"
     20 #include "mozilla/dom/WindowContext.h"
     21 #include "mozilla/dom/WindowGlobalActor.h"
     22 #include "mozilla/dom/WindowGlobalActorsBinding.h"
     23 #include "mozilla/net/CookieJarSettings.h"
     24 #include "nsIDOMProcessParent.h"
     25 #include "nsISupports.h"
     26 #include "nsRefPtrHashtable.h"
     27 #include "nsTHashMap.h"
     28 #include "nsWrapperCache.h"
     29 
     30 class nsIPrincipal;
     31 class nsIURI;
     32 class nsFrameLoader;
     33 
     34 namespace mozilla {
     35 
     36 namespace gfx {
     37 class CrossProcessPaint;
     38 }  // namespace gfx
     39 
     40 namespace dom {
     41 
     42 class BrowserParent;
     43 class WindowGlobalChild;
     44 class JSWindowActorParent;
     45 class JSActorMessageMeta;
     46 struct PageUseCounters;
     47 class WindowSessionStoreState;
     48 struct WindowSessionStoreUpdate;
     49 class SSCacheQueryResult;
     50 
     51 /**
     52 * A handle in the parent process to a specific nsGlobalWindowInner object.
     53 */
     54 class WindowGlobalParent final : public WindowContext,
     55                                 public WindowGlobalActor,
     56                                 public PWindowGlobalParent {
     57  friend class gfx::CrossProcessPaint;
     58  friend class PWindowGlobalParent;
     59 
     60 public:
     61  NS_DECL_ISUPPORTS_INHERITED
     62  NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS_INHERITED(WindowGlobalParent,
     63                                                         WindowContext)
     64 
     65  static already_AddRefed<WindowGlobalParent> GetByInnerWindowId(
     66      uint64_t aInnerWindowId);
     67 
     68  static already_AddRefed<WindowGlobalParent> GetByInnerWindowId(
     69      const GlobalObject& aGlobal, uint64_t aInnerWindowId) {
     70    return GetByInnerWindowId(aInnerWindowId);
     71  }
     72 
     73  // The same as the corresponding methods on `WindowContext`, except that the
     74  // return types are already cast to their parent-process type variants, such
     75  // as `WindowGlobalParent` or `CanonicalBrowsingContext`.
     76  WindowGlobalParent* GetParentWindowContext() {
     77    return static_cast<WindowGlobalParent*>(
     78        WindowContext::GetParentWindowContext());
     79  }
     80  WindowGlobalParent* TopWindowContext() {
     81    return static_cast<WindowGlobalParent*>(WindowContext::TopWindowContext());
     82  }
     83  CanonicalBrowsingContext* GetBrowsingContext() const {
     84    return CanonicalBrowsingContext::Cast(WindowContext::GetBrowsingContext());
     85  }
     86 
     87  Element* GetRootOwnerElement();
     88 
     89  // Has this actor been shut down
     90  bool IsClosed() { return !CanSend(); }
     91 
     92  // Get the other side of this actor if it is an in-process actor. Returns
     93  // |nullptr| if the actor has been torn down, or is not in-process.
     94  already_AddRefed<WindowGlobalChild> GetChildActor();
     95 
     96  // Get a JS actor object by name.
     97  already_AddRefed<JSWindowActorParent> GetActor(JSContext* aCx,
     98                                                 const nsACString& aName,
     99                                                 ErrorResult& aRv);
    100  already_AddRefed<JSWindowActorParent> GetExistingActor(
    101      const nsACString& aName);
    102 
    103  // Get this actor's manager if it is not an in-process actor. Returns
    104  // |nullptr| if the actor has been torn down, or is in-process.
    105  BrowserParent* GetBrowserParent() const;
    106 
    107  ContentParent* GetContentParent();
    108 
    109  // The principal of this WindowGlobal. This value will not change over the
    110  // lifetime of the WindowGlobal object, even to reflect changes in
    111  // |document.domain|.
    112  nsIPrincipal* DocumentPrincipal() { return mDocumentPrincipal; }
    113 
    114  nsIPrincipal* DocumentStoragePrincipal() { return mDocumentStoragePrincipal; }
    115 
    116  // The BrowsingContext which this WindowGlobal has been loaded into.
    117  // FIXME: It's quite awkward that this method has a slightly different name
    118  // than the one on WindowContext.
    119  CanonicalBrowsingContext* BrowsingContext() override {
    120    return GetBrowsingContext();
    121  }
    122 
    123  // Get the root nsFrameLoader object for the tree of BrowsingContext nodes
    124  // which this WindowGlobal is a part of. This will be the nsFrameLoader
    125  // holding the BrowserParent for remote tabs, and the root content frameloader
    126  // for non-remote tabs.
    127  already_AddRefed<nsFrameLoader> GetRootFrameLoader();
    128 
    129  // The current URI which loaded in the document.
    130  nsIURI* GetDocumentURI() override { return mDocumentURI; }
    131 
    132  void GetDocumentTitle(nsAString& aTitle) const {
    133    aTitle = mDocumentTitle.valueOr(nsString());
    134  }
    135 
    136  nsIPrincipal* GetContentBlockingAllowListPrincipal() const {
    137    return mDocContentBlockingAllowListPrincipal;
    138  }
    139 
    140  Maybe<ClientInfo> GetClientInfo() { return mClientInfo; }
    141 
    142  uint64_t ContentParentId();
    143 
    144  int32_t OsPid();
    145 
    146  bool IsCurrentGlobal();
    147 
    148  bool IsActiveInTab();
    149 
    150  bool IsProcessRoot();
    151 
    152  uint32_t ContentBlockingEvents();
    153 
    154  void GetContentBlockingLog(nsAString& aLog);
    155 
    156  bool IsInitialDocument() {
    157    return mIsInitialDocument.isSome() && mIsInitialDocument.value();
    158  }
    159 
    160  bool IsUncommittedInitialDocument() { return mIsUncommittedInitialDocument; }
    161 
    162  already_AddRefed<mozilla::dom::Promise> PermitUnload(
    163      PermitUnloadAction aAction, uint32_t aTimeout, mozilla::ErrorResult& aRv);
    164 
    165  void PermitUnload(
    166      std::function<void(nsIDocumentViewer::PermitUnloadResult)>&& aResolver);
    167 
    168  void PermitUnloadTraversable(
    169      const SessionHistoryInfo& aInfo,
    170      nsIDocumentViewer::PermitUnloadAction aAction,
    171      std::function<void(nsIDocumentViewer::PermitUnloadResult)>&& aResolver);
    172 
    173  void PermitUnloadChildNavigables(
    174      nsIDocumentViewer::PermitUnloadAction aAction,
    175      std::function<void(nsIDocumentViewer::PermitUnloadResult)>&& aResolver);
    176 
    177  already_AddRefed<mozilla::dom::Promise> DrawSnapshot(
    178      const DOMRect* aRect, double aScale, const nsACString& aBackgroundColor,
    179      bool aResetScrollPosition, mozilla::ErrorResult& aRv);
    180 
    181  static already_AddRefed<WindowGlobalParent> CreateDisconnected(
    182      const WindowGlobalInit& aInit);
    183 
    184  // Initialize the mFrameLoader fields for a created WindowGlobalParent. Must
    185  // be called after setting the Manager actor.
    186  void Init() final;
    187 
    188  nsIGlobalObject* GetParentObject();
    189  JSObject* WrapObject(JSContext* aCx,
    190                       JS::Handle<JSObject*> aGivenProto) override;
    191 
    192  void NotifyContentBlockingEvent(
    193      uint32_t aEvent, nsIRequest* aRequest, bool aBlocked,
    194      const nsACString& aTrackingOrigin,
    195      const nsTArray<nsCString>& aTrackingFullHashes,
    196      const Maybe<
    197          ContentBlockingNotifier::StorageAccessPermissionGrantedReason>&
    198          aReason,
    199      const Maybe<CanvasFingerprintingEvent>& aCanvasFingerprintingEvent);
    200 
    201  ContentBlockingLog* GetContentBlockingLog() { return &mContentBlockingLog; }
    202 
    203  nsIDOMProcessParent* GetDomProcess();
    204 
    205  nsICookieJarSettings* CookieJarSettings() { return mCookieJarSettings; }
    206 
    207  nsICookieJarSettings* GetCookieJarSettings() const {
    208    return mCookieJarSettings;
    209  }
    210 
    211  bool DocumentHasLoaded() { return mDocumentHasLoaded; }
    212 
    213  bool DocumentHasUserInteracted() { return mDocumentHasUserInteracted; }
    214 
    215  uint32_t SandboxFlags() { return mSandboxFlags; }
    216 
    217  bool GetDocumentBlockAllMixedContent() { return mBlockAllMixedContent; }
    218 
    219  bool GetDocumentUpgradeInsecureRequests() { return mUpgradeInsecureRequests; }
    220 
    221  void DidBecomeCurrentWindowGlobal(bool aCurrent);
    222 
    223  uint32_t HttpsOnlyStatus() { return mHttpsOnlyStatus; }
    224 
    225  void AddSecurityState(uint32_t aStateFlags);
    226  uint32_t GetSecurityFlags() { return mSecurityState; }
    227 
    228  nsITransportSecurityInfo* GetSecurityInfo() { return mSecurityInfo; }
    229 
    230  const nsACString& GetRemoteType() const override;
    231 
    232  void NotifySessionStoreUpdatesComplete(Element* aEmbedder);
    233 
    234  Maybe<uint64_t> GetSingleChannelId() { return mSingleChannelId; }
    235 
    236  uint32_t GetBFCacheStatus() { return mBFCacheStatus; }
    237 
    238  bool HasActivePeerConnections();
    239 
    240  bool Fullscreen() { return mFullscreen; }
    241  void SetFullscreen(bool aFullscreen) { mFullscreen = aFullscreen; }
    242 
    243  void ExitTopChromeDocumentFullscreen();
    244 
    245  void SetShouldReportHasBlockedOpaqueResponse(
    246      nsContentPolicyType aContentPolicy);
    247 
    248 protected:
    249  already_AddRefed<JSActor> InitJSActor(JS::Handle<JSObject*> aMaybeActor,
    250                                        const nsACString& aName,
    251                                        ErrorResult& aRv) override;
    252  mozilla::ipc::IProtocol* AsNativeActor() override { return this; }
    253 
    254  // IPC messages
    255  mozilla::ipc::IPCResult RecvLoadURI(
    256      const MaybeDiscarded<dom::BrowsingContext>& aTargetBC,
    257      nsDocShellLoadState* aLoadState, bool aSetNavigating);
    258  mozilla::ipc::IPCResult RecvInternalLoad(nsDocShellLoadState* aLoadState);
    259  mozilla::ipc::IPCResult RecvUpdateDocumentURI(NotNull<nsIURI*> aURI);
    260  mozilla::ipc::IPCResult RecvUpdateDocumentPrincipal(
    261      nsIPrincipal* aNewDocumentPrincipal,
    262      nsIPrincipal* aNewDocumentStoragePrincipal);
    263  mozilla::ipc::IPCResult RecvUpdateDocumentHasLoaded(bool aDocumentHasLoaded);
    264  mozilla::ipc::IPCResult RecvUpdateDocumentHasUserInteracted(
    265      bool aDocumentHasUserInteracted);
    266  mozilla::ipc::IPCResult RecvUpdateSandboxFlags(uint32_t aSandboxFlags);
    267  mozilla::ipc::IPCResult RecvUpdateDocumentCspSettings(
    268      bool aBlockAllMixedContent, bool aUpgradeInsecureRequests);
    269  mozilla::ipc::IPCResult RecvUpdateDocumentTitle(const nsString& aTitle);
    270  mozilla::ipc::IPCResult RecvUpdateHttpsOnlyStatus(uint32_t aHttpsOnlyStatus);
    271  mozilla::ipc::IPCResult RecvSetIsInitialDocument(bool aIsInitialDocument) {
    272    if (aIsInitialDocument && mIsInitialDocument.isSome() &&
    273        (mIsInitialDocument.value() != aIsInitialDocument)) {
    274      return IPC_FAIL_NO_REASON(this);
    275    }
    276 
    277    mIsInitialDocument = Some(aIsInitialDocument);
    278    mIsUncommittedInitialDocument = aIsInitialDocument;
    279    return IPC_OK();
    280  }
    281  mozilla::ipc::IPCResult RecvCommitToInitialDocument() {
    282    MOZ_ASSERT(mIsInitialDocument.isSome() && mIsInitialDocument.value());
    283    mIsUncommittedInitialDocument = false;
    284    return IPC_OK();
    285  }
    286  mozilla::ipc::IPCResult RecvUpdateDocumentSecurityInfo(
    287      nsITransportSecurityInfo* aSecurityInfo);
    288  mozilla::ipc::IPCResult RecvSetClientInfo(
    289      const IPCClientInfo& aIPCClientInfo);
    290  mozilla::ipc::IPCResult RecvDestroy();
    291  mozilla::ipc::IPCResult RecvRawMessage(
    292      const JSActorMessageMeta& aMeta, JSIPCValue&& aData,
    293      const UniquePtr<ClonedMessageData>& aStack);
    294 
    295  mozilla::ipc::IPCResult RecvGetContentBlockingEvents(
    296      GetContentBlockingEventsResolver&& aResolver);
    297  mozilla::ipc::IPCResult RecvUpdateCookieJarSettings(
    298      const CookieJarSettingsArgs& aCookieJarSettingsArgs);
    299 
    300  void ActorDestroy(ActorDestroyReason aWhy) override;
    301 
    302  void DrawSnapshotInternal(gfx::CrossProcessPaint* aPaint,
    303                            const Maybe<IntRect>& aRect, float aScale,
    304                            nscolor aBackgroundColor, uint32_t aFlags);
    305 
    306  // WebShare API - try to share
    307  mozilla::ipc::IPCResult RecvShare(IPCWebShareData&& aData,
    308                                    ShareResolver&& aResolver);
    309 
    310  mozilla::ipc::IPCResult RecvCheckPermitUnload(
    311      bool aHasInProcessBlocker, XPCOMPermitUnloadAction aAction,
    312      CheckPermitUnloadResolver&& aResolver);
    313 
    314  mozilla::ipc::IPCResult RecvExpectPageUseCounters(
    315      const MaybeDiscarded<dom::WindowContext>& aTop);
    316  mozilla::ipc::IPCResult RecvAccumulatePageUseCounters(
    317      const UseCounters& aUseCounters);
    318 
    319  mozilla::ipc::IPCResult RecvRequestRestoreTabContent();
    320 
    321  mozilla::ipc::IPCResult RecvUpdateBFCacheStatus(const uint32_t& aOnFlags,
    322                                                  const uint32_t& aOffFlags);
    323 
    324  // This IPC method is to notify the parent process that the caller process
    325  // creates the first active peer connection (aIsAdded = true) or closes the
    326  // last active peer connection (aIsAdded = false).
    327  mozilla::ipc::IPCResult RecvUpdateActivePeerConnectionStatus(bool aIsAdded);
    328 
    329 public:
    330  mozilla::ipc::IPCResult RecvSetSingleChannelId(
    331      const Maybe<uint64_t>& aSingleChannelId);
    332 
    333  mozilla::ipc::IPCResult RecvSetDocumentDomain(NotNull<nsIURI*> aDomain);
    334 
    335  mozilla::ipc::IPCResult RecvReloadWithHttpsOnlyException();
    336 
    337  mozilla::ipc::IPCResult RecvGetStorageAccessPermission(
    338      bool aIncludeIdentityCredential,
    339      GetStorageAccessPermissionResolver&& aResolve);
    340 
    341  mozilla::ipc::IPCResult RecvSetCookies(
    342      const nsCString& aBaseDomain, const OriginAttributes& aOriginAttributes,
    343      nsIURI* aHost, bool aFromHttp, bool aIsThirdParty,
    344      const nsTArray<CookieStruct>& aCookies);
    345 
    346  mozilla::ipc::IPCResult RecvOnInitialStorageAccess();
    347 
    348  mozilla::ipc::IPCResult RecvRecordUserActivationForBTP();
    349 
    350  already_AddRefed<dom::PWebAuthnTransactionParent>
    351  AllocPWebAuthnTransactionParent();
    352 
    353  already_AddRefed<dom::PWebIdentityParent> AllocPWebIdentityParent();
    354 
    355 private:
    356  WindowGlobalParent(CanonicalBrowsingContext* aBrowsingContext,
    357                     uint64_t aInnerWindowId, uint64_t aOuterWindowId,
    358                     FieldValues&& aInit);
    359 
    360  ~WindowGlobalParent();
    361 
    362  bool ShouldTrackSiteOriginTelemetry();
    363  enum class PageUseCounterResultBits : uint8_t {
    364    WAITING,
    365    DATA_RECEIVED,
    366    EMPTY_DATA,
    367  };
    368  using PageUseCounterResult = EnumSet<PageUseCounterResultBits>;
    369  PageUseCounterResult FinishAccumulatingPageUseCounters();
    370 
    371  // Returns failure if the new storage principal cannot be validated
    372  // against the current document principle.
    373  nsresult SetDocumentStoragePrincipal(
    374      nsIPrincipal* aNewDocumentStoragePrincipal);
    375 
    376  // NOTE: Neither this document principal nor the document storage
    377  // principal doesn't reflect possible |document.domain| mutations
    378  // which may have been made in the actual document.
    379  nsCOMPtr<nsIPrincipal> mDocumentPrincipal;
    380  nsCOMPtr<nsIPrincipal> mDocumentStoragePrincipal;
    381 
    382  // The principal to use for the content blocking allow list.
    383  nsCOMPtr<nsIPrincipal> mDocContentBlockingAllowListPrincipal;
    384 
    385  nsCOMPtr<nsIURI> mDocumentURI;
    386  Maybe<nsString> mDocumentTitle;
    387 
    388  Maybe<bool> mIsInitialDocument;
    389 
    390  bool mIsUncommittedInitialDocument;
    391 
    392  // True if this window has a "beforeunload" event listener.
    393  bool mHasBeforeUnload;
    394 
    395  // The log of all content blocking actions taken on the document related to
    396  // this WindowGlobalParent. This is only stored on top-level documents and
    397  // includes the activity log for all of the nested subdocuments as well.
    398  ContentBlockingLog mContentBlockingLog;
    399 
    400  uint32_t mSecurityState = 0;
    401 
    402  Maybe<ClientInfo> mClientInfo;
    403  // Fields being mirrored from the corresponding document
    404  nsCOMPtr<nsICookieJarSettings> mCookieJarSettings;
    405  nsCOMPtr<nsITransportSecurityInfo> mSecurityInfo;
    406 
    407  uint32_t mSandboxFlags;
    408 
    409  struct OriginCounter {
    410    void UpdateSiteOriginsFrom(WindowGlobalParent* aParent, bool aIncrease);
    411    void Accumulate();
    412 
    413    nsTHashMap<nsCStringHashKey, int32_t> mOriginMap;
    414    uint32_t mMaxOrigins = 0;
    415  };
    416 
    417  // Used to collect unique site origin telemetry.
    418  //
    419  // Is only Some() on top-level content windows.
    420  Maybe<OriginCounter> mOriginCounter;
    421 
    422  bool mDocumentHasLoaded;
    423  bool mDocumentHasUserInteracted;
    424  bool mDocumentTreeWouldPreloadResources = false;
    425  bool mBlockAllMixedContent;
    426  bool mUpgradeInsecureRequests;
    427 
    428  // HTTPS-Only Mode flags
    429  uint32_t mHttpsOnlyStatus;
    430 
    431  // The window of the document whose page use counters our document's use
    432  // counters will contribute to.  (If we are a top-level document, this
    433  // will point to ourselves.)
    434  RefPtr<WindowGlobalParent> mPageUseCountersWindow;
    435 
    436  // Our page use counters, if we are a top-level document.
    437  UniquePtr<PageUseCounters> mPageUseCounters;
    438 
    439  // Whether we have sent our page use counters, and so should ignore any
    440  // subsequent ExpectPageUseCounters calls.
    441  bool mSentPageUseCounters = false;
    442 
    443  uint32_t mBFCacheStatus = 0;
    444 
    445  // If this WindowGlobalParent is a top window, this field indicates how many
    446  // child processes have active peer connections for this window and its
    447  // descendants.
    448  uint32_t mNumOfProcessesWithActivePeerConnections = 0;
    449 
    450  // mSingleChannelId records whether the loadgroup contains a single request
    451  // with an id. If there is one channel in the loadgroup and it has an id then
    452  // mSingleChannelId is set to Some(id) (ids are non-zero). If there is one
    453  // request in the loadgroup and it's not a channel or it doesn't have an id,
    454  // or there are multiple requests in the loadgroup, then mSingleChannelId is
    455  // set to Some(0). If there are no requests in the loadgroup then
    456  // mSingleChannelId is set to Nothing().
    457  // Note: We ignore favicon loads when considering the requests in the
    458  // loadgroup.
    459  Maybe<uint64_t> mSingleChannelId;
    460 
    461  // True if the current loaded document is in fullscreen.
    462  bool mFullscreen = false;
    463 
    464  bool mShouldReportHasBlockedOpaqueResponse = false;
    465 };
    466 
    467 }  // namespace dom
    468 }  // namespace mozilla
    469 
    470 inline nsISupports* ToSupports(
    471    mozilla::dom::WindowGlobalParent* aWindowGlobal) {
    472  return static_cast<mozilla::dom::WindowContext*>(aWindowGlobal);
    473 }
    474 
    475 #endif  // !defined(mozilla_dom_WindowGlobalParent_h)