OLD | NEW |
1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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 <errno.h> | 5 #include <errno.h> |
6 #include <stdio.h> | 6 #include <stdio.h> |
7 #include <stdlib.h> | 7 #include <stdlib.h> |
8 #include <string.h> | 8 #include <string.h> |
9 #include <unistd.h> | 9 #include <unistd.h> |
10 | 10 |
11 #include "bin/fdutils.h" | 11 #include "bin/fdutils.h" |
12 #include "bin/socket.h" | 12 #include "bin/socket.h" |
13 | 13 |
14 | 14 |
15 bool Socket::Initialize() { | 15 bool Socket::Initialize() { |
16 // Nothing to do on Linux. | 16 // Nothing to do on Android. |
17 return true; | 17 return true; |
18 } | 18 } |
19 | 19 |
20 | 20 |
21 intptr_t Socket::CreateConnect(const char* host, const intptr_t port) { | 21 intptr_t Socket::CreateConnect(const char* host, const intptr_t port) { |
22 intptr_t fd; | 22 intptr_t fd; |
23 struct hostent* server; | 23 struct hostent* server; |
24 struct sockaddr_in server_address; | 24 struct sockaddr_in server_address; |
25 | 25 |
26 fd = TEMP_FAILURE_RETRY(socket(AF_INET, SOCK_STREAM, 0)); | 26 fd = TEMP_FAILURE_RETRY(socket(AF_INET, SOCK_STREAM, 0)); |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
116 INET_ADDRSTRLEN) == NULL) { | 116 INET_ADDRSTRLEN) == NULL) { |
117 fprintf(stderr, "Error inet_ntop: %s\n", strerror(errno)); | 117 fprintf(stderr, "Error inet_ntop: %s\n", strerror(errno)); |
118 return false; | 118 return false; |
119 } | 119 } |
120 *port = ntohs(socket_address.sin_port); | 120 *port = ntohs(socket_address.sin_port); |
121 return true; | 121 return true; |
122 } | 122 } |
123 | 123 |
124 | 124 |
125 void Socket::GetError(intptr_t fd, OSError* os_error) { | 125 void Socket::GetError(intptr_t fd, OSError* os_error) { |
126 int len = sizeof(errno); | 126 int errorNumber; |
| 127 socklen_t len = sizeof(errorNumber); |
127 getsockopt(fd, | 128 getsockopt(fd, |
128 SOL_SOCKET, | 129 SOL_SOCKET, |
129 SO_ERROR, | 130 SO_ERROR, |
130 &errno, | 131 reinterpret_cast<void*>(&errorNumber), |
131 reinterpret_cast<socklen_t*>(&len)); | 132 &len); |
132 os_error->SetCodeAndMessage(OSError::kSystem, errno); | 133 os_error->SetCodeAndMessage(OSError::kSystem, errorNumber); |
133 } | 134 } |
134 | 135 |
135 | 136 |
136 intptr_t Socket::GetStdioHandle(int num) { | 137 intptr_t Socket::GetStdioHandle(int num) { |
137 return static_cast<intptr_t>(num); | 138 return static_cast<intptr_t>(num); |
138 } | 139 } |
139 | 140 |
140 | 141 |
141 const char* Socket::LookupIPv4Address(char* host, OSError** os_error) { | 142 const char* Socket::LookupIPv4Address(char* host, OSError** os_error) { |
142 // Perform a name lookup for an IPv4 address. | 143 // Perform a name lookup for an IPv4 address. |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
204 fprintf(stderr, "Error Listen: %s\n", strerror(errno)); | 205 fprintf(stderr, "Error Listen: %s\n", strerror(errno)); |
205 return -1; | 206 return -1; |
206 } | 207 } |
207 | 208 |
208 FDUtils::SetNonBlocking(fd); | 209 FDUtils::SetNonBlocking(fd); |
209 return fd; | 210 return fd; |
210 } | 211 } |
211 | 212 |
212 | 213 |
213 static bool IsTemporaryAcceptError(int error) { | 214 static bool IsTemporaryAcceptError(int error) { |
214 // On Linux a number of protocol errors should be treated as EAGAIN. | 215 // On Android a number of protocol errors should be treated as EAGAIN. |
215 // These are the ones for TCP/IP. | 216 // These are the ones for TCP/IP. |
216 return (error == EAGAIN) || (error == ENETDOWN) || (error == EPROTO) || | 217 return (error == EAGAIN) || (error == ENETDOWN) || (error == EPROTO) || |
217 (error == ENOPROTOOPT) || (error == EHOSTDOWN) || (error == ENONET) || | 218 (error == ENOPROTOOPT) || (error == EHOSTDOWN) || (error == ENONET) || |
218 (error == EHOSTUNREACH) || (error == EOPNOTSUPP) || | 219 (error == EHOSTUNREACH) || (error == EOPNOTSUPP) || |
219 (error == ENETUNREACH); | 220 (error == ENETUNREACH); |
220 } | 221 } |
221 | 222 |
222 | 223 |
223 intptr_t ServerSocket::Accept(intptr_t fd) { | 224 intptr_t ServerSocket::Accept(intptr_t fd) { |
224 intptr_t socket; | 225 intptr_t socket; |
225 struct sockaddr clientaddr; | 226 struct sockaddr clientaddr; |
226 socklen_t addrlen = sizeof(clientaddr); | 227 socklen_t addrlen = sizeof(clientaddr); |
227 socket = TEMP_FAILURE_RETRY(accept(fd, &clientaddr, &addrlen)); | 228 socket = TEMP_FAILURE_RETRY(accept(fd, &clientaddr, &addrlen)); |
228 if (socket == -1) { | 229 if (socket == -1) { |
229 if (IsTemporaryAcceptError(errno)) { | 230 if (IsTemporaryAcceptError(errno)) { |
230 // We need to signal to the caller that this is actually not an | 231 // We need to signal to the caller that this is actually not an |
231 // error. We got woken up from the poll on the listening socket, | 232 // error. We got woken up from the poll on the listening socket, |
232 // but there is no connection ready to be accepted. | 233 // but there is no connection ready to be accepted. |
233 ASSERT(kTemporaryFailure != -1); | 234 ASSERT(kTemporaryFailure != -1); |
234 socket = kTemporaryFailure; | 235 socket = kTemporaryFailure; |
235 } | 236 } |
236 } else { | 237 } else { |
237 FDUtils::SetNonBlocking(socket); | 238 FDUtils::SetNonBlocking(socket); |
238 } | 239 } |
239 return socket; | 240 return socket; |
240 } | 241 } |
OLD | NEW |