1 // 2 // 3 // Copyright 2017 gRPC authors. 4 // 5 // Licensed under the Apache License, Version 2.0 (the "License"); 6 // you may not use this file except in compliance with the License. 7 // You may obtain a copy of the License at 8 // 9 // http://www.apache.org/licenses/LICENSE-2.0 10 // 11 // Unless required by applicable law or agreed to in writing, software 12 // distributed under the License is distributed on an "AS IS" BASIS, 13 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 // See the License for the specific language governing permissions and 15 // limitations under the License. 16 // 17 // 18 19 #ifndef GRPC_SRC_CORE_LIB_IOMGR_TCP_SERVER_UTILS_POSIX_H 20 #define GRPC_SRC_CORE_LIB_IOMGR_TCP_SERVER_UTILS_POSIX_H 21 22 #include <grpc/support/port_platform.h> 23 24 #include <memory> 25 26 #include "absl/container/flat_hash_map.h" 27 #include "src/core/lib/event_engine/posix.h" 28 #include "src/core/lib/iomgr/ev_posix.h" 29 #include "src/core/lib/iomgr/resolve_address.h" 30 #include "src/core/lib/iomgr/socket_utils_posix.h" 31 #include "src/core/lib/iomgr/tcp_server.h" 32 #include "src/core/lib/iomgr/timer.h" 33 #include "src/core/lib/resource_quota/memory_quota.h" 34 35 // one listening port 36 typedef struct grpc_tcp_listener { 37 int fd; 38 grpc_fd* emfd; 39 grpc_tcp_server* server; 40 grpc_resolved_address addr; 41 int port; 42 unsigned port_index; 43 unsigned fd_index; 44 grpc_closure read_closure; 45 grpc_closure destroyed_closure; 46 struct grpc_tcp_listener* next; 47 // sibling is a linked list of all listeners for a given port. add_port and 48 // clone_port place all new listeners in the same sibling list. A member of 49 // the 'sibling' list is also a member of the 'next' list. The head of each 50 // sibling list has is_sibling==0, and subsequent members of sibling lists 51 // have is_sibling==1. is_sibling allows separate sibling lists to be 52 // identified while iterating through 'next'. 53 struct grpc_tcp_listener* sibling; 54 int is_sibling; 55 // If an accept4() call fails, a timer is started to drain the accept queue in 56 // case no further connection attempts reach the gRPC server. 57 grpc_closure retry_closure; 58 grpc_timer retry_timer; 59 gpr_atm retry_timer_armed; 60 } grpc_tcp_listener; 61 62 // the overall server 63 struct grpc_tcp_server { 64 gpr_refcount refs; 65 // Called whenever accept() succeeds on a server port. 66 grpc_tcp_server_cb on_accept_cb = nullptr; 67 void* on_accept_cb_arg = nullptr; 68 69 gpr_mu mu; 70 71 // active port count: how many ports are actually still listening 72 size_t active_ports = 0; 73 // destroyed port count: how many ports are completely destroyed 74 size_t destroyed_ports = 0; 75 76 // is this server shutting down? 77 bool shutdown = false; 78 // have listeners been shutdown? 79 bool shutdown_listeners = false; 80 // use SO_REUSEPORT 81 bool so_reuseport = false; 82 // expand wildcard addresses to a list of all local addresses 83 bool expand_wildcard_addrs = false; 84 85 // linked list of server ports 86 grpc_tcp_listener* head = nullptr; 87 grpc_tcp_listener* tail = nullptr; 88 unsigned nports = 0; 89 90 // List of closures passed to shutdown_starting_add(). 91 grpc_closure_list shutdown_starting{nullptr, nullptr}; 92 93 // shutdown callback 94 grpc_closure* shutdown_complete = nullptr; 95 96 // all pollsets interested in new connections. The object pointed at is not 97 // owned by this struct 98 const std::vector<grpc_pollset*>* pollsets = nullptr; 99 100 // next pollset to assign a channel to 101 gpr_atm next_pollset_to_assign = 0; 102 103 // Contains config extracted from channel args for this server 104 grpc_core::PosixTcpOptions options; 105 106 // a handler for external connections, owned 107 grpc_core::TcpServerFdHandler* fd_handler = nullptr; 108 109 // used to create slice allocators for endpoints, owned 110 grpc_core::MemoryQuotaRefPtr memory_quota; 111 112 /* used when event engine based servers are enabled */ 113 int n_bind_ports = 0; 114 absl::flat_hash_map<int, std::tuple<int, int>> listen_fd_to_index_map; 115 std::unique_ptr<grpc_event_engine::experimental::EventEngine::Listener> 116 ee_listener = nullptr; 117 /* used to store a pre-allocated FD assigned to a socket */ 118 int pre_allocated_fd; 119 }; 120 121 // If successful, add a listener to \a s for \a addr, set \a dsmode for the 122 // socket, and return the \a listener. 123 grpc_error_handle grpc_tcp_server_add_addr(grpc_tcp_server* s, 124 const grpc_resolved_address* addr, 125 unsigned port_index, 126 unsigned fd_index, 127 grpc_dualstack_mode* dsmode, 128 grpc_tcp_listener** listener); 129 130 // Get all addresses assigned to network interfaces on the machine and create a 131 // listener for each. requested_port is the port to use for every listener, or 0 132 // to select one random port that will be used for every listener. Set *out_port 133 // to the port selected. Return absl::OkStatus() only if all listeners were 134 // added. 135 grpc_error_handle grpc_tcp_server_add_all_local_addrs(grpc_tcp_server* s, 136 unsigned port_index, 137 int requested_port, 138 int* out_port); 139 140 // Prepare a recently-created socket for listening. 141 grpc_error_handle grpc_tcp_server_prepare_socket( 142 grpc_tcp_server*, int fd, const grpc_resolved_address* addr, 143 bool so_reuseport, int* port); 144 // Ruturn true if the platform supports ifaddrs 145 bool grpc_tcp_server_have_ifaddrs(void); 146 147 // Initialize (but don't start) the timer and callback to retry accept4() on a 148 // listening socket after file descriptors have been exhausted. This must be 149 // called when creating a new listener. 150 void grpc_tcp_server_listener_initialize_retry_timer( 151 grpc_tcp_listener* listener); 152 153 #endif // GRPC_SRC_CORE_LIB_IOMGR_TCP_SERVER_UTILS_POSIX_H 154