OLD | NEW |
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
4 | 4 |
5 #include "platform/globals.h" | 5 #include "platform/globals.h" |
6 #if defined(TARGET_OS_LINUX) | 6 #if defined(TARGET_OS_LINUX) |
7 | 7 |
8 #include <errno.h> // NOLINT | 8 #include <errno.h> // NOLINT |
9 #include <stdio.h> // NOLINT | 9 #include <stdio.h> // NOLINT |
10 #include <stdlib.h> // NOLINT | 10 #include <stdlib.h> // NOLINT |
(...skipping 18 matching lines...) Expand all Loading... |
29 struct hostent server; | 29 struct hostent server; |
30 struct sockaddr_in server_address; | 30 struct sockaddr_in server_address; |
31 | 31 |
32 fd = TEMP_FAILURE_RETRY(socket(AF_INET, SOCK_STREAM, 0)); | 32 fd = TEMP_FAILURE_RETRY(socket(AF_INET, SOCK_STREAM, 0)); |
33 if (fd < 0) { | 33 if (fd < 0) { |
34 Log::PrintErr("Error CreateConnect: %s\n", strerror(errno)); | 34 Log::PrintErr("Error CreateConnect: %s\n", strerror(errno)); |
35 return -1; | 35 return -1; |
36 } | 36 } |
37 | 37 |
38 FDUtils::SetCloseOnExec(fd); | 38 FDUtils::SetCloseOnExec(fd); |
39 FDUtils::SetNonBlocking(fd); | 39 Socket::SetNonBlocking(fd); |
40 | 40 |
41 static const size_t kTempBufSize = 1024; | 41 static const size_t kTempBufSize = 1024; |
42 char temp_buf[kTempBufSize]; | 42 char temp_buf[kTempBufSize]; |
43 struct hostent *unused; | 43 struct hostent *unused; |
44 int err; | 44 int err; |
45 if (gethostbyname_r( | 45 if (gethostbyname_r( |
46 host, &server, temp_buf, kTempBufSize, &unused, &err) != 0) { | 46 host, &server, temp_buf, kTempBufSize, &unused, &err) != 0) { |
47 TEMP_FAILURE_RETRY(close(fd)); | 47 TEMP_FAILURE_RETRY(close(fd)); |
48 Log::PrintErr("Error CreateConnect: %s\n", strerror(errno)); | 48 Log::PrintErr("Error CreateConnect: %s\n", strerror(errno)); |
49 return -1; | 49 return -1; |
(...skipping 173 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
223 sizeof(server_address))) < 0) { | 223 sizeof(server_address))) < 0) { |
224 TEMP_FAILURE_RETRY(close(fd)); | 224 TEMP_FAILURE_RETRY(close(fd)); |
225 return -1; | 225 return -1; |
226 } | 226 } |
227 | 227 |
228 if (TEMP_FAILURE_RETRY(listen(fd, backlog > 0 ? backlog : SOMAXCONN)) != 0) { | 228 if (TEMP_FAILURE_RETRY(listen(fd, backlog > 0 ? backlog : SOMAXCONN)) != 0) { |
229 TEMP_FAILURE_RETRY(close(fd)); | 229 TEMP_FAILURE_RETRY(close(fd)); |
230 return -1; | 230 return -1; |
231 } | 231 } |
232 | 232 |
233 FDUtils::SetNonBlocking(fd); | 233 Socket::SetNonBlocking(fd); |
234 return fd; | 234 return fd; |
235 } | 235 } |
236 | 236 |
237 | 237 |
238 static bool IsTemporaryAcceptError(int error) { | 238 static bool IsTemporaryAcceptError(int error) { |
239 // On Linux a number of protocol errors should be treated as EAGAIN. | 239 // On Linux a number of protocol errors should be treated as EAGAIN. |
240 // These are the ones for TCP/IP. | 240 // These are the ones for TCP/IP. |
241 return (error == EAGAIN) || (error == ENETDOWN) || (error == EPROTO) || | 241 return (error == EAGAIN) || (error == ENETDOWN) || (error == EPROTO) || |
242 (error == ENOPROTOOPT) || (error == EHOSTDOWN) || (error == ENONET) || | 242 (error == ENOPROTOOPT) || (error == EHOSTDOWN) || (error == ENONET) || |
243 (error == EHOSTUNREACH) || (error == EOPNOTSUPP) || | 243 (error == EHOSTUNREACH) || (error == EOPNOTSUPP) || |
244 (error == ENETUNREACH); | 244 (error == ENETUNREACH); |
245 } | 245 } |
246 | 246 |
247 | 247 |
248 intptr_t ServerSocket::Accept(intptr_t fd) { | 248 intptr_t ServerSocket::Accept(intptr_t fd) { |
249 intptr_t socket; | 249 intptr_t socket; |
250 struct sockaddr clientaddr; | 250 struct sockaddr clientaddr; |
251 socklen_t addrlen = sizeof(clientaddr); | 251 socklen_t addrlen = sizeof(clientaddr); |
252 socket = TEMP_FAILURE_RETRY(accept(fd, &clientaddr, &addrlen)); | 252 socket = TEMP_FAILURE_RETRY(accept(fd, &clientaddr, &addrlen)); |
253 if (socket == -1) { | 253 if (socket == -1) { |
254 if (IsTemporaryAcceptError(errno)) { | 254 if (IsTemporaryAcceptError(errno)) { |
255 // We need to signal to the caller that this is actually not an | 255 // We need to signal to the caller that this is actually not an |
256 // error. We got woken up from the poll on the listening socket, | 256 // error. We got woken up from the poll on the listening socket, |
257 // but there is no connection ready to be accepted. | 257 // but there is no connection ready to be accepted. |
258 ASSERT(kTemporaryFailure != -1); | 258 ASSERT(kTemporaryFailure != -1); |
259 socket = kTemporaryFailure; | 259 socket = kTemporaryFailure; |
260 } | 260 } |
261 } else { | 261 } else { |
262 FDUtils::SetNonBlocking(socket); | 262 Socket::SetNonBlocking(socket); |
263 } | 263 } |
264 return socket; | 264 return socket; |
265 } | 265 } |
266 | 266 |
267 | 267 |
268 void Socket::Close(intptr_t fd) { | 268 void Socket::Close(intptr_t fd) { |
269 ASSERT(fd >= 0); | 269 ASSERT(fd >= 0); |
270 int err = TEMP_FAILURE_RETRY(close(fd)); | 270 int err = TEMP_FAILURE_RETRY(close(fd)); |
271 if (err != 0) { | 271 if (err != 0) { |
272 const int kBufferSize = 1024; | 272 const int kBufferSize = 1024; |
273 char error_message[kBufferSize]; | 273 char error_message[kBufferSize]; |
274 strerror_r(errno, error_message, kBufferSize); | 274 strerror_r(errno, error_message, kBufferSize); |
275 Log::PrintErr("%s\n", error_message); | 275 Log::PrintErr("%s\n", error_message); |
276 } | 276 } |
277 } | 277 } |
278 | 278 |
| 279 |
| 280 bool Socket::SetNonBlocking(intptr_t fd) { |
| 281 return FDUtils::SetNonBlocking(fd); |
| 282 } |
| 283 |
| 284 |
| 285 bool Socket::SetBlocking(intptr_t fd) { |
| 286 return FDUtils::SetBlocking(fd); |
| 287 } |
| 288 |
279 #endif // defined(TARGET_OS_LINUX) | 289 #endif // defined(TARGET_OS_LINUX) |
OLD | NEW |