Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(31)

Side by Side Diff: content/browser/devtools/shared_worker_devtools_manager.cc

Issue 196503005: Make DevTools support for the embedded SharedWorker. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Introduce SharedWorkerDevToolsManager Created 6 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2011 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "content/browser/devtools/worker_devtools_manager.h" 5 #include "content/browser/devtools/shared_worker_devtools_manager.h"
6 6
7 #include <list>
8 #include <map>
9
10 #include "base/bind.h"
11 #include "base/lazy_instance.h" 7 #include "base/lazy_instance.h"
8 #include "base/logging.h"
9 #include "base/memory/singleton.h"
12 #include "content/browser/devtools/devtools_manager_impl.h" 10 #include "content/browser/devtools/devtools_manager_impl.h"
13 #include "content/browser/devtools/devtools_protocol.h" 11 #include "content/browser/devtools/devtools_protocol.h"
14 #include "content/browser/devtools/devtools_protocol_constants.h" 12 #include "content/browser/devtools/devtools_protocol_constants.h"
15 #include "content/browser/devtools/ipc_devtools_agent_host.h" 13 #include "content/browser/devtools/ipc_devtools_agent_host.h"
16 #include "content/browser/devtools/worker_devtools_message_filter.h"
17 #include "content/browser/worker_host/worker_service_impl.h"
18 #include "content/common/devtools_messages.h" 14 #include "content/common/devtools_messages.h"
19 #include "content/public/browser/browser_thread.h" 15 #include "content/public/browser/browser_thread.h"
20 #include "content/public/browser/child_process_data.h" 16 #include "content/public/browser/render_process_host.h"
21 #include "content/public/common/process_type.h" 17 #include "content/public/browser/worker_service.h"
22 18
23 namespace content { 19 namespace content {
24 20
25 // Called on the UI thread.
26 // static
27 scoped_refptr<DevToolsAgentHost> DevToolsAgentHost::GetForWorker(
28 int worker_process_id,
29 int worker_route_id) {
30 return WorkerDevToolsManager::GetDevToolsAgentHostForWorker(
31 worker_process_id,
32 worker_route_id);
33 }
34
35 // Called on the UI thread.
36 // static
37 bool DevToolsAgentHost::HasForWorker(
38 int worker_process_id,
39 int worker_route_id) {
40 return WorkerDevToolsManager::HasDevToolsAgentHostForWorker(
41 worker_process_id,
42 worker_route_id);
43 }
44
45 namespace { 21 namespace {
46 22
47 typedef std::map<WorkerDevToolsManager::WorkerId, 23 typedef std::map<SharedWorkerDevToolsManager::WorkerId,
48 WorkerDevToolsManager::WorkerDevToolsAgentHost*> AgentHosts; 24 SharedWorkerDevToolsManager::SharedWorkerDevtoolsAgentHost*>
25 AgentHosts;
49 base::LazyInstance<AgentHosts>::Leaky g_agent_map = LAZY_INSTANCE_INITIALIZER; 26 base::LazyInstance<AgentHosts>::Leaky g_agent_map = LAZY_INSTANCE_INITIALIZER;
50 base::LazyInstance<AgentHosts>::Leaky g_orphan_map = LAZY_INSTANCE_INITIALIZER; 27 base::LazyInstance<AgentHosts>::Leaky g_orphan_map = LAZY_INSTANCE_INITIALIZER;
51 28
29 bool SendMessageToWorker(const SharedWorkerDevToolsManager::WorkerId& worker_id,
30 IPC::Message* message) {
31 RenderProcessHost* host = RenderProcessHost::FromID(worker_id.first);
32 if (!host) {
33 delete message;
34 return false;
35 }
36 message->set_routing_id(worker_id.second);
37 host->Send(message);
38 return true;
39 }
40
52 } // namespace 41 } // namespace
53 42
54 struct WorkerDevToolsManager::TerminatedInspectedWorker { 43 class SharedWorkerDevToolsManager::SharedWorkerDevtoolsAgentHost
55 TerminatedInspectedWorker(WorkerId id,
56 const GURL& url,
57 const base::string16& name)
58 : old_worker_id(id),
59 worker_url(url),
60 worker_name(name) {}
61 WorkerId old_worker_id;
62 GURL worker_url;
63 base::string16 worker_name;
64 };
65
66
67 class WorkerDevToolsManager::WorkerDevToolsAgentHost
68 : public IPCDevToolsAgentHost { 44 : public IPCDevToolsAgentHost {
69 public: 45 public:
70 explicit WorkerDevToolsAgentHost(WorkerId worker_id) 46 SharedWorkerDevtoolsAgentHost(WorkerId worker_id) : has_worker_id_(false) {
71 : has_worker_id_(false) {
72 SetWorkerId(worker_id, false); 47 SetWorkerId(worker_id, false);
73 } 48 }
49 // IPCDevToolsAgentHost implementation.
50 virtual void SendMessageToAgent(IPC::Message* message) OVERRIDE {
51 SendMessageToWorker(worker_id_, message);
52 }
53 virtual void OnClientAttached() OVERRIDE {}
54 virtual void OnClientDetached() OVERRIDE {}
74 55
75 void SetWorkerId(WorkerId worker_id, bool reattach) { 56 void SetWorkerId(WorkerId worker_id, bool reattach) {
76 worker_id_ = worker_id; 57 worker_id_ = worker_id;
77 if (!has_worker_id_) 58 if (!has_worker_id_)
78 AddRef(); // Balanced in ResetWorkerId. 59 AddRef(); // Balanced in ResetWorkerId.
79 has_worker_id_ = true; 60 has_worker_id_ = true;
80 g_agent_map.Get()[worker_id_] = this; 61 g_agent_map.Get()[worker_id_] = this;
81 62
82 BrowserThread::PostTask( 63 if (!SharedWorkerDevToolsManager::GetInstance()
83 BrowserThread::IO, 64 ->ConnectDevToolsAgentHostToWorker(worker_id)) {
84 FROM_HERE, 65 NotifyCloseListener();
85 base::Bind( 66 return;
86 &ConnectToWorker, 67 }
87 worker_id.first,
88 worker_id.second));
89 68
90 if (reattach) 69 if (reattach)
91 Reattach(state_); 70 Reattach(state_);
92 } 71 }
93 72
94 void ResetWorkerId() { 73 void ResetWorkerId() {
95 g_agent_map.Get().erase(worker_id_); 74 g_agent_map.Get().erase(worker_id_);
96 has_worker_id_ = false; 75 has_worker_id_ = false;
97 Release(); // Balanced in SetWorkerId. 76 Release(); // Balanced in SetWorkerId.
98 } 77 }
99 78
100 void SaveAgentRuntimeState(const std::string& state) { 79 void SaveAgentRuntimeState(const std::string& state) { state_ = state; }
101 state_ = state;
102 }
103 80
104 void ConnectionFailed() { 81 void ConnectionFailed() {}
105 NotifyCloseListener();
106 // Object can be deleted here.
107 }
108 82
109 private: 83 private:
110 virtual ~WorkerDevToolsAgentHost(); 84 ~SharedWorkerDevtoolsAgentHost() {
111 85 SharedWorkerDevToolsManager::GetInstance()->RemoveInspectedWorkerData(
112 static void ConnectToWorker( 86 worker_id_);
113 int worker_process_id, 87 g_agent_map.Get().erase(worker_id_);
114 int worker_route_id) { 88 g_orphan_map.Get().erase(worker_id_);
115 WorkerDevToolsManager::GetInstance()->ConnectDevToolsAgentHostToWorker(
116 worker_process_id, worker_route_id);
117 } 89 }
118
119 static void ForwardToWorkerDevToolsAgent(
120 int worker_process_id,
121 int worker_route_id,
122 IPC::Message* message) {
123 WorkerDevToolsManager::GetInstance()->ForwardToWorkerDevToolsAgent(
124 worker_process_id, worker_route_id, *message);
125 }
126
127 // IPCDevToolsAgentHost implementation.
128 virtual void SendMessageToAgent(IPC::Message* message) OVERRIDE {
129 if (!has_worker_id_) {
130 delete message;
131 return;
132 }
133 BrowserThread::PostTask(
134 BrowserThread::IO, FROM_HERE,
135 base::Bind(
136 &WorkerDevToolsAgentHost::ForwardToWorkerDevToolsAgent,
137 worker_id_.first,
138 worker_id_.second,
139 base::Owned(message)));
140 }
141
142 virtual void OnClientAttached() OVERRIDE {}
143 virtual void OnClientDetached() OVERRIDE {}
144
145 bool has_worker_id_; 90 bool has_worker_id_;
146 WorkerId worker_id_; 91 WorkerId worker_id_;
147 std::string state_; 92 std::string state_;
148 93 DISALLOW_COPY_AND_ASSIGN(SharedWorkerDevtoolsAgentHost);
149 DISALLOW_COPY_AND_ASSIGN(WorkerDevToolsAgentHost);
150 }; 94 };
151 95
152 96 struct SharedWorkerDevToolsManager::WorkerInfo {
153 class WorkerDevToolsManager::DetachedClientHosts { 97 WorkerInfo(WorkerId id, const GURL& url, const base::string16& name)
154 public: 98 : worker_id(id), worker_url(url), worker_name(name) {}
155 static void WorkerReloaded(WorkerId old_id, WorkerId new_id) { 99 WorkerId worker_id;
156 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
157 AgentHosts::iterator it = g_orphan_map.Get().find(old_id);
158 if (it != g_orphan_map.Get().end()) {
159 it->second->SetWorkerId(new_id, true);
160 g_orphan_map.Get().erase(old_id);
161 return;
162 }
163 RemovePendingWorkerData(old_id);
164 }
165
166 static void WorkerDestroyed(WorkerId id) {
167 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
168 AgentHosts::iterator it = g_agent_map.Get().find(id);
169 if (it == g_agent_map.Get().end()) {
170 RemovePendingWorkerData(id);
171 return;
172 }
173
174 WorkerDevToolsAgentHost* agent = it->second;
175 DevToolsManagerImpl* devtools_manager = DevToolsManagerImpl::GetInstance();
176 if (!agent->IsAttached()) {
177 // Agent has no client hosts -> delete it.
178 RemovePendingWorkerData(id);
179 return;
180 }
181
182 // Client host is debugging this worker agent host.
183 std::string notification = DevToolsProtocol::CreateNotification(
184 devtools::Worker::disconnectedFromWorker::kName, NULL)->Serialize();
185 devtools_manager->DispatchOnInspectorFrontend(agent, notification);
186 g_orphan_map.Get()[id] = agent;
187 agent->ResetWorkerId();
188 }
189
190 static void RemovePendingWorkerData(WorkerId id) {
191 BrowserThread::PostTask(
192 BrowserThread::IO, FROM_HERE,
193 base::Bind(&RemoveInspectedWorkerDataOnIOThread, id));
194 }
195
196 private:
197 DetachedClientHosts() {}
198 ~DetachedClientHosts() {}
199
200 static void RemoveInspectedWorkerDataOnIOThread(WorkerId id) {
201 WorkerDevToolsManager::GetInstance()->RemoveInspectedWorkerData(id);
202 }
203 };
204
205 struct WorkerDevToolsManager::InspectedWorker {
206 InspectedWorker(WorkerProcessHost* host, int route_id, const GURL& url,
207 const base::string16& name)
208 : host(host),
209 route_id(route_id),
210 worker_url(url),
211 worker_name(name) {}
212 WorkerProcessHost* const host;
213 int const route_id;
214 GURL worker_url; 100 GURL worker_url;
215 base::string16 worker_name; 101 base::string16 worker_name;
216 }; 102 };
217 103
218 // static 104 // static
219 WorkerDevToolsManager* WorkerDevToolsManager::GetInstance() { 105 SharedWorkerDevToolsManager* SharedWorkerDevToolsManager::GetInstance() {
220 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::IO)); 106 DCHECK(WorkerService::EmbeddedSharedWorkerEnabled());
221 return Singleton<WorkerDevToolsManager>::get(); 107 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
108 return Singleton<SharedWorkerDevToolsManager>::get();
222 } 109 }
223 110
224 // static 111 // static
225 DevToolsAgentHost* WorkerDevToolsManager::GetDevToolsAgentHostForWorker( 112 DevToolsAgentHost* SharedWorkerDevToolsManager::GetDevToolsAgentHostForWorker(
226 int worker_process_id, 113 int worker_process_id,
227 int worker_route_id) { 114 int worker_route_id) {
115 DCHECK(WorkerService::EmbeddedSharedWorkerEnabled());
228 WorkerId id(worker_process_id, worker_route_id); 116 WorkerId id(worker_process_id, worker_route_id);
229 AgentHosts::iterator it = g_agent_map.Get().find(id); 117 AgentHosts::iterator it = g_agent_map.Get().find(id);
230 if (it == g_agent_map.Get().end()) 118 if (it == g_agent_map.Get().end())
231 return new WorkerDevToolsAgentHost(id); 119 return new SharedWorkerDevtoolsAgentHost(id);
232 return it->second; 120 return it->second;
233 } 121 }
234 122
235 // static 123 // static
236 bool WorkerDevToolsManager::HasDevToolsAgentHostForWorker( 124 bool SharedWorkerDevToolsManager::HasDevToolsAgentHostForWorker(
237 int worker_process_id, 125 int worker_process_id,
238 int worker_route_id) { 126 int worker_route_id) {
127 DCHECK(WorkerService::EmbeddedSharedWorkerEnabled());
239 WorkerId id(worker_process_id, worker_route_id); 128 WorkerId id(worker_process_id, worker_route_id);
240 return g_agent_map.Get().find(id) != g_agent_map.Get().end(); 129 return g_agent_map.Get().find(id) != g_agent_map.Get().end();
241 } 130 }
242 131
243 WorkerDevToolsManager::WorkerDevToolsManager() { 132 SharedWorkerDevToolsManager::SharedWorkerDevToolsManager() {}
244 }
245 133
246 WorkerDevToolsManager::~WorkerDevToolsManager() { 134 SharedWorkerDevToolsManager::~SharedWorkerDevToolsManager() {}
247 }
248 135
249 void WorkerDevToolsManager::WorkerCreated( 136 void SharedWorkerDevToolsManager::WorkerCreated(int worker_process_id,
250 WorkerProcessHost* worker, 137 int worker_route_id,
251 const WorkerProcessHost::WorkerInstance& instance) { 138 const GURL& url,
252 for (TerminatedInspectedWorkers::iterator it = terminated_workers_.begin(); 139 const base::string16& name) {
253 it != terminated_workers_.end(); ++it) { 140 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
254 if (instance.Matches(it->worker_url, it->worker_name, 141 const WorkerId id(worker_process_id, worker_route_id);
255 instance.partition(), 142 WorkerInfoMap::iterator it = FindTerminatedWorker(url, name);
256 instance.resource_context())) { 143 if (it != terminated_workers_.end()) {
257 worker->Send(new DevToolsAgentMsg_PauseWorkerContextOnStart( 144 scoped_ptr<WorkerInfo> info = terminated_workers_.take_and_erase(it);
258 instance.worker_route_id())); 145 paused_workers_.set(id, info.Pass());
259 WorkerId new_worker_id(worker->GetData().id, instance.worker_route_id()); 146 SendMessageToWorker(
260 paused_workers_[new_worker_id] = it->old_worker_id; 147 id, new DevToolsAgentMsg_PauseWorkerContextOnStart(worker_route_id));
261 terminated_workers_.erase(it); 148 } else {
262 return; 149 scoped_ptr<WorkerInfo> info(new WorkerInfo(id, url, name));
263 } 150 uninspected_workers_.set(id, info.Pass());
264 } 151 }
265 } 152 }
266 153
267 void WorkerDevToolsManager::WorkerDestroyed( 154 void SharedWorkerDevToolsManager::WorkerDestroyed(int worker_process_id,
268 WorkerProcessHost* worker, 155 int worker_route_id) {
269 int worker_route_id) { 156 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
270 InspectedWorkersList::iterator it = FindInspectedWorker( 157 const WorkerId id(worker_process_id, worker_route_id);
271 worker->GetData().id, 158 if (uninspected_workers_.erase(id))
272 worker_route_id); 159 return;
160 WorkerInfoMap::iterator it = inspected_workers_.find(id);
273 if (it == inspected_workers_.end()) 161 if (it == inspected_workers_.end())
274 return; 162 return;
yurys 2014/03/13 09:06:52 Looks like you need to remove the id from uninspec
horo 2014/03/14 08:53:20 The id is removed from uninspected_workers_ in lin
163 scoped_ptr<WorkerInfo> info = inspected_workers_.take_and_erase(it);
275 164
276 WorkerId worker_id(worker->GetData().id, worker_route_id); 165 AgentHosts::iterator agent_host_it = g_agent_map.Get().find(id);
277 terminated_workers_.push_back(TerminatedInspectedWorker( 166 if (agent_host_it == g_agent_map.Get().end() ||
278 worker_id, 167 !agent_host_it->second->IsAttached()) {
yurys 2014/03/13 09:06:52 If the worker is destroyed and there is a detached
horo 2014/03/14 08:53:20 Done.
279 it->worker_url, 168 return;
280 it->worker_name)); 169 }
281 inspected_workers_.erase(it); 170
282 BrowserThread::PostTask( 171 // Client host is debugging this worker agent host.
283 BrowserThread::UI, FROM_HERE, 172 std::string notification =
284 base::Bind(&DetachedClientHosts::WorkerDestroyed, worker_id)); 173 DevToolsProtocol::CreateNotification(
174 devtools::Worker::disconnectedFromWorker::kName, NULL)->Serialize();
175 DevToolsManagerImpl::GetInstance()->DispatchOnInspectorFrontend(
176 agent_host_it->second, notification);
177 terminated_workers_.set(id, info.Pass());
178 g_orphan_map.Get()[id] = agent_host_it->second;
179 agent_host_it->second->ResetWorkerId();
285 } 180 }
286 181
287 void WorkerDevToolsManager::WorkerContextStarted(WorkerProcessHost* process, 182 void SharedWorkerDevToolsManager::WorkerContextStarted(int worker_process_id,
288 int worker_route_id) { 183 int worker_route_id) {
289 WorkerId new_worker_id(process->GetData().id, worker_route_id); 184 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
290 PausedWorkers::iterator it = paused_workers_.find(new_worker_id); 185 const WorkerId id(worker_process_id, worker_route_id);
186 WorkerInfoMap::iterator it = paused_workers_.find(id);
291 if (it == paused_workers_.end()) 187 if (it == paused_workers_.end())
292 return; 188 return;
189 scoped_ptr<WorkerInfo> info = paused_workers_.take_and_erase(it);
190 const WorkerId old_id(info->worker_id);
191 info->worker_id = id;
192 uninspected_workers_.set(id, info.Pass());
293 193
294 BrowserThread::PostTask( 194 AgentHosts::iterator agent_host_it = g_orphan_map.Get().find(old_id);
295 BrowserThread::UI, FROM_HERE, 195 if (agent_host_it == g_orphan_map.Get().end())
296 base::Bind( 196 return;
297 &DetachedClientHosts::WorkerReloaded, 197 agent_host_it->second->SetWorkerId(id, true);
298 it->second, 198 g_orphan_map.Get().erase(old_id);
299 new_worker_id));
300 paused_workers_.erase(it);
301 } 199 }
302 200
303 void WorkerDevToolsManager::RemoveInspectedWorkerData( 201 void SharedWorkerDevToolsManager::ForwardToDevToolsClient(
304 const WorkerId& id) { 202 int worker_process_id,
305 for (TerminatedInspectedWorkers::iterator it = terminated_workers_.begin(); 203 int worker_route_id,
306 it != terminated_workers_.end(); ++it) { 204 const std::string& message) {
307 if (it->old_worker_id == id) { 205 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
308 terminated_workers_.erase(it); 206 AgentHosts::iterator it =
309 return; 207 g_agent_map.Get().find(WorkerId(worker_process_id, worker_route_id));
310 } 208 if (it == g_agent_map.Get().end())
311 } 209 return;
210 DevToolsManagerImpl::GetInstance()->DispatchOnInspectorFrontend(it->second,
211 message);
212 }
312 213
313 for (PausedWorkers::iterator it = paused_workers_.begin(); 214 void SharedWorkerDevToolsManager::SaveAgentRuntimeState(
314 it != paused_workers_.end(); ++it) { 215 int worker_process_id,
315 if (it->second == id) { 216 int worker_route_id,
316 SendResumeToWorker(it->first); 217 const std::string& state) {
218 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
219 AgentHosts::iterator it =
220 g_agent_map.Get().find(WorkerId(worker_process_id, worker_route_id));
221 if (it == g_agent_map.Get().end())
222 return;
223 it->second->SaveAgentRuntimeState(state);
224 }
225
226 bool SharedWorkerDevToolsManager::ConnectDevToolsAgentHostToWorker(
227 const WorkerId& worker_id) {
228 DCHECK(BrowserThread::CurrentlyOn(BrowserThread::UI));
229 WorkerInfoMap::iterator it = uninspected_workers_.find(worker_id);
230 if (it == uninspected_workers_.end())
231 return false;
232 inspected_workers_.set(worker_id, uninspected_workers_.take_and_erase(it));
233 return true;
234 }
235
236 void SharedWorkerDevToolsManager::RemoveInspectedWorkerData(
237 const WorkerId& worker_id) {
238 if (terminated_workers_.erase(worker_id))
239 return;
240
241 for (WorkerInfoMap::iterator it = paused_workers_.begin();
242 it != paused_workers_.end();
243 ++it) {
244 if (it->second->worker_id == worker_id) {
245 SendMessageToWorker(
246 it->first,
247 new DevToolsAgentMsg_ResumeWorkerContext(it->first.second));
317 paused_workers_.erase(it); 248 paused_workers_.erase(it);
318 return; 249 return;
319 } 250 }
320 } 251 }
321 } 252 }
322 253
323 WorkerDevToolsManager::InspectedWorkersList::iterator 254 SharedWorkerDevToolsManager::WorkerInfoMap::iterator
324 WorkerDevToolsManager::FindInspectedWorker( 255 SharedWorkerDevToolsManager::FindTerminatedWorker(const GURL& url,
325 int host_id, int route_id) { 256 const base::string16& name) {
326 InspectedWorkersList::iterator it = inspected_workers_.begin(); 257 WorkerInfoMap::iterator it = terminated_workers_.begin();
327 while (it != inspected_workers_.end()) { 258 for (; it != terminated_workers_.end(); ++it) {
328 if (it->host->GetData().id == host_id && it->route_id == route_id) 259 if (url.GetOrigin() != it->second->worker_url.GetOrigin())
yurys 2014/03/13 09:06:52 Can we reuse a mechanism that implements a spec-co
horo 2014/03/14 08:53:20 Done.
yurys 2014/03/26 13:11:32 I wonder if we can use SharedWorkerInstance::Match
329 break; 260 continue;
330 ++it; 261 if (name.empty() && it->second->worker_name.empty()) {
262 if (url != it->second->worker_url)
263 continue;
264 } else if (name != it->second->worker_name)
265 continue;
266 break;
331 } 267 }
332 return it; 268 return it;
333 } 269 }
334 270
335 static WorkerProcessHost* FindWorkerProcess(int worker_process_id) {
336 for (WorkerProcessHostIterator iter; !iter.Done(); ++iter) {
337 if (iter.GetData().id == worker_process_id)
338 return *iter;
339 }
340 return NULL;
341 }
342
343 void WorkerDevToolsManager::ConnectDevToolsAgentHostToWorker(
344 int worker_process_id,
345 int worker_route_id) {
346 if (WorkerProcessHost* process = FindWorkerProcess(worker_process_id)) {
347 const WorkerProcessHost::Instances& instances = process->instances();
348 for (WorkerProcessHost::Instances::const_iterator i = instances.begin();
349 i != instances.end(); ++i) {
350 if (i->worker_route_id() == worker_route_id) {
351 DCHECK(FindInspectedWorker(worker_process_id, worker_route_id) ==
352 inspected_workers_.end());
353 inspected_workers_.push_back(
354 InspectedWorker(process, worker_route_id, i->url(), i->name()));
355 return;
356 }
357 }
358 }
359 NotifyConnectionFailedOnIOThread(worker_process_id, worker_route_id);
360 }
361
362 void WorkerDevToolsManager::ForwardToDevToolsClient(
363 int worker_process_id,
364 int worker_route_id,
365 const std::string& message) {
366 if (FindInspectedWorker(worker_process_id, worker_route_id) ==
367 inspected_workers_.end()) {
368 NOTREACHED();
369 return;
370 }
371 BrowserThread::PostTask(
372 BrowserThread::UI, FROM_HERE,
373 base::Bind(
374 &ForwardToDevToolsClientOnUIThread,
375 worker_process_id,
376 worker_route_id,
377 message));
378 }
379
380 void WorkerDevToolsManager::SaveAgentRuntimeState(int worker_process_id,
381 int worker_route_id,
382 const std::string& state) {
383 BrowserThread::PostTask(
384 BrowserThread::UI, FROM_HERE,
385 base::Bind(
386 &SaveAgentRuntimeStateOnUIThread,
387 worker_process_id,
388 worker_route_id,
389 state));
390 }
391
392 void WorkerDevToolsManager::ForwardToWorkerDevToolsAgent(
393 int worker_process_id,
394 int worker_route_id,
395 const IPC::Message& message) {
396 InspectedWorkersList::iterator it = FindInspectedWorker(
397 worker_process_id,
398 worker_route_id);
399 if (it == inspected_workers_.end())
400 return;
401 IPC::Message* msg = new IPC::Message(message);
402 msg->set_routing_id(worker_route_id);
403 it->host->Send(msg);
404 }
405
406 // static
407 void WorkerDevToolsManager::ForwardToDevToolsClientOnUIThread(
408 int worker_process_id,
409 int worker_route_id,
410 const std::string& message) {
411 AgentHosts::iterator it = g_agent_map.Get().find(WorkerId(worker_process_id,
412 worker_route_id));
413 if (it == g_agent_map.Get().end())
414 return;
415 DevToolsManagerImpl::GetInstance()->DispatchOnInspectorFrontend(it->second,
416 message);
417 }
418
419 // static
420 void WorkerDevToolsManager::SaveAgentRuntimeStateOnUIThread(
421 int worker_process_id,
422 int worker_route_id,
423 const std::string& state) {
424 AgentHosts::iterator it = g_agent_map.Get().find(WorkerId(worker_process_id,
425 worker_route_id));
426 if (it == g_agent_map.Get().end())
427 return;
428 it->second->SaveAgentRuntimeState(state);
429 }
430
431 // static
432 void WorkerDevToolsManager::NotifyConnectionFailedOnIOThread(
433 int worker_process_id,
434 int worker_route_id) {
435 BrowserThread::PostTask(
436 BrowserThread::UI, FROM_HERE,
437 base::Bind(
438 &WorkerDevToolsManager::NotifyConnectionFailedOnUIThread,
439 worker_process_id,
440 worker_route_id));
441 }
442
443 // static
444 void WorkerDevToolsManager::NotifyConnectionFailedOnUIThread(
445 int worker_process_id,
446 int worker_route_id) {
447 AgentHosts::iterator it = g_agent_map.Get().find(WorkerId(worker_process_id,
448 worker_route_id));
449 if (it != g_agent_map.Get().end())
450 it->second->ConnectionFailed();
451 }
452
453 // static
454 void WorkerDevToolsManager::SendResumeToWorker(const WorkerId& id) {
455 if (WorkerProcessHost* process = FindWorkerProcess(id.first))
456 process->Send(new DevToolsAgentMsg_ResumeWorkerContext(id.second));
457 }
458
459 WorkerDevToolsManager::WorkerDevToolsAgentHost::~WorkerDevToolsAgentHost() {
460 DetachedClientHosts::RemovePendingWorkerData(worker_id_);
461 g_agent_map.Get().erase(worker_id_);
462 g_orphan_map.Get().erase(worker_id_);
463 }
464
465 } // namespace content 271 } // namespace content
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698