OLD | NEW |
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 "ipc/ipc_channel_posix.h" | 5 #include "ipc/ipc_channel_posix.h" |
6 | 6 |
7 #include <errno.h> | 7 #include <errno.h> |
8 #include <fcntl.h> | 8 #include <fcntl.h> |
9 #include <stddef.h> | 9 #include <stddef.h> |
10 #include <sys/socket.h> | 10 #include <sys/socket.h> |
(...skipping 117 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
128 << "(fd " << i->second << ") still exists"; | 128 << "(fd " << i->second << ") still exists"; |
129 map_[channel_id] = fd; | 129 map_[channel_id] = fd; |
130 } | 130 } |
131 | 131 |
132 private: | 132 private: |
133 base::Lock lock_; | 133 base::Lock lock_; |
134 typedef std::map<std::string, int> ChannelToFDMap; | 134 typedef std::map<std::string, int> ChannelToFDMap; |
135 ChannelToFDMap map_; | 135 ChannelToFDMap map_; |
136 | 136 |
137 friend struct DefaultSingletonTraits<PipeMap>; | 137 friend struct DefaultSingletonTraits<PipeMap>; |
| 138 #if defined(OS_ANDROID) |
| 139 friend void ::IPC::Channel::NotifyProcessForkedForTesting(); |
| 140 #endif |
138 }; | 141 }; |
139 | 142 |
140 //------------------------------------------------------------------------------ | 143 //------------------------------------------------------------------------------ |
141 | 144 |
142 bool SocketWriteErrorIsRecoverable() { | 145 bool SocketWriteErrorIsRecoverable() { |
143 #if defined(OS_MACOSX) | 146 #if defined(OS_MACOSX) |
144 // On OS X if sendmsg() is trying to send fds between processes and there | 147 // On OS X if sendmsg() is trying to send fds between processes and there |
145 // isn't enough room in the output buffer to send the fd structure over | 148 // isn't enough room in the output buffer to send the fd structure over |
146 // atomically then EMSGSIZE is returned. | 149 // atomically then EMSGSIZE is returned. |
147 // | 150 // |
148 // EMSGSIZE presents a problem since the system APIs can only call us when | 151 // EMSGSIZE presents a problem since the system APIs can only call us when |
149 // there's room in the socket buffer and not when there is "enough" room. | 152 // there's room in the socket buffer and not when there is "enough" room. |
150 // | 153 // |
151 // The current behavior is to return to the event loop when EMSGSIZE is | 154 // The current behavior is to return to the event loop when EMSGSIZE is |
152 // received and hopefull service another FD. This is however still | 155 // received and hopefull service another FD. This is however still |
153 // technically a busy wait since the event loop will call us right back until | 156 // technically a busy wait since the event loop will call us right back until |
154 // the receiver has read enough data to allow passing the FD over atomically. | 157 // the receiver has read enough data to allow passing the FD over atomically. |
155 return errno == EAGAIN || errno == EMSGSIZE; | 158 return errno == EAGAIN || errno == EMSGSIZE; |
156 #else | 159 #else |
157 return errno == EAGAIN; | 160 return errno == EAGAIN; |
158 #endif // OS_MACOSX | 161 #endif // OS_MACOSX |
159 } | 162 } |
160 | 163 |
161 } // namespace | 164 } // namespace |
| 165 |
| 166 #if defined(OS_ANDROID) |
| 167 // When we fork for simple tests on Android, we can't 'exec', so we need to |
| 168 // reset these entries manually to get the expected testing behavior. |
| 169 void Channel::NotifyProcessForkedForTesting() { |
| 170 PipeMap::GetInstance()->map_.clear(); |
| 171 } |
| 172 #endif |
| 173 |
162 //------------------------------------------------------------------------------ | 174 //------------------------------------------------------------------------------ |
163 | 175 |
164 #if defined(OS_LINUX) | 176 #if defined(OS_LINUX) |
165 int Channel::ChannelImpl::global_pid_ = 0; | 177 int Channel::ChannelImpl::global_pid_ = 0; |
166 #endif // OS_LINUX | 178 #endif // OS_LINUX |
167 | 179 |
168 Channel::ChannelImpl::ChannelImpl(const IPC::ChannelHandle& channel_handle, | 180 Channel::ChannelImpl::ChannelImpl(const IPC::ChannelHandle& channel_handle, |
169 Mode mode, Listener* listener) | 181 Mode mode, Listener* listener) |
170 : ChannelReader(listener), | 182 : ChannelReader(listener), |
171 mode_(mode), | 183 mode_(mode), |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
220 } | 232 } |
221 | 233 |
222 bool Channel::ChannelImpl::CreatePipe( | 234 bool Channel::ChannelImpl::CreatePipe( |
223 const IPC::ChannelHandle& channel_handle) { | 235 const IPC::ChannelHandle& channel_handle) { |
224 DCHECK(server_listen_pipe_ == -1 && pipe_ == -1); | 236 DCHECK(server_listen_pipe_ == -1 && pipe_ == -1); |
225 | 237 |
226 // Four possible cases: | 238 // Four possible cases: |
227 // 1) It's a channel wrapping a pipe that is given to us. | 239 // 1) It's a channel wrapping a pipe that is given to us. |
228 // 2) It's for a named channel, so we create it. | 240 // 2) It's for a named channel, so we create it. |
229 // 3) It's for a client that we implement ourself. This is used | 241 // 3) It's for a client that we implement ourself. This is used |
230 // in unittesting. | 242 // in single-process unittesting. |
231 // 4) It's the initial IPC channel: | 243 // 4) It's the initial IPC channel: |
232 // 4a) Client side: Pull the pipe out of the GlobalDescriptors set. | 244 // 4a) Client side: Pull the pipe out of the GlobalDescriptors set. |
233 // 4b) Server side: create the pipe. | 245 // 4b) Server side: create the pipe. |
234 | 246 |
235 int local_pipe = -1; | 247 int local_pipe = -1; |
236 if (channel_handle.socket.fd != -1) { | 248 if (channel_handle.socket.fd != -1) { |
237 // Case 1 from comment above. | 249 // Case 1 from comment above. |
238 local_pipe = channel_handle.socket.fd; | 250 local_pipe = channel_handle.socket.fd; |
239 #if defined(IPC_USES_READWRITE) | 251 #if defined(IPC_USES_READWRITE) |
240 // Test the socket passed into us to make sure it is nonblocking. | 252 // Test the socket passed into us to make sure it is nonblocking. |
(...skipping 864 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1105 | 1117 |
1106 | 1118 |
1107 #if defined(OS_LINUX) | 1119 #if defined(OS_LINUX) |
1108 // static | 1120 // static |
1109 void Channel::SetGlobalPid(int pid) { | 1121 void Channel::SetGlobalPid(int pid) { |
1110 ChannelImpl::SetGlobalPid(pid); | 1122 ChannelImpl::SetGlobalPid(pid); |
1111 } | 1123 } |
1112 #endif // OS_LINUX | 1124 #endif // OS_LINUX |
1113 | 1125 |
1114 } // namespace IPC | 1126 } // namespace IPC |
OLD | NEW |