| OLD | NEW |
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 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 "mojo/edk/system/channel_endpoint.h" | 5 #include "mojo/edk/system/channel_endpoint.h" |
| 6 | 6 |
| 7 #include "base/logging.h" | 7 #include "base/logging.h" |
| 8 #include "mojo/edk/system/channel.h" | 8 #include "mojo/edk/system/channel.h" |
| 9 #include "mojo/edk/system/message_pipe.h" | 9 #include "mojo/edk/system/message_pipe.h" |
| 10 #include "mojo/edk/system/transport_data.h" | 10 #include "mojo/edk/system/transport_data.h" |
| 11 | 11 |
| 12 namespace mojo { | 12 namespace mojo { |
| 13 namespace system { | 13 namespace system { |
| 14 | 14 |
| 15 ChannelEndpoint::ChannelEndpoint(MessagePipe* message_pipe, unsigned port) | 15 ChannelEndpoint::ChannelEndpoint(MessagePipe* message_pipe, |
| 16 unsigned port, |
| 17 MessageInTransitQueue* message_queue) |
| 16 : message_pipe_(message_pipe), port_(port), channel_(nullptr) { | 18 : message_pipe_(message_pipe), port_(port), channel_(nullptr) { |
| 17 DCHECK(message_pipe_.get()); | 19 DCHECK(message_pipe_.get() || message_queue); |
| 18 DCHECK(port_ == 0 || port_ == 1); | 20 DCHECK(port_ == 0 || port_ == 1); |
| 19 } | |
| 20 | 21 |
| 21 void ChannelEndpoint::TakeMessages(MessageInTransitQueue* message_queue) { | 22 if (message_queue) |
| 22 DCHECK(paused_message_queue_.IsEmpty()); | 23 paused_message_queue_.Swap(message_queue); |
| 23 paused_message_queue_.Swap(message_queue); | |
| 24 } | 24 } |
| 25 | 25 |
| 26 bool ChannelEndpoint::EnqueueMessage(scoped_ptr<MessageInTransit> message) { | 26 bool ChannelEndpoint::EnqueueMessage(scoped_ptr<MessageInTransit> message) { |
| 27 DCHECK(message); | 27 DCHECK(message); |
| 28 | 28 |
| 29 base::AutoLock locker(lock_); | 29 base::AutoLock locker(lock_); |
| 30 | 30 |
| 31 if (!channel_ || !remote_id_.is_valid()) { | 31 if (!channel_ || !remote_id_.is_valid()) { |
| 32 // We may reach here if we haven't been attached or run yet. | 32 // We may reach here if we haven't been attached or run yet. |
| 33 // TODO(vtl): We may also reach here if the channel is shut down early for | 33 // TODO(vtl): We may also reach here if the channel is shut down early for |
| 34 // some reason (with live message pipes on it). We can't check |state_| yet, | 34 // some reason (with live message pipes on it). We can't check |state_| yet, |
| 35 // until it's protected under lock, but in this case we should return false | 35 // until it's protected under lock, but in this case we should return false |
| 36 // (and not enqueue any messages). | 36 // (and not enqueue any messages). |
| 37 paused_message_queue_.AddMessage(message.Pass()); | 37 paused_message_queue_.AddMessage(message.Pass()); |
| 38 return true; | 38 return true; |
| 39 } | 39 } |
| 40 | 40 |
| 41 // TODO(vtl): Currently, this only works in the "running" case. | 41 // TODO(vtl): Currently, this only works in the "running" case. |
| 42 DCHECK(remote_id_.is_valid()); | 42 DCHECK(remote_id_.is_valid()); |
| 43 | 43 |
| 44 return WriteMessageNoLock(message.Pass()); | 44 return WriteMessageNoLock(message.Pass()); |
| 45 } | 45 } |
| 46 | 46 |
| 47 void ChannelEndpoint::DetachFromMessagePipe() { | 47 void ChannelEndpoint::DetachFromMessagePipe() { |
| 48 // TODO(vtl): Once |message_pipe_| is under |lock_|, we should null it out | |
| 49 // here. For now, get the channel to do so for us. | |
| 50 | |
| 51 { | 48 { |
| 52 base::AutoLock locker(lock_); | 49 base::AutoLock locker(lock_); |
| 53 DCHECK(message_pipe_.get()); | 50 DCHECK(message_pipe_.get()); |
| 54 message_pipe_ = nullptr; | 51 message_pipe_ = nullptr; |
| 55 | 52 |
| 56 if (!channel_) | 53 if (!channel_) |
| 57 return; | 54 return; |
| 58 DCHECK(local_id_.is_valid()); | 55 DCHECK(local_id_.is_valid()); |
| 59 // TODO(vtl): Once we combine "run" into "attach", |remote_id_| should valid | 56 // TODO(vtl): Once we combine "run" into "attach", |remote_id_| should valid |
| 60 // here as well. | 57 // here as well. |
| (...skipping 16 matching lines...) Expand all Loading... |
| 77 DCHECK(!local_id_.is_valid()); | 74 DCHECK(!local_id_.is_valid()); |
| 78 DCHECK(!remote_id_.is_valid()); | 75 DCHECK(!remote_id_.is_valid()); |
| 79 channel_ = channel; | 76 channel_ = channel; |
| 80 local_id_ = local_id; | 77 local_id_ = local_id; |
| 81 remote_id_ = remote_id; | 78 remote_id_ = remote_id; |
| 82 | 79 |
| 83 while (!paused_message_queue_.IsEmpty()) { | 80 while (!paused_message_queue_.IsEmpty()) { |
| 84 LOG_IF(WARNING, !WriteMessageNoLock(paused_message_queue_.GetMessage())) | 81 LOG_IF(WARNING, !WriteMessageNoLock(paused_message_queue_.GetMessage())) |
| 85 << "Failed to write enqueue message to channel"; | 82 << "Failed to write enqueue message to channel"; |
| 86 } | 83 } |
| 84 |
| 85 if (!message_pipe_.get()) { |
| 86 channel_->DetachEndpoint(this, local_id_, remote_id_); |
| 87 channel_ = nullptr; |
| 88 local_id_ = ChannelEndpointId(); |
| 89 remote_id_ = ChannelEndpointId(); |
| 90 } |
| 87 } | 91 } |
| 88 | 92 |
| 89 bool ChannelEndpoint::OnReadMessage( | 93 bool ChannelEndpoint::OnReadMessage( |
| 90 const MessageInTransit::View& message_view, | 94 const MessageInTransit::View& message_view, |
| 91 embedder::ScopedPlatformHandleVectorPtr platform_handles) { | 95 embedder::ScopedPlatformHandleVectorPtr platform_handles) { |
| 92 scoped_ptr<MessageInTransit> message(new MessageInTransit(message_view)); | 96 scoped_ptr<MessageInTransit> message(new MessageInTransit(message_view)); |
| 93 scoped_refptr<MessagePipe> message_pipe; | 97 scoped_refptr<MessagePipe> message_pipe; |
| 94 unsigned port; | 98 unsigned port; |
| 95 { | 99 { |
| 96 base::AutoLock locker(lock_); | 100 base::AutoLock locker(lock_); |
| (...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 168 DCHECK(remote_id_.is_valid()); | 172 DCHECK(remote_id_.is_valid()); |
| 169 | 173 |
| 170 message->SerializeAndCloseDispatchers(channel_); | 174 message->SerializeAndCloseDispatchers(channel_); |
| 171 message->set_source_id(local_id_); | 175 message->set_source_id(local_id_); |
| 172 message->set_destination_id(remote_id_); | 176 message->set_destination_id(remote_id_); |
| 173 return channel_->WriteMessage(message.Pass()); | 177 return channel_->WriteMessage(message.Pass()); |
| 174 } | 178 } |
| 175 | 179 |
| 176 } // namespace system | 180 } // namespace system |
| 177 } // namespace mojo | 181 } // namespace mojo |
| OLD | NEW |