1 /*
2  *
3  * Copyright 2015 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 #include <grpc/support/port_platform.h>
20 
21 #include "src/core/lib/iomgr/port.h"
22 
23 #ifdef GRPC_POSIX_SOCKET_UTILS_COMMON
24 
25 #include <arpa/inet.h>
26 #include <errno.h>
27 #include <fcntl.h>
28 #include <limits.h>
29 #include <netinet/in.h>
30 
31 #include "src/core/lib/iomgr/socket_utils.h"
32 #include "src/core/lib/iomgr/socket_utils_posix.h"
33 #ifdef GRPC_LINUX_TCP_H
34 #include <linux/tcp.h>
35 #else
36 #include <netinet/tcp.h>
37 #endif
38 #include <stdio.h>
39 #include <string.h>
40 #include <sys/socket.h>
41 #include <sys/types.h>
42 #include <unistd.h>
43 
44 #include <string>
45 
46 #include <grpc/support/alloc.h>
47 #include <grpc/support/log.h>
48 #include <grpc/support/sync.h>
49 
50 #include "src/core/lib/address_utils/sockaddr_utils.h"
51 #include "src/core/lib/channel/channel_args.h"
52 #include "src/core/lib/gpr/string.h"
53 #include "src/core/lib/iomgr/sockaddr.h"
54 
55 /* set a socket to use zerocopy */
grpc_set_socket_zerocopy(int fd)56 grpc_error_handle grpc_set_socket_zerocopy(int fd) {
57 #ifdef GRPC_LINUX_ERRQUEUE
58   const int enable = 1;
59   auto err = setsockopt(fd, SOL_SOCKET, SO_ZEROCOPY, &enable, sizeof(enable));
60   if (err != 0) {
61     return GRPC_OS_ERROR(errno, "setsockopt(SO_ZEROCOPY)");
62   }
63   return GRPC_ERROR_NONE;
64 #else
65   (void)fd;
66   return GRPC_OS_ERROR(ENOSYS, "setsockopt(SO_ZEROCOPY)");
67 #endif
68 }
69 
70 /* set a socket to non blocking mode */
grpc_set_socket_nonblocking(int fd,int non_blocking)71 grpc_error_handle grpc_set_socket_nonblocking(int fd, int non_blocking) {
72   int oldflags = fcntl(fd, F_GETFL, 0);
73   if (oldflags < 0) {
74     return GRPC_OS_ERROR(errno, "fcntl");
75   }
76 
77   if (non_blocking) {
78     oldflags |= O_NONBLOCK;
79   } else {
80     oldflags &= ~O_NONBLOCK;
81   }
82 
83   if (fcntl(fd, F_SETFL, oldflags) != 0) {
84     return GRPC_OS_ERROR(errno, "fcntl");
85   }
86 
87   return GRPC_ERROR_NONE;
88 }
89 
grpc_set_socket_no_sigpipe_if_possible(int fd)90 grpc_error_handle grpc_set_socket_no_sigpipe_if_possible(int fd) {
91 #ifdef GRPC_HAVE_SO_NOSIGPIPE
92   int val = 1;
93   int newval;
94   socklen_t intlen = sizeof(newval);
95   if (0 != setsockopt(fd, SOL_SOCKET, SO_NOSIGPIPE, &val, sizeof(val))) {
96     return GRPC_OS_ERROR(errno, "setsockopt(SO_NOSIGPIPE)");
97   }
98   if (0 != getsockopt(fd, SOL_SOCKET, SO_NOSIGPIPE, &newval, &intlen)) {
99     return GRPC_OS_ERROR(errno, "getsockopt(SO_NOSIGPIPE)");
100   }
101   if ((newval != 0) != (val != 0)) {
102     return GRPC_ERROR_CREATE_FROM_STATIC_STRING("Failed to set SO_NOSIGPIPE");
103   }
104 #else
105   // Avoid unused parameter warning for conditional parameter
106   (void)fd;
107 #endif
108   return GRPC_ERROR_NONE;
109 }
110 
grpc_set_socket_ip_pktinfo_if_possible(int fd)111 grpc_error_handle grpc_set_socket_ip_pktinfo_if_possible(int fd) {
112   // Use conditionally-important parameter to avoid warning
113   (void)fd;
114 #ifdef GRPC_HAVE_IP_PKTINFO
115   int get_local_ip = 1;
116   if (0 != setsockopt(fd, IPPROTO_IP, IP_PKTINFO, &get_local_ip,
117                       sizeof(get_local_ip))) {
118     return GRPC_OS_ERROR(errno, "setsockopt(IP_PKTINFO)");
119   }
120 #endif
121   return GRPC_ERROR_NONE;
122 }
123 
grpc_set_socket_ipv6_recvpktinfo_if_possible(int fd)124 grpc_error_handle grpc_set_socket_ipv6_recvpktinfo_if_possible(int fd) {
125   // Use conditionally-important parameter to avoid warning
126   (void)fd;
127 #ifdef GRPC_HAVE_IPV6_RECVPKTINFO
128   int get_local_ip = 1;
129   if (0 != setsockopt(fd, IPPROTO_IPV6, IPV6_RECVPKTINFO, &get_local_ip,
130                       sizeof(get_local_ip))) {
131     return GRPC_OS_ERROR(errno, "setsockopt(IPV6_RECVPKTINFO)");
132   }
133 #endif
134   return GRPC_ERROR_NONE;
135 }
136 
grpc_set_socket_sndbuf(int fd,int buffer_size_bytes)137 grpc_error_handle grpc_set_socket_sndbuf(int fd, int buffer_size_bytes) {
138   return 0 == setsockopt(fd, SOL_SOCKET, SO_SNDBUF, &buffer_size_bytes,
139                          sizeof(buffer_size_bytes))
140              ? GRPC_ERROR_NONE
141              : GRPC_OS_ERROR(errno, "setsockopt(SO_SNDBUF)");
142 }
143 
grpc_set_socket_rcvbuf(int fd,int buffer_size_bytes)144 grpc_error_handle grpc_set_socket_rcvbuf(int fd, int buffer_size_bytes) {
145   return 0 == setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &buffer_size_bytes,
146                          sizeof(buffer_size_bytes))
147              ? GRPC_ERROR_NONE
148              : GRPC_OS_ERROR(errno, "setsockopt(SO_RCVBUF)");
149 }
150 
151 /* set a socket to close on exec */
grpc_set_socket_cloexec(int fd,int close_on_exec)152 grpc_error_handle grpc_set_socket_cloexec(int fd, int close_on_exec) {
153   int oldflags = fcntl(fd, F_GETFD, 0);
154   if (oldflags < 0) {
155     return GRPC_OS_ERROR(errno, "fcntl");
156   }
157 
158   if (close_on_exec) {
159     oldflags |= FD_CLOEXEC;
160   } else {
161     oldflags &= ~FD_CLOEXEC;
162   }
163 
164   if (fcntl(fd, F_SETFD, oldflags) != 0) {
165     return GRPC_OS_ERROR(errno, "fcntl");
166   }
167 
168   return GRPC_ERROR_NONE;
169 }
170 
171 /* set a socket to reuse old addresses */
grpc_set_socket_reuse_addr(int fd,int reuse)172 grpc_error_handle grpc_set_socket_reuse_addr(int fd, int reuse) {
173   int val = (reuse != 0);
174   int newval;
175   socklen_t intlen = sizeof(newval);
176   if (0 != setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &val, sizeof(val))) {
177     return GRPC_OS_ERROR(errno, "setsockopt(SO_REUSEADDR)");
178   }
179   if (0 != getsockopt(fd, SOL_SOCKET, SO_REUSEADDR, &newval, &intlen)) {
180     return GRPC_OS_ERROR(errno, "getsockopt(SO_REUSEADDR)");
181   }
182   if ((newval != 0) != val) {
183     return GRPC_ERROR_CREATE_FROM_STATIC_STRING("Failed to set SO_REUSEADDR");
184   }
185 
186   return GRPC_ERROR_NONE;
187 }
188 
189 /* set a socket to reuse old addresses */
grpc_set_socket_reuse_port(int fd,int reuse)190 grpc_error_handle grpc_set_socket_reuse_port(int fd, int reuse) {
191 #ifndef SO_REUSEPORT
192   return GRPC_ERROR_CREATE_FROM_STATIC_STRING(
193       "SO_REUSEPORT unavailable on compiling system");
194 #else
195   int val = (reuse != 0);
196   int newval;
197   socklen_t intlen = sizeof(newval);
198   if (0 != setsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &val, sizeof(val))) {
199     return GRPC_OS_ERROR(errno, "setsockopt(SO_REUSEPORT)");
200   }
201   if (0 != getsockopt(fd, SOL_SOCKET, SO_REUSEPORT, &newval, &intlen)) {
202     return GRPC_OS_ERROR(errno, "getsockopt(SO_REUSEPORT)");
203   }
204   if ((newval != 0) != val) {
205     return GRPC_ERROR_CREATE_FROM_STATIC_STRING("Failed to set SO_REUSEPORT");
206   }
207 
208   return GRPC_ERROR_NONE;
209 #endif
210 }
211 
212 static gpr_once g_probe_so_reuesport_once = GPR_ONCE_INIT;
213 static int g_support_so_reuseport = false;
214 
probe_so_reuseport_once(void)215 void probe_so_reuseport_once(void) {
216   int s = socket(AF_INET, SOCK_STREAM, 0);
217   if (s < 0) {
218     /* This might be an ipv6-only environment in which case 'socket(AF_INET,..)'
219        call would fail. Try creating IPv6 socket in that case */
220     s = socket(AF_INET6, SOCK_STREAM, 0);
221   }
222   if (s >= 0) {
223     g_support_so_reuseport = GRPC_LOG_IF_ERROR(
224         "check for SO_REUSEPORT", grpc_set_socket_reuse_port(s, 1));
225     close(s);
226   }
227 }
228 
grpc_is_socket_reuse_port_supported()229 bool grpc_is_socket_reuse_port_supported() {
230   gpr_once_init(&g_probe_so_reuesport_once, probe_so_reuseport_once);
231   return g_support_so_reuseport;
232 }
233 
234 /* disable nagle */
grpc_set_socket_low_latency(int fd,int low_latency)235 grpc_error_handle grpc_set_socket_low_latency(int fd, int low_latency) {
236   int val = (low_latency != 0);
237   int newval;
238   socklen_t intlen = sizeof(newval);
239   if (0 != setsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &val, sizeof(val))) {
240     return GRPC_OS_ERROR(errno, "setsockopt(TCP_NODELAY)");
241   }
242   if (0 != getsockopt(fd, IPPROTO_TCP, TCP_NODELAY, &newval, &intlen)) {
243     return GRPC_OS_ERROR(errno, "getsockopt(TCP_NODELAY)");
244   }
245   if ((newval != 0) != val) {
246     return GRPC_ERROR_CREATE_FROM_STATIC_STRING("Failed to set TCP_NODELAY");
247   }
248   return GRPC_ERROR_NONE;
249 }
250 
251 /* The default values for TCP_USER_TIMEOUT are currently configured to be in
252  * line with the default values of KEEPALIVE_TIMEOUT as proposed in
253  * https://github.com/grpc/proposal/blob/master/A18-tcp-user-timeout.md */
254 #define DEFAULT_CLIENT_TCP_USER_TIMEOUT_MS 20000 /* 20 seconds */
255 #define DEFAULT_SERVER_TCP_USER_TIMEOUT_MS 20000 /* 20 seconds */
256 
257 static int g_default_client_tcp_user_timeout_ms =
258     DEFAULT_CLIENT_TCP_USER_TIMEOUT_MS;
259 static int g_default_server_tcp_user_timeout_ms =
260     DEFAULT_SERVER_TCP_USER_TIMEOUT_MS;
261 static bool g_default_client_tcp_user_timeout_enabled = false;
262 static bool g_default_server_tcp_user_timeout_enabled = true;
263 
264 #if GPR_LINUX == 1
265 // For Linux, it will be detected to support TCP_USER_TIMEOUT
266 #ifndef TCP_USER_TIMEOUT
267 #define TCP_USER_TIMEOUT 18
268 #endif
269 #define SOCKET_SUPPORTS_TCP_USER_TIMEOUT_DEFAULT 0
270 #else
271 // For non-Linux, TCP_USER_TIMEOUT will be used if TCP_USER_TIMEOUT is defined.
272 #ifdef TCP_USER_TIMEOUT
273 #define SOCKET_SUPPORTS_TCP_USER_TIMEOUT_DEFAULT 0
274 #else
275 #define TCP_USER_TIMEOUT 0
276 #define SOCKET_SUPPORTS_TCP_USER_TIMEOUT_DEFAULT -1
277 #endif  // TCP_USER_TIMEOUT
278 #endif  // GPR_LINUX == 1
279 
280 // Whether the socket supports TCP_USER_TIMEOUT option.
281 // (0: don't know, 1: support, -1: not support)
282 static std::atomic<int> g_socket_supports_tcp_user_timeout(
283     SOCKET_SUPPORTS_TCP_USER_TIMEOUT_DEFAULT);
284 
config_default_tcp_user_timeout(bool enable,int timeout,bool is_client)285 void config_default_tcp_user_timeout(bool enable, int timeout, bool is_client) {
286   if (is_client) {
287     g_default_client_tcp_user_timeout_enabled = enable;
288     if (timeout > 0) {
289       g_default_client_tcp_user_timeout_ms = timeout;
290     }
291   } else {
292     g_default_server_tcp_user_timeout_enabled = enable;
293     if (timeout > 0) {
294       g_default_server_tcp_user_timeout_ms = timeout;
295     }
296   }
297 }
298 
299 /* Set TCP_USER_TIMEOUT */
grpc_set_socket_tcp_user_timeout(int fd,const grpc_channel_args * channel_args,bool is_client)300 grpc_error_handle grpc_set_socket_tcp_user_timeout(
301     int fd, const grpc_channel_args* channel_args, bool is_client) {
302   // Use conditionally-important parameter to avoid warning
303   (void)fd;
304   (void)channel_args;
305   (void)is_client;
306   extern grpc_core::TraceFlag grpc_tcp_trace;
307   if (g_socket_supports_tcp_user_timeout.load() >= 0) {
308     bool enable;
309     int timeout;
310     if (is_client) {
311       enable = g_default_client_tcp_user_timeout_enabled;
312       timeout = g_default_client_tcp_user_timeout_ms;
313     } else {
314       enable = g_default_server_tcp_user_timeout_enabled;
315       timeout = g_default_server_tcp_user_timeout_ms;
316     }
317     if (channel_args) {
318       for (unsigned int i = 0; i < channel_args->num_args; i++) {
319         if (0 ==
320             strcmp(channel_args->args[i].key, GRPC_ARG_KEEPALIVE_TIME_MS)) {
321           const int value = grpc_channel_arg_get_integer(
322               &channel_args->args[i], grpc_integer_options{0, 1, INT_MAX});
323           /* Continue using default if value is 0 */
324           if (value == 0) {
325             continue;
326           }
327           /* Disable if value is INT_MAX */
328           enable = value != INT_MAX;
329         } else if (0 == strcmp(channel_args->args[i].key,
330                                GRPC_ARG_KEEPALIVE_TIMEOUT_MS)) {
331           const int value = grpc_channel_arg_get_integer(
332               &channel_args->args[i], grpc_integer_options{0, 1, INT_MAX});
333           /* Continue using default if value is 0 */
334           if (value == 0) {
335             continue;
336           }
337           timeout = value;
338         }
339       }
340     }
341     if (enable) {
342       int newval;
343       socklen_t len = sizeof(newval);
344       // If this is the first time to use TCP_USER_TIMEOUT, try to check
345       // if it is available.
346       if (g_socket_supports_tcp_user_timeout.load() == 0) {
347         if (0 != getsockopt(fd, IPPROTO_TCP, TCP_USER_TIMEOUT, &newval, &len)) {
348           gpr_log(GPR_INFO,
349                   "TCP_USER_TIMEOUT is not available. TCP_USER_TIMEOUT won't "
350                   "be used thereafter");
351           g_socket_supports_tcp_user_timeout.store(-1);
352         } else {
353           gpr_log(GPR_INFO,
354                   "TCP_USER_TIMEOUT is available. TCP_USER_TIMEOUT will be "
355                   "used thereafter");
356           g_socket_supports_tcp_user_timeout.store(1);
357         }
358       }
359       if (g_socket_supports_tcp_user_timeout.load() > 0) {
360         if (GRPC_TRACE_FLAG_ENABLED(grpc_tcp_trace)) {
361           gpr_log(GPR_INFO, "Enabling TCP_USER_TIMEOUT with a timeout of %d ms",
362                   timeout);
363         }
364         if (0 != setsockopt(fd, IPPROTO_TCP, TCP_USER_TIMEOUT, &timeout,
365                             sizeof(timeout))) {
366           gpr_log(GPR_ERROR, "setsockopt(TCP_USER_TIMEOUT) %s",
367                   strerror(errno));
368           return GRPC_ERROR_NONE;
369         }
370         if (0 != getsockopt(fd, IPPROTO_TCP, TCP_USER_TIMEOUT, &newval, &len)) {
371           gpr_log(GPR_ERROR, "getsockopt(TCP_USER_TIMEOUT) %s",
372                   strerror(errno));
373           return GRPC_ERROR_NONE;
374         }
375         if (newval != timeout) {
376           /* Do not fail on failing to set TCP_USER_TIMEOUT for now. */
377           gpr_log(GPR_ERROR, "Failed to set TCP_USER_TIMEOUT");
378           return GRPC_ERROR_NONE;
379         }
380       }
381     }
382   } else {
383     if (GRPC_TRACE_FLAG_ENABLED(grpc_tcp_trace)) {
384       gpr_log(GPR_INFO, "TCP_USER_TIMEOUT not supported for this platform");
385     }
386   }
387   return GRPC_ERROR_NONE;
388 }
389 
390 /* set a socket using a grpc_socket_mutator */
grpc_set_socket_with_mutator(int fd,grpc_fd_usage usage,grpc_socket_mutator * mutator)391 grpc_error_handle grpc_set_socket_with_mutator(int fd, grpc_fd_usage usage,
392                                                grpc_socket_mutator* mutator) {
393   GPR_ASSERT(mutator);
394   if (!grpc_socket_mutator_mutate_fd(mutator, fd, usage)) {
395     return GRPC_ERROR_CREATE_FROM_STATIC_STRING("grpc_socket_mutator failed.");
396   }
397   return GRPC_ERROR_NONE;
398 }
399 
grpc_apply_socket_mutator_in_args(int fd,grpc_fd_usage usage,const grpc_channel_args * args)400 grpc_error_handle grpc_apply_socket_mutator_in_args(
401     int fd, grpc_fd_usage usage, const grpc_channel_args* args) {
402   const grpc_arg* socket_mutator_arg =
403       grpc_channel_args_find(args, GRPC_ARG_SOCKET_MUTATOR);
404   if (socket_mutator_arg == nullptr) {
405     return GRPC_ERROR_NONE;
406   }
407   GPR_DEBUG_ASSERT(socket_mutator_arg->type == GRPC_ARG_POINTER);
408   grpc_socket_mutator* mutator =
409       static_cast<grpc_socket_mutator*>(socket_mutator_arg->value.pointer.p);
410   return grpc_set_socket_with_mutator(fd, usage, mutator);
411 }
412 
413 static gpr_once g_probe_ipv6_once = GPR_ONCE_INIT;
414 static int g_ipv6_loopback_available;
415 
probe_ipv6_once(void)416 static void probe_ipv6_once(void) {
417   int fd = socket(AF_INET6, SOCK_STREAM, 0);
418   g_ipv6_loopback_available = 0;
419   if (fd < 0) {
420     gpr_log(GPR_INFO, "Disabling AF_INET6 sockets because socket() failed.");
421   } else {
422     grpc_sockaddr_in6 addr;
423     memset(&addr, 0, sizeof(addr));
424     addr.sin6_family = AF_INET6;
425     addr.sin6_addr.s6_addr[15] = 1; /* [::1]:0 */
426     if (bind(fd, reinterpret_cast<grpc_sockaddr*>(&addr), sizeof(addr)) == 0) {
427       g_ipv6_loopback_available = 1;
428     } else {
429       gpr_log(GPR_INFO,
430               "Disabling AF_INET6 sockets because ::1 is not available.");
431     }
432     close(fd);
433   }
434 }
435 
grpc_ipv6_loopback_available(void)436 int grpc_ipv6_loopback_available(void) {
437   gpr_once_init(&g_probe_ipv6_once, probe_ipv6_once);
438   return g_ipv6_loopback_available;
439 }
440 
error_for_fd(int fd,const grpc_resolved_address * addr)441 static grpc_error_handle error_for_fd(int fd,
442                                       const grpc_resolved_address* addr) {
443   if (fd >= 0) return GRPC_ERROR_NONE;
444   std::string addr_str = grpc_sockaddr_to_string(addr, false);
445   grpc_error_handle err = grpc_error_set_str(
446       GRPC_OS_ERROR(errno, "socket"), GRPC_ERROR_STR_TARGET_ADDRESS, addr_str);
447   return err;
448 }
449 
grpc_create_dualstack_socket(const grpc_resolved_address * resolved_addr,int type,int protocol,grpc_dualstack_mode * dsmode,int * newfd)450 grpc_error_handle grpc_create_dualstack_socket(
451     const grpc_resolved_address* resolved_addr, int type, int protocol,
452     grpc_dualstack_mode* dsmode, int* newfd) {
453   return grpc_create_dualstack_socket_using_factory(
454       nullptr, resolved_addr, type, protocol, dsmode, newfd);
455 }
456 
create_socket(grpc_socket_factory * factory,int domain,int type,int protocol)457 static int create_socket(grpc_socket_factory* factory, int domain, int type,
458                          int protocol) {
459   return (factory != nullptr)
460              ? grpc_socket_factory_socket(factory, domain, type, protocol)
461              : socket(domain, type, protocol);
462 }
463 
grpc_create_dualstack_socket_using_factory(grpc_socket_factory * factory,const grpc_resolved_address * resolved_addr,int type,int protocol,grpc_dualstack_mode * dsmode,int * newfd)464 grpc_error_handle grpc_create_dualstack_socket_using_factory(
465     grpc_socket_factory* factory, const grpc_resolved_address* resolved_addr,
466     int type, int protocol, grpc_dualstack_mode* dsmode, int* newfd) {
467   const grpc_sockaddr* addr =
468       reinterpret_cast<const grpc_sockaddr*>(resolved_addr->addr);
469   int family = addr->sa_family;
470   if (family == AF_INET6) {
471     if (grpc_ipv6_loopback_available()) {
472       *newfd = create_socket(factory, family, type, protocol);
473     } else {
474       *newfd = -1;
475       errno = EAFNOSUPPORT;
476     }
477     /* Check if we've got a valid dualstack socket. */
478     if (*newfd >= 0 && grpc_set_socket_dualstack(*newfd)) {
479       *dsmode = GRPC_DSMODE_DUALSTACK;
480       return GRPC_ERROR_NONE;
481     }
482     /* If this isn't an IPv4 address, then return whatever we've got. */
483     if (!grpc_sockaddr_is_v4mapped(resolved_addr, nullptr)) {
484       *dsmode = GRPC_DSMODE_IPV6;
485       return error_for_fd(*newfd, resolved_addr);
486     }
487     /* Fall back to AF_INET. */
488     if (*newfd >= 0) {
489       close(*newfd);
490     }
491     family = AF_INET;
492   }
493   *dsmode = family == AF_INET ? GRPC_DSMODE_IPV4 : GRPC_DSMODE_NONE;
494   *newfd = create_socket(factory, family, type, protocol);
495   return error_for_fd(*newfd, resolved_addr);
496 }
497 
grpc_htons(uint16_t hostshort)498 uint16_t grpc_htons(uint16_t hostshort) { return htons(hostshort); }
499 
grpc_ntohs(uint16_t netshort)500 uint16_t grpc_ntohs(uint16_t netshort) { return ntohs(netshort); }
501 
grpc_htonl(uint32_t hostlong)502 uint32_t grpc_htonl(uint32_t hostlong) { return htonl(hostlong); }
503 
grpc_ntohl(uint32_t netlong)504 uint32_t grpc_ntohl(uint32_t netlong) { return ntohl(netlong); }
505 
grpc_inet_pton(int af,const char * src,void * dst)506 int grpc_inet_pton(int af, const char* src, void* dst) {
507   return inet_pton(af, src, dst);
508 }
509 
grpc_inet_ntop(int af,const void * src,char * dst,size_t size)510 const char* grpc_inet_ntop(int af, const void* src, char* dst, size_t size) {
511   GPR_ASSERT(size <= (socklen_t)-1);
512   return inet_ntop(af, src, dst, static_cast<socklen_t>(size));
513 }
514 
515 #endif
516