blob: 40e264504cfab5f95695c3735d1ef87dc7e4b1df [file] [log] [blame]
Yuchen Zeng85750b02016-08-08 14:16:34 -07001/*
2 *
Jan Tattermusch7897ae92017-06-07 22:57:36 +02003 * Copyright 2016 gRPC authors.
Yuchen Zeng85750b02016-08-08 14:16:34 -07004 *
Jan Tattermusch7897ae92017-06-07 22:57:36 +02005 * 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
Yuchen Zeng85750b02016-08-08 14:16:34 -07008 *
Jan Tattermusch7897ae92017-06-07 22:57:36 +02009 * http://www.apache.org/licenses/LICENSE-2.0
Yuchen Zeng85750b02016-08-08 14:16:34 -070010 *
Jan Tattermusch7897ae92017-06-07 22:57:36 +020011 * 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.
Yuchen Zeng85750b02016-08-08 14:16:34 -070016 *
17 */
18#include <grpc/support/port_platform.h>
Yuchen Zeng4e298e12016-10-28 16:08:19 -070019#include "src/core/lib/iomgr/port.h"
Yuchen Zeng9e4c8eb2016-11-18 01:06:57 -080020#if GRPC_ARES == 1 && defined(GRPC_POSIX_SOCKET)
Yuchen Zeng85750b02016-08-08 14:16:34 -070021
Nicolas "Pixel" Noble00f2c932017-04-04 20:38:14 +020022#include <ares.h>
Yuchen Zeng79c12b92017-09-18 22:02:52 -070023#include <sys/ioctl.h>
Nicolas "Pixel" Noble00f2c932017-04-04 20:38:14 +020024
Craig Tiller9eb0fde2017-03-31 16:59:30 -070025#include "src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_ev_driver.h"
Yuchen Zeng85750b02016-08-08 14:16:34 -070026
Yuchen Zeng85750b02016-08-08 14:16:34 -070027#include <grpc/support/alloc.h>
28#include <grpc/support/log.h>
29#include <grpc/support/string_util.h>
30#include <grpc/support/time.h>
31#include <grpc/support/useful.h>
Craig Tiller9eb0fde2017-03-31 16:59:30 -070032#include "src/core/ext/filters/client_channel/resolver/dns/c_ares/grpc_ares_wrapper.h"
Yuchen Zeng4e298e12016-10-28 16:08:19 -070033#include "src/core/lib/iomgr/ev_posix.h"
Yuchen Zeng85750b02016-08-08 14:16:34 -070034#include "src/core/lib/iomgr/iomgr_internal.h"
35#include "src/core/lib/iomgr/sockaddr_utils.h"
Yuchen Zeng85750b02016-08-08 14:16:34 -070036#include "src/core/lib/support/string.h"
37
Yuchen Zengc1893dc2016-09-30 18:49:41 -070038typedef struct fd_node {
Yuchen Zenge8d83092016-10-27 17:30:17 -070039 /** the owner of this fd node */
Craig Tillerbaa14a92017-11-03 09:09:36 -070040 grpc_ares_ev_driver* ev_driver;
Yuchen Zenge8d83092016-10-27 17:30:17 -070041 /** a closure wrapping on_readable_cb, which should be invoked when the
42 grpc_fd in this node becomes readable. */
43 grpc_closure read_closure;
44 /** a closure wrapping on_writable_cb, which should be invoked when the
45 grpc_fd in this node becomes writable. */
46 grpc_closure write_closure;
47 /** next fd node in the list */
Craig Tillerbaa14a92017-11-03 09:09:36 -070048 struct fd_node* next;
Yuchen Zenge8d83092016-10-27 17:30:17 -070049
50 /** mutex guarding the rest of the state */
51 gpr_mu mu;
Yuchen Zengb56cf2d2017-09-19 15:01:39 -070052 /** the grpc_fd owned by this fd node */
Craig Tillerbaa14a92017-11-03 09:09:36 -070053 grpc_fd* fd;
Yuchen Zenge8d83092016-10-27 17:30:17 -070054 /** if the readable closure has been registered */
55 bool readable_registered;
56 /** if the writable closure has been registered */
57 bool writable_registered;
Yuchen Zeng79c12b92017-09-18 22:02:52 -070058 /** if the fd is being shut down */
59 bool shutting_down;
Yuchen Zengc1893dc2016-09-30 18:49:41 -070060} fd_node;
Yuchen Zeng85750b02016-08-08 14:16:34 -070061
62struct grpc_ares_ev_driver {
Yuchen Zengc1893dc2016-09-30 18:49:41 -070063 /** the ares_channel owned by this event driver */
Yuchen Zeng8917aec2016-08-09 18:41:31 -070064 ares_channel channel;
Yuchen Zengc1893dc2016-09-30 18:49:41 -070065 /** pollset set for driving the IO events of the channel */
Craig Tillerbaa14a92017-11-03 09:09:36 -070066 grpc_pollset_set* pollset_set;
Yuchen Zeng8a6cba22016-11-09 18:19:13 -080067 /** refcount of the event driver */
68 gpr_refcount refs;
Yuchen Zengc87b77f2016-10-03 11:36:36 -070069
Yuchen Zeng43aa9a12016-10-25 10:44:39 -070070 /** mutex guarding the rest of the state */
Yuchen Zengc87b77f2016-10-03 11:36:36 -070071 gpr_mu mu;
Yuchen Zenge8d83092016-10-27 17:30:17 -070072 /** a list of grpc_fd that this event driver is currently using. */
Craig Tillerbaa14a92017-11-03 09:09:36 -070073 fd_node* fds;
Yuchen Zengc87b77f2016-10-03 11:36:36 -070074 /** is this event driver currently working? */
75 bool working;
Yuchen Zeng117a3002016-11-17 19:43:36 -080076 /** is this event driver being shut down */
77 bool shutting_down;
Yuchen Zeng85750b02016-08-08 14:16:34 -070078};
79
Yash Tibrewal8cf14702017-12-06 09:47:54 -080080static void grpc_ares_notify_on_event_locked(grpc_ares_ev_driver* ev_driver);
Yuchen Zenge8d83092016-10-27 17:30:17 -070081
Craig Tillerbaa14a92017-11-03 09:09:36 -070082static grpc_ares_ev_driver* grpc_ares_ev_driver_ref(
83 grpc_ares_ev_driver* ev_driver) {
Yuchen Zeng8a6cba22016-11-09 18:19:13 -080084 gpr_log(GPR_DEBUG, "Ref ev_driver %" PRIuPTR, (uintptr_t)ev_driver);
85 gpr_ref(&ev_driver->refs);
86 return ev_driver;
Yuchen Zenge8d83092016-10-27 17:30:17 -070087}
88
Craig Tillerbaa14a92017-11-03 09:09:36 -070089static void grpc_ares_ev_driver_unref(grpc_ares_ev_driver* ev_driver) {
Yuchen Zeng8a6cba22016-11-09 18:19:13 -080090 gpr_log(GPR_DEBUG, "Unref ev_driver %" PRIuPTR, (uintptr_t)ev_driver);
91 if (gpr_unref(&ev_driver->refs)) {
92 gpr_log(GPR_DEBUG, "destroy ev_driver %" PRIuPTR, (uintptr_t)ev_driver);
Craig Tiller4782d922017-11-10 09:53:21 -080093 GPR_ASSERT(ev_driver->fds == nullptr);
Yuchen Zeng8a6cba22016-11-09 18:19:13 -080094 gpr_mu_destroy(&ev_driver->mu);
95 ares_destroy(ev_driver->channel);
96 gpr_free(ev_driver);
Yuchen Zenge8d83092016-10-27 17:30:17 -070097 }
98}
Yuchen Zeng213d7842016-08-26 19:28:16 -070099
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800100static void fd_node_destroy(fd_node* fdn) {
Yash Tibrewalbc130da2017-09-12 22:44:08 -0700101 gpr_log(GPR_DEBUG, "delete fd: %d", grpc_fd_wrapped_fd(fdn->fd));
Yuchen Zeng8a6cba22016-11-09 18:19:13 -0800102 GPR_ASSERT(!fdn->readable_registered);
103 GPR_ASSERT(!fdn->writable_registered);
104 gpr_mu_destroy(&fdn->mu);
Yuchen Zeng1f4b2a82017-06-05 15:24:31 -0700105 /* c-ares library has closed the fd inside grpc_fd. This fd may be picked up
106 immediately by another thread, and should not be closed by the following
Yuchen Zengd40a7ae2017-07-12 15:59:56 -0700107 grpc_fd_orphan. */
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800108 grpc_fd_orphan(fdn->fd, nullptr, nullptr, true /* already_closed */,
Yuchen Zengd40a7ae2017-07-12 15:59:56 -0700109 "c-ares query finished");
Yuchen Zeng8a6cba22016-11-09 18:19:13 -0800110 gpr_free(fdn);
111}
112
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800113static void fd_node_shutdown(fd_node* fdn) {
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700114 gpr_mu_lock(&fdn->mu);
115 fdn->shutting_down = true;
116 if (!fdn->readable_registered && !fdn->writable_registered) {
117 gpr_mu_unlock(&fdn->mu);
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800118 fd_node_destroy(fdn);
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700119 } else {
Yash Tibrewal0ee75742017-10-13 16:07:13 -0700120 grpc_fd_shutdown(
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800121 fdn->fd, GRPC_ERROR_CREATE_FROM_STATIC_STRING("c-ares fd shutdown"));
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700122 gpr_mu_unlock(&fdn->mu);
123 }
124}
125
Craig Tillerbaa14a92017-11-03 09:09:36 -0700126grpc_error* grpc_ares_ev_driver_create(grpc_ares_ev_driver** ev_driver,
127 grpc_pollset_set* pollset_set) {
128 *ev_driver = (grpc_ares_ev_driver*)gpr_malloc(sizeof(grpc_ares_ev_driver));
Yuchen Zeng19d7bab2016-11-30 15:51:19 -0800129 int status = ares_init(&(*ev_driver)->channel);
Yuchen Zeng8a6cba22016-11-09 18:19:13 -0800130 gpr_log(GPR_DEBUG, "grpc_ares_ev_driver_create");
Yuchen Zeng8917aec2016-08-09 18:41:31 -0700131 if (status != ARES_SUCCESS) {
Craig Tillerbaa14a92017-11-03 09:09:36 -0700132 char* err_msg;
Yuchen Zeng43aa9a12016-10-25 10:44:39 -0700133 gpr_asprintf(&err_msg, "Failed to init ares channel. C-ares error: %s",
134 ares_strerror(status));
Craig Tillerbaa14a92017-11-03 09:09:36 -0700135 grpc_error* err = GRPC_ERROR_CREATE_FROM_COPIED_STRING(err_msg);
Yuchen Zeng43aa9a12016-10-25 10:44:39 -0700136 gpr_free(err_msg);
Yuchen Zeng8917aec2016-08-09 18:41:31 -0700137 gpr_free(*ev_driver);
Yuchen Zeng43aa9a12016-10-25 10:44:39 -0700138 return err;
Yuchen Zeng8917aec2016-08-09 18:41:31 -0700139 }
Yuchen Zeng213d7842016-08-26 19:28:16 -0700140 gpr_mu_init(&(*ev_driver)->mu);
Yuchen Zeng8a6cba22016-11-09 18:19:13 -0800141 gpr_ref_init(&(*ev_driver)->refs, 1);
Yuchen Zeng8917aec2016-08-09 18:41:31 -0700142 (*ev_driver)->pollset_set = pollset_set;
Craig Tiller4782d922017-11-10 09:53:21 -0800143 (*ev_driver)->fds = nullptr;
Yuchen Zengffbc1672016-10-03 11:29:22 -0700144 (*ev_driver)->working = false;
Yuchen Zeng117a3002016-11-17 19:43:36 -0800145 (*ev_driver)->shutting_down = false;
Yuchen Zeng8917aec2016-08-09 18:41:31 -0700146 return GRPC_ERROR_NONE;
147}
148
Craig Tillerbaa14a92017-11-03 09:09:36 -0700149void grpc_ares_ev_driver_destroy(grpc_ares_ev_driver* ev_driver) {
Yuchen Zeng117a3002016-11-17 19:43:36 -0800150 // It's not safe to shut down remaining fds here directly, becauses
151 // ares_host_callback does not provide an exec_ctx. We mark the event driver
152 // as being shut down. If the event driver is working,
153 // grpc_ares_notify_on_event_locked will shut down the fds; if it's not
Yuchen Zengf47c9632016-11-18 20:41:20 -0800154 // working, there are no fds to shut down.
Yuchen Zenge8d83092016-10-27 17:30:17 -0700155 gpr_mu_lock(&ev_driver->mu);
Yuchen Zeng117a3002016-11-17 19:43:36 -0800156 ev_driver->shutting_down = true;
Yuchen Zenge8d83092016-10-27 17:30:17 -0700157 gpr_mu_unlock(&ev_driver->mu);
Yuchen Zeng8a6cba22016-11-09 18:19:13 -0800158 grpc_ares_ev_driver_unref(ev_driver);
Yuchen Zeng8917aec2016-08-09 18:41:31 -0700159}
160
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800161void grpc_ares_ev_driver_shutdown(grpc_ares_ev_driver* ev_driver) {
Yuchen Zeng3b4bed22017-06-04 01:41:15 -0700162 gpr_mu_lock(&ev_driver->mu);
163 ev_driver->shutting_down = true;
Craig Tillerbaa14a92017-11-03 09:09:36 -0700164 fd_node* fn = ev_driver->fds;
Craig Tiller4782d922017-11-10 09:53:21 -0800165 while (fn != nullptr) {
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800166 grpc_fd_shutdown(fn->fd, GRPC_ERROR_CREATE_FROM_STATIC_STRING(
167 "grpc_ares_ev_driver_shutdown"));
Yuchen Zeng3b4bed22017-06-04 01:41:15 -0700168 fn = fn->next;
169 }
170 gpr_mu_unlock(&ev_driver->mu);
171}
172
Yuchen Zeng3026b6c2016-10-03 16:03:29 -0700173// Search fd in the fd_node list head. This is an O(n) search, the max possible
Yuchen Zenge8d83092016-10-27 17:30:17 -0700174// value of n is ARES_GETSOCK_MAXNUM (16). n is typically 1 - 2 in our tests.
Craig Tillerbaa14a92017-11-03 09:09:36 -0700175static fd_node* pop_fd_node(fd_node** head, int fd) {
Yuchen Zengc1893dc2016-09-30 18:49:41 -0700176 fd_node dummy_head;
Yuchen Zeng85750b02016-08-08 14:16:34 -0700177 dummy_head.next = *head;
Craig Tillerbaa14a92017-11-03 09:09:36 -0700178 fd_node* node = &dummy_head;
Craig Tiller4782d922017-11-10 09:53:21 -0800179 while (node->next != nullptr) {
Yash Tibrewalbc130da2017-09-12 22:44:08 -0700180 if (grpc_fd_wrapped_fd(node->next->fd) == fd) {
Craig Tillerbaa14a92017-11-03 09:09:36 -0700181 fd_node* ret = node->next;
Yuchen Zeng85750b02016-08-08 14:16:34 -0700182 node->next = node->next->next;
183 *head = dummy_head.next;
184 return ret;
185 }
Yuchen Zengc87b77f2016-10-03 11:36:36 -0700186 node = node->next;
Yuchen Zeng85750b02016-08-08 14:16:34 -0700187 }
Craig Tiller4782d922017-11-10 09:53:21 -0800188 return nullptr;
Yuchen Zeng85750b02016-08-08 14:16:34 -0700189}
190
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700191/* Check if \a fd is still readable */
Craig Tillerbaa14a92017-11-03 09:09:36 -0700192static bool grpc_ares_is_fd_still_readable(grpc_ares_ev_driver* ev_driver,
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700193 int fd) {
194 size_t bytes_available = 0;
195 return ioctl(fd, FIONREAD, &bytes_available) == 0 && bytes_available > 0;
196}
197
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800198static void on_readable_cb(void* arg, grpc_error* error) {
Craig Tillerbaa14a92017-11-03 09:09:36 -0700199 fd_node* fdn = (fd_node*)arg;
200 grpc_ares_ev_driver* ev_driver = fdn->ev_driver;
Yuchen Zenge8d83092016-10-27 17:30:17 -0700201 gpr_mu_lock(&fdn->mu);
Yuchen Zengb56cf2d2017-09-19 15:01:39 -0700202 const int fd = grpc_fd_wrapped_fd(fdn->fd);
Yuchen Zenge8d83092016-10-27 17:30:17 -0700203 fdn->readable_registered = false;
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700204 if (fdn->shutting_down && !fdn->writable_registered) {
205 gpr_mu_unlock(&fdn->mu);
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800206 fd_node_destroy(fdn);
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700207 grpc_ares_ev_driver_unref(ev_driver);
208 return;
209 }
Yuchen Zenge8d83092016-10-27 17:30:17 -0700210 gpr_mu_unlock(&fdn->mu);
Yuchen Zeng925b6882016-08-24 18:42:25 -0700211
Yuchen Zengb56cf2d2017-09-19 15:01:39 -0700212 gpr_log(GPR_DEBUG, "readable on %d", fd);
Yuchen Zeng85750b02016-08-08 14:16:34 -0700213 if (error == GRPC_ERROR_NONE) {
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700214 do {
Yuchen Zengb56cf2d2017-09-19 15:01:39 -0700215 ares_process_fd(ev_driver->channel, fd, ARES_SOCKET_BAD);
216 } while (grpc_ares_is_fd_still_readable(ev_driver, fd));
Yuchen Zeng4dd18912016-08-24 17:17:17 -0700217 } else {
Yuchen Zenge8d83092016-10-27 17:30:17 -0700218 // If error is not GRPC_ERROR_NONE, it means the fd has been shutdown or
219 // timed out. The pending lookups made on this ev_driver will be cancelled
Yuchen Zeng3ae26632016-11-09 15:53:50 -0800220 // by the following ares_cancel() and the on_done callbacks will be invoked
Yuchen Zenge8d83092016-10-27 17:30:17 -0700221 // with a status of ARES_ECANCELLED. The remaining file descriptors in this
222 // ev_driver will be cleaned up in the follwing
223 // grpc_ares_notify_on_event_locked().
224 ares_cancel(ev_driver->channel);
Yuchen Zeng85750b02016-08-08 14:16:34 -0700225 }
Yuchen Zenge8d83092016-10-27 17:30:17 -0700226 gpr_mu_lock(&ev_driver->mu);
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800227 grpc_ares_notify_on_event_locked(ev_driver);
Yuchen Zenge8d83092016-10-27 17:30:17 -0700228 gpr_mu_unlock(&ev_driver->mu);
Yuchen Zeng8a6cba22016-11-09 18:19:13 -0800229 grpc_ares_ev_driver_unref(ev_driver);
Yuchen Zeng85750b02016-08-08 14:16:34 -0700230}
231
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800232static void on_writable_cb(void* arg, grpc_error* error) {
Craig Tillerbaa14a92017-11-03 09:09:36 -0700233 fd_node* fdn = (fd_node*)arg;
234 grpc_ares_ev_driver* ev_driver = fdn->ev_driver;
Yuchen Zenge8d83092016-10-27 17:30:17 -0700235 gpr_mu_lock(&fdn->mu);
Yuchen Zengb56cf2d2017-09-19 15:01:39 -0700236 const int fd = grpc_fd_wrapped_fd(fdn->fd);
Yuchen Zenge8d83092016-10-27 17:30:17 -0700237 fdn->writable_registered = false;
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700238 if (fdn->shutting_down && !fdn->readable_registered) {
239 gpr_mu_unlock(&fdn->mu);
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800240 fd_node_destroy(fdn);
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700241 grpc_ares_ev_driver_unref(ev_driver);
242 return;
243 }
Yuchen Zenge8d83092016-10-27 17:30:17 -0700244 gpr_mu_unlock(&fdn->mu);
245
Yuchen Zengb56cf2d2017-09-19 15:01:39 -0700246 gpr_log(GPR_DEBUG, "writable on %d", fd);
Yuchen Zenge8d83092016-10-27 17:30:17 -0700247 if (error == GRPC_ERROR_NONE) {
Yuchen Zengb56cf2d2017-09-19 15:01:39 -0700248 ares_process_fd(ev_driver->channel, ARES_SOCKET_BAD, fd);
Yuchen Zenge8d83092016-10-27 17:30:17 -0700249 } else {
250 // If error is not GRPC_ERROR_NONE, it means the fd has been shutdown or
251 // timed out. The pending lookups made on this ev_driver will be cancelled
Yuchen Zeng3ae26632016-11-09 15:53:50 -0800252 // by the following ares_cancel() and the on_done callbacks will be invoked
Yuchen Zenge8d83092016-10-27 17:30:17 -0700253 // with a status of ARES_ECANCELLED. The remaining file descriptors in this
254 // ev_driver will be cleaned up in the follwing
255 // grpc_ares_notify_on_event_locked().
256 ares_cancel(ev_driver->channel);
257 }
Yuchen Zenge8d83092016-10-27 17:30:17 -0700258 gpr_mu_lock(&ev_driver->mu);
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800259 grpc_ares_notify_on_event_locked(ev_driver);
Yuchen Zenge8d83092016-10-27 17:30:17 -0700260 gpr_mu_unlock(&ev_driver->mu);
Yuchen Zeng8a6cba22016-11-09 18:19:13 -0800261 grpc_ares_ev_driver_unref(ev_driver);
Yuchen Zenge8d83092016-10-27 17:30:17 -0700262}
263
Craig Tillerbaa14a92017-11-03 09:09:36 -0700264ares_channel* grpc_ares_ev_driver_get_channel(grpc_ares_ev_driver* ev_driver) {
Yuchen Zeng9248d352016-08-16 16:33:10 -0700265 return &ev_driver->channel;
266}
267
Yuchen Zeng3026b6c2016-10-03 16:03:29 -0700268// Get the file descriptors used by the ev_driver's ares channel, register
269// driver_closure with these filedescriptors.
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800270static void grpc_ares_notify_on_event_locked(grpc_ares_ev_driver* ev_driver) {
Craig Tiller4782d922017-11-10 09:53:21 -0800271 fd_node* new_list = nullptr;
Yuchen Zeng117a3002016-11-17 19:43:36 -0800272 if (!ev_driver->shutting_down) {
273 ares_socket_t socks[ARES_GETSOCK_MAXNUM];
274 int socks_bitmask =
275 ares_getsock(ev_driver->channel, socks, ARES_GETSOCK_MAXNUM);
276 for (size_t i = 0; i < ARES_GETSOCK_MAXNUM; i++) {
277 if (ARES_GETSOCK_READABLE(socks_bitmask, i) ||
278 ARES_GETSOCK_WRITABLE(socks_bitmask, i)) {
Craig Tillerbaa14a92017-11-03 09:09:36 -0700279 fd_node* fdn = pop_fd_node(&ev_driver->fds, socks[i]);
Yuchen Zeng117a3002016-11-17 19:43:36 -0800280 // Create a new fd_node if sock[i] is not in the fd_node list.
Craig Tiller4ac2b8e2017-11-10 14:14:17 -0800281 if (fdn == nullptr) {
Craig Tillerbaa14a92017-11-03 09:09:36 -0700282 char* fd_name;
Yuchen Zeng117a3002016-11-17 19:43:36 -0800283 gpr_asprintf(&fd_name, "ares_ev_driver-%" PRIuPTR, i);
Craig Tillerbaa14a92017-11-03 09:09:36 -0700284 fdn = (fd_node*)gpr_malloc(sizeof(fd_node));
Yuchen Zeng117a3002016-11-17 19:43:36 -0800285 gpr_log(GPR_DEBUG, "new fd: %d", socks[i]);
Yash Tibrewalbc130da2017-09-12 22:44:08 -0700286 fdn->fd = grpc_fd_create(socks[i], fd_name);
Yuchen Zeng117a3002016-11-17 19:43:36 -0800287 fdn->ev_driver = ev_driver;
288 fdn->readable_registered = false;
289 fdn->writable_registered = false;
Yuchen Zeng79c12b92017-09-18 22:02:52 -0700290 fdn->shutting_down = false;
Yuchen Zeng117a3002016-11-17 19:43:36 -0800291 gpr_mu_init(&fdn->mu);
ncteisen274bbbe2017-06-08 14:57:11 -0700292 GRPC_CLOSURE_INIT(&fdn->read_closure, on_readable_cb, fdn,
Yuchen Zeng2ef172b2017-01-19 16:26:55 -0800293 grpc_schedule_on_exec_ctx);
ncteisen274bbbe2017-06-08 14:57:11 -0700294 GRPC_CLOSURE_INIT(&fdn->write_closure, on_writable_cb, fdn,
Yuchen Zeng2ef172b2017-01-19 16:26:55 -0800295 grpc_schedule_on_exec_ctx);
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800296 grpc_pollset_set_add_fd(ev_driver->pollset_set, fdn->fd);
Yuchen Zeng117a3002016-11-17 19:43:36 -0800297 gpr_free(fd_name);
298 }
299 fdn->next = new_list;
300 new_list = fdn;
301 gpr_mu_lock(&fdn->mu);
302 // Register read_closure if the socket is readable and read_closure has
303 // not been registered with this socket.
304 if (ARES_GETSOCK_READABLE(socks_bitmask, i) &&
305 !fdn->readable_registered) {
306 grpc_ares_ev_driver_ref(ev_driver);
Yash Tibrewalbc130da2017-09-12 22:44:08 -0700307 gpr_log(GPR_DEBUG, "notify read on: %d", grpc_fd_wrapped_fd(fdn->fd));
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800308 grpc_fd_notify_on_read(fdn->fd, &fdn->read_closure);
Yuchen Zeng117a3002016-11-17 19:43:36 -0800309 fdn->readable_registered = true;
310 }
311 // Register write_closure if the socket is writable and write_closure
Yuchen Zengf47c9632016-11-18 20:41:20 -0800312 // has not been registered with this socket.
Yuchen Zeng117a3002016-11-17 19:43:36 -0800313 if (ARES_GETSOCK_WRITABLE(socks_bitmask, i) &&
314 !fdn->writable_registered) {
315 gpr_log(GPR_DEBUG, "notify write on: %d",
Yash Tibrewalbc130da2017-09-12 22:44:08 -0700316 grpc_fd_wrapped_fd(fdn->fd));
Yuchen Zeng117a3002016-11-17 19:43:36 -0800317 grpc_ares_ev_driver_ref(ev_driver);
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800318 grpc_fd_notify_on_write(fdn->fd, &fdn->write_closure);
Yuchen Zeng117a3002016-11-17 19:43:36 -0800319 fdn->writable_registered = true;
320 }
321 gpr_mu_unlock(&fdn->mu);
Yuchen Zeng85750b02016-08-08 14:16:34 -0700322 }
Yuchen Zeng85750b02016-08-08 14:16:34 -0700323 }
Yuchen Zeng85750b02016-08-08 14:16:34 -0700324 }
Yuchen Zeng3483cf52016-11-10 23:09:00 -0800325 // Any remaining fds in ev_driver->fds were not returned by ares_getsock() and
326 // are therefore no longer in use, so they can be shut down and removed from
Yuchen Zeng3ae26632016-11-09 15:53:50 -0800327 // the list.
Craig Tiller4782d922017-11-10 09:53:21 -0800328 while (ev_driver->fds != nullptr) {
Craig Tillerbaa14a92017-11-03 09:09:36 -0700329 fd_node* cur = ev_driver->fds;
Yuchen Zeng85750b02016-08-08 14:16:34 -0700330 ev_driver->fds = ev_driver->fds->next;
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800331 fd_node_shutdown(cur);
Yuchen Zeng85750b02016-08-08 14:16:34 -0700332 }
Yuchen Zeng85750b02016-08-08 14:16:34 -0700333 ev_driver->fds = new_list;
Yuchen Zengc1893dc2016-09-30 18:49:41 -0700334 // If the ev driver has no working fd, all the tasks are done.
Craig Tiller4782d922017-11-10 09:53:21 -0800335 if (new_list == nullptr) {
Yuchen Zengc1893dc2016-09-30 18:49:41 -0700336 ev_driver->working = false;
Yuchen Zenge8d83092016-10-27 17:30:17 -0700337 gpr_log(GPR_DEBUG, "ev driver stop working");
Yuchen Zeng8917aec2016-08-09 18:41:31 -0700338 }
Yuchen Zengc1893dc2016-09-30 18:49:41 -0700339}
340
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800341void grpc_ares_ev_driver_start(grpc_ares_ev_driver* ev_driver) {
Yuchen Zengc1893dc2016-09-30 18:49:41 -0700342 gpr_mu_lock(&ev_driver->mu);
Yuchen Zeng3ae26632016-11-09 15:53:50 -0800343 if (!ev_driver->working) {
344 ev_driver->working = true;
Yash Tibrewal8cf14702017-12-06 09:47:54 -0800345 grpc_ares_notify_on_event_locked(ev_driver);
Yuchen Zengc1893dc2016-09-30 18:49:41 -0700346 }
Yuchen Zeng213d7842016-08-26 19:28:16 -0700347 gpr_mu_unlock(&ev_driver->mu);
Yuchen Zeng85750b02016-08-08 14:16:34 -0700348}
349
Yuchen Zeng9e4c8eb2016-11-18 01:06:57 -0800350#endif /* GRPC_ARES == 1 && defined(GRPC_POSIX_SOCKET) */