1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
|
// Copyright 2014 The Chromium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#ifndef EXTENSIONS_RENDERER_MESSAGING_BINDINGS_H_
#define EXTENSIONS_RENDERER_MESSAGING_BINDINGS_H_
#include <string>
#include "base/macros.h"
#include "base/memory/weak_ptr.h"
#include "base/unguessable_token.h"
#include "extensions/renderer/object_backed_native_handler.h"
struct ExtensionMsg_ExternalConnectionInfo;
struct ExtensionMsg_TabConnectionInfo;
namespace content {
class RenderFrame;
}
namespace extensions {
class ExtensionPort;
struct Message;
struct PortId;
class ScriptContextSet;
// Manually implements JavaScript bindings for extension messaging.
class MessagingBindings : public ObjectBackedNativeHandler {
public:
explicit MessagingBindings(ScriptContext* script_context);
~MessagingBindings() override;
// Checks whether the port exists in the given frame. If it does not, a reply
// is sent back to the browser.
static void ValidateMessagePort(const ScriptContextSet& context_set,
const PortId& port_id,
content::RenderFrame* render_frame);
// Dispatches the onConnect content script messaging event to some contexts
// in |context_set|. If |restrict_to_render_frame| is specified, only contexts
// in that render frame will receive the message.
static void DispatchOnConnect(const ScriptContextSet& context_set,
const PortId& target_port_id,
const std::string& channel_name,
const ExtensionMsg_TabConnectionInfo& source,
const ExtensionMsg_ExternalConnectionInfo& info,
const std::string& tls_channel_id,
content::RenderFrame* restrict_to_render_frame);
// Delivers a message sent using content script messaging to some of the
// contexts in |bindings_context_set|. If |restrict_to_render_frame| is
// specified, only contexts in that render view will receive the message.
static void DeliverMessage(const ScriptContextSet& context_set,
const PortId& target_port_id,
const Message& message,
content::RenderFrame* restrict_to_render_frame);
// Dispatches the onDisconnect event in response to the channel being closed.
static void DispatchOnDisconnect(
const ScriptContextSet& context_set,
const PortId& port_id,
const std::string& error_message,
content::RenderFrame* restrict_to_render_frame);
// Returns an existing port with the given |id|, or null.
ExtensionPort* GetPortWithId(const PortId& id);
// Creates a new port with the given |id|. MessagingBindings owns the
// returned port.
ExtensionPort* CreateNewPortWithId(const PortId& id);
// Removes the port with the given |js_id|.
void RemovePortWithJsId(int js_id);
const base::UnguessableToken& context_id() const { return context_id_; }
base::WeakPtr<MessagingBindings> GetWeakPtr();
private:
using PortMap = std::map<int, std::unique_ptr<ExtensionPort>>;
// JS Exposed Function: Sends a message along the given channel.
void PostMessage(const v8::FunctionCallbackInfo<v8::Value>& args);
// JS Exposed Function: Close a port, optionally forcefully (i.e. close the
// whole channel instead of just the given port).
void CloseChannel(const v8::FunctionCallbackInfo<v8::Value>& args);
// JS Exposed Function: Binds |callback| to be invoked *sometime after*
// |object| is garbage collected. We don't call the method re-entrantly so as
// to avoid executing JS in some bizarro undefined mid-GC state, nor do we
// then call into the script context if it's been invalidated.
void BindToGC(const v8::FunctionCallbackInfo<v8::Value>& args);
// JS Exposed Function: Opens a new channel to an extension.
void OpenChannelToExtension(const v8::FunctionCallbackInfo<v8::Value>& args);
// JS Exposed Function: Opens a new channel to a native application.
void OpenChannelToNativeApp(const v8::FunctionCallbackInfo<v8::Value>& args);
// JS Exposed Function: Opens a new channel to a tab.
void OpenChannelToTab(const v8::FunctionCallbackInfo<v8::Value>& args);
// Helper function to close a port. See CloseChannel() for |force_close|
// documentation.
void ClosePort(int local_port_id, bool force_close);
int GetNextJsId();
// Active ports, mapped by local port id.
PortMap ports_;
// The next available js id for a port.
size_t next_js_id_ = 0;
// The number of extension ports created.
size_t num_extension_ports_ = 0;
// A unique identifier for this JS context.
const base::UnguessableToken context_id_;
base::WeakPtrFactory<MessagingBindings> weak_ptr_factory_;
DISALLOW_COPY_AND_ASSIGN(MessagingBindings);
};
} // namespace extensions
#endif // EXTENSIONS_RENDERER_MESSAGING_BINDINGS_H_
|