OLD | NEW |
---|---|
(Empty) | |
1 // Copyright 2016 The Chromium Authors. All rights reserved. | |
2 // Use of this source code is governed by a BSD-style license that can be | |
3 // found in the LICENSE file. | |
4 | |
5 #ifndef CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_INTERFACE_REGISTRY_H_ | |
6 #define CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_INTERFACE_REGISTRY_H_ | |
7 | |
8 #include <map> | |
9 #include <string> | |
10 | |
11 #include "base/macros.h" | |
12 #include "base/memory/weak_ptr.h" | |
13 #include "content/common/content_export.h" | |
14 #include "mojo/public/cpp/bindings/associated_binding_set.h" | |
15 #include "mojo/public/cpp/bindings/associated_interface_request.h" | |
16 #include "mojo/public/cpp/bindings/scoped_interface_endpoint_handle.h" | |
17 | |
18 namespace content { | |
19 | |
20 class RenderFrameHost; | |
21 class WebContents; | |
22 | |
23 // A helper class to hold per-frame associated interface bindings for every | |
24 // frame belonging to a single WebContents. Each WebContents owns a single | |
25 // instance of this class. | |
26 class CONTENT_EXPORT WebContentsInterfaceRegistry { | |
27 public: | |
28 virtual ~WebContentsInterfaceRegistry() {} | |
29 | |
30 // Returns the RenderFrameHost targeted by the current binding dispatch. See | |
31 // AddFrameInterface() below for details. | |
32 virtual RenderFrameHost* GetCurrentTargetFrame() = 0; | |
33 | |
34 virtual base::WeakPtr<WebContentsInterfaceRegistry> GetWeakPtr() = 0; | |
35 | |
36 // Allows test code to control the target frame currently seen by calls to | |
37 // GetCurrentTargetFrame(). Useful when simulating incoming message calls. | |
38 virtual void SetCurrentTargetFrameForTesting( | |
39 RenderFrameHost* render_frame_host) = 0; | |
40 | |
41 // Adds a new interface to the registry. A separate Interface binding is | |
42 // (lazily) established for every RenderFrameHost belonging to every | |
43 // WebContents the registry knows about. | |
44 // | |
45 // Incoming messages on Interface are routed to |impl|, and during the extent | |
Sam McNally
2016/09/09 05:33:15
impl?
| |
46 // of any message dispatch (i.e. any Interface call on |impl|), |impl| may | |
47 // call GetCurrentTargetFrame() above to get the RenderFrameHost whose | |
48 // specific binding was targeted by the message. | |
49 template <typename Interface> | |
50 void AddFrameInterface(Interface* iface) { | |
Sam McNally
2016/09/09 05:33:15
What's wrong with interface?
| |
51 AddFrameInterface(Interface::Name_, | |
52 base::MakeUnique<FrameInterface<Interface>>(iface, this)); | |
53 } | |
54 | |
55 template <typename Interface> | |
56 void RemoveFrameInterface() { RemoveFrameInterface(Interface::Name_); } | |
57 | |
58 protected: | |
59 class FrameInterfaceBase { | |
60 public: | |
61 virtual ~FrameInterfaceBase() {} | |
62 | |
63 virtual void AddBinding(RenderFrameHost* render_frame_host, | |
64 mojo::ScopedInterfaceEndpointHandle handle) = 0; | |
65 virtual void RemoveBinding(RenderFrameHost* render_frame_host) = 0; | |
66 virtual RenderFrameHost* GetCurrentTargetFrame() = 0; | |
67 }; | |
68 | |
69 // Generic helpers for the implementation to provide. See the templated | |
70 // AddFrameInterface and RemoveFrameInterface above. | |
71 virtual void AddFrameInterface(const std::string& name, | |
72 std::unique_ptr<FrameInterfaceBase> iface) = 0; | |
73 virtual void RemoveFrameInterface(const std::string& name) = 0; | |
74 | |
75 // Called immediately before any message or error is dispatched on behalf of | |
76 // any owned bindings. | |
77 virtual void WillDispatchForFrame(RenderFrameHost* render_frame_host) = 0; | |
78 | |
79 template <typename Interface> | |
80 class FrameInterface : public FrameInterfaceBase { | |
81 public: | |
82 FrameInterface(Interface* impl, WebContentsInterfaceRegistry* registry) | |
83 : impl_(impl), bindings_(mojo::BindingSetDispatchMode::WITH_CONTEXT) { | |
84 bindings_.set_pre_dispatch_handler( | |
85 base::Bind(&WebContentsInterfaceRegistry::WillDispatchForContext, | |
86 base::Unretained(registry))); | |
87 } | |
88 | |
89 ~FrameInterface() override {} | |
90 | |
91 void AddBinding(RenderFrameHost* render_frame_host, | |
92 mojo::ScopedInterfaceEndpointHandle handle) override { | |
93 mojo::AssociatedInterfaceRequest<Interface> request; | |
94 request.Bind(std::move(handle)); | |
95 frame_binding_map_[render_frame_host].push_back(bindings_.AddBinding( | |
96 impl_, std::move(request), static_cast<void*>(render_frame_host))); | |
97 } | |
98 | |
99 void RemoveBinding(RenderFrameHost* render_frame_host) override { | |
100 auto it = frame_binding_map_.find(render_frame_host); | |
101 DCHECK(it != frame_binding_map_.end()); | |
102 for (auto id : it->second) | |
103 bindings_.RemoveBinding(id); | |
104 frame_binding_map_.erase(it); | |
105 } | |
106 | |
107 RenderFrameHost* GetCurrentTargetFrame() override { | |
108 return static_cast<RenderFrameHost*>(bindings_.dispatch_context()); | |
109 } | |
110 | |
111 private: | |
112 Interface* const impl_; | |
113 mojo::AssociatedBindingSet<Interface> bindings_; | |
114 std::map<RenderFrameHost*, std::vector<mojo::BindingId>> frame_binding_map_; | |
115 | |
116 DISALLOW_COPY_AND_ASSIGN(FrameInterface); | |
117 }; | |
118 | |
119 private: | |
120 void WillDispatchForContext(void* context) { | |
121 WillDispatchForFrame(reinterpret_cast<RenderFrameHost*>(context)); | |
122 } | |
123 }; | |
124 | |
125 } // namespace content | |
126 | |
127 #endif // CONTENT_PUBLIC_BROWSER_WEB_CONTENTS_INTERFACE_REGISTRY_H_ | |
OLD | NEW |