| 2057 | } |
| 2058 | |
| 2059 | static void *runtime_accept_loop(void *opaque) { |
| 2060 | cbm_daemon_runtime_service_t *service = opaque; |
| 2061 | for (;;) { |
| 2062 | runtime_reap_completed_workers(service); |
| 2063 | cbm_mutex_lock(&service->mutex); |
| 2064 | cbm_daemon_runtime_service_state_t state = service->state; |
| 2065 | cbm_mutex_unlock(&service->mutex); |
| 2066 | if (state == CBM_DAEMON_RUNTIME_SERVICE_EXITED) { |
| 2067 | break; |
| 2068 | } |
| 2069 | if (state == CBM_DAEMON_RUNTIME_SERVICE_STOPPING) { |
| 2070 | runtime_service_interrupt_connections(service); |
| 2071 | if (runtime_service_can_exit(service, cbm_now_ms())) { |
| 2072 | break; |
| 2073 | } |
| 2074 | uint64_t tick_deadline = runtime_deadline_after(1); |
| 2075 | runtime_wait_tick(tick_deadline); |
| 2076 | continue; |
| 2077 | } |
| 2078 | |
| 2079 | cbm_daemon_ipc_connection_t *connection = NULL; |
| 2080 | int accepted = |
| 2081 | cbm_daemon_ipc_accept(service->listener, RUNTIME_ACCEPT_POLL_MS, &connection); |
| 2082 | if (accepted == 1 && connection) { |
| 2083 | runtime_accept_connection(service, connection); |
| 2084 | } else if (accepted < 0) { |
| 2085 | /* IPC intentionally combines invalid-peer and listener errors. |
| 2086 | * Retry while RUNNING so one hostile peer cannot stop the daemon. */ |
| 2087 | uint64_t tick_deadline = runtime_deadline_after(1); |
| 2088 | runtime_wait_tick(tick_deadline); |
| 2089 | } |
| 2090 | } |
| 2091 | runtime_reap_completed_workers(service); |
| 2092 | atomic_store_explicit(&service->accept_thread_done, true, memory_order_release); |
| 2093 | return NULL; |
| 2094 | } |
| 2095 | |
| 2096 | static char *runtime_string_copy_bounded(const char *value, size_t capacity) { |
| 2097 | size_t length = 0; |
nothing calls this directly
no test coverage detected