diff --git a/Userland/Libraries/LibWeb/HTML/FrameHostElement.cpp b/Userland/Libraries/LibWeb/HTML/FrameHostElement.cpp index 19d5d6a560e..30b338a8d37 100644 --- a/Userland/Libraries/LibWeb/HTML/FrameHostElement.cpp +++ b/Userland/Libraries/LibWeb/HTML/FrameHostElement.cpp @@ -26,8 +26,11 @@ void FrameHostElement::inserted() HTMLElement::inserted(); if (!is_connected()) return; - if (auto* frame = document().frame()) + if (auto* frame = document().frame()) { m_content_frame = Frame::create_subframe(*this, frame->main_frame()); + m_content_frame->set_frame_nesting_levels(frame->frame_nesting_levels()); + m_content_frame->register_frame_nesting(document().url()); + } } Origin FrameHostElement::content_origin() const diff --git a/Userland/Libraries/LibWeb/Loader/FrameLoader.cpp b/Userland/Libraries/LibWeb/Loader/FrameLoader.cpp index d0052aed99c..c36000191b7 100644 --- a/Userland/Libraries/LibWeb/Loader/FrameLoader.cpp +++ b/Userland/Libraries/LibWeb/Loader/FrameLoader.cpp @@ -136,6 +136,11 @@ bool FrameLoader::load(const LoadRequest& request, Type type) return false; } + if (!m_frame.is_frame_nesting_allowed(request.url())) { + dbgln("No further recursion is allowed for the frame, abort load!"); + return false; + } + auto& url = request.url(); set_resource(ResourceLoader::the().load_resource(Resource::Type::Generic, request)); diff --git a/Userland/Libraries/LibWeb/Page/Frame.cpp b/Userland/Libraries/LibWeb/Page/Frame.cpp index 99c0e111b36..0a4386fadce 100644 --- a/Userland/Libraries/LibWeb/Page/Frame.cpp +++ b/Userland/Libraries/LibWeb/Page/Frame.cpp @@ -286,4 +286,14 @@ void Frame::unregister_viewport_client(ViewportClient& client) VERIFY(was_removed); } +void Frame::register_frame_nesting(URL const& url) +{ + m_frame_nesting_levels.ensure(url)++; +} + +bool Frame::is_frame_nesting_allowed(URL const& url) const +{ + return m_frame_nesting_levels.get(url).value_or(0) < 3; +} + } diff --git a/Userland/Libraries/LibWeb/Page/Frame.h b/Userland/Libraries/LibWeb/Page/Frame.h index 49370b86837..daac8635815 100644 --- a/Userland/Libraries/LibWeb/Page/Frame.h +++ b/Userland/Libraries/LibWeb/Page/Frame.h @@ -81,6 +81,12 @@ public: void did_edit(Badge); + void register_frame_nesting(URL const&); + bool is_frame_nesting_allowed(URL const&) const; + + void set_frame_nesting_levels(const HashMap frame_nesting_levels) { m_frame_nesting_levels = move(frame_nesting_levels); }; + HashMap const& frame_nesting_levels() const { return m_frame_nesting_levels; } + private: explicit Frame(DOM::Element& host_element, Frame& main_frame); explicit Frame(Page&); @@ -105,6 +111,8 @@ private: bool m_cursor_blink_state { false }; HashTable m_viewport_clients; + + HashMap m_frame_nesting_levels; }; }