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

Side by Side Diff: chrome/browser/extensions/api/messaging/message_service.cc

Issue 145463002: Extensions: Send the tab id to platform apps. (Closed) Base URL: svn://chrome-svn/chrome/trunk/src/
Patch Set: fix null pointer deref Created 6 years, 10 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 | Annotate | Revision Log
OLDNEW
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 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 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 "chrome/browser/extensions/api/messaging/message_service.h" 5 #include "chrome/browser/extensions/api/messaging/message_service.h"
6 6
7 #include "base/atomic_sequence_num.h" 7 #include "base/atomic_sequence_num.h"
8 #include "base/bind.h" 8 #include "base/bind.h"
9 #include "base/callback.h" 9 #include "base/callback.h"
10 #include "base/json/json_writer.h" 10 #include "base/json/json_writer.h"
11 #include "base/lazy_instance.h" 11 #include "base/lazy_instance.h"
12 #include "base/metrics/histogram.h" 12 #include "base/metrics/histogram.h"
13 #include "base/stl_util.h" 13 #include "base/stl_util.h"
14 #include "base/values.h" 14 #include "base/values.h"
15 #include "chrome/browser/chrome_notification_types.h" 15 #include "chrome/browser/chrome_notification_types.h"
16 #include "chrome/browser/extensions/api/messaging/extension_message_port.h" 16 #include "chrome/browser/extensions/api/messaging/extension_message_port.h"
17 #include "chrome/browser/extensions/api/messaging/incognito_connectability.h" 17 #include "chrome/browser/extensions/api/messaging/incognito_connectability.h"
18 #include "chrome/browser/extensions/api/messaging/native_message_port.h" 18 #include "chrome/browser/extensions/api/messaging/native_message_port.h"
19 #include "chrome/browser/extensions/api/tabs/tabs_constants.h"
19 #include "chrome/browser/extensions/extension_host.h" 20 #include "chrome/browser/extensions/extension_host.h"
20 #include "chrome/browser/extensions/extension_service.h" 21 #include "chrome/browser/extensions/extension_service.h"
21 #include "chrome/browser/extensions/extension_tab_util.h" 22 #include "chrome/browser/extensions/extension_tab_util.h"
22 #include "chrome/browser/extensions/extension_util.h" 23 #include "chrome/browser/extensions/extension_util.h"
23 #include "chrome/browser/profiles/profile.h" 24 #include "chrome/browser/profiles/profile.h"
24 #include "chrome/browser/tab_contents/tab_util.h" 25 #include "chrome/browser/tab_contents/tab_util.h"
25 #include "chrome/common/extensions/extension_messages.h" 26 #include "chrome/common/extensions/extension_messages.h"
26 #include "chrome/common/extensions/manifest_handlers/externally_connectable.h" 27 #include "chrome/common/extensions/manifest_handlers/externally_connectable.h"
27 #include "content/public/browser/notification_service.h" 28 #include "content/public/browser/notification_service.h"
28 #include "content/public/browser/render_process_host.h" 29 #include "content/public/browser/render_process_host.h"
(...skipping 83 matching lines...) Expand 10 before | Expand all | Expand 10 after
112 }; 113 };
113 114
114 namespace { 115 namespace {
115 116
116 static base::StaticAtomicSequenceNumber g_next_channel_id; 117 static base::StaticAtomicSequenceNumber g_next_channel_id;
117 static base::StaticAtomicSequenceNumber g_channel_id_overflow_count; 118 static base::StaticAtomicSequenceNumber g_channel_id_overflow_count;
118 119
119 static content::RenderProcessHost* GetExtensionProcess( 120 static content::RenderProcessHost* GetExtensionProcess(
120 Profile* profile, const std::string& extension_id) { 121 Profile* profile, const std::string& extension_id) {
121 SiteInstance* site_instance = 122 SiteInstance* site_instance =
122 ExtensionSystem::Get(profile)->process_manager()-> 123 ExtensionSystem::Get(profile)->process_manager()->GetSiteInstanceForURL(
123 GetSiteInstanceForURL( 124 Extension::GetBaseURLFromExtensionId(extension_id));
124 Extension::GetBaseURLFromExtensionId(extension_id)); 125 return site_instance->HasProcess() ? site_instance->GetProcess() : NULL;
125
126 if (!site_instance->HasProcess())
127 return NULL;
128
129 return site_instance->GetProcess();
130 } 126 }
131 127
132 } // namespace 128 } // namespace
133 129
134 content::RenderProcessHost* 130 content::RenderProcessHost*
135 MessageService::MessagePort::GetRenderProcessHost() { 131 MessageService::MessagePort::GetRenderProcessHost() {
136 return NULL; 132 return NULL;
137 } 133 }
138 134
139 // static 135 // static
140 void MessageService::AllocatePortIdPair(int* port1, int* port2) { 136 void MessageService::AllocatePortIdPair(int* port1, int* port2) {
141 unsigned channel_id = 137 unsigned channel_id =
142 static_cast<unsigned>(g_next_channel_id.GetNext()) % (kint32max/2); 138 static_cast<unsigned>(g_next_channel_id.GetNext()) % (kint32max/2);
143 139
144 if (channel_id == 0) { 140 if (channel_id == 0) {
145 int overflow_count = g_channel_id_overflow_count.GetNext(); 141 int overflow_count = g_channel_id_overflow_count.GetNext();
146 if (overflow_count > 0) 142 if (overflow_count > 0)
147 UMA_HISTOGRAM_BOOLEAN("Extensions.AllocatePortIdPairOverflow", true); 143 UMA_HISTOGRAM_BOOLEAN("Extensions.AllocatePortIdPairOverflow", true);
148 } 144 }
149 145
150 unsigned port1_id = channel_id * 2; 146 unsigned port1_id = channel_id * 2;
151 unsigned port2_id = channel_id * 2 + 1; 147 unsigned port2_id = channel_id * 2 + 1;
152 148
153 // Sanity checks to make sure our channel<->port converters are correct. 149 // Sanity checks to make sure our channel<->port converters are correct.
154 DCHECK(IS_OPENER_PORT_ID(port1_id)); 150 DCHECK(IS_OPENER_PORT_ID(port1_id));
155 DCHECK(GET_OPPOSITE_PORT_ID(port1_id) == port2_id); 151 DCHECK_EQ(GET_OPPOSITE_PORT_ID(port1_id), port2_id);
156 DCHECK(GET_OPPOSITE_PORT_ID(port2_id) == port1_id); 152 DCHECK_EQ(GET_OPPOSITE_PORT_ID(port2_id), port1_id);
157 DCHECK(GET_CHANNEL_ID(port1_id) == GET_CHANNEL_ID(port2_id)); 153 DCHECK_EQ(GET_CHANNEL_ID(port1_id), GET_CHANNEL_ID(port2_id));
158 DCHECK(GET_CHANNEL_ID(port1_id) == channel_id); 154 DCHECK_EQ(GET_CHANNEL_ID(port1_id), channel_id);
159 DCHECK(GET_CHANNEL_OPENER_ID(channel_id) == port1_id); 155 DCHECK_EQ(GET_CHANNEL_OPENER_ID(channel_id), port1_id);
160 DCHECK(GET_CHANNEL_RECEIVERS_ID(channel_id) == port2_id); 156 DCHECK_EQ(GET_CHANNEL_RECEIVERS_ID(channel_id), port2_id);
161 157
162 *port1 = port1_id; 158 *port1 = port1_id;
163 *port2 = port2_id; 159 *port2 = port2_id;
164 } 160 }
165 161
166 MessageService::MessageService(Profile* profile) 162 MessageService::MessageService(Profile* profile)
167 : lazy_background_task_queue_( 163 : lazy_background_task_queue_(
168 ExtensionSystem::Get(profile)->lazy_background_task_queue()), 164 ExtensionSystem::Get(profile)->lazy_background_task_queue()),
169 weak_factory_(this) { 165 weak_factory_(this) {
170 registrar_.Add(this, content::NOTIFICATION_RENDERER_PROCESS_TERMINATED, 166 registrar_.Add(this, content::NOTIFICATION_RENDERER_PROCESS_TERMINATED,
(...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after
293 // which depends on whether the extension uses spanning or split mode. 289 // which depends on whether the extension uses spanning or split mode.
294 MessagePort* receiver = new ExtensionMessagePort( 290 MessagePort* receiver = new ExtensionMessagePort(
295 GetExtensionProcess(profile, target_extension_id), MSG_ROUTING_CONTROL, 291 GetExtensionProcess(profile, target_extension_id), MSG_ROUTING_CONTROL,
296 target_extension_id); 292 target_extension_id);
297 293
298 // Include info about the opener's tab (if it was a tab). 294 // Include info about the opener's tab (if it was a tab).
299 scoped_ptr<base::DictionaryValue> source_tab; 295 scoped_ptr<base::DictionaryValue> source_tab;
300 GURL source_url_for_tab; 296 GURL source_url_for_tab;
301 297
302 if (source_contents && ExtensionTabUtil::GetTabId(source_contents) >= 0) { 298 if (source_contents && ExtensionTabUtil::GetTabId(source_contents) >= 0) {
303 // Platform apps can be sent messages, but don't have a Tab concept. 299 // Only the tab id is useful to platform apps for internal use. The
304 if (!target_extension->is_platform_app()) 300 // unnecessary bits will be stripped out in
305 source_tab.reset(ExtensionTabUtil::CreateTabValue(source_contents)); 301 // MessagingBindings::DispatchOnConnect().
302 source_tab.reset(ExtensionTabUtil::CreateTabValue(source_contents));
306 source_url_for_tab = source_url; 303 source_url_for_tab = source_url;
307 } 304 }
308 305
309 OpenChannelParams* params = new OpenChannelParams(source, 306 OpenChannelParams* params = new OpenChannelParams(source,
310 source_tab.Pass(), 307 source_tab.Pass(),
311 receiver, 308 receiver,
312 receiver_port_id, 309 receiver_port_id,
313 source_extension_id, 310 source_extension_id,
314 target_extension_id, 311 target_extension_id,
315 source_url_for_tab, 312 source_url_for_tab,
316 channel_name, 313 channel_name,
317 include_tls_channel_id); 314 include_tls_channel_id);
318 315
319 // If the target requests the TLS channel id, begin the lookup for it. 316 // If the target requests the TLS channel id, begin the lookup for it.
320 // The target might also be a lazy background page, checked next, but the 317 // The target might also be a lazy background page, checked next, but the
321 // loading of lazy background pages continues asynchronously, so enqueue 318 // loading of lazy background pages continues asynchronously, so enqueue
322 // messages awaiting TLS channel ID first. 319 // messages awaiting TLS channel ID first.
323 if (include_tls_channel_id) { 320 if (include_tls_channel_id) {
324 pending_tls_channel_id_channels_[GET_CHANNEL_ID(params->receiver_port_id)] 321 pending_tls_channel_id_channels_[GET_CHANNEL_ID(params->receiver_port_id)]
325 = PendingMessagesQueue(); 322 = PendingMessagesQueue();
326 property_provider_.GetDomainBoundCert(profile, params->source_url, 323 property_provider_.GetDomainBoundCert(
324 profile,
325 source_url,
327 base::Bind(&MessageService::GotDomainBoundCert, 326 base::Bind(&MessageService::GotDomainBoundCert,
328 weak_factory_.GetWeakPtr(), 327 weak_factory_.GetWeakPtr(),
329 base::Passed(make_scoped_ptr(params)))); 328 base::Passed(make_scoped_ptr(params))));
330 return; 329 return;
331 } 330 }
332 331
333 // The target might be a lazy background page. In that case, we have to check 332 // The target might be a lazy background page. In that case, we have to check
334 // if it is loaded and ready, and if not, queue up the task and load the 333 // if it is loaded and ready, and if not, queue up the task and load the
335 // page. 334 // page.
336 if (MaybeAddPendingLazyBackgroundPageOpenChannelTask(profile, 335 if (MaybeAddPendingLazyBackgroundPageOpenChannelTask(profile,
(...skipping 207 matching lines...) Expand 10 before | Expand all | Expand 10 after
544 } 543 }
545 544
546 // Balance the IncrementLazyKeepaliveCount() in OpenChannelImpl. 545 // Balance the IncrementLazyKeepaliveCount() in OpenChannelImpl.
547 channel->opener->DecrementLazyKeepaliveCount(); 546 channel->opener->DecrementLazyKeepaliveCount();
548 channel->receiver->DecrementLazyKeepaliveCount(); 547 channel->receiver->DecrementLazyKeepaliveCount();
549 548
550 delete channel_iter->second; 549 delete channel_iter->second;
551 channels_.erase(channel_iter); 550 channels_.erase(channel_iter);
552 } 551 }
553 552
554 void MessageService::PostMessage( 553 void MessageService::PostMessage(int source_port_id, const Message& message) {
555 int source_port_id, const Message& message) {
556 int channel_id = GET_CHANNEL_ID(source_port_id); 554 int channel_id = GET_CHANNEL_ID(source_port_id);
557 MessageChannelMap::iterator iter = channels_.find(channel_id); 555 MessageChannelMap::iterator iter = channels_.find(channel_id);
558 if (iter == channels_.end()) { 556 if (iter == channels_.end()) {
559 // If this channel is pending, queue up the PostMessage to run once 557 // If this channel is pending, queue up the PostMessage to run once
560 // the channel opens. 558 // the channel opens.
561 EnqueuePendingMessage(source_port_id, channel_id, message); 559 EnqueuePendingMessage(source_port_id, channel_id, message);
562 return; 560 return;
563 } 561 }
564 562
565 DispatchMessage(source_port_id, iter->second, message); 563 DispatchMessage(source_port_id, iter->second, message);
(...skipping 190 matching lines...) Expand 10 before | Expand all | Expand 10 after
756 } 754 }
757 755
758 void MessageService::DispatchOnDisconnect(content::RenderProcessHost* source, 756 void MessageService::DispatchOnDisconnect(content::RenderProcessHost* source,
759 int port_id, 757 int port_id,
760 const std::string& error_message) { 758 const std::string& error_message) {
761 ExtensionMessagePort port(source, MSG_ROUTING_CONTROL, ""); 759 ExtensionMessagePort port(source, MSG_ROUTING_CONTROL, "");
762 port.DispatchOnDisconnect(GET_OPPOSITE_PORT_ID(port_id), error_message); 760 port.DispatchOnDisconnect(GET_OPPOSITE_PORT_ID(port_id), error_message);
763 } 761 }
764 762
765 } // namespace extensions 763 } // namespace extensions
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698