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

Side by Side Diff: ipc/ipc_channel_proxy.cc

Issue 183553004: Eliminate a potential race in IPC::ChannelProxy (Closed) Base URL: http://git.chromium.org/chromium/src.git@master
Patch Set: 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
« no previous file with comments | « ipc/ipc_channel_proxy.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
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 "base/bind.h" 5 #include "base/bind.h"
6 #include "base/compiler_specific.h" 6 #include "base/compiler_specific.h"
7 #include "base/debug/trace_event.h" 7 #include "base/debug/trace_event.h"
8 #include "base/location.h" 8 #include "base/location.h"
9 #include "base/memory/ref_counted.h" 9 #include "base/memory/ref_counted.h"
10 #include "base/memory/scoped_ptr.h" 10 #include "base/memory/scoped_ptr.h"
(...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after
136 136
137 //------------------------------------------------------------------------------ 137 //------------------------------------------------------------------------------
138 138
139 ChannelProxy::Context::Context(Listener* listener, 139 ChannelProxy::Context::Context(Listener* listener,
140 base::SingleThreadTaskRunner* ipc_task_runner) 140 base::SingleThreadTaskRunner* ipc_task_runner)
141 : listener_task_runner_(base::ThreadTaskRunnerHandle::Get()), 141 : listener_task_runner_(base::ThreadTaskRunnerHandle::Get()),
142 listener_(listener), 142 listener_(listener),
143 ipc_task_runner_(ipc_task_runner), 143 ipc_task_runner_(ipc_task_runner),
144 channel_connected_called_(false), 144 channel_connected_called_(false),
145 message_filter_router_(new MessageFilterRouter()), 145 message_filter_router_(new MessageFilterRouter()),
146 peer_pid_(base::kNullProcessId) { 146 peer_pid_(base::kNullProcessId),
147 channel_is_connected_(false) {
147 DCHECK(ipc_task_runner_.get()); 148 DCHECK(ipc_task_runner_.get());
148 } 149 }
149 150
150 ChannelProxy::Context::~Context() { 151 ChannelProxy::Context::~Context() {
151 } 152 }
152 153
153 void ChannelProxy::Context::ClearIPCTaskRunner() { 154 void ChannelProxy::Context::ClearIPCTaskRunner() {
154 ipc_task_runner_ = NULL; 155 ipc_task_runner_ = NULL;
155 } 156 }
156 157
(...skipping 36 matching lines...) Expand 10 before | Expand all | Expand 10 after
193 FROM_HERE, base::Bind(&Context::OnDispatchMessage, this, message)); 194 FROM_HERE, base::Bind(&Context::OnDispatchMessage, this, message));
194 return true; 195 return true;
195 } 196 }
196 197
197 // Called on the IPC::Channel thread 198 // Called on the IPC::Channel thread
198 void ChannelProxy::Context::OnChannelConnected(int32 peer_pid) { 199 void ChannelProxy::Context::OnChannelConnected(int32 peer_pid) {
199 // Add any pending filters. This avoids a race condition where someone 200 // Add any pending filters. This avoids a race condition where someone
200 // creates a ChannelProxy, calls AddFilter, and then right after starts the 201 // creates a ChannelProxy, calls AddFilter, and then right after starts the
201 // peer process. The IO thread could receive a message before the task to add 202 // peer process. The IO thread could receive a message before the task to add
202 // the filter is run on the IO thread. 203 // the filter is run on the IO thread.
204 channel_is_connected_ = true;
203 OnAddFilter(); 205 OnAddFilter();
204 206
205 // We cache off the peer_pid so it can be safely accessed from both threads. 207 // We cache off the peer_pid so it can be safely accessed from both threads.
206 peer_pid_ = channel_->peer_pid(); 208 peer_pid_ = channel_->peer_pid();
jam 2014/02/28 00:41:42 nit: if you move these two lines to the two of the
207 for (size_t i = 0; i < filters_.size(); ++i) 209 for (size_t i = 0; i < filters_.size(); ++i)
208 filters_[i]->OnChannelConnected(peer_pid); 210 filters_[i]->OnChannelConnected(peer_pid);
209 211
210 // See above comment about using listener_task_runner_ here. 212 // See above comment about using listener_task_runner_ here.
211 listener_task_runner_->PostTask( 213 listener_task_runner_->PostTask(
212 FROM_HERE, base::Bind(&Context::OnDispatchConnected, this)); 214 FROM_HERE, base::Bind(&Context::OnDispatchConnected, this));
213 } 215 }
214 216
215 // Called on the IPC::Channel thread 217 // Called on the IPC::Channel thread
216 void ChannelProxy::Context::OnChannelError() { 218 void ChannelProxy::Context::OnChannelError() {
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
271 if (!channel_.get()) { 273 if (!channel_.get()) {
272 OnChannelClosed(); 274 OnChannelClosed();
273 return; 275 return;
274 } 276 }
275 if (!channel_->Send(message.release())) 277 if (!channel_->Send(message.release()))
276 OnChannelError(); 278 OnChannelError();
277 } 279 }
278 280
279 // Called on the IPC::Channel thread 281 // Called on the IPC::Channel thread
280 void ChannelProxy::Context::OnAddFilter() { 282 void ChannelProxy::Context::OnAddFilter() {
283 if (!channel_is_connected_)
284 return;
285
281 std::vector<scoped_refptr<MessageFilter> > new_filters; 286 std::vector<scoped_refptr<MessageFilter> > new_filters;
282 { 287 {
283 base::AutoLock auto_lock(pending_filters_lock_); 288 base::AutoLock auto_lock(pending_filters_lock_);
284 new_filters.swap(pending_filters_); 289 new_filters.swap(pending_filters_);
285 } 290 }
286 291
287 for (size_t i = 0; i < new_filters.size(); ++i) { 292 for (size_t i = 0; i < new_filters.size(); ++i) {
288 filters_.push_back(new_filters[i]); 293 filters_.push_back(new_filters[i]);
289 294
290 message_filter_router_->AddFilter(new_filters[i].get()); 295 message_filter_router_->AddFilter(new_filters[i].get());
(...skipping 221 matching lines...) Expand 10 before | Expand all | Expand 10 after
512 Channel* channel = context_.get()->channel_.get(); 517 Channel* channel = context_.get()->channel_.get();
513 // Channel must have been created first. 518 // Channel must have been created first.
514 DCHECK(channel) << context_.get()->channel_id_; 519 DCHECK(channel) << context_.get()->channel_id_;
515 return channel->GetPeerEuid(peer_euid); 520 return channel->GetPeerEuid(peer_euid);
516 } 521 }
517 #endif 522 #endif
518 523
519 //----------------------------------------------------------------------------- 524 //-----------------------------------------------------------------------------
520 525
521 } // namespace IPC 526 } // namespace IPC
OLDNEW
« no previous file with comments | « ipc/ipc_channel_proxy.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698