diff options
Diffstat (limited to '')
-rw-r--r-- | man3/getaddrinfo_a.3 | 109 |
1 files changed, 71 insertions, 38 deletions
diff --git a/man3/getaddrinfo_a.3 b/man3/getaddrinfo_a.3 index 4b891ab..fe27b6c 100644 --- a/man3/getaddrinfo_a.3 +++ b/man3/getaddrinfo_a.3 @@ -8,7 +8,7 @@ .\" References: http://people.redhat.com/drepper/asynchnl.pdf, .\" http://www.imperialviolet.org/2005/06/01/asynchronous-dns-lookups-with-glibc.html .\" -.TH getaddrinfo_a 3 2023-07-20 "Linux man-pages 6.05.01" +.TH getaddrinfo_a 3 2023-10-31 "Linux man-pages 6.7" .SH NAME getaddrinfo_a, gai_suspend, gai_error, gai_cancel \- asynchronous network address and service translation @@ -19,12 +19,12 @@ Asynchronous name lookup library .nf .BR "#define _GNU_SOURCE" " /* See feature_test_macros(7) */" .B #include <netdb.h> -.PP +.P .BI "int getaddrinfo_a(int " mode ", struct gaicb *" list [restrict], .BI " int " nitems ", struct sigevent *restrict " sevp ); .BI "int gai_suspend(const struct gaicb *const " list "[], int " nitems , .BI " const struct timespec *" timeout ); -.PP +.P .BI "int gai_error(struct gaicb *" req ); .BI "int gai_cancel(struct gaicb *" req ); .fi @@ -35,7 +35,7 @@ function performs the same task as .BR getaddrinfo (3), but allows multiple name look-ups to be performed asynchronously, with optional notification on completion of look-up operations. -.PP +.P The .I mode argument has one of the following values: @@ -51,7 +51,7 @@ and the requests are resolved in the background. See the discussion of the .I sevp argument below. -.PP +.P The array .I list specifies the look-up requests to process. @@ -66,7 +66,7 @@ are ignored. Each request is described by a .I gaicb structure, defined as follows: -.PP +.P .in +4n .EX struct gaicb { @@ -77,7 +77,7 @@ struct gaicb { }; .EE .in -.PP +.P The elements of this structure correspond to the arguments of .BR getaddrinfo (3). Thus, @@ -106,7 +106,7 @@ The .I addrinfo structure referenced by the last two elements is described in .BR getaddrinfo (3). -.PP +.P When .I mode is specified as @@ -118,7 +118,7 @@ structure pointed to by the .I sevp argument. For the definition and general details of this structure, see -.BR sigevent (7). +.BR sigevent (3type). The .I sevp\->sigev_notify field can have the following values: @@ -131,7 +131,7 @@ When a look-up completes, generate the signal .I sigev_signo for the process. See -.BR sigevent (7) +.BR sigevent (3type) for general details. The .I si_code @@ -147,9 +147,9 @@ When a look-up completes, invoke .I sigev_notify_function as if it were the start function of a new thread. See -.BR sigevent (7) +.BR sigevent (3type) for details. -.PP +.P For .B SIGEV_SIGNAL and @@ -158,7 +158,7 @@ it may be useful to point .I sevp\->sigev_value.sival_ptr to .IR list . -.PP +.P The .BR gai_suspend () function suspends execution of the calling thread, @@ -188,12 +188,12 @@ If .I timeout is NULL, then the call blocks indefinitely (until one of the events above occurs). -.PP +.P No explicit indication of which request was completed is given; you must determine which request(s) have completed by iterating with .BR gai_error () over the list of requests. -.PP +.P The .BR gai_error () function returns the status of the request @@ -203,7 +203,7 @@ either if the request was not completed yet, 0 if it was handled successfully, or an error code if the request could not be resolved. -.PP +.P The .BR gai_cancel () function cancels the request @@ -237,7 +237,7 @@ Out of memory. .B EAI_SYSTEM .I mode is invalid. -.PP +.P The .BR gai_suspend () function returns 0 if at least one of the listed requests has been completed. @@ -253,7 +253,7 @@ There were no actual requests given to the function. A signal has interrupted the function. Note that this interruption might have been caused by signal notification of some completed look-up request. -.PP +.P The .BR gai_error () function can return @@ -265,7 +265,7 @@ for an unfinished look-up request, or the error code .B EAI_CANCELED if the request has been canceled explicitly before it could be finished. -.PP +.P The .BR gai_cancel () function can return one of these values: @@ -278,7 +278,7 @@ The request has not been canceled. .TP .B EAI_ALLDONE The request has already completed. -.PP +.P The .BR gai_strerror (3) function translates these error codes to a human readable string, @@ -300,12 +300,11 @@ T{ .BR gai_cancel () T} Thread safety MT-Safe .TE -.sp 1 .SH STANDARDS GNU. .SH HISTORY glibc 2.2.3. -.PP +.P The interface of .BR getaddrinfo_a () was modeled after the @@ -320,7 +319,7 @@ The program below simply resolves several hostnames in parallel, giving a speed-up compared to resolving the hostnames sequentially using .BR getaddrinfo (3). The program might be used like this: -.PP +.P .in +4n .EX $ \fB./a.out mirrors.kernel.org enoent.linuxfoundation.org gnu.org\fP @@ -329,17 +328,20 @@ enoent.linuxfoundation.org: Name or service not known gnu.org: 209.51.188.116 .EE .in -.PP +.P Here is the program source code -.PP +.P .\" SRC BEGIN (sync.c) .EX #define _GNU_SOURCE +#include <err.h> #include <netdb.h> #include <stdio.h> #include <stdlib.h> #include <string.h> \& +#define MALLOC(n, type) ((type *) reallocarray(NULL, n, sizeof(type))) +\& int main(int argc, char *argv[]) { @@ -354,11 +356,10 @@ main(int argc, char *argv[]) } \& for (size_t i = 0; i < argc \- 1; i++) { - reqs[i] = malloc(sizeof(*reqs[0])); - if (reqs[i] == NULL) { - perror("malloc"); - exit(EXIT_FAILURE); - } + reqs[i] = MALLOC(1, struct gaicb); + if (reqs[i] == NULL) + err(EXIT_FAILURE, "malloc"); +\& memset(reqs[i], 0, sizeof(*reqs[0])); reqs[i]\->ar_name = argv[i + 1]; } @@ -399,9 +400,9 @@ This example shows a simple interactive .BR getaddrinfo_a () front-end. The notification facility is not demonstrated. -.PP +.P An example session might look like this: -.PP +.P .in +4n .EX $ \fB./a.out\fP @@ -420,20 +421,42 @@ $ \fB./a.out\fP [02] gnu.org: 209.51.188.116 .EE .in -.PP +.P The program source is as follows: -.PP +.P .\" SRC BEGIN (async.c) .EX #define _GNU_SOURCE +#include <assert.h> +#include <err.h> #include <netdb.h> #include <stdio.h> #include <stdlib.h> #include <string.h> \& +#define CALLOC(n, type) ((type *) calloc(n, sizeof(type))) +\& +#define REALLOCF(ptr, n, type) \e +({ \e + static_assert(__builtin_types_compatible_p(typeof(ptr), type *)); \e + \e + (type *) reallocarrayf(ptr, n, sizeof(type)); \e +}) +\& static struct gaicb **reqs = NULL; static size_t nreqs = 0; \& +static inline void * +reallocarrayf(void *p, size_t nmemb, size_t size) +{ + void *q; +\& + q = reallocarray(p, nmemb, size); + if (q == NULL && nmemb != 0 && size != 0) + free(p); + return q; +} +\& static char * getcmd(void) { @@ -459,9 +482,14 @@ add_requests(void) \& while ((host = strtok(NULL, " "))) { nreqs++; - reqs = realloc(reqs, sizeof(reqs[0]) * nreqs); + reqs = REALLOCF(reqs, nreqs, struct gaicb *); + if (reqs == NULL) + err(EXIT_FAILURE, "reallocf"); +\& + reqs[nreqs \- 1] = CALLOC(1, struct gaicb); + if (reqs[nreqs \- 1] == NULL) + err(EXIT_FAILURE, "calloc"); \& - reqs[nreqs \- 1] = calloc(1, sizeof(*reqs[0])); reqs[nreqs \- 1]\->ar_name = strdup(host); } \& @@ -483,7 +511,12 @@ wait_requests(void) char *id; int ret; size_t n; - struct gaicb const **wait_reqs = calloc(nreqs, sizeof(*wait_reqs)); + struct gaicb const **wait_reqs; +\& + wait_reqs = CALLOC(nreqs, const struct gaicb *); + if (wait_reqs == NULL) + err(EXIT_FAILURE, "calloc"); +\& /* NULL elements are ignored by gai_suspend(). */ \& while ((id = strtok(NULL, " ")) != NULL) { @@ -609,4 +642,4 @@ main(void) .BR lio_listio (3), .BR hostname (7), .BR ip (7), -.BR sigevent (7) +.BR sigevent (3type) |