Bug Summary

File:build-scan/../src/libsystemd/sd-resolve/sd-resolve.c
Warning:line 554, column 17
Use of memory after it is freed

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-unknown-linux-gnu -analyze -disable-free -disable-llvm-verifier -discard-value-names -main-file-name sd-resolve.c -analyzer-store=region -analyzer-opt-analyze-nested-blocks -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -fhalf-no-semantic-interposition -mframe-pointer=all -relaxed-aliasing -menable-no-infs -menable-no-nans -menable-unsafe-fp-math -fno-signed-zeros -mreassociate -freciprocal-math -fdenormal-fp-math=preserve-sign,preserve-sign -ffp-contract=fast -fno-rounding-math -ffast-math -ffinite-math-only -mconstructor-aliases -munwind-tables -target-cpu x86-64 -tune-cpu generic -fno-split-dwarf-inlining -debugger-tuning=gdb -resource-dir /usr/lib64/clang/12.0.0 -include config.h -I src/libsystemd/libsystemd_static.a.p -I src/libsystemd -I ../src/libsystemd -I src/basic -I ../src/basic -I src/shared -I ../src/shared -I src/systemd -I ../src/systemd -I src/journal -I ../src/journal -I src/journal-remote -I ../src/journal-remote -I src/nspawn -I ../src/nspawn -I src/resolve -I ../src/resolve -I src/timesync -I ../src/timesync -I ../src/time-wait-sync -I src/login -I ../src/login -I src/udev -I ../src/udev -I src/libudev -I ../src/libudev -I src/core -I ../src/core -I ../src/libsystemd/sd-bus -I ../src/libsystemd/sd-device -I ../src/libsystemd/sd-hwdb -I ../src/libsystemd/sd-id128 -I ../src/libsystemd/sd-netlink -I ../src/libsystemd/sd-network -I src/libsystemd-network -I ../src/libsystemd-network -I . -I .. -D _FILE_OFFSET_BITS=64 -internal-isystem /usr/local/include -internal-isystem /usr/lib64/clang/12.0.0/include -internal-externc-isystem /include -internal-externc-isystem /usr/include -Wwrite-strings -Wno-unused-parameter -Wno-missing-field-initializers -Wno-unused-result -Wno-format-signedness -Wno-error=nonnull -std=gnu99 -fconst-strings -fdebug-compilation-dir /home/mrc0mmand/repos/@redhat-plumbers/systemd-rhel8/build-scan -ferror-limit 19 -fvisibility default -stack-protector 2 -fgnuc-version=4.2.1 -fcolor-diagnostics -analyzer-output=html -faddrsig -o /tmp/scan-build-2021-07-16-221226-1465241-1 -x c ../src/libsystemd/sd-resolve/sd-resolve.c
1/* SPDX-License-Identifier: LGPL-2.1+ */
2/***
3***/
4
5#include <errno(*__errno_location ()).h>
6#include <poll.h>
7#include <pthread.h>
8#include <resolv.h>
9#include <signal.h>
10#include <stdint.h>
11#include <stdio.h>
12#include <stdlib.h>
13#include <string.h>
14#include <sys/prctl.h>
15#include <unistd.h>
16
17#include "sd-resolve.h"
18
19#include "alloc-util.h"
20#include "dns-domain.h"
21#include "fd-util.h"
22#include "io-util.h"
23#include "list.h"
24#include "missing.h"
25#include "socket-util.h"
26#include "util.h"
27#include "process-util.h"
28
29#define WORKERS_MIN1U 1U
30#define WORKERS_MAX16U 16U
31#define QUERIES_MAX256U 256U
32#define BUFSIZE10240U 10240U
33
34typedef enum {
35 REQUEST_ADDRINFO,
36 RESPONSE_ADDRINFO,
37 REQUEST_NAMEINFO,
38 RESPONSE_NAMEINFO,
39 REQUEST_TERMINATE,
40 RESPONSE_DIED
41} QueryType;
42
43enum {
44 REQUEST_RECV_FD,
45 REQUEST_SEND_FD,
46 RESPONSE_RECV_FD,
47 RESPONSE_SEND_FD,
48 _FD_MAX
49};
50
51struct sd_resolve {
52 unsigned n_ref;
53
54 bool_Bool dead:1;
55 pid_t original_pid;
56
57 int fds[_FD_MAX];
58
59 pthread_t workers[WORKERS_MAX16U];
60 unsigned n_valid_workers;
61
62 unsigned current_id;
63 sd_resolve_query* query_array[QUERIES_MAX256U];
64 unsigned n_queries, n_done, n_outstanding;
65
66 sd_event_source *event_source;
67 sd_event *event;
68
69 sd_resolve_query *current;
70
71 sd_resolve **default_resolve_ptr;
72 pid_t tid;
73
74 LIST_HEAD(sd_resolve_query, queries)sd_resolve_query *queries;
75};
76
77struct sd_resolve_query {
78 unsigned n_ref;
79
80 sd_resolve *resolve;
81
82 QueryType type:4;
83 bool_Bool done:1;
84 bool_Bool floating:1;
85 unsigned id;
86
87 int ret;
88 int _errno;
89 int _h_errno;
90 struct addrinfo *addrinfo;
91 char *serv, *host;
92
93 union {
94 sd_resolve_getaddrinfo_handler_t getaddrinfo_handler;
95 sd_resolve_getnameinfo_handler_t getnameinfo_handler;
96 };
97
98 void *userdata;
99
100 LIST_FIELDS(sd_resolve_query, queries)sd_resolve_query *queries_next, *queries_prev;
101};
102
103typedef struct RHeader {
104 QueryType type;
105 unsigned id;
106 size_t length;
107} RHeader;
108
109typedef struct AddrInfoRequest {
110 struct RHeader header;
111 bool_Bool hints_valid;
112 int ai_flags;
113 int ai_family;
114 int ai_socktype;
115 int ai_protocol;
116 size_t node_len, service_len;
117} AddrInfoRequest;
118
119typedef struct AddrInfoResponse {
120 struct RHeader header;
121 int ret;
122 int _errno;
123 int _h_errno;
124 /* followed by addrinfo_serialization[] */
125} AddrInfoResponse;
126
127typedef struct AddrInfoSerialization {
128 int ai_flags;
129 int ai_family;
130 int ai_socktype;
131 int ai_protocol;
132 size_t ai_addrlen;
133 size_t canonname_len;
134 /* Followed by ai_addr amd ai_canonname with variable lengths */
135} AddrInfoSerialization;
136
137typedef struct NameInfoRequest {
138 struct RHeader header;
139 int flags;
140 socklen_t sockaddr_len;
141 bool_Bool gethost:1, getserv:1;
142} NameInfoRequest;
143
144typedef struct NameInfoResponse {
145 struct RHeader header;
146 size_t hostlen, servlen;
147 int ret;
148 int _errno;
149 int _h_errno;
150} NameInfoResponse;
151
152typedef union Packet {
153 RHeader rheader;
154 AddrInfoRequest addrinfo_request;
155 AddrInfoResponse addrinfo_response;
156 NameInfoRequest nameinfo_request;
157 NameInfoResponse nameinfo_response;
158} Packet;
159
160static int getaddrinfo_done(sd_resolve_query* q);
161static int getnameinfo_done(sd_resolve_query *q);
162
163static void resolve_query_disconnect(sd_resolve_query *q);
164
165#define RESOLVE_DONT_DESTROY(resolve)__attribute__((cleanup(sd_resolve_unrefp))) __attribute__ ((unused
)) sd_resolve *_dont_destroy_resolve = sd_resolve_ref(resolve
)
\
166 _cleanup_(sd_resolve_unrefp)__attribute__((cleanup(sd_resolve_unrefp))) _unused___attribute__ ((unused)) sd_resolve *_dont_destroy_##resolve = sd_resolve_ref(resolve)
167
168static void query_assign_errno(sd_resolve_query *q, int ret, int error, int h_error) {
169 assert(q)do { if ((__builtin_expect(!!(!(q)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 169, __PRETTY_FUNCTION__); } while (0)
;
170
171 q->ret = ret;
172 q->_errno = abs(error);
173 q->_h_errno = h_error;
174}
175
176static int send_died(int out_fd) {
177 RHeader rh = {
178 .type = RESPONSE_DIED,
179 .length = sizeof(RHeader),
180 };
181
182 assert(out_fd >= 0)do { if ((__builtin_expect(!!(!(out_fd >= 0)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("out_fd >= 0"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 182, __PRETTY_FUNCTION__); } while (0)
;
183
184 if (send(out_fd, &rh, rh.length, MSG_NOSIGNALMSG_NOSIGNAL) < 0)
185 return -errno(*__errno_location ());
186
187 return 0;
188}
189
190static void *serialize_addrinfo(void *p, const struct addrinfo *ai, size_t *length, size_t maxlength) {
191 AddrInfoSerialization s;
192 size_t cnl, l;
193
194 assert(p)do { if ((__builtin_expect(!!(!(p)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("p"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 194, __PRETTY_FUNCTION__); } while (0)
;
195 assert(ai)do { if ((__builtin_expect(!!(!(ai)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("ai"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 195, __PRETTY_FUNCTION__); } while (0)
;
196 assert(length)do { if ((__builtin_expect(!!(!(length)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("length"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 196, __PRETTY_FUNCTION__); } while (0)
;
197 assert(*length <= maxlength)do { if ((__builtin_expect(!!(!(*length <= maxlength)),0))
) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("*length <= maxlength"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 197, __PRETTY_FUNCTION__
); } while (0)
;
198
199 cnl = ai->ai_canonname ? strlen(ai->ai_canonname)+1 : 0;
200 l = sizeof(AddrInfoSerialization) + ai->ai_addrlen + cnl;
201
202 if (*length + l > maxlength)
203 return NULL((void*)0);
204
205 s.ai_flags = ai->ai_flags;
206 s.ai_family = ai->ai_family;
207 s.ai_socktype = ai->ai_socktype;
208 s.ai_protocol = ai->ai_protocol;
209 s.ai_addrlen = ai->ai_addrlen;
210 s.canonname_len = cnl;
211
212 memcpy((uint8_t*) p, &s, sizeof(AddrInfoSerialization));
213 memcpy((uint8_t*) p + sizeof(AddrInfoSerialization), ai->ai_addr, ai->ai_addrlen);
214 memcpy_safe((char*) p + sizeof(AddrInfoSerialization) + ai->ai_addrlen,
215 ai->ai_canonname, cnl);
216
217 *length += l;
218 return (uint8_t*) p + l;
219}
220
221static int send_addrinfo_reply(
222 int out_fd,
223 unsigned id,
224 int ret,
225 struct addrinfo *ai,
226 int _errno,
227 int _h_errno) {
228
229 AddrInfoResponse resp = {
230 .header.type = RESPONSE_ADDRINFO,
231 .header.id = id,
232 .header.length = sizeof(AddrInfoResponse),
233 .ret = ret,
234 ._errno = _errno,
235 ._h_errno = _h_errno,
236 };
237
238 union {
239 AddrInfoSerialization ais;
240 uint8_t space[BUFSIZE10240U];
241 } buffer;
242 struct iovec iov[2];
243 struct msghdr mh;
244
245 assert(out_fd >= 0)do { if ((__builtin_expect(!!(!(out_fd >= 0)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("out_fd >= 0"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 245, __PRETTY_FUNCTION__); } while (0)
;
246
247 if (ret == 0 && ai) {
248 void *p = &buffer;
249 struct addrinfo *k;
250
251 for (k = ai; k; k = k->ai_next) {
252 p = serialize_addrinfo(p, k, &resp.header.length, (uint8_t*) &buffer + BUFSIZE10240U - (uint8_t*) p);
253 if (!p) {
254 freeaddrinfo(ai);
255 return -ENOBUFS105;
256 }
257 }
258 }
259
260 if (ai)
261 freeaddrinfo(ai);
262
263 iov[0] = (struct iovec) { .iov_base = &resp, .iov_len = sizeof(AddrInfoResponse) };
264 iov[1] = (struct iovec) { .iov_base = &buffer, .iov_len = resp.header.length - sizeof(AddrInfoResponse) };
265
266 mh = (struct msghdr) { .msg_iov = iov, .msg_iovlen = ELEMENTSOF(iov)__extension__ (__builtin_choose_expr( !__builtin_types_compatible_p
(typeof(iov), typeof(&*(iov))), sizeof(iov)/sizeof((iov)[
0]), ((void)0)))
};
267
268 if (sendmsg(out_fd, &mh, MSG_NOSIGNALMSG_NOSIGNAL) < 0)
269 return -errno(*__errno_location ());
270
271 return 0;
272}
273
274static int send_nameinfo_reply(
275 int out_fd,
276 unsigned id,
277 int ret,
278 const char *host,
279 const char *serv,
280 int _errno,
281 int _h_errno) {
282
283 NameInfoResponse resp = {
284 .header.type = RESPONSE_NAMEINFO,
285 .header.id = id,
286 .ret = ret,
287 ._errno = _errno,
288 ._h_errno = _h_errno,
289 };
290
291 struct iovec iov[3];
292 struct msghdr mh;
293 size_t hl, sl;
294
295 assert(out_fd >= 0)do { if ((__builtin_expect(!!(!(out_fd >= 0)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("out_fd >= 0"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 295, __PRETTY_FUNCTION__); } while (0)
;
296
297 sl = serv ? strlen(serv)+1 : 0;
298 hl = host ? strlen(host)+1 : 0;
299
300 resp.header.length = sizeof(NameInfoResponse) + hl + sl;
301 resp.hostlen = hl;
302 resp.servlen = sl;
303
304 iov[0] = (struct iovec) { .iov_base = &resp, .iov_len = sizeof(NameInfoResponse) };
305 iov[1] = (struct iovec) { .iov_base = (void*) host, .iov_len = hl };
306 iov[2] = (struct iovec) { .iov_base = (void*) serv, .iov_len = sl };
307
308 mh = (struct msghdr) { .msg_iov = iov, .msg_iovlen = ELEMENTSOF(iov)__extension__ (__builtin_choose_expr( !__builtin_types_compatible_p
(typeof(iov), typeof(&*(iov))), sizeof(iov)/sizeof((iov)[
0]), ((void)0)))
};
309
310 if (sendmsg(out_fd, &mh, MSG_NOSIGNALMSG_NOSIGNAL) < 0)
311 return -errno(*__errno_location ());
312
313 return 0;
314}
315
316static int handle_request(int out_fd, const Packet *packet, size_t length) {
317 const RHeader *req;
318
319 assert(out_fd >= 0)do { if ((__builtin_expect(!!(!(out_fd >= 0)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("out_fd >= 0"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 319, __PRETTY_FUNCTION__); } while (0)
;
320 assert(packet)do { if ((__builtin_expect(!!(!(packet)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("packet"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 320, __PRETTY_FUNCTION__); } while (0)
;
321
322 req = &packet->rheader;
323
324 assert_return(length >= sizeof(RHeader), -EIO)do { if (!(((__builtin_expect(!!(length >= sizeof(RHeader)
),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("length >= sizeof(RHeader)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 324, __PRETTY_FUNCTION__), 0))) return (-5); } while (0)
;
325 assert_return(length == req->length, -EIO)do { if (!(((__builtin_expect(!!(length == req->length),1)
)) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD,
("length == req->length"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 325, __PRETTY_FUNCTION__), 0))) return (-5); } while (0)
;
326
327 switch (req->type) {
328
329 case REQUEST_ADDRINFO: {
330 const AddrInfoRequest *ai_req = &packet->addrinfo_request;
331 struct addrinfo hints, *result = NULL((void*)0);
332 const char *node, *service;
333 int ret;
334
335 assert_return(length >= sizeof(AddrInfoRequest), -EBADMSG)do { if (!(((__builtin_expect(!!(length >= sizeof(AddrInfoRequest
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("length >= sizeof(AddrInfoRequest)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 335, __PRETTY_FUNCTION__), 0))) return (-74); } while (0)
;
336 assert_return(length == sizeof(AddrInfoRequest) + ai_req->node_len + ai_req->service_len, -EBADMSG)do { if (!(((__builtin_expect(!!(length == sizeof(AddrInfoRequest
) + ai_req->node_len + ai_req->service_len),1))) ? (1) :
(log_assert_failed_return_realm(LOG_REALM_SYSTEMD, ("length == sizeof(AddrInfoRequest) + ai_req->node_len + ai_req->service_len"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 336, __PRETTY_FUNCTION__
), 0))) return (-74); } while (0)
;
337
338 hints = (struct addrinfo) {
339 .ai_flags = ai_req->ai_flags,
340 .ai_family = ai_req->ai_family,
341 .ai_socktype = ai_req->ai_socktype,
342 .ai_protocol = ai_req->ai_protocol,
343 };
344
345 node = ai_req->node_len ? (const char*) ai_req + sizeof(AddrInfoRequest) : NULL((void*)0);
346 service = ai_req->service_len ? (const char*) ai_req + sizeof(AddrInfoRequest) + ai_req->node_len : NULL((void*)0);
347
348 ret = getaddrinfo(node, service,
349 ai_req->hints_valid ? &hints : NULL((void*)0),
350 &result);
351
352 /* send_addrinfo_reply() frees result */
353 return send_addrinfo_reply(out_fd, req->id, ret, result, errno(*__errno_location ()), h_errno(*__h_errno_location ()));
354 }
355
356 case REQUEST_NAMEINFO: {
357 const NameInfoRequest *ni_req = &packet->nameinfo_request;
358 char hostbuf[NI_MAXHOST1025], servbuf[NI_MAXSERV32];
359 union sockaddr_union sa;
360 int ret;
361
362 assert_return(length >= sizeof(NameInfoRequest), -EBADMSG)do { if (!(((__builtin_expect(!!(length >= sizeof(NameInfoRequest
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("length >= sizeof(NameInfoRequest)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 362, __PRETTY_FUNCTION__), 0))) return (-74); } while (0)
;
363 assert_return(length == sizeof(NameInfoRequest) + ni_req->sockaddr_len, -EBADMSG)do { if (!(((__builtin_expect(!!(length == sizeof(NameInfoRequest
) + ni_req->sockaddr_len),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("length == sizeof(NameInfoRequest) + ni_req->sockaddr_len"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 363, __PRETTY_FUNCTION__
), 0))) return (-74); } while (0)
;
364 assert_return(ni_req->sockaddr_len <= sizeof(sa), -EBADMSG)do { if (!(((__builtin_expect(!!(ni_req->sockaddr_len <=
sizeof(sa)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("ni_req->sockaddr_len <= sizeof(sa)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 364, __PRETTY_FUNCTION__), 0))) return (-74); } while (0)
;
365
366 memcpy(&sa, (const uint8_t *) ni_req + sizeof(NameInfoRequest), ni_req->sockaddr_len);
367
368 ret = getnameinfo(&sa.sa, ni_req->sockaddr_len,
369 ni_req->gethost ? hostbuf : NULL((void*)0), ni_req->gethost ? sizeof(hostbuf) : 0,
370 ni_req->getserv ? servbuf : NULL((void*)0), ni_req->getserv ? sizeof(servbuf) : 0,
371 ni_req->flags);
372
373 return send_nameinfo_reply(out_fd, req->id, ret,
374 ret == 0 && ni_req->gethost ? hostbuf : NULL((void*)0),
375 ret == 0 && ni_req->getserv ? servbuf : NULL((void*)0),
376 errno(*__errno_location ()), h_errno(*__h_errno_location ()));
377 }
378
379 case REQUEST_TERMINATE:
380 /* Quit */
381 return -ECONNRESET104;
382
383 default:
384 assert_not_reached("Unknown request")do { log_assert_failed_unreachable_realm(LOG_REALM_SYSTEMD, (
"Unknown request"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 384, __PRETTY_FUNCTION__); } while (0)
;
385 }
386
387 return 0;
388}
389
390static void* thread_worker(void *p) {
391 sd_resolve *resolve = p;
392
393 /* Assign a pretty name to this thread */
394 (void) pthread_setname_np(pthread_self(), "sd-resolve");
395
396 while (!resolve->dead) {
397 union {
398 Packet packet;
399 uint8_t space[BUFSIZE10240U];
400 } buf;
401 ssize_t length;
402
403 length = recv(resolve->fds[REQUEST_RECV_FD], &buf, sizeof buf, 0);
404 if (length < 0) {
405 if (errno(*__errno_location ()) == EINTR4)
406 continue;
407
408 break;
409 }
410 if (length == 0)
411 break;
412
413 if (handle_request(resolve->fds[RESPONSE_SEND_FD], &buf.packet, (size_t) length) < 0)
414 break;
415 }
416
417 send_died(resolve->fds[RESPONSE_SEND_FD]);
418
419 return NULL((void*)0);
420}
421
422static int start_threads(sd_resolve *resolve, unsigned extra) {
423 sigset_t ss, saved_ss;
424 unsigned n;
425 int r, k;
426
427 if (sigfillset(&ss) < 0)
428 return -errno(*__errno_location ());
429
430 /* No signals in forked off threads please. We set the mask before forking, so that the threads never exist
431 * with a different mask than a fully blocked one */
432 r = pthread_sigmask(SIG_BLOCK0, &ss, &saved_ss);
433 if (r > 0)
434 return -r;
435
436 n = resolve->n_outstanding + extra;
437 n = CLAMP(n, WORKERS_MIN, WORKERS_MAX)__extension__ ({ const typeof((n)) __unique_prefix_X6 = ((n))
; const typeof((1U)) __unique_prefix_LOW7 = ((1U)); const typeof
((16U)) __unique_prefix_HIGH8 = ((16U)); __unique_prefix_X6 >
__unique_prefix_HIGH8 ? __unique_prefix_HIGH8 : __unique_prefix_X6
< __unique_prefix_LOW7 ? __unique_prefix_LOW7 : __unique_prefix_X6
; })
;
438
439 while (resolve->n_valid_workers < n) {
440 r = pthread_create(&resolve->workers[resolve->n_valid_workers], NULL((void*)0), thread_worker, resolve);
441 if (r > 0) {
442 r = -r;
443 goto finish;
444 }
445
446 resolve->n_valid_workers++;
447 }
448
449 r = 0;
450
451finish:
452 k = pthread_sigmask(SIG_SETMASK2, &saved_ss, NULL((void*)0));
453 if (k > 0 && r >= 0)
454 r = -k;
455
456 return r;
457}
458
459static bool_Bool resolve_pid_changed(sd_resolve *r) {
460 assert(r)do { if ((__builtin_expect(!!(!(r)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("r"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 460, __PRETTY_FUNCTION__); } while (0)
;
461
462 /* We don't support people creating a resolver and keeping it
463 * around after fork(). Let's complain. */
464
465 return r->original_pid != getpid_cached();
466}
467
468_public___attribute__ ((visibility("default"))) int sd_resolve_new(sd_resolve **ret) {
469 _cleanup_(sd_resolve_unrefp)__attribute__((cleanup(sd_resolve_unrefp))) sd_resolve *resolve = NULL((void*)0);
470 int i;
471
472 assert_return(ret, -EINVAL)do { if (!(((__builtin_expect(!!(ret),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("ret"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 472, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
473
474 resolve = new0(sd_resolve, 1)((sd_resolve*) calloc((1), sizeof(sd_resolve)));
475 if (!resolve)
476 return -ENOMEM12;
477
478 resolve->n_ref = 1;
479 resolve->original_pid = getpid_cached();
480
481 for (i = 0; i < _FD_MAX; i++)
482 resolve->fds[i] = -1;
483
484 if (socketpair(PF_UNIX1, SOCK_DGRAMSOCK_DGRAM|SOCK_CLOEXECSOCK_CLOEXEC, 0, resolve->fds + REQUEST_RECV_FD) < 0)
485 return -errno(*__errno_location ());
486
487 if (socketpair(PF_UNIX1, SOCK_DGRAMSOCK_DGRAM|SOCK_CLOEXECSOCK_CLOEXEC, 0, resolve->fds + RESPONSE_RECV_FD) < 0)
488 return -errno(*__errno_location ());
489
490 for (i = 0; i < _FD_MAX; i++)
491 resolve->fds[i] = fd_move_above_stdio(resolve->fds[i]);
492
493 (void) fd_inc_sndbuf(resolve->fds[REQUEST_SEND_FD], QUERIES_MAX256U * BUFSIZE10240U);
494 (void) fd_inc_rcvbuf(resolve->fds[REQUEST_RECV_FD], QUERIES_MAX256U * BUFSIZE10240U);
495 (void) fd_inc_sndbuf(resolve->fds[RESPONSE_SEND_FD], QUERIES_MAX256U * BUFSIZE10240U);
496 (void) fd_inc_rcvbuf(resolve->fds[RESPONSE_RECV_FD], QUERIES_MAX256U * BUFSIZE10240U);
497
498 (void) fd_nonblock(resolve->fds[RESPONSE_RECV_FD], true1);
499
500 *ret = TAKE_PTR(resolve)({ typeof(resolve) _ptr_ = (resolve); (resolve) = ((void*)0);
_ptr_; })
;
501 return 0;
502}
503
504_public___attribute__ ((visibility("default"))) int sd_resolve_default(sd_resolve **ret) {
505
506 static thread_local__thread sd_resolve *default_resolve = NULL((void*)0);
507 sd_resolve *e = NULL((void*)0);
508 int r;
509
510 if (!ret)
511 return !!default_resolve;
512
513 if (default_resolve) {
514 *ret = sd_resolve_ref(default_resolve);
515 return 0;
516 }
517
518 r = sd_resolve_new(&e);
519 if (r < 0)
520 return r;
521
522 e->default_resolve_ptr = &default_resolve;
523 e->tid = gettid();
524 default_resolve = e;
525
526 *ret = e;
527 return 1;
528}
529
530_public___attribute__ ((visibility("default"))) int sd_resolve_get_tid(sd_resolve *resolve, pid_t *tid) {
531 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 531, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
532 assert_return(tid, -EINVAL)do { if (!(((__builtin_expect(!!(tid),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("tid"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 532, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
533 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 533, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
534
535 if (resolve->tid != 0) {
536 *tid = resolve->tid;
537 return 0;
538 }
539
540 if (resolve->event)
541 return sd_event_get_tid(resolve->event, tid);
542
543 return -ENXIO6;
544}
545
546static void resolve_free(sd_resolve *resolve) {
547 PROTECT_ERRNO__attribute__((cleanup(_reset_errno_))) __attribute__((unused
)) int _saved_errno_ = (*__errno_location ())
;
548 sd_resolve_query *q;
549 unsigned i;
550
551 assert(resolve)do { if ((__builtin_expect(!!(!(resolve)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 551, __PRETTY_FUNCTION__); } while (0)
;
9
Taking false branch
10
Loop condition is false. Exiting loop
552
553 while ((q = resolve->queries)) {
11
Loop condition is true. Entering loop body
28
Loop condition is true. Entering loop body
554 assert(q->floating)do { if ((__builtin_expect(!!(!(q->floating)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q->floating"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 554, __PRETTY_FUNCTION__); } while (0)
;
12
Assuming field 'floating' is true
13
Taking false branch
14
Loop condition is false. Exiting loop
29
Use of memory after it is freed
555 resolve_query_disconnect(q);
556 sd_resolve_query_unref(q);
15
Calling 'sd_resolve_query_unref'
27
Returning; memory was released via 1st parameter
557 }
558
559 if (resolve->default_resolve_ptr)
560 *(resolve->default_resolve_ptr) = NULL((void*)0);
561
562 resolve->dead = true1;
563
564 sd_resolve_detach_event(resolve);
565
566 if (resolve->fds[REQUEST_SEND_FD] >= 0) {
567
568 RHeader req = {
569 .type = REQUEST_TERMINATE,
570 .length = sizeof req,
571 };
572
573 /* Send one termination packet for each worker */
574 for (i = 0; i < resolve->n_valid_workers; i++)
575 (void) send(resolve->fds[REQUEST_SEND_FD], &req, req.length, MSG_NOSIGNALMSG_NOSIGNAL);
576 }
577
578 /* Now terminate them and wait until they are gone.
579 If we get an error than most likely the thread already exited. */
580 for (i = 0; i < resolve->n_valid_workers; i++)
581 (void) pthread_join(resolve->workers[i], NULL((void*)0));
582
583 /* Close all communication channels */
584 close_many(resolve->fds, _FD_MAX);
585 free(resolve);
586}
587
588_public___attribute__ ((visibility("default"))) sd_resolve* sd_resolve_ref(sd_resolve *resolve) {
589 assert_return(resolve, NULL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 589, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
590
591 assert(resolve->n_ref >= 1)do { if ((__builtin_expect(!!(!(resolve->n_ref >= 1)),0
))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("resolve->n_ref >= 1"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 591, __PRETTY_FUNCTION__
); } while (0)
;
592 resolve->n_ref++;
593
594 return resolve;
595}
596
597_public___attribute__ ((visibility("default"))) sd_resolve* sd_resolve_unref(sd_resolve *resolve) {
598 if (!resolve)
1
Assuming 'resolve' is non-null
2
Taking false branch
599 return NULL((void*)0);
600
601 assert(resolve->n_ref >= 1)do { if ((__builtin_expect(!!(!(resolve->n_ref >= 1)),0
))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("resolve->n_ref >= 1"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 601, __PRETTY_FUNCTION__
); } while (0)
;
3
Assuming field 'n_ref' is >= 1
4
Taking false branch
5
Loop condition is false. Exiting loop
602 resolve->n_ref--;
603
604 if (resolve->n_ref <= 0)
6
Assuming field 'n_ref' is <= 0
7
Taking true branch
605 resolve_free(resolve);
8
Calling 'resolve_free'
606
607 return NULL((void*)0);
608}
609
610_public___attribute__ ((visibility("default"))) int sd_resolve_get_fd(sd_resolve *resolve) {
611 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 611, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
612 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 612, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
613
614 return resolve->fds[RESPONSE_RECV_FD];
615}
616
617_public___attribute__ ((visibility("default"))) int sd_resolve_get_events(sd_resolve *resolve) {
618 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 618, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
619 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 619, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
620
621 return resolve->n_queries > resolve->n_done ? POLLIN0x001 : 0;
622}
623
624_public___attribute__ ((visibility("default"))) int sd_resolve_get_timeout(sd_resolve *resolve, uint64_t *usec) {
625 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 625, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
626 assert_return(usec, -EINVAL)do { if (!(((__builtin_expect(!!(usec),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("usec"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 626, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
627 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 627, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
628
629 *usec = (uint64_t) -1;
630 return 0;
631}
632
633static sd_resolve_query *lookup_query(sd_resolve *resolve, unsigned id) {
634 sd_resolve_query *q;
635
636 assert(resolve)do { if ((__builtin_expect(!!(!(resolve)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 636, __PRETTY_FUNCTION__); } while (0)
;
637
638 q = resolve->query_array[id % QUERIES_MAX256U];
639 if (q)
640 if (q->id == id)
641 return q;
642
643 return NULL((void*)0);
644}
645
646static int complete_query(sd_resolve *resolve, sd_resolve_query *q) {
647 int r;
648
649 assert(q)do { if ((__builtin_expect(!!(!(q)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 649, __PRETTY_FUNCTION__); } while (0)
;
650 assert(!q->done)do { if ((__builtin_expect(!!(!(!q->done)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("!q->done"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 650, __PRETTY_FUNCTION__); } while (0)
;
651 assert(q->resolve == resolve)do { if ((__builtin_expect(!!(!(q->resolve == resolve)),0)
)) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("q->resolve == resolve"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 651, __PRETTY_FUNCTION__
); } while (0)
;
652
653 q->done = true1;
654 resolve->n_done++;
655
656 resolve->current = sd_resolve_query_ref(q);
657
658 switch (q->type) {
659
660 case REQUEST_ADDRINFO:
661 r = getaddrinfo_done(q);
662 break;
663
664 case REQUEST_NAMEINFO:
665 r = getnameinfo_done(q);
666 break;
667
668 default:
669 assert_not_reached("Cannot complete unknown query type")do { log_assert_failed_unreachable_realm(LOG_REALM_SYSTEMD, (
"Cannot complete unknown query type"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 669, __PRETTY_FUNCTION__); } while (0)
;
670 }
671
672 resolve->current = NULL((void*)0);
673
674 if (q->floating) {
675 resolve_query_disconnect(q);
676 sd_resolve_query_unref(q);
677 }
678
679 sd_resolve_query_unref(q);
680
681 return r;
682}
683
684static int unserialize_addrinfo(const void **p, size_t *length, struct addrinfo **ret_ai) {
685 AddrInfoSerialization s;
686 size_t l;
687 struct addrinfo *ai;
688
689 assert(p)do { if ((__builtin_expect(!!(!(p)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("p"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 689, __PRETTY_FUNCTION__); } while (0)
;
690 assert(*p)do { if ((__builtin_expect(!!(!(*p)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("*p"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 690, __PRETTY_FUNCTION__); } while (0)
;
691 assert(ret_ai)do { if ((__builtin_expect(!!(!(ret_ai)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("ret_ai"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 691, __PRETTY_FUNCTION__); } while (0)
;
692 assert(length)do { if ((__builtin_expect(!!(!(length)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("length"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 692, __PRETTY_FUNCTION__); } while (0)
;
693
694 if (*length < sizeof(AddrInfoSerialization))
695 return -EBADMSG74;
696
697 memcpy(&s, *p, sizeof(s));
698
699 l = sizeof(AddrInfoSerialization) + s.ai_addrlen + s.canonname_len;
700 if (*length < l)
701 return -EBADMSG74;
702
703 ai = new0(struct addrinfo, 1)((struct addrinfo*) calloc((1), sizeof(struct addrinfo)));
704 if (!ai)
705 return -ENOMEM12;
706
707 ai->ai_flags = s.ai_flags;
708 ai->ai_family = s.ai_family;
709 ai->ai_socktype = s.ai_socktype;
710 ai->ai_protocol = s.ai_protocol;
711 ai->ai_addrlen = s.ai_addrlen;
712
713 if (s.ai_addrlen > 0) {
714 ai->ai_addr = memdup((const uint8_t*) *p + sizeof(AddrInfoSerialization), s.ai_addrlen);
715 if (!ai->ai_addr) {
716 free(ai);
717 return -ENOMEM12;
718 }
719 }
720
721 if (s.canonname_len > 0) {
722 ai->ai_canonname = memdup((const uint8_t*) *p + sizeof(AddrInfoSerialization) + s.ai_addrlen, s.canonname_len);
723 if (!ai->ai_canonname) {
724 free(ai->ai_addr);
725 free(ai);
726 return -ENOMEM12;
727 }
728 }
729
730 *length -= l;
731 *ret_ai = ai;
732 *p = ((const uint8_t*) *p) + l;
733
734 return 0;
735}
736
737static int handle_response(sd_resolve *resolve, const Packet *packet, size_t length) {
738 const RHeader *resp;
739 sd_resolve_query *q;
740 int r;
741
742 assert(resolve)do { if ((__builtin_expect(!!(!(resolve)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 742, __PRETTY_FUNCTION__); } while (0)
;
743 assert(packet)do { if ((__builtin_expect(!!(!(packet)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("packet"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 743, __PRETTY_FUNCTION__); } while (0)
;
744
745 resp = &packet->rheader;
746 assert_return(length >= sizeof(RHeader), -EIO)do { if (!(((__builtin_expect(!!(length >= sizeof(RHeader)
),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("length >= sizeof(RHeader)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 746, __PRETTY_FUNCTION__), 0))) return (-5); } while (0)
;
747 assert_return(length == resp->length, -EIO)do { if (!(((__builtin_expect(!!(length == resp->length),1
))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("length == resp->length"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 747, __PRETTY_FUNCTION__), 0))) return (-5); } while (0)
;
748
749 if (resp->type == RESPONSE_DIED) {
750 resolve->dead = true1;
751 return 0;
752 }
753
754 assert(resolve->n_outstanding > 0)do { if ((__builtin_expect(!!(!(resolve->n_outstanding >
0)),0))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("resolve->n_outstanding > 0"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 754, __PRETTY_FUNCTION__
); } while (0)
;
755 resolve->n_outstanding--;
756
757 q = lookup_query(resolve, resp->id);
758 if (!q)
759 return 0;
760
761 switch (resp->type) {
762
763 case RESPONSE_ADDRINFO: {
764 const AddrInfoResponse *ai_resp = &packet->addrinfo_response;
765 const void *p;
766 size_t l;
767 struct addrinfo *prev = NULL((void*)0);
768
769 assert_return(length >= sizeof(AddrInfoResponse), -EBADMSG)do { if (!(((__builtin_expect(!!(length >= sizeof(AddrInfoResponse
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("length >= sizeof(AddrInfoResponse)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 769, __PRETTY_FUNCTION__), 0))) return (-74); } while (0)
;
770 assert_return(q->type == REQUEST_ADDRINFO, -EBADMSG)do { if (!(((__builtin_expect(!!(q->type == REQUEST_ADDRINFO
),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("q->type == REQUEST_ADDRINFO"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 770, __PRETTY_FUNCTION__), 0))) return (-74); } while (0)
;
771
772 query_assign_errno(q, ai_resp->ret, ai_resp->_errno, ai_resp->_h_errno);
773
774 l = length - sizeof(AddrInfoResponse);
775 p = (const uint8_t*) resp + sizeof(AddrInfoResponse);
776
777 while (l > 0 && p) {
778 struct addrinfo *ai = NULL((void*)0);
779
780 r = unserialize_addrinfo(&p, &l, &ai);
781 if (r < 0) {
782 query_assign_errno(q, EAI_SYSTEM-11, r, 0);
783 freeaddrinfo(q->addrinfo);
784 q->addrinfo = NULL((void*)0);
785 break;
786 }
787
788 if (prev)
789 prev->ai_next = ai;
790 else
791 q->addrinfo = ai;
792
793 prev = ai;
794 }
795
796 return complete_query(resolve, q);
797 }
798
799 case RESPONSE_NAMEINFO: {
800 const NameInfoResponse *ni_resp = &packet->nameinfo_response;
801
802 assert_return(length >= sizeof(NameInfoResponse), -EBADMSG)do { if (!(((__builtin_expect(!!(length >= sizeof(NameInfoResponse
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("length >= sizeof(NameInfoResponse)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 802, __PRETTY_FUNCTION__), 0))) return (-74); } while (0)
;
803 assert_return(q->type == REQUEST_NAMEINFO, -EBADMSG)do { if (!(((__builtin_expect(!!(q->type == REQUEST_NAMEINFO
),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("q->type == REQUEST_NAMEINFO"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 803, __PRETTY_FUNCTION__), 0))) return (-74); } while (0)
;
804
805 if (ni_resp->hostlen > DNS_HOSTNAME_MAX253 ||
806 ni_resp->servlen > DNS_HOSTNAME_MAX253 ||
807 sizeof(NameInfoResponse) + ni_resp->hostlen + ni_resp->servlen > length)
808 query_assign_errno(q, EAI_SYSTEM-11, EIO5, 0);
809 else {
810 query_assign_errno(q, ni_resp->ret, ni_resp->_errno, ni_resp->_h_errno);
811
812 if (ni_resp->hostlen > 0) {
813 q->host = strndup((const char*) ni_resp + sizeof(NameInfoResponse),
814 ni_resp->hostlen-1);
815 if (!q->host)
816 query_assign_errno(q, EAI_MEMORY-10, ENOMEM12, 0);
817 }
818
819 if (ni_resp->servlen > 0) {
820 q->serv = strndup((const char*) ni_resp + sizeof(NameInfoResponse) + ni_resp->hostlen,
821 ni_resp->servlen-1);
822 if (!q->serv)
823 query_assign_errno(q, EAI_MEMORY-10, ENOMEM12, 0);
824 }
825 }
826
827 return complete_query(resolve, q);
828 }
829
830 default:
831 return 0;
832 }
833}
834
835_public___attribute__ ((visibility("default"))) int sd_resolve_process(sd_resolve *resolve) {
836 RESOLVE_DONT_DESTROY(resolve)__attribute__((cleanup(sd_resolve_unrefp))) __attribute__ ((unused
)) sd_resolve *_dont_destroy_resolve = sd_resolve_ref(resolve
)
;
837
838 union {
839 Packet packet;
840 uint8_t space[BUFSIZE10240U];
841 } buf;
842 ssize_t l;
843 int r;
844
845 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 845, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
846 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 846, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
847
848 /* We don't allow recursively invoking sd_resolve_process(). */
849 assert_return(!resolve->current, -EBUSY)do { if (!(((__builtin_expect(!!(!resolve->current),1))) ?
(1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD, ("!resolve->current"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 849, __PRETTY_FUNCTION__
), 0))) return (-16); } while (0)
;
850
851 l = recv(resolve->fds[RESPONSE_RECV_FD], &buf, sizeof buf, 0);
852 if (l < 0) {
853 if (errno(*__errno_location ()) == EAGAIN11)
854 return 0;
855
856 return -errno(*__errno_location ());
857 }
858 if (l == 0)
859 return -ECONNREFUSED111;
860
861 r = handle_response(resolve, &buf.packet, (size_t) l);
862 if (r < 0)
863 return r;
864
865 return 1;
866}
867
868_public___attribute__ ((visibility("default"))) int sd_resolve_wait(sd_resolve *resolve, uint64_t timeout_usec) {
869 int r;
870
871 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 871, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
872 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 872, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
873
874 if (resolve->n_done >= resolve->n_queries)
875 return 0;
876
877 do {
878 r = fd_wait_for_event(resolve->fds[RESPONSE_RECV_FD], POLLIN0x001, timeout_usec);
879 } while (r == -EINTR4);
880
881 if (r < 0)
882 return r;
883 if (r == 0)
884 return -ETIMEDOUT110;
885
886 return sd_resolve_process(resolve);
887}
888
889static int alloc_query(sd_resolve *resolve, bool_Bool floating, sd_resolve_query **_q) {
890 sd_resolve_query *q;
891 int r;
892
893 assert(resolve)do { if ((__builtin_expect(!!(!(resolve)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 893, __PRETTY_FUNCTION__); } while (0)
;
894 assert(_q)do { if ((__builtin_expect(!!(!(_q)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("_q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 894, __PRETTY_FUNCTION__); } while (0)
;
895
896 if (resolve->n_queries >= QUERIES_MAX256U)
897 return -ENOBUFS105;
898
899 r = start_threads(resolve, 1);
900 if (r < 0)
901 return r;
902
903 while (resolve->query_array[resolve->current_id % QUERIES_MAX256U])
904 resolve->current_id++;
905
906 q = resolve->query_array[resolve->current_id % QUERIES_MAX256U] = new0(sd_resolve_query, 1)((sd_resolve_query*) calloc((1), sizeof(sd_resolve_query)));
907 if (!q)
908 return -ENOMEM12;
909
910 q->n_ref = 1;
911 q->resolve = resolve;
912 q->floating = floating;
913 q->id = resolve->current_id++;
914
915 if (!floating)
916 sd_resolve_ref(resolve);
917
918 LIST_PREPEND(queries, resolve->queries, q)do { typeof(*(resolve->queries)) **_head = &(resolve->
queries), *_item = (q); do { if ((__builtin_expect(!!(!(_item
)),0))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("_item"),
"../src/libsystemd/sd-resolve/sd-resolve.c", 918, __PRETTY_FUNCTION__
); } while (0); if ((_item->queries_next = *_head)) _item->
queries_next->queries_prev = _item; _item->queries_prev
= ((void*)0); *_head = _item; } while (0)
;
919 resolve->n_queries++;
920
921 *_q = q;
922 return 0;
923}
924
925_public___attribute__ ((visibility("default"))) int sd_resolve_getaddrinfo(
926 sd_resolve *resolve,
927 sd_resolve_query **_q,
928 const char *node, const char *service,
929 const struct addrinfo *hints,
930 sd_resolve_getaddrinfo_handler_t callback, void *userdata) {
931
932 _cleanup_(sd_resolve_query_unrefp)__attribute__((cleanup(sd_resolve_query_unrefp))) sd_resolve_query *q = NULL((void*)0);
933 AddrInfoRequest req;
934 struct iovec iov[3];
935 struct msghdr mh = {};
936 int r;
937 size_t node_len, service_len;
938
939 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 939, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
940 assert_return(node || service, -EINVAL)do { if (!(((__builtin_expect(!!(node || service),1))) ? (1) :
(log_assert_failed_return_realm(LOG_REALM_SYSTEMD, ("node || service"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 940, __PRETTY_FUNCTION__
), 0))) return (-22); } while (0)
;
941 assert_return(callback, -EINVAL)do { if (!(((__builtin_expect(!!(callback),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("callback"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 941, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
942 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 942, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
943
944 r = alloc_query(resolve, !_q, &q);
945 if (r < 0)
946 return r;
947
948 q->type = REQUEST_ADDRINFO;
949 q->getaddrinfo_handler = callback;
950 q->userdata = userdata;
951
952 node_len = node ? strlen(node) + 1 : 0;
953 service_len = service ? strlen(service) + 1 : 0;
954
955 req = (AddrInfoRequest) {
956 .node_len = node_len,
957 .service_len = service_len,
958
959 .header.id = q->id,
960 .header.type = REQUEST_ADDRINFO,
961 .header.length = sizeof(AddrInfoRequest) + node_len + service_len,
962
963 .hints_valid = hints,
964 .ai_flags = hints ? hints->ai_flags : 0,
965 .ai_family = hints ? hints->ai_family : 0,
966 .ai_socktype = hints ? hints->ai_socktype : 0,
967 .ai_protocol = hints ? hints->ai_protocol : 0,
968 };
969
970 iov[mh.msg_iovlen++] = (struct iovec) { .iov_base = &req, .iov_len = sizeof(AddrInfoRequest) };
971 if (node)
972 iov[mh.msg_iovlen++] = (struct iovec) { .iov_base = (void*) node, .iov_len = req.node_len };
973 if (service)
974 iov[mh.msg_iovlen++] = (struct iovec) { .iov_base = (void*) service, .iov_len = req.service_len };
975 mh.msg_iov = iov;
976
977 if (sendmsg(resolve->fds[REQUEST_SEND_FD], &mh, MSG_NOSIGNALMSG_NOSIGNAL) < 0)
978 return -errno(*__errno_location ());
979
980 resolve->n_outstanding++;
981
982 if (_q)
983 *_q = q;
984 TAKE_PTR(q)({ typeof(q) _ptr_ = (q); (q) = ((void*)0); _ptr_; });
985
986 return 0;
987}
988
989static int getaddrinfo_done(sd_resolve_query* q) {
990 assert(q)do { if ((__builtin_expect(!!(!(q)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 990, __PRETTY_FUNCTION__); } while (0)
;
991 assert(q->done)do { if ((__builtin_expect(!!(!(q->done)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q->done"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 991, __PRETTY_FUNCTION__); } while (0)
;
992 assert(q->getaddrinfo_handler)do { if ((__builtin_expect(!!(!(q->getaddrinfo_handler)),0
))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("q->getaddrinfo_handler"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 992, __PRETTY_FUNCTION__
); } while (0)
;
993
994 errno(*__errno_location ()) = q->_errno;
995 h_errno(*__h_errno_location ()) = q->_h_errno;
996
997 return q->getaddrinfo_handler(q, q->ret, q->addrinfo, q->userdata);
998}
999
1000_public___attribute__ ((visibility("default"))) int sd_resolve_getnameinfo(
1001 sd_resolve *resolve,
1002 sd_resolve_query**_q,
1003 const struct sockaddr *sa, socklen_t salen,
1004 int flags,
1005 uint64_t get,
1006 sd_resolve_getnameinfo_handler_t callback,
1007 void *userdata) {
1008
1009 _cleanup_(sd_resolve_query_unrefp)__attribute__((cleanup(sd_resolve_query_unrefp))) sd_resolve_query *q = NULL((void*)0);
1010 NameInfoRequest req;
1011 struct iovec iov[2];
1012 struct msghdr mh;
1013 int r;
1014
1015 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1015, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1016 assert_return(sa, -EINVAL)do { if (!(((__builtin_expect(!!(sa),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("sa"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1016, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1017 assert_return(salen >= sizeof(struct sockaddr), -EINVAL)do { if (!(((__builtin_expect(!!(salen >= sizeof(struct sockaddr
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("salen >= sizeof(struct sockaddr)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1017, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1018 assert_return(salen <= sizeof(union sockaddr_union), -EINVAL)do { if (!(((__builtin_expect(!!(salen <= sizeof(union sockaddr_union
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("salen <= sizeof(union sockaddr_union)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1018, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1019 assert_return((get & ~SD_RESOLVE_GET_BOTH) == 0, -EINVAL)do { if (!(((__builtin_expect(!!((get & ~SD_RESOLVE_GET_BOTH
) == 0),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("(get & ~SD_RESOLVE_GET_BOTH) == 0"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1019, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1020 assert_return(callback, -EINVAL)do { if (!(((__builtin_expect(!!(callback),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("callback"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1020, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1021 assert_return(!resolve_pid_changed(resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1021, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
1022
1023 r = alloc_query(resolve, !_q, &q);
1024 if (r < 0)
1025 return r;
1026
1027 q->type = REQUEST_NAMEINFO;
1028 q->getnameinfo_handler = callback;
1029 q->userdata = userdata;
1030
1031 req = (NameInfoRequest) {
1032 .header.id = q->id,
1033 .header.type = REQUEST_NAMEINFO,
1034 .header.length = sizeof(NameInfoRequest) + salen,
1035
1036 .flags = flags,
1037 .sockaddr_len = salen,
1038 .gethost = !!(get & SD_RESOLVE_GET_HOST),
1039 .getserv = !!(get & SD_RESOLVE_GET_SERVICE),
1040 };
1041
1042 iov[0] = (struct iovec) { .iov_base = &req, .iov_len = sizeof(NameInfoRequest) };
1043 iov[1] = (struct iovec) { .iov_base = (void*) sa, .iov_len = salen };
1044
1045 mh = (struct msghdr) { .msg_iov = iov, .msg_iovlen = ELEMENTSOF(iov)__extension__ (__builtin_choose_expr( !__builtin_types_compatible_p
(typeof(iov), typeof(&*(iov))), sizeof(iov)/sizeof((iov)[
0]), ((void)0)))
};
1046
1047 if (sendmsg(resolve->fds[REQUEST_SEND_FD], &mh, MSG_NOSIGNALMSG_NOSIGNAL) < 0)
1048 return -errno(*__errno_location ());
1049
1050 if (_q)
1051 *_q = q;
1052
1053 resolve->n_outstanding++;
1054 TAKE_PTR(q)({ typeof(q) _ptr_ = (q); (q) = ((void*)0); _ptr_; });
1055
1056 return 0;
1057}
1058
1059static int getnameinfo_done(sd_resolve_query *q) {
1060
1061 assert(q)do { if ((__builtin_expect(!!(!(q)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1061, __PRETTY_FUNCTION__); } while (0)
;
1062 assert(q->done)do { if ((__builtin_expect(!!(!(q->done)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q->done"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1062, __PRETTY_FUNCTION__); } while (0)
;
1063 assert(q->getnameinfo_handler)do { if ((__builtin_expect(!!(!(q->getnameinfo_handler)),0
))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("q->getnameinfo_handler"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 1063, __PRETTY_FUNCTION__
); } while (0)
;
1064
1065 errno(*__errno_location ()) = q->_errno;
1066 h_errno(*__h_errno_location ()) = q->_h_errno;
1067
1068 return q->getnameinfo_handler(q, q->ret, q->host, q->serv, q->userdata);
1069}
1070
1071_public___attribute__ ((visibility("default"))) sd_resolve_query* sd_resolve_query_ref(sd_resolve_query *q) {
1072 assert_return(q, NULL)do { if (!(((__builtin_expect(!!(q),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1072, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1073
1074 assert(q->n_ref >= 1)do { if ((__builtin_expect(!!(!(q->n_ref >= 1)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q->n_ref >= 1"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1074, __PRETTY_FUNCTION__); } while (0)
;
1075 q->n_ref++;
1076
1077 return q;
1078}
1079
1080static void resolve_freeaddrinfo(struct addrinfo *ai) {
1081 while (ai) {
1082 struct addrinfo *next = ai->ai_next;
1083
1084 free(ai->ai_addr);
1085 free(ai->ai_canonname);
1086 free(ai);
1087 ai = next;
1088 }
1089}
1090
1091static void resolve_query_disconnect(sd_resolve_query *q) {
1092 sd_resolve *resolve;
1093 unsigned i;
1094
1095 assert(q)do { if ((__builtin_expect(!!(!(q)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1095, __PRETTY_FUNCTION__); } while (0)
;
1096
1097 if (!q->resolve)
1098 return;
1099
1100 resolve = q->resolve;
1101 assert(resolve->n_queries > 0)do { if ((__builtin_expect(!!(!(resolve->n_queries > 0)
),0))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("resolve->n_queries > 0"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 1101, __PRETTY_FUNCTION__
); } while (0)
;
1102
1103 if (q->done) {
1104 assert(resolve->n_done > 0)do { if ((__builtin_expect(!!(!(resolve->n_done > 0)),0
))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("resolve->n_done > 0"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 1104, __PRETTY_FUNCTION__
); } while (0)
;
1105 resolve->n_done--;
1106 }
1107
1108 i = q->id % QUERIES_MAX256U;
1109 assert(resolve->query_array[i] == q)do { if ((__builtin_expect(!!(!(resolve->query_array[i] ==
q)),0))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("resolve->query_array[i] == q"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 1109, __PRETTY_FUNCTION__
); } while (0)
;
1110 resolve->query_array[i] = NULL((void*)0);
1111 LIST_REMOVE(queries, resolve->queries, q)do { typeof(*(resolve->queries)) **_head = &(resolve->
queries), *_item = (q); do { if ((__builtin_expect(!!(!(_item
)),0))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("_item"),
"../src/libsystemd/sd-resolve/sd-resolve.c", 1111, __PRETTY_FUNCTION__
); } while (0); if (_item->queries_next) _item->queries_next
->queries_prev = _item->queries_prev; if (_item->queries_prev
) _item->queries_prev->queries_next = _item->queries_next
; else { do { if ((__builtin_expect(!!(!(*_head == _item)),0)
)) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("*_head == _item"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 1111, __PRETTY_FUNCTION__
); } while (0); *_head = _item->queries_next; } _item->
queries_next = _item->queries_prev = ((void*)0); } while (
0)
;
1112 resolve->n_queries--;
1113
1114 q->resolve = NULL((void*)0);
1115 if (!q->floating)
1116 sd_resolve_unref(resolve);
1117}
1118
1119static void resolve_query_free(sd_resolve_query *q) {
1120 assert(q)do { if ((__builtin_expect(!!(!(q)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1120, __PRETTY_FUNCTION__); } while (0)
;
23
Taking false branch
24
Loop condition is false. Exiting loop
1121
1122 resolve_query_disconnect(q);
1123
1124 resolve_freeaddrinfo(q->addrinfo);
1125 free(q->host);
1126 free(q->serv);
1127 free(q);
25
Memory is released
1128}
1129
1130_public___attribute__ ((visibility("default"))) sd_resolve_query* sd_resolve_query_unref(sd_resolve_query* q) {
1131 if (!q
15.1
'q' is non-null
)
16
Taking false branch
1132 return NULL((void*)0);
1133
1134 assert(q->n_ref >= 1)do { if ((__builtin_expect(!!(!(q->n_ref >= 1)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("q->n_ref >= 1"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1134, __PRETTY_FUNCTION__); } while (0)
;
17
Assuming field 'n_ref' is >= 1
18
Taking false branch
19
Loop condition is false. Exiting loop
1135 q->n_ref--;
1136
1137 if (q->n_ref <= 0)
20
Assuming field 'n_ref' is <= 0
21
Taking true branch
1138 resolve_query_free(q);
22
Calling 'resolve_query_free'
26
Returning; memory was released via 1st parameter
1139
1140 return NULL((void*)0);
1141}
1142
1143_public___attribute__ ((visibility("default"))) int sd_resolve_query_is_done(sd_resolve_query *q) {
1144 assert_return(q, -EINVAL)do { if (!(((__builtin_expect(!!(q),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1144, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1145 assert_return(!resolve_pid_changed(q->resolve), -ECHILD)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(q->resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(q->resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1145, __PRETTY_FUNCTION__), 0))) return (-10); } while (0)
;
1146
1147 return q->done;
1148}
1149
1150_public___attribute__ ((visibility("default"))) void* sd_resolve_query_set_userdata(sd_resolve_query *q, void *userdata) {
1151 void *ret;
1152
1153 assert_return(q, NULL)do { if (!(((__builtin_expect(!!(q),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1153, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1154 assert_return(!resolve_pid_changed(q->resolve), NULL)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(q->resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(q->resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1154, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1155
1156 ret = q->userdata;
1157 q->userdata = userdata;
1158
1159 return ret;
1160}
1161
1162_public___attribute__ ((visibility("default"))) void* sd_resolve_query_get_userdata(sd_resolve_query *q) {
1163 assert_return(q, NULL)do { if (!(((__builtin_expect(!!(q),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1163, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1164 assert_return(!resolve_pid_changed(q->resolve), NULL)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(q->resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(q->resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1164, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1165
1166 return q->userdata;
1167}
1168
1169_public___attribute__ ((visibility("default"))) sd_resolve *sd_resolve_query_get_resolve(sd_resolve_query *q) {
1170 assert_return(q, NULL)do { if (!(((__builtin_expect(!!(q),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("q"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1170, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1171 assert_return(!resolve_pid_changed(q->resolve), NULL)do { if (!(((__builtin_expect(!!(!resolve_pid_changed(q->resolve
)),1))) ? (1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD
, ("!resolve_pid_changed(q->resolve)"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1171, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1172
1173 return q->resolve;
1174}
1175
1176static int io_callback(sd_event_source *s, int fd, uint32_t revents, void *userdata) {
1177 sd_resolve *resolve = userdata;
1178 int r;
1179
1180 assert(resolve)do { if ((__builtin_expect(!!(!(resolve)),0))) log_assert_failed_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1180, __PRETTY_FUNCTION__); } while (0)
;
1181
1182 r = sd_resolve_process(resolve);
1183 if (r < 0)
1184 return r;
1185
1186 return 1;
1187}
1188
1189_public___attribute__ ((visibility("default"))) int sd_resolve_attach_event(sd_resolve *resolve, sd_event *event, int64_t priority) {
1190 int r;
1191
1192 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1192, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1193 assert_return(!resolve->event, -EBUSY)do { if (!(((__builtin_expect(!!(!resolve->event),1))) ? (
1) : (log_assert_failed_return_realm(LOG_REALM_SYSTEMD, ("!resolve->event"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 1193, __PRETTY_FUNCTION__
), 0))) return (-16); } while (0)
;
1194
1195 assert(!resolve->event_source)do { if ((__builtin_expect(!!(!(!resolve->event_source)),0
))) log_assert_failed_realm(LOG_REALM_SYSTEMD, ("!resolve->event_source"
), "../src/libsystemd/sd-resolve/sd-resolve.c", 1195, __PRETTY_FUNCTION__
); } while (0)
;
1196
1197 if (event)
1198 resolve->event = sd_event_ref(event);
1199 else {
1200 r = sd_event_default(&resolve->event);
1201 if (r < 0)
1202 return r;
1203 }
1204
1205 r = sd_event_add_io(resolve->event, &resolve->event_source, resolve->fds[RESPONSE_RECV_FD], POLLIN0x001, io_callback, resolve);
1206 if (r < 0)
1207 goto fail;
1208
1209 r = sd_event_source_set_priority(resolve->event_source, priority);
1210 if (r < 0)
1211 goto fail;
1212
1213 return 0;
1214
1215fail:
1216 sd_resolve_detach_event(resolve);
1217 return r;
1218}
1219
1220_public___attribute__ ((visibility("default"))) int sd_resolve_detach_event(sd_resolve *resolve) {
1221 assert_return(resolve, -EINVAL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1221, __PRETTY_FUNCTION__), 0))) return (-22); } while (0)
;
1222
1223 if (!resolve->event)
1224 return 0;
1225
1226 if (resolve->event_source) {
1227 sd_event_source_set_enabled(resolve->event_source, SD_EVENT_OFF);
1228 resolve->event_source = sd_event_source_unref(resolve->event_source);
1229 }
1230
1231 resolve->event = sd_event_unref(resolve->event);
1232 return 1;
1233}
1234
1235_public___attribute__ ((visibility("default"))) sd_event *sd_resolve_get_event(sd_resolve *resolve) {
1236 assert_return(resolve, NULL)do { if (!(((__builtin_expect(!!(resolve),1))) ? (1) : (log_assert_failed_return_realm
(LOG_REALM_SYSTEMD, ("resolve"), "../src/libsystemd/sd-resolve/sd-resolve.c"
, 1236, __PRETTY_FUNCTION__), 0))) return (((void*)0)); } while
(0)
;
1237
1238 return resolve->event;
1239}