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 #ifndef BIN_SOCKET_H_ | 5 #ifndef BIN_SOCKET_H_ |
6 #define BIN_SOCKET_H_ | 6 #define BIN_SOCKET_H_ |
7 | 7 |
8 #include <map> | |
9 | |
8 #include "platform/globals.h" | 10 #include "platform/globals.h" |
9 | 11 |
10 #include "bin/builtin.h" | 12 #include "bin/builtin.h" |
11 #include "bin/dartutils.h" | 13 #include "bin/dartutils.h" |
12 // Declare the OS-specific types ahead of defining the generic class. | 14 // Declare the OS-specific types ahead of defining the generic class. |
13 #if defined(TARGET_OS_ANDROID) | 15 #if defined(TARGET_OS_ANDROID) |
14 #include "bin/socket_android.h" | 16 #include "bin/socket_android.h" |
15 #elif defined(TARGET_OS_LINUX) | 17 #elif defined(TARGET_OS_LINUX) |
16 #include "bin/socket_linux.h" | 18 #include "bin/socket_linux.h" |
17 #elif defined(TARGET_OS_MACOS) | 19 #elif defined(TARGET_OS_MACOS) |
(...skipping 51 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
69 return addr->ss.ss_family == AF_INET6 ? | 71 return addr->ss.ss_family == AF_INET6 ? |
70 sizeof(struct sockaddr_in6) : sizeof(struct sockaddr_in); | 72 sizeof(struct sockaddr_in6) : sizeof(struct sockaddr_in); |
71 } | 73 } |
72 | 74 |
73 static intptr_t GetInAddrLength(const RawAddr* addr) { | 75 static intptr_t GetInAddrLength(const RawAddr* addr) { |
74 ASSERT(addr->ss.ss_family == AF_INET || addr->ss.ss_family == AF_INET6); | 76 ASSERT(addr->ss.ss_family == AF_INET || addr->ss.ss_family == AF_INET6); |
75 return addr->ss.ss_family == AF_INET6 ? | 77 return addr->ss.ss_family == AF_INET6 ? |
76 sizeof(struct in6_addr) : sizeof(struct in_addr); | 78 sizeof(struct in6_addr) : sizeof(struct in_addr); |
77 } | 79 } |
78 | 80 |
81 static bool AreAddressesEqual(const RawAddr& a, const RawAddr& b) { | |
82 if (a.ss.ss_family == AF_INET) { | |
83 if (b.ss.ss_family != AF_INET) return false; | |
84 return memcmp(&a.in.sin_addr, &b.in.sin_addr, sizeof(a.in.sin_addr)) == 0; | |
85 } else if (a.ss.ss_family == AF_INET6) { | |
86 if (b.ss.ss_family != AF_INET6) return false; | |
87 return memcmp(&a.in6.sin6_addr, | |
88 &b.in6.sin6_addr, | |
89 sizeof(a.in6.sin6_addr)) == 0; | |
90 } else { | |
91 UNREACHABLE(); | |
92 return false; | |
93 } | |
94 } | |
95 | |
79 static void GetSockAddr(Dart_Handle obj, RawAddr* addr) { | 96 static void GetSockAddr(Dart_Handle obj, RawAddr* addr) { |
80 Dart_TypedData_Type data_type; | 97 Dart_TypedData_Type data_type; |
81 uint8_t* data = NULL; | 98 uint8_t* data = NULL; |
82 intptr_t len; | 99 intptr_t len; |
83 Dart_Handle result = Dart_TypedDataAcquireData( | 100 Dart_Handle result = Dart_TypedDataAcquireData( |
84 obj, &data_type, reinterpret_cast<void**>(&data), &len); | 101 obj, &data_type, reinterpret_cast<void**>(&data), &len); |
85 if (Dart_IsError(result)) Dart_PropagateError(result); | 102 if (Dart_IsError(result)) Dart_PropagateError(result); |
86 if (data_type != Dart_TypedData_kUint8 || | 103 if (data_type != Dart_TypedData_kUint8 || |
87 (len != sizeof(in_addr) && len != sizeof(in6_addr))) { | 104 (len != sizeof(in_addr) && len != sizeof(in6_addr))) { |
88 Dart_PropagateError( | 105 Dart_PropagateError( |
(...skipping 215 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
304 | 321 |
305 // Start accepting on a newly created listening socket. If it was unable to | 322 // Start accepting on a newly created listening socket. If it was unable to |
306 // start accepting incoming sockets, the fd is invalidated. | 323 // start accepting incoming sockets, the fd is invalidated. |
307 static bool StartAccept(intptr_t fd); | 324 static bool StartAccept(intptr_t fd); |
308 | 325 |
309 private: | 326 private: |
310 DISALLOW_ALLOCATION(); | 327 DISALLOW_ALLOCATION(); |
311 DISALLOW_IMPLICIT_CONSTRUCTORS(ServerSocket); | 328 DISALLOW_IMPLICIT_CONSTRUCTORS(ServerSocket); |
312 }; | 329 }; |
313 | 330 |
331 class ListeningSocketRegistry { | |
332 private: | |
333 struct OSSocket { | |
334 RawAddr address; | |
335 int port; | |
336 bool v6_only; | |
337 bool shared; | |
338 int ref_count; | |
339 intptr_t socketfd; | |
340 | |
341 // Singly linked lists of OSSocket instances which listen on the same port | |
342 // but on different addresses. | |
343 OSSocket *next; | |
344 | |
345 OSSocket(RawAddr address, int port, bool v6_only, bool shared, | |
346 intptr_t socketfd) | |
347 : address(address), port(port), v6_only(v6_only), shared(shared), | |
348 ref_count(0), socketfd(socketfd), next(NULL) {} | |
349 }; | |
350 | |
351 public: | |
352 static bool Initialize(); | |
353 | |
354 static ListeningSocketRegistry *Instance(); | |
355 | |
356 static void Cleanup(); | |
357 | |
358 | |
359 ListeningSocketRegistry() : mutex_(new Mutex()) {} | |
360 | |
361 ~ListeningSocketRegistry() { | |
362 delete mutex_; | |
363 mutex_ = NULL; | |
364 } | |
365 | |
366 // This function should be called from a dart runtime call in order to create | |
367 // a new (potentially shared) socket. | |
368 Dart_Handle CreateBindListen(Dart_Handle socket_object, | |
369 RawAddr addr, | |
370 intptr_t port, | |
371 intptr_t backlog, | |
372 bool v6_only, | |
373 bool shared); | |
374 | |
375 // This should be called from the event handler for every kCloseEvent it gets | |
376 // on listening sockets. | |
377 // | |
378 // Returns `true` if the last reference has been dropped and the underlying | |
379 // socket can be closed. | |
380 // | |
381 // The caller is responsible for obtaining the mutex first, before calling | |
382 // this function. | |
383 bool CloseSafe(intptr_t socketfd); | |
384 | |
385 // Mark an existing socket as sharable if it is not already marked as | |
386 // sharable. | |
387 // | |
388 // NOTE: This is a temporary measure until ServerSocketReference's are | |
389 // removed. | |
390 Dart_Handle MarkSocketFdAsSharableHack(intptr_t socketfd); | |
391 | |
392 Mutex *mutex() { return mutex_; } | |
393 | |
394 private: | |
395 OSSocket *findOSSocketWithAddress(OSSocket *current, const RawAddr& addr) { | |
396 while (current != NULL) { | |
397 if (SocketAddress::AreAddressesEqual(current->address, addr)) { | |
398 return current; | |
399 } | |
400 current = current->next; | |
401 } | |
402 return NULL; | |
403 } | |
404 | |
405 std::map<intptr_t, OSSocket*> sockets_by_port_; | |
406 std::map<intptr_t, OSSocket*> sockets_by_fd_; | |
407 Mutex *mutex_; | |
408 | |
409 typedef std::map<intptr_t, OSSocket*>::iterator SocketsIterator; | |
Søren Gjesse
2015/02/11 08:51:05
Please add
DISALLOW_COPY_AND_ASSIGN(ListeningSock
kustermann
2015/02/11 09:56:09
Done.
| |
410 }; | |
411 | |
412 | |
314 } // namespace bin | 413 } // namespace bin |
315 } // namespace dart | 414 } // namespace dart |
316 | 415 |
317 #endif // BIN_SOCKET_H_ | 416 #endif // BIN_SOCKET_H_ |
OLD | NEW |