OLD | NEW |
| (Empty) |
1 // Copyright (c) 2012 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 #include "chrome/browser/extensions/extension_function.h" | |
6 | |
7 #include "base/logging.h" | |
8 #include "base/metrics/histogram.h" | |
9 #include "chrome/browser/extensions/extension_function_dispatcher.h" | |
10 #include "chrome/browser/extensions/extension_service.h" | |
11 #include "chrome/browser/renderer_host/chrome_render_message_filter.h" | |
12 #include "chrome/common/extensions/extension_messages.h" | |
13 #include "content/public/browser/notification_source.h" | |
14 #include "content/public/browser/notification_types.h" | |
15 #include "content/public/browser/render_view_host.h" | |
16 #include "content/public/browser/web_contents.h" | |
17 #include "content/public/browser/web_contents_observer.h" | |
18 #include "extensions/common/extension_api.h" | |
19 | |
20 using content::BrowserThread; | |
21 using content::RenderViewHost; | |
22 using content::WebContents; | |
23 using extensions::ExtensionAPI; | |
24 using extensions::Feature; | |
25 | |
26 // static | |
27 void ExtensionFunctionDeleteTraits::Destruct(const ExtensionFunction* x) { | |
28 x->Destruct(); | |
29 } | |
30 | |
31 // Helper class to track the lifetime of ExtensionFunction's RenderViewHost | |
32 // pointer and NULL it out when it dies. It also allows us to filter IPC | |
33 // messages coming from the RenderViewHost. | |
34 class UIThreadExtensionFunction::RenderViewHostTracker | |
35 : public content::WebContentsObserver { | |
36 public: | |
37 explicit RenderViewHostTracker(UIThreadExtensionFunction* function) | |
38 : content::WebContentsObserver( | |
39 WebContents::FromRenderViewHost(function->render_view_host())), | |
40 function_(function) { | |
41 } | |
42 | |
43 private: | |
44 // content::WebContentsObserver: | |
45 virtual void RenderViewDeleted( | |
46 content::RenderViewHost* render_view_host) OVERRIDE { | |
47 if (render_view_host != function_->render_view_host()) | |
48 return; | |
49 | |
50 function_->SetRenderViewHost(NULL); | |
51 } | |
52 | |
53 virtual bool OnMessageReceived(const IPC::Message& message) OVERRIDE { | |
54 return function_->OnMessageReceivedFromRenderView(message); | |
55 } | |
56 | |
57 UIThreadExtensionFunction* function_; | |
58 | |
59 DISALLOW_COPY_AND_ASSIGN(RenderViewHostTracker); | |
60 }; | |
61 | |
62 ExtensionFunction::ExtensionFunction() | |
63 : request_id_(-1), | |
64 profile_id_(NULL), | |
65 has_callback_(false), | |
66 include_incognito_(false), | |
67 user_gesture_(false), | |
68 bad_message_(false), | |
69 histogram_value_(extensions::functions::UNKNOWN) {} | |
70 | |
71 ExtensionFunction::~ExtensionFunction() { | |
72 } | |
73 | |
74 UIThreadExtensionFunction* ExtensionFunction::AsUIThreadExtensionFunction() { | |
75 return NULL; | |
76 } | |
77 | |
78 IOThreadExtensionFunction* ExtensionFunction::AsIOThreadExtensionFunction() { | |
79 return NULL; | |
80 } | |
81 | |
82 bool ExtensionFunction::HasPermission() { | |
83 Feature::Availability availability = | |
84 ExtensionAPI::GetSharedInstance()->IsAvailable( | |
85 name_, extension_, Feature::BLESSED_EXTENSION_CONTEXT, source_url()); | |
86 return availability.is_available(); | |
87 } | |
88 | |
89 void ExtensionFunction::OnQuotaExceeded(const std::string& violation_error) { | |
90 error_ = violation_error; | |
91 SendResponse(false); | |
92 } | |
93 | |
94 void ExtensionFunction::SetArgs(const base::ListValue* args) { | |
95 DCHECK(!args_.get()); // Should only be called once. | |
96 args_.reset(args->DeepCopy()); | |
97 } | |
98 | |
99 void ExtensionFunction::SetResult(base::Value* result) { | |
100 results_.reset(new base::ListValue()); | |
101 results_->Append(result); | |
102 } | |
103 | |
104 const base::ListValue* ExtensionFunction::GetResultList() { | |
105 return results_.get(); | |
106 } | |
107 | |
108 const std::string ExtensionFunction::GetError() { | |
109 return error_; | |
110 } | |
111 | |
112 void ExtensionFunction::SetError(const std::string& error) { | |
113 error_ = error; | |
114 } | |
115 | |
116 void ExtensionFunction::Run() { | |
117 UMA_HISTOGRAM_ENUMERATION("Extensions.FunctionCalls", histogram_value(), | |
118 extensions::functions::ENUM_BOUNDARY); | |
119 | |
120 if (!RunImpl()) | |
121 SendResponse(false); | |
122 } | |
123 | |
124 bool ExtensionFunction::ShouldSkipQuotaLimiting() const { | |
125 return false; | |
126 } | |
127 | |
128 bool ExtensionFunction::HasOptionalArgument(size_t index) { | |
129 Value* value; | |
130 return args_->Get(index, &value) && !value->IsType(Value::TYPE_NULL); | |
131 } | |
132 | |
133 void ExtensionFunction::SendResponseImpl(bool success) { | |
134 DCHECK(!response_callback_.is_null()); | |
135 | |
136 ResponseType type = success ? SUCCEEDED : FAILED; | |
137 if (bad_message_) { | |
138 type = BAD_MESSAGE; | |
139 LOG(ERROR) << "Bad extension message " << name_; | |
140 } | |
141 | |
142 // If results were never set, we send an empty argument list. | |
143 if (!results_) | |
144 results_.reset(new base::ListValue()); | |
145 | |
146 response_callback_.Run(type, *results_, GetError()); | |
147 } | |
148 | |
149 UIThreadExtensionFunction::UIThreadExtensionFunction() | |
150 : render_view_host_(NULL), context_(NULL), delegate_(NULL) {} | |
151 | |
152 UIThreadExtensionFunction::~UIThreadExtensionFunction() { | |
153 if (dispatcher() && render_view_host()) | |
154 dispatcher()->OnExtensionFunctionCompleted(GetExtension()); | |
155 } | |
156 | |
157 UIThreadExtensionFunction* | |
158 UIThreadExtensionFunction::AsUIThreadExtensionFunction() { | |
159 return this; | |
160 } | |
161 | |
162 bool UIThreadExtensionFunction::OnMessageReceivedFromRenderView( | |
163 const IPC::Message& message) { | |
164 return false; | |
165 } | |
166 | |
167 void UIThreadExtensionFunction::Destruct() const { | |
168 BrowserThread::DeleteOnUIThread::Destruct(this); | |
169 } | |
170 | |
171 void UIThreadExtensionFunction::SetRenderViewHost( | |
172 RenderViewHost* render_view_host) { | |
173 render_view_host_ = render_view_host; | |
174 tracker_.reset(render_view_host ? new RenderViewHostTracker(this) : NULL); | |
175 } | |
176 | |
177 content::WebContents* UIThreadExtensionFunction::GetAssociatedWebContents() { | |
178 content::WebContents* web_contents = NULL; | |
179 if (dispatcher()) | |
180 web_contents = dispatcher()->delegate()->GetAssociatedWebContents(); | |
181 | |
182 return web_contents; | |
183 } | |
184 | |
185 void UIThreadExtensionFunction::SendResponse(bool success) { | |
186 if (delegate_) | |
187 delegate_->OnSendResponse(this, success, bad_message_); | |
188 else | |
189 SendResponseImpl(success); | |
190 } | |
191 | |
192 void UIThreadExtensionFunction::WriteToConsole( | |
193 content::ConsoleMessageLevel level, | |
194 const std::string& message) { | |
195 render_view_host_->Send(new ExtensionMsg_AddMessageToConsole( | |
196 render_view_host_->GetRoutingID(), level, message)); | |
197 } | |
198 | |
199 IOThreadExtensionFunction::IOThreadExtensionFunction() | |
200 : routing_id_(MSG_ROUTING_NONE) { | |
201 } | |
202 | |
203 IOThreadExtensionFunction::~IOThreadExtensionFunction() { | |
204 } | |
205 | |
206 IOThreadExtensionFunction* | |
207 IOThreadExtensionFunction::AsIOThreadExtensionFunction() { | |
208 return this; | |
209 } | |
210 | |
211 void IOThreadExtensionFunction::Destruct() const { | |
212 BrowserThread::DeleteOnIOThread::Destruct(this); | |
213 } | |
214 | |
215 void IOThreadExtensionFunction::SendResponse(bool success) { | |
216 SendResponseImpl(success); | |
217 } | |
218 | |
219 AsyncExtensionFunction::AsyncExtensionFunction() { | |
220 } | |
221 | |
222 AsyncExtensionFunction::~AsyncExtensionFunction() { | |
223 } | |
224 | |
225 SyncExtensionFunction::SyncExtensionFunction() { | |
226 } | |
227 | |
228 SyncExtensionFunction::~SyncExtensionFunction() { | |
229 } | |
230 | |
231 void SyncExtensionFunction::Run() { | |
232 SendResponse(RunImpl()); | |
233 } | |
234 | |
235 SyncIOThreadExtensionFunction::SyncIOThreadExtensionFunction() { | |
236 } | |
237 | |
238 SyncIOThreadExtensionFunction::~SyncIOThreadExtensionFunction() { | |
239 } | |
240 | |
241 void SyncIOThreadExtensionFunction::Run() { | |
242 SendResponse(RunImpl()); | |
243 } | |
OLD | NEW |