diff options
Diffstat (limited to 'chromium/third_party/blink/renderer/core/html/portal/html_portal_element.cc')
-rw-r--r-- | chromium/third_party/blink/renderer/core/html/portal/html_portal_element.cc | 100 |
1 files changed, 69 insertions, 31 deletions
diff --git a/chromium/third_party/blink/renderer/core/html/portal/html_portal_element.cc b/chromium/third_party/blink/renderer/core/html/portal/html_portal_element.cc index bf97a2d4bd7..babc1411ae0 100644 --- a/chromium/third_party/blink/renderer/core/html/portal/html_portal_element.cc +++ b/chromium/third_party/blink/renderer/core/html/portal/html_portal_element.cc @@ -6,6 +6,7 @@ #include <utility> #include "services/service_manager/public/cpp/interface_provider.h" +#include "third_party/blink/public/mojom/referrer.mojom-blink.h" #include "third_party/blink/renderer/bindings/core/v8/script_event_listener.h" #include "third_party/blink/renderer/bindings/core/v8/script_promise.h" #include "third_party/blink/renderer/bindings/core/v8/script_promise_resolver.h" @@ -36,7 +37,9 @@ #include "third_party/blink/renderer/platform/heap/handle.h" #include "third_party/blink/renderer/platform/heap/heap.h" #include "third_party/blink/renderer/platform/runtime_enabled_features.h" +#include "third_party/blink/renderer/platform/weborigin/referrer.h" #include "third_party/blink/renderer/platform/weborigin/security_origin.h" +#include "third_party/blink/renderer/platform/weborigin/security_policy.h" #include "third_party/blink/renderer/platform/wtf/functional.h" namespace blink { @@ -44,12 +47,20 @@ namespace blink { HTMLPortalElement::HTMLPortalElement( Document& document, const base::UnguessableToken& portal_token, - mojom::blink::PortalAssociatedPtr portal_ptr, - mojom::blink::PortalClientAssociatedRequest portal_client_request) + mojo::AssociatedRemote<mojom::blink::Portal> remote_portal, + mojo::PendingAssociatedReceiver<mojom::blink::PortalClient> + portal_client_receiver) : HTMLFrameOwnerElement(html_names::kPortalTag, document), portal_token_(portal_token), - portal_ptr_(std::move(portal_ptr)), - portal_client_binding_(this, std::move(portal_client_request)) {} + remote_portal_(std::move(remote_portal)), + portal_client_receiver_(this, std::move(portal_client_receiver)) { + if (remote_portal_) { + // If the portal element hosts a predecessor from activation, it can be + // activated before being inserted into the DOM, and we need to keep track + // of it from creation. + DocumentPortals::From(GetDocument()).OnPortalInserted(this); + } +} HTMLPortalElement::~HTMLPortalElement() {} @@ -58,9 +69,18 @@ void HTMLPortalElement::Trace(Visitor* visitor) { visitor->Trace(portal_frame_); } +void HTMLPortalElement::ConsumePortal() { + if (portal_token_) { + DocumentPortals::From(GetDocument()).OnPortalRemoved(this); + portal_token_ = base::UnguessableToken(); + } + remote_portal_.reset(); + portal_client_receiver_.reset(); +} + void HTMLPortalElement::Navigate() { KURL url = GetNonEmptyURLAttribute(html_names::kSrcAttr); - if (!portal_ptr_ || url.IsEmpty()) + if (!remote_portal_ || url.IsEmpty()) return; if (!url.ProtocolIsInHTTPFamily()) { @@ -71,16 +91,15 @@ void HTMLPortalElement::Navigate() { return; } - portal_ptr_->Navigate(url); -} + auto referrer_policy_to_use = ReferrerPolicyAttribute(); + if (referrer_policy_to_use == network::mojom::ReferrerPolicy::kDefault) + referrer_policy_to_use = GetDocument().GetReferrerPolicy(); + Referrer referrer = SecurityPolicy::GenerateReferrer( + referrer_policy_to_use, url, GetDocument().OutgoingReferrer()); + auto mojo_referrer = mojom::blink::Referrer::New( + KURL(NullURL(), referrer.referrer), referrer.referrer_policy); -void HTMLPortalElement::ConsumePortal() { - if (portal_token_) { - DocumentPortals::From(GetDocument()).OnPortalRemoved(this); - portal_token_ = base::UnguessableToken(); - } - portal_ptr_.reset(); - portal_client_binding_.Close(); + remote_portal_->Navigate(url, std::move(mojo_referrer)); } namespace { @@ -147,7 +166,7 @@ ScriptPromise HTMLPortalElement::activate(ScriptState* script_state, ExceptionState::kExecutionContext, "HTMLPortalElement", "activate"); - if (!portal_ptr_) { + if (!remote_portal_) { exception_state.ThrowDOMException( DOMExceptionCode::kInvalidStateError, "The HTMLPortalElement is not associated with a portal context."); @@ -189,12 +208,12 @@ ScriptPromise HTMLPortalElement::activate(ScriptState* script_state, // We also pass the ownership of the PortalPtr, which guarantees that the // PortalPtr stays alive until the callback is called. is_activating_ = true; - auto* raw_portal_ptr = portal_ptr_.get(); - raw_portal_ptr->Activate( + auto* raw_remote_portal = remote_portal_.get(); + raw_remote_portal->Activate( std::move(data), WTF::Bind( [](HTMLPortalElement* portal, - mojom::blink::PortalAssociatedPtr portal_ptr, + mojo::AssociatedRemote<mojom::blink::Portal>, ScriptPromiseResolver* resolver, bool was_adopted) { if (was_adopted) portal->GetDocument().GetPage()->SetInsidePortal(true); @@ -202,7 +221,7 @@ ScriptPromise HTMLPortalElement::activate(ScriptState* script_state, portal->is_activating_ = false; portal->ConsumePortal(); }, - WrapPersistent(this), std::move(portal_ptr_), + WrapPersistent(this), std::move(remote_portal_), WrapPersistent(resolver))); return promise; } @@ -223,7 +242,7 @@ void HTMLPortalElement::postMessage(ScriptState* script_state, const ScriptValue& message, const WindowPostMessageOptions* options, ExceptionState& exception_state) { - if (!portal_ptr_ || is_activating_) { + if (!remote_portal_ || is_activating_) { exception_state.ThrowDOMException( DOMExceptionCode::kInvalidStateError, "The HTMLPortalElement is not associated with a portal context"); @@ -242,8 +261,8 @@ void HTMLPortalElement::postMessage(ScriptState* script_state, if (exception_state.HadException()) return; - portal_ptr_->PostMessageToGuest(std::move(transferable_message), - target_origin); + remote_portal_->PostMessageToGuest(std::move(transferable_message), + target_origin); } EventListener* HTMLPortalElement::onmessage() { @@ -266,7 +285,7 @@ void HTMLPortalElement::ForwardMessageFromGuest( BlinkTransferableMessage message, const scoped_refptr<const SecurityOrigin>& source_origin, const scoped_refptr<const SecurityOrigin>& target_origin) { - if (!portal_ptr_) + if (!remote_portal_) return; PortalPostMessageHelper::CreateAndDispatchMessageEvent( @@ -274,7 +293,7 @@ void HTMLPortalElement::ForwardMessageFromGuest( } void HTMLPortalElement::DispatchLoadEvent() { - if (!portal_ptr_) + if (!remote_portal_) return; DispatchLoad(); @@ -298,20 +317,20 @@ HTMLPortalElement::InsertionNotificationRequest HTMLPortalElement::InsertedInto( return result; } - if (portal_ptr_) { + if (remote_portal_) { // The interface is already bound if the HTMLPortalElement is adopting the // predecessor. portal_frame_ = GetDocument().GetFrame()->Client()->AdoptPortal(this); - portal_ptr_.set_connection_error_handler( + remote_portal_.set_disconnect_handler( WTF::Bind(&HTMLPortalElement::ConsumePortal, WrapWeakPersistent(this))); - DocumentPortals::From(GetDocument()).OnPortalInserted(this); } else { - mojom::blink::PortalClientAssociatedPtr client; - portal_client_binding_.Bind(mojo::MakeRequest(&client)); + mojo::PendingAssociatedRemote<mojom::blink::PortalClient> client; + portal_client_receiver_.Bind(client.InitWithNewEndpointAndPassReceiver()); std::tie(portal_frame_, portal_token_) = GetDocument().GetFrame()->Client()->CreatePortal( - this, mojo::MakeRequest(&portal_ptr_), client.PassInterface()); - portal_ptr_.set_connection_error_handler( + this, remote_portal_.BindNewEndpointAndPassReceiver(), + std::move(client)); + remote_portal_.set_disconnect_handler( WTF::Bind(&HTMLPortalElement::ConsumePortal, WrapWeakPersistent(this))); DocumentPortals::From(GetDocument()).OnPortalInserted(this); Navigate(); @@ -344,6 +363,16 @@ void HTMLPortalElement::ParseAttribute( return; } + if (params.name == html_names::kReferrerpolicyAttr) { + referrer_policy_ = network::mojom::ReferrerPolicy::kDefault; + if (!params.new_value.IsNull()) { + SecurityPolicy::ReferrerPolicyFromString( + params.new_value, kDoNotSupportReferrerPolicyLegacyKeywords, + &referrer_policy_); + } + return; + } + struct { const QualifiedName& name; const AtomicString& event_name; @@ -366,6 +395,11 @@ LayoutObject* HTMLPortalElement::CreateLayoutObject(const ComputedStyle& style, return new LayoutIFrame(this); } +void HTMLPortalElement::DisconnectContentFrame() { + HTMLFrameOwnerElement::DisconnectContentFrame(); + ConsumePortal(); +} + void HTMLPortalElement::AttachLayoutTree(AttachContext& context) { HTMLFrameOwnerElement::AttachLayoutTree(context); @@ -373,4 +407,8 @@ void HTMLPortalElement::AttachLayoutTree(AttachContext& context) { SetEmbeddedContentView(ContentFrame()->View()); } +network::mojom::ReferrerPolicy HTMLPortalElement::ReferrerPolicyAttribute() { + return referrer_policy_; +} + } // namespace blink |