/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ /* This Source Code Form is subject to the terms of the Mozilla Public * License, v. 2.0. If a copy of the MPL was not distributed with this * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ /* * Class for managing loading of a subframe (creation of the docshell, * handling of loads in it, recursion-checking). */ #ifndef nsFrameLoader_h_ #define nsFrameLoader_h_ #include "nsIDocShell.h" #include "nsStringFwd.h" #include "nsIFrameLoader.h" #include "nsPoint.h" #include "nsSize.h" #include "nsIURI.h" #include "nsAutoPtr.h" #include "nsFrameMessageManager.h" #include "mozilla/dom/Element.h" #include "mozilla/Attributes.h" #include "FrameMetrics.h" #include "nsStubMutationObserver.h" class nsIURI; class nsSubDocumentFrame; class nsView; class nsIInProcessContentFrameMessageManager; class AutoResetInShow; class nsITabParent; class nsIDocShellTreeItem; class nsIDocShellTreeOwner; class mozIApplication; namespace mozilla { namespace dom { class ContentParent; class PBrowserParent; class TabParent; struct StructuredCloneData; } namespace layout { class RenderFrameParent; } } #if defined(MOZ_WIDGET_GTK) typedef struct _GtkWidget GtkWidget; #endif #ifdef MOZ_WIDGET_QT class QX11EmbedContainer; #endif class nsFrameLoader MOZ_FINAL : public nsIFrameLoader, public nsStubMutationObserver, public mozilla::dom::ipc::MessageManagerCallback { friend class AutoResetInShow; typedef mozilla::dom::PBrowserParent PBrowserParent; typedef mozilla::dom::TabParent TabParent; typedef mozilla::layout::RenderFrameParent RenderFrameParent; protected: nsFrameLoader(mozilla::dom::Element* aOwner, bool aNetworkCreated); ~nsFrameLoader(); public: static nsFrameLoader* Create(mozilla::dom::Element* aOwner, bool aNetworkCreated); NS_DECL_CYCLE_COLLECTING_ISUPPORTS NS_DECL_CYCLE_COLLECTION_CLASS_AMBIGUOUS(nsFrameLoader, nsIFrameLoader) NS_DECL_NSIFRAMELOADER NS_DECL_NSIMUTATIONOBSERVER_ATTRIBUTECHANGED nsresult CheckForRecursiveLoad(nsIURI* aURI); nsresult ReallyStartLoading(); void Finalize(); nsIDocShell* GetExistingDocShell() { return mDocShell; } mozilla::dom::EventTarget* GetTabChildGlobalAsEventTarget(); nsresult CreateStaticClone(nsIFrameLoader* aDest); /** * MessageManagerCallback methods that we override. */ virtual bool DoLoadFrameScript(const nsAString& aURL, bool aRunInGlobalScope) MOZ_OVERRIDE; virtual bool DoSendAsyncMessage(JSContext* aCx, const nsAString& aMessage, const mozilla::dom::StructuredCloneData& aData, JS::Handle aCpows, nsIPrincipal* aPrincipal) MOZ_OVERRIDE; virtual bool CheckPermission(const nsAString& aPermission) MOZ_OVERRIDE; virtual bool CheckManifestURL(const nsAString& aManifestURL) MOZ_OVERRIDE; virtual bool CheckAppHasPermission(const nsAString& aPermission) MOZ_OVERRIDE; /** * Called from the layout frame associated with this frame loader; * this notifies us to hook up with the widget and view. */ bool Show(int32_t marginWidth, int32_t marginHeight, int32_t scrollbarPrefX, int32_t scrollbarPrefY, nsSubDocumentFrame* frame); /** * Called when the margin properties of the containing frame are changed. */ void MarginsChanged(uint32_t aMarginWidth, uint32_t aMarginHeight); /** * Called from the layout frame associated with this frame loader, when * the frame is being torn down; this notifies us that out widget and view * are going away and we should unhook from them. */ void Hide(); nsresult CloneForStatic(nsIFrameLoader* aOriginal); // The guts of an nsIFrameLoaderOwner::SwapFrameLoader implementation. A // frame loader owner needs to call this, and pass in the two references to // nsRefPtrs for frame loaders that need to be swapped. nsresult SwapWithOtherLoader(nsFrameLoader* aOther, nsRefPtr& aFirstToSwap, nsRefPtr& aSecondToSwap); nsresult SwapWithOtherRemoteLoader(nsFrameLoader* aOther, nsRefPtr& aFirstToSwap, nsRefPtr& aSecondToSwap); // When IPC is enabled, destroy any associated child process. void DestroyChild(); /** * Return the primary frame for our owning content, or null if it * can't be found. */ nsIFrame* GetPrimaryFrameOfOwningContent() const { return mOwnerContent ? mOwnerContent->GetPrimaryFrame() : nullptr; } /** * Return the document that owns this, or null if we don't have * an owner. */ nsIDocument* GetOwnerDoc() const { return mOwnerContent ? mOwnerContent->OwnerDoc() : nullptr; } PBrowserParent* GetRemoteBrowser(); /** * The "current" render frame is the one on which the most recent * remote layer-tree transaction was executed. If no content has * been drawn yet, or the remote browser doesn't have any drawn * content for whatever reason, return nullptr. The returned render * frame has an associated shadow layer tree. * * Note that the returned render frame might not be a frame * constructed for this->GetURL(). This can happen, e.g., if the * was just navigated to a new URL, but hasn't painted the * new page yet. A render frame for the previous page may be * returned. (In-process behaves similarly, and this * behavior seems desirable.) */ RenderFrameParent* GetCurrentRemoteFrame() const { return mCurrentRemoteFrame; } /** * |aFrame| can be null. If non-null, it must be the remote frame * on which the most recent layer transaction completed for this's * . */ void SetCurrentRemoteFrame(RenderFrameParent* aFrame) { mCurrentRemoteFrame = aFrame; } nsFrameMessageManager* GetFrameMessageManager() { return mMessageManager; } mozilla::dom::Element* GetOwnerContent() { return mOwnerContent; } bool ShouldClipSubdocument() { return mClipSubdocument; } bool ShouldClampScrollPosition() { return mClampScrollPosition; } /** * Tell this FrameLoader to use a particular remote browser. * * This will assert if mRemoteBrowser or mCurrentRemoteFrame is non-null. In * practice, this means you can't have successfully run TryRemoteBrowser() on * this object, which means you can't have called ShowRemoteFrame() or * ReallyStartLoading(). */ void SetRemoteBrowser(nsITabParent* aTabParent); /** * Stashes a detached view on the frame loader. We do this when we're * destroying the nsSubDocumentFrame. If the nsSubdocumentFrame is * being reframed we'll restore the detached view when it's recreated, * otherwise we'll discard the old presentation and set the detached * subdoc view to null. aContainerDoc is the document containing the * the subdoc frame. This enables us to detect when the containing * document has changed during reframe, so we can discard the presentation * in that case. */ void SetDetachedSubdocView(nsView* aDetachedView, nsIDocument* aContainerDoc); /** * Retrieves the detached view and the document containing the view, * as set by SetDetachedSubdocView(). */ nsView* GetDetachedSubdocView(nsIDocument** aContainerDoc) const; /** * Applies a new set of sandbox flags. These are merged with the sandbox * flags from our owning content's owning document with a logical OR, this * ensures that we can only add restrictions and never remove them. */ void ApplySandboxFlags(uint32_t sandboxFlags); void GetURL(nsString& aURL); private: void SetOwnerContent(mozilla::dom::Element* aContent); bool ShouldUseRemoteProcess(); /** * Is this a frameloader for a bona fide