Mercurial
comparison third_party/libuv/src/unix/loop.c @ 160:948de3f54cea
[ThirdParty] Added libuv
| author | June Park <parkjune1995@gmail.com> |
|---|---|
| date | Wed, 14 Jan 2026 19:39:52 -0800 |
| parents | |
| children |
comparison
equal
deleted
inserted
replaced
| 159:05cf9467a1c3 | 160:948de3f54cea |
|---|---|
| 1 /* Copyright Joyent, Inc. and other Node contributors. All rights reserved. | |
| 2 * | |
| 3 * Permission is hereby granted, free of charge, to any person obtaining a copy | |
| 4 * of this software and associated documentation files (the "Software"), to | |
| 5 * deal in the Software without restriction, including without limitation the | |
| 6 * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or | |
| 7 * sell copies of the Software, and to permit persons to whom the Software is | |
| 8 * furnished to do so, subject to the following conditions: | |
| 9 * | |
| 10 * The above copyright notice and this permission notice shall be included in | |
| 11 * all copies or substantial portions of the Software. | |
| 12 * | |
| 13 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | |
| 14 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | |
| 15 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | |
| 16 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | |
| 17 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING | |
| 18 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS | |
| 19 * IN THE SOFTWARE. | |
| 20 */ | |
| 21 | |
| 22 #include "uv.h" | |
| 23 #include "uv/tree.h" | |
| 24 #include "internal.h" | |
| 25 #include "heap-inl.h" | |
| 26 #include <stdlib.h> | |
| 27 #include <string.h> | |
| 28 #include <unistd.h> | |
| 29 | |
| 30 int uv_loop_init(uv_loop_t* loop) { | |
| 31 uv__loop_internal_fields_t* lfields; | |
| 32 void* saved_data; | |
| 33 int err; | |
| 34 | |
| 35 saved_data = loop->data; | |
| 36 memset(loop, 0, sizeof(*loop)); | |
| 37 loop->data = saved_data; | |
| 38 | |
| 39 lfields = uv__calloc(1, sizeof(*lfields)); | |
| 40 if (lfields == NULL) | |
| 41 return UV_ENOMEM; | |
| 42 loop->internal_fields = lfields; | |
| 43 | |
| 44 err = uv_mutex_init(&lfields->loop_metrics.lock); | |
| 45 if (err) | |
| 46 goto fail_metrics_mutex_init; | |
| 47 memset(&lfields->loop_metrics.metrics, | |
| 48 0, | |
| 49 sizeof(lfields->loop_metrics.metrics)); | |
| 50 | |
| 51 heap_init((struct heap*) &loop->timer_heap); | |
| 52 uv__queue_init(&loop->wq); | |
| 53 uv__queue_init(&loop->idle_handles); | |
| 54 uv__queue_init(&loop->async_handles); | |
| 55 uv__queue_init(&loop->check_handles); | |
| 56 uv__queue_init(&loop->prepare_handles); | |
| 57 uv__queue_init(&loop->handle_queue); | |
| 58 | |
| 59 loop->active_handles = 0; | |
| 60 loop->active_reqs.count = 0; | |
| 61 loop->nfds = 0; | |
| 62 loop->watchers = NULL; | |
| 63 loop->nwatchers = 0; | |
| 64 uv__queue_init(&loop->pending_queue); | |
| 65 uv__queue_init(&loop->watcher_queue); | |
| 66 | |
| 67 loop->closing_handles = NULL; | |
| 68 uv__update_time(loop); | |
| 69 loop->async_io_watcher.fd = -1; | |
| 70 loop->async_wfd = -1; | |
| 71 loop->signal_pipefd[0] = -1; | |
| 72 loop->signal_pipefd[1] = -1; | |
| 73 loop->backend_fd = -1; | |
| 74 loop->emfile_fd = -1; | |
| 75 | |
| 76 loop->timer_counter = 0; | |
| 77 loop->stop_flag = 0; | |
| 78 | |
| 79 err = uv__platform_loop_init(loop); | |
| 80 if (err) | |
| 81 goto fail_platform_init; | |
| 82 | |
| 83 uv__signal_global_once_init(); | |
| 84 err = uv__process_init(loop); | |
| 85 if (err) | |
| 86 goto fail_signal_init; | |
| 87 uv__queue_init(&loop->process_handles); | |
| 88 | |
| 89 err = uv_rwlock_init(&loop->cloexec_lock); | |
| 90 if (err) | |
| 91 goto fail_rwlock_init; | |
| 92 | |
| 93 err = uv_mutex_init(&loop->wq_mutex); | |
| 94 if (err) | |
| 95 goto fail_mutex_init; | |
| 96 | |
| 97 err = uv_async_init(loop, &loop->wq_async, uv__work_done); | |
| 98 if (err) | |
| 99 goto fail_async_init; | |
| 100 | |
| 101 uv__handle_unref(&loop->wq_async); | |
| 102 loop->wq_async.flags |= UV_HANDLE_INTERNAL; | |
| 103 | |
| 104 return 0; | |
| 105 | |
| 106 fail_async_init: | |
| 107 uv_mutex_destroy(&loop->wq_mutex); | |
| 108 | |
| 109 fail_mutex_init: | |
| 110 uv_rwlock_destroy(&loop->cloexec_lock); | |
| 111 | |
| 112 fail_rwlock_init: | |
| 113 uv__signal_loop_cleanup(loop); | |
| 114 | |
| 115 fail_signal_init: | |
| 116 uv__platform_loop_delete(loop); | |
| 117 | |
| 118 if (loop->backend_fd != -1) { | |
| 119 uv__close(loop->backend_fd); | |
| 120 loop->backend_fd = -1; | |
| 121 } | |
| 122 | |
| 123 fail_platform_init: | |
| 124 uv_mutex_destroy(&lfields->loop_metrics.lock); | |
| 125 | |
| 126 fail_metrics_mutex_init: | |
| 127 uv__free(lfields); | |
| 128 loop->internal_fields = NULL; | |
| 129 | |
| 130 uv__free(loop->watchers); | |
| 131 loop->nwatchers = 0; | |
| 132 return err; | |
| 133 } | |
| 134 | |
| 135 | |
| 136 int uv_loop_fork(uv_loop_t* loop) { | |
| 137 int err; | |
| 138 unsigned int i; | |
| 139 uv__io_t* w; | |
| 140 | |
| 141 err = uv__io_fork(loop); | |
| 142 if (err) | |
| 143 return err; | |
| 144 | |
| 145 err = uv__async_fork(loop); | |
| 146 if (err) | |
| 147 return err; | |
| 148 | |
| 149 err = uv__signal_loop_fork(loop); | |
| 150 if (err) | |
| 151 return err; | |
| 152 | |
| 153 /* Rearm all the watchers that aren't re-queued by the above. */ | |
| 154 for (i = 0; i < loop->nwatchers; i++) { | |
| 155 w = loop->watchers[i]; | |
| 156 if (w == NULL) | |
| 157 continue; | |
| 158 | |
| 159 if (w->pevents != 0 && uv__queue_empty(&w->watcher_queue)) { | |
| 160 w->events = 0; /* Force re-registration in uv__io_poll. */ | |
| 161 uv__queue_insert_tail(&loop->watcher_queue, &w->watcher_queue); | |
| 162 } | |
| 163 } | |
| 164 | |
| 165 return 0; | |
| 166 } | |
| 167 | |
| 168 | |
| 169 void uv__loop_close(uv_loop_t* loop) { | |
| 170 uv__loop_internal_fields_t* lfields; | |
| 171 | |
| 172 uv__signal_loop_cleanup(loop); | |
| 173 uv__platform_loop_delete(loop); | |
| 174 uv__async_stop(loop); | |
| 175 | |
| 176 if (loop->emfile_fd != -1) { | |
| 177 uv__close(loop->emfile_fd); | |
| 178 loop->emfile_fd = -1; | |
| 179 } | |
| 180 | |
| 181 if (loop->backend_fd != -1) { | |
| 182 uv__close(loop->backend_fd); | |
| 183 loop->backend_fd = -1; | |
| 184 } | |
| 185 | |
| 186 uv_mutex_lock(&loop->wq_mutex); | |
| 187 assert(uv__queue_empty(&loop->wq) && "thread pool work queue not empty!"); | |
| 188 assert(!uv__has_active_reqs(loop)); | |
| 189 uv_mutex_unlock(&loop->wq_mutex); | |
| 190 uv_mutex_destroy(&loop->wq_mutex); | |
| 191 | |
| 192 /* | |
| 193 * Note that all thread pool stuff is finished at this point and | |
| 194 * it is safe to just destroy rw lock | |
| 195 */ | |
| 196 uv_rwlock_destroy(&loop->cloexec_lock); | |
| 197 | |
| 198 #if 0 | |
| 199 assert(uv__queue_empty(&loop->pending_queue)); | |
| 200 assert(uv__queue_empty(&loop->watcher_queue)); | |
| 201 assert(loop->nfds == 0); | |
| 202 #endif | |
| 203 | |
| 204 uv__free(loop->watchers); | |
| 205 loop->watchers = NULL; | |
| 206 loop->nwatchers = 0; | |
| 207 | |
| 208 lfields = uv__get_internal_fields(loop); | |
| 209 uv_mutex_destroy(&lfields->loop_metrics.lock); | |
| 210 uv__free(lfields); | |
| 211 loop->internal_fields = NULL; | |
| 212 } | |
| 213 | |
| 214 | |
| 215 int uv__loop_configure(uv_loop_t* loop, uv_loop_option option, va_list ap) { | |
| 216 uv__loop_internal_fields_t* lfields; | |
| 217 | |
| 218 lfields = uv__get_internal_fields(loop); | |
| 219 if (option == UV_METRICS_IDLE_TIME) { | |
| 220 lfields->flags |= UV_METRICS_IDLE_TIME; | |
| 221 return 0; | |
| 222 } | |
| 223 | |
| 224 #if defined(__linux__) | |
| 225 if (option == UV_LOOP_USE_IO_URING_SQPOLL) { | |
| 226 loop->flags |= UV_LOOP_ENABLE_IO_URING_SQPOLL; | |
| 227 return 0; | |
| 228 } | |
| 229 #endif | |
| 230 | |
| 231 | |
| 232 if (option != UV_LOOP_BLOCK_SIGNAL) | |
| 233 return UV_ENOSYS; | |
| 234 | |
| 235 if (va_arg(ap, int) != SIGPROF) | |
| 236 return UV_EINVAL; | |
| 237 | |
| 238 loop->flags |= UV_LOOP_BLOCK_SIGPROF; | |
| 239 return 0; | |
| 240 } |