[LTP] [PATCH v3] network/lib6/getaddrinfo01: rewrite with the new API + use static hostnames
Alexey Kodanev
aleksei.kodanev@bell-sw.com
Tue Jun 1 11:48:07 CEST 2021
The test is now independent of various machine settings
regarding the test host name as it adds predefined names
and aliases to /etc/hosts file and restores it to its
original state after completing the test.
This should fix the following failures:
* when gethostname() returns an alias name that doesn't
match canonical name;
* No AAAA record for the returned name from gethostname().
Addresses and names added to /etc/hosts are more or less
unique, so that there are no conflicts with the existing
configuration.
Also most of the duplicate code is now gone.
Signed-off-by: Alexey Kodanev <aleksei.kodanev@bell-sw.com>
Reviewed-by: Petr Vorel <pvorel@suse.cz>
---
v3: Check access to /etc/hosts file. Also, add host_file_changed flag
to avoid a warning on cleanup (after TCONF).
testcases/network/lib6/getaddrinfo_01.c | 1153 +++++------------------
1 file changed, 249 insertions(+), 904 deletions(-)
diff --git a/testcases/network/lib6/getaddrinfo_01.c b/testcases/network/lib6/getaddrinfo_01.c
index db252a998..8c76f5d02 100644
--- a/testcases/network/lib6/getaddrinfo_01.c
+++ b/testcases/network/lib6/getaddrinfo_01.c
@@ -1,979 +1,324 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
/*
+ * Copyright (c) 2021, BELLSOFT. All rights reserved.
* Copyright (c) 2015 Fujitsu Ltd.
* Copyright (c) International Business Machines Corp., 2001
*
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
+ * Author: David L Stevens
+ */
+
+/*\
+ * [Description]
*
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ * Basic getaddrinfo() tests.
*
- * Author: David L Stevens
+ * The test adds LTP specific addresses and names to /etc/hosts to avoid
+ * DNS, hostname setup issues and conflicts with existing configuration.
*/
#include <unistd.h>
#include <errno.h>
+#include <stdlib.h>
#include <sys/socket.h>
#include <netdb.h>
#include <arpa/inet.h>
#include <sys/param.h>
-#include "test.h"
+#include "tst_safe_stdio.h"
+#include "tst_test.h"
+#include "tst_safe_net.h"
#ifndef AI_V4MAPPED
-#define AI_V4MAPPED 0x0008 /* IPv4 mapped addresses are acceptable. */
+# define AI_V4MAPPED 0x0008 /* IPv4 mapped addresses are acceptable. */
#endif
-static void setup(void);
-static void gaiv4(void);
-static void gaiv6(void);
+static const char *const host_file = "/etc/hosts";
+static const char *hostname;
+static const char *shortname;
+static sa_family_t family;
+static int host_file_changed;
-char *TCID = "getaddrinfo_01";
-int TST_TOTAL = 22;
-
-int main(int argc, char *argv[])
+static void verify_res(struct addrinfo *res, int sock_type, in_port_t servnum,
+ int (*test_cb)(struct addrinfo *))
{
- int lc;
-
- tst_parse_opts(argc, argv, NULL, NULL);
+ sa_family_t sin_family = 0;
+ in_port_t sin_port = 0;
+ struct addrinfo *p = res;
+ int got_tcp = 0;
+ int got_udp = 0;
+ int ret = 0;
+
+ size_t exp_addrlen = (family == AF_INET) ? sizeof(struct sockaddr_in) :
+ sizeof(struct sockaddr_in6);
+
+ for (; p; p = p->ai_next) {
+ ret |= p->ai_family != family;
+ ret |= p->ai_addrlen != exp_addrlen;
+ ret |= p->ai_addr == 0;
+ got_tcp |= p->ai_socktype == SOCK_STREAM;
+ got_udp |= p->ai_socktype == SOCK_DGRAM;
+
+ if (p->ai_addr) {
+
+ if (test_cb)
+ ret |= test_cb(p);
+
+ if (p->ai_family == AF_INET) {
+ struct sockaddr_in *psin;
+
+ psin = (struct sockaddr_in *)p->ai_addr;
+ sin_family = psin->sin_family;
+ sin_port = psin->sin_port;
+ } else {
+ struct sockaddr_in6 *psin6;
+
+ psin6 = (struct sockaddr_in6 *)p->ai_addr;
+ sin_family = psin6->sin6_family;
+ sin_port = psin6->sin6_port;
+ }
- setup();
+ ret |= sin_family != family;
+ ret |= sin_port != htons(servnum);
+ }
- for (lc = 0; TEST_LOOPING(lc); ++lc) {
- tst_count = 0;
+ if (ret)
+ break;
+ }
- gaiv4();
- gaiv6();
+ if (!sock_type && (!got_tcp || !got_udp)) {
+ tst_brk(TFAIL, "socktype 0,%d TCP %d UDP %d",
+ htons(sin_port), got_tcp, got_udp);
}
- tst_exit();
+ if (ret) {
+ tst_brk(TFAIL, "family %d alen %d sin family %d port %d",
+ p->ai_family, p->ai_addrlen, sin_family,
+ htons(sin_port));
+ }
}
-static void setup(void)
+static void print_test_family(const char *name)
{
- TEST_PAUSE;
+ tst_res(TINFO, "test %s: %s", (family == AF_INET) ? "IPv4" : "IPv6",
+ name);
}
-/* getaddrinfo tests (v4) */
-static void gaiv4(void)
+static void check_addrinfo(int safe, const char *name, const char *host,
+ in_port_t servnum, const char *service,
+ int flags, int type, int proto,
+ int (*test_cb)(struct addrinfo *))
{
- struct addrinfo *aires, hints, *pai;
- char hostname[MAXHOSTNAMELEN + 1];
- char shortname[MAXHOSTNAMELEN + 1];
- char service[NI_MAXSERV + 1];
- int servnum;
- char *p;
-
- if (gethostname(hostname, sizeof(hostname)) < 0)
- tst_brkm(TBROK | TERRNO, NULL, "gethostname failed");
- strncpy(shortname, hostname, MAXHOSTNAMELEN);
- shortname[MAXHOSTNAMELEN] = '\0';
- p = strchr(shortname, '.');
- if (p)
- *p = '\0';
-
- /* test 1, IPv4 basic lookup */
+ struct addrinfo *res = NULL;
+ struct addrinfo hints;
+
+ print_test_family(name);
+
memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
- TEST(getaddrinfo(hostname, 0, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in *psin = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in);
- err |= pai->ai_addr == 0;
- psin = (struct sockaddr_in *)pai->ai_addr;
- if (pai->ai_addr) {
- err |= psin->sin_family != AF_INET;
- err |= psin->sin_port != 0;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv4 basic lookup: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin,
- psin ? psin->sin_family : 0,
- psin ? psin->sin_port : 0,
- psin ? htons(psin->sin_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 basic lookup");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 basic "
- "lookup (\"%s\") returns %ld (\"%s\")", hostname,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
+ hints.ai_family = family;
+ hints.ai_flags = flags;
+ hints.ai_socktype = type;
+ hints.ai_protocol = proto;
+
+ if (safe)
+ SAFE_GETADDRINFO(host, service, &hints, &res);
+ else
+ TEST(getaddrinfo(host, service, &hints, &res));
+
+ if (res) {
+ verify_res(res, type, servnum, test_cb);
+ freeaddrinfo(res);
+ tst_res(TPASS, "%s", name);
}
+}
+
+static void check_addrinfo_name(const char *name)
+{
+ struct addrinfo *p, *res;
+ struct addrinfo hints;
+
+ print_test_family(name);
- /* test 2, IPv4 canonical name */
memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
+ hints.ai_family = family;
hints.ai_flags = AI_CANONNAME;
- TEST(getaddrinfo(shortname, 0, &hints, &aires));
- if (!TEST_RETURN) {
- for (pai = aires; pai; pai = pai->ai_next)
- if (pai->ai_canonname)
- break;
- if (!pai) {
- tst_resm(TFAIL, "getaddrinfo IPv4 canonical name: no "
- "entries with canonical name set");
- freeaddrinfo(aires);
- return;
- } else if (strcasecmp(hostname, pai->ai_canonname)) {
- tst_resm(TFAIL, "getaddrinfo IPv4 canonical name "
- "(\"%s\") doesn't match hostname (\"%s\")",
- pai->ai_canonname, hostname);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 canonical name");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 "
- "canonical name (\"%s\") returns %ld (\"%s\")",
- shortname, TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
- }
- /* test 3, IPv4 host+service name */
- memset(&hints, 0, sizeof(hints));
- /*
- * These are hard-coded for echo/7 to avoid using getservbyname(),
- * since it isn't thread-safe and these tests may be re-used
- * multithreaded. Sigh.
- */
- strcpy(service, "echo");
- servnum = 7;
- hints.ai_family = AF_INET;
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in *psin = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in);
- err |= pai->ai_addr == 0;
- psin = (struct sockaddr_in *)pai->ai_addr;
- if (pai->ai_addr) {
- err |= psin->sin_family != AF_INET;
- err |= psin->sin_port != htons(servnum);
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv4 host+service: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin,
- psin ? psin->sin_family : 0,
- psin ? psin->sin_port : 0,
- psin ? htons(psin->sin_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 host+service");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 host+"
- "service returns %ld (\"%s\")", TEST_RETURN,
- gai_strerror(TEST_RETURN));
- return;
- }
+ SAFE_GETADDRINFO(shortname, 0, &hints, &res);
- /* test 4, IPv4 hostname+service, AI_PASSIVE */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
- hints.ai_flags = AI_PASSIVE;
- hints.ai_socktype = SOCK_STREAM;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in *psin = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in);
- err |= pai->ai_addr == 0;
- psin = (struct sockaddr_in *)pai->ai_addr;
- if (pai->ai_addr) {
- /* AI_PASSIVE is ignored if hostname is
- * non-null; address must be set
- */
- err |= psin->sin_addr.s_addr == 0;
- err |= psin->sin_family != AF_INET;
- err |= psin->sin_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv4 host+service, PASSIVE"
- ": fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin,
- psin ? psin->sin_family : 0,
- psin ? psin->sin_port : 0,
- psin ? htons(psin->sin_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 host+service PASSIVE");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 host+"
- "service, PASSIVE (\"%s\", \"%s\") returns %ld (\"%s\")",
- hostname, service, TEST_RETURN,
- gai_strerror(TEST_RETURN));
- return;
+ for (p = res; p; p = p->ai_next) {
+ if (p->ai_canonname)
+ break;
}
+ if (!p)
+ tst_brk(TFAIL, "%s: no entries with canonical name set", name);
+ else if (strcasecmp(hostname, p->ai_canonname))
+ tst_brk(TFAIL, "%s: ai_canonname '%s' doesn't match hostname '%s'",
+ name, p->ai_canonname, hostname);
+
+ tst_res(TPASS, "%s: ai_canonname '%s'", name, p->ai_canonname);
+ freeaddrinfo(res);
+}
- /* test 5, IPv4 host+service w/ AI_NUMERICHOST */
- memset(&hints, 0, sizeof(hints));
- strcpy(service, "echo");
- servnum = 7;
- hints.ai_family = AF_INET;
- hints.ai_flags = AI_NUMERICHOST;
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (TEST_RETURN != EAI_NONAME) {
- tst_resm(TFAIL, "getaddrinfo IPv4 AI_NUMERICHOST w/ hostname: "
- "returns %ld expected %d (EAI_NONAME)",
- TEST_RETURN, EAI_NONAME);
- if (!TEST_RETURN)
- freeaddrinfo(aires);
- return;
+static void check_addrinfo_badflags(const char *name)
+{
+ if (TST_RET == EAI_BADFLAGS) {
+ tst_res(TPASS, "%s returns %ld '%s'", name,
+ TST_RET, gai_strerror(TST_RET));
+ } else if (TST_RET) {
+ tst_brk(TFAIL, "%s returns %ld '%s'", name,
+ TST_RET, gai_strerror(TST_RET));
}
- tst_resm(TPASS, "getaddrinfo IPv4 AI_NUMERICHOST w/ hostname");
- if (!TEST_RETURN)
- freeaddrinfo(aires);
+}
- /* test 6, IPv4 0+service, AI_PASSIVE */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
- hints.ai_flags = AI_PASSIVE;
- hints.ai_socktype = SOCK_STREAM;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in *psin = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in);
- err |= pai->ai_addr == 0;
- psin = (struct sockaddr_in *)pai->ai_addr;
- if (pai->ai_addr) {
-
- /* AI_PASSIVE means addr must be INADDR_ANY */
- err |= psin->sin_addr.s_addr != 0;
- err |= psin->sin_family != AF_INET;
- err |= psin->sin_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv4 0+service, PASSIVE:"
- " fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin,
- psin ? psin->sin_family : 0,
- psin ? psin->sin_port : 0,
- psin ? htons(psin->sin_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 0+service, PASSIVE");
- freeaddrinfo(aires);
- } else {
- if (TEST_RETURN == EAI_BADFLAGS) {
- tst_resm(TPASS, "getaddrinfo IPv4 0+service,"
- " PASSIVE (\"\", \"%s\") returns %ld (\"%s\")",
- service, TEST_RETURN,
- gai_strerror(TEST_RETURN));
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 0+service,"
- " PASSIVE (\"\", \"%s\") returns %ld (\"%s\")",
- service, TEST_RETURN,
- gai_strerror(TEST_RETURN));
- return;
- }
- }
+static int test_loopback(struct addrinfo *p)
+{
+ /* hostname not set; addr should be loopback */
+ if (family == AF_INET) {
+ struct sockaddr_in *psin = (struct sockaddr_in *)p->ai_addr;
- /* test 7, IPv4 0+service */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
- hints.ai_socktype = SOCK_STREAM;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in *psin = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in);
- err |= pai->ai_addr == 0;
- psin = (struct sockaddr_in *)pai->ai_addr;
- if (pai->ai_addr) {
- /* hostname not set; addr should be loopback */
- err |= psin->sin_addr.s_addr !=
- htonl(INADDR_LOOPBACK);
- err |= psin->sin_family != AF_INET;
- err |= psin->sin_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv4 0+service: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin,
- psin ? psin->sin_family : 0,
- psin ? psin->sin_port : 0,
- psin ? htons(psin->sin_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 0+service");
- freeaddrinfo(aires);
+ return psin->sin_addr.s_addr != htonl(INADDR_LOOPBACK);
} else {
- if (TEST_RETURN == EAI_BADFLAGS) {
- tst_resm(TPASS, "getaddrinfo IPv4 "
- "0+service (\"\", \"%s\") returns %ld (\"%s\")",
- service, TEST_RETURN,
- gai_strerror(TEST_RETURN));
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 "
- "0+service (\"\", \"%s\") returns %ld (\"%s\")",
- service, TEST_RETURN,
- gai_strerror(TEST_RETURN));
- return;
- }
- }
+ struct sockaddr_in6 *psin6 = (struct sockaddr_in6 *)p->ai_addr;
- /* test 8, IPv4 host+service, AI_NUMERICSERV */
-#ifndef AI_NUMERICSERV
- tst_resm(TCONF, "getaddrinfo IPv4 host+service, AI_NUMERICSERV: flag "
- "not implemented");
-#else
- memset(&hints, 0, sizeof(hints));
- strcpy(service, "echo");
- servnum = 7;
- hints.ai_family = AF_INET;
- hints.ai_flags = AI_NUMERICSERV;
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (TEST_RETURN != EAI_NONAME) {
- tst_resm(TFAIL,
- "getaddrinfo IPv4 host+service, AI_NUMERICSERV: "
- "returns %ld (\"%s\") expected %d (EAI_NONAME)",
- TEST_RETURN, gai_strerror(TEST_RETURN), EAI_NONAME);
- if (!TEST_RETURN)
- freeaddrinfo(aires);
- return;
+ return memcmp(&psin6->sin6_addr, &in6addr_loopback,
+ sizeof(struct in6_addr)) != 0;
}
- tst_resm(TPASS, "getaddrinfo IPv4 host+service, AI_NUMERICSERV");
- if (!TEST_RETURN)
- freeaddrinfo(aires);
-#endif /* AI_NUMERICSERV */
+}
- /* test 9, IPv4 SOCK_STREAM/IPPROTO_UDP hints */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
- hints.ai_socktype = SOCK_STREAM;
- hints.ai_protocol = IPPROTO_UDP;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- tst_resm(TFAIL, "getaddrinfo IPv4 SOCK_STREAM/IPPROTO_UDP "
- "hints");
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 SOCK_STREAM/IPPROTO_UDP hints");
+static int test_passive(struct addrinfo *p)
+{
+ if (family == AF_INET) {
+ struct sockaddr_in *psin = (struct sockaddr_in *)p->ai_addr;
- /* test 10, IPv4 socktype 0, 513 */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
- hints.ai_socktype = 0;
- strcpy(service, "513");
- servnum = htons(513);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in *psin = 0;
- int got_tcp, got_udp;
- int err = 0;
-
- got_tcp = got_udp = 0;
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in);
- err |= pai->ai_addr == 0;
- got_tcp |= pai->ai_socktype == SOCK_STREAM;
- got_udp |= pai->ai_socktype == SOCK_DGRAM;
- psin = (struct sockaddr_in *)pai->ai_addr;
- if (pai->ai_addr) {
- /* hostname not set; addr should be loopback */
- err |= psin->sin_addr.s_addr !=
- htonl(INADDR_LOOPBACK);
- err |= psin->sin_family != AF_INET;
- err |= psin->sin_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv4 socktype 0,513: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin,
- psin ? psin->sin_family : 0,
- psin ? psin->sin_port : 0,
- psin ? htons(psin->sin_port) : 0);
- freeaddrinfo(aires);
- return;
- } else if (got_tcp && got_udp) {
- tst_resm(TPASS, "getaddrinfo IPv4 socktype 0,513");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 socktype 0,513 TCP %d"
- " UDP %d", got_tcp, got_udp);
- freeaddrinfo(aires);
- return;
- }
+ return psin->sin_addr.s_addr == 0;
} else {
- if (TEST_RETURN == EAI_BADFLAGS) {
- tst_resm(TPASS, "getaddrinfo IPv4 socktype 0,513"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 socktype 0,513"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
- }
- }
+ struct sockaddr_in6 *psin6 = (struct sockaddr_in6 *)p->ai_addr;
- /* test 11, IPv4 AI_V4MAPPED */
- /* AI_V4MAPPED should be ignored because family != AF_INET6 */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET;
- hints.ai_flags = AI_V4MAPPED;
- TEST(getaddrinfo(hostname, 0, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in *psin = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in);
- err |= pai->ai_addr == 0;
- psin = (struct sockaddr_in *)pai->ai_addr;
- if (pai->ai_addr) {
- err |= psin->sin_family != AF_INET;
- err |= psin->sin_port != 0;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv4 AI_V4MAPPED: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin,
- psin ? psin->sin_family : 0,
- psin ? psin->sin_port : 0,
- psin ? htons(psin->sin_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv4 AI_V4MAPPED");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv4 "
- "AI_V4MAPPED (\"%s\") returns %ld (\"%s\")", hostname,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
+ return memcmp(&psin6->sin6_addr, &in6addr_any,
+ sizeof(struct in6_addr)) == 0;
}
}
-/* getaddrinfo tests (v6) */
-static void gaiv6(void)
+static int test_passive_no_host(struct addrinfo *p)
{
- struct addrinfo *aires, hints, *pai;
- char hostname[MAXHOSTNAMELEN + 1];
- char shortname[MAXHOSTNAMELEN + 1];
- char service[NI_MAXSERV + 1];
- int servnum;
- char *p;
-
- if (gethostname(hostname, sizeof(hostname)) < 0)
- tst_brkm(TBROK, NULL, "gethostname failed - %s",
- strerror(errno));
- strncpy(shortname, hostname, MAXHOSTNAMELEN);
- shortname[MAXHOSTNAMELEN] = '\0';
- p = strchr(shortname, '.');
- if (p)
- *p = '\0';
-
- /* test 12, IPv6 basic lookup */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- TEST(getaddrinfo(hostname, 0, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in6 *psin6 = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET6;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in6);
- err |= pai->ai_addr == 0;
- psin6 = (struct sockaddr_in6 *)pai->ai_addr;
- if (pai->ai_addr) {
- err |= psin6->sin6_family != AF_INET6;
- err |= psin6->sin6_port != 0;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv6 basic lookup: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin6,
- psin6 ? psin6->sin6_family : 0,
- psin6 ? psin6->sin6_port : 0,
- psin6 ? htons(psin6->sin6_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 basic lookup");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 basic "
- "lookup (\"%s\") returns %ld (\"%s\")", hostname,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
- }
+ if (family == AF_INET) {
+ struct sockaddr_in *psin = (struct sockaddr_in *)p->ai_addr;
- /* test 13, IPv6 canonical name */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- hints.ai_flags = AI_CANONNAME;
- TEST(getaddrinfo(shortname, 0, &hints, &aires));
- if (!TEST_RETURN) {
- for (pai = aires; pai; pai = pai->ai_next)
- if (pai->ai_canonname)
- break;
- if (!pai) {
- tst_resm(TFAIL, "getaddrinfo IPv6 canonical name: no "
- "entries with canonical name set");
- freeaddrinfo(aires);
- return;
- } else if (strcasecmp(hostname, pai->ai_canonname)) {
- tst_resm(TFAIL, "getaddrinfo IPv6 canonical name "
- "(\"%s\") doesn't match hostname (\"%s\")",
- pai->ai_canonname, hostname);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 canonical name");
- freeaddrinfo(aires);
+ return psin->sin_addr.s_addr != 0;
} else {
- tst_resm(TFAIL, "getaddrinfo IPv6 "
- "canonical name (\"%s\") returns %ld (\"%s\")",
- shortname, TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
+ struct sockaddr_in6 *psin6 = (struct sockaddr_in6 *)p->ai_addr;
+
+ return memcmp(&psin6->sin6_addr, &in6addr_any,
+ sizeof(struct in6_addr));
}
+}
+
+static void gaiv(void)
+{
+ check_addrinfo(1, "basic lookup", hostname, 0, NULL, 0, 0, 0, NULL);
+ check_addrinfo_name("canonical name");
- /* test 14, IPv6 host+service name */
- memset(&hints, 0, sizeof(hints));
/*
* These are hard-coded for echo/7 to avoid using getservbyname(),
* since it isn't thread-safe and these tests may be re-used
* multithreaded. Sigh.
*/
- strcpy(service, "echo");
- servnum = 7;
- hints.ai_family = AF_INET6;
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in6 *psin6 = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET6;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in6);
- err |= pai->ai_addr == 0;
- psin6 = (struct sockaddr_in6 *)pai->ai_addr;
- if (pai->ai_addr) {
- err |= psin6->sin6_family != AF_INET6;
- err |= psin6->sin6_port != htons(servnum);
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv6 host+service: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin6,
- psin6 ? psin6->sin6_family : 0,
- psin6 ? psin6->sin6_port : 0,
- psin6 ? htons(psin6->sin6_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 host+service");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 host+"
- "service returns %ld (\"%s\")", TEST_RETURN,
- gai_strerror(TEST_RETURN));
- return;
- }
+ check_addrinfo(1, "host+service", hostname, 7, "echo", 0, 0, 0, NULL);
+
+ check_addrinfo(1, "host+service, AI_PASSIVE", hostname, 9462, "9462",
+ AI_PASSIVE, SOCK_STREAM, 0, test_passive);
+
+ check_addrinfo(0, "host+service, AI_NUMERICHOST", hostname, 7, "echo",
+ AI_NUMERICHOST, SOCK_STREAM, 0, NULL);
+ if (TST_RET != EAI_NONAME)
+ tst_brk(TFAIL, "AI_NUMERICHOST: ret %ld exp %d (EAI_NONAME)",
+ TST_RET, EAI_NONAME);
+ tst_res(TPASS, "AI_NUMERICHOST: expected %ld (EAI_NONAME)", TST_RET);
+
+ check_addrinfo(1, "0+service, AI_PASSIVE", NULL, 9462, "9462",
+ AI_PASSIVE, SOCK_STREAM, 0, test_passive_no_host);
+
+ check_addrinfo(0, "0+service", NULL, 9462, "9462",
+ 0, SOCK_STREAM, 0, test_loopback);
+ check_addrinfo_badflags("0+service ('', '9462')");
+
+#ifdef AI_NUMERICSERV
+ check_addrinfo(0, "host+service, AI_NUMERICSERV", hostname, 7, "echo",
+ AI_NUMERICSERV, 0, 0, NULL);
+ if (TST_RET != EAI_NONAME)
+ tst_brk(TFAIL, "AI_NUMERICSERV: returns %ld '%s', expected %d (EAI_NONAME)",
+ TST_RET, gai_strerror(TST_RET), EAI_NONAME);
+ tst_res(TPASS, "AI_NUMERICSERV: returns %ld (EAI_NONAME)", TST_RET);
+#else
+ tst_res(TCONF, "AI_NUMERICSERV: flag not implemented");
+#endif
- /* test 15, IPv6 hostname+service, AI_PASSIVE */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- hints.ai_flags = AI_PASSIVE;
- hints.ai_socktype = SOCK_STREAM;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in6 *psin6 = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET6;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in6);
- err |= pai->ai_addr == 0;
- psin6 = (struct sockaddr_in6 *)pai->ai_addr;
- if (pai->ai_addr) {
- /* AI_PASSIVE is ignored if hostname is
- * non-null; address must be set
- */
- err |= memcmp(&psin6->sin6_addr, &in6addr_any,
- sizeof(struct in6_addr)) == 0;
- err |= psin6->sin6_family != AF_INET6;
- err |= psin6->sin6_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv6 host+service, PASSIVE"
- ": fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin6,
- psin6 ? psin6->sin6_family : 0,
- psin6 ? psin6->sin6_port : 0,
- psin6 ? htons(psin6->sin6_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 host+service PASSIVE");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 host+"
- "service, PASSIVE (\"%s\", \"%s\") returns %ld (\"%s\")",
- hostname, service, TEST_RETURN,
- gai_strerror(TEST_RETURN));
- return;
- }
+ check_addrinfo(0, "SOCK_STREAM/IPPROTO_UDP", NULL, 0, NULL, 0,
+ SOCK_STREAM, IPPROTO_UDP, NULL);
+ if (!TST_RET)
+ tst_brk(TFAIL, "SOCK_STREAM/IPPROTO_UDP: unexpected pass");
+ tst_res(TPASS, "SOCK_STREAM/IPPROTO_UDP: failed as expected");
- /* test 16, IPv6 host+service w/ AI_NUMERICHOST */
- memset(&hints, 0, sizeof(hints));
- strcpy(service, "echo");
- servnum = 7;
- hints.ai_family = AF_INET6;
- hints.ai_flags = AI_NUMERICHOST;
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (TEST_RETURN != EAI_NONAME) {
- tst_resm(TFAIL, "getaddrinfo IPv6 AI_NUMERICHOST w/ hostname: "
- "returns %ld expected %d (EAI_NONAME)",
- TEST_RETURN, EAI_NONAME);
- if (!TEST_RETURN)
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 AI_NUMERICHOST w/ hostname");
- if (!TEST_RETURN)
- freeaddrinfo(aires);
+ check_addrinfo(0, "socktype 0,513", NULL, 513, "513", 0, 0, 0, NULL);
+ check_addrinfo_badflags("socktype 0,513");
- /* test 17, IPv6 0+service, AI_PASSIVE */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- hints.ai_flags = AI_PASSIVE;
- hints.ai_socktype = SOCK_STREAM;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in6 *psin6 = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET6;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in6);
- err |= pai->ai_addr == 0;
- psin6 = (struct sockaddr_in6 *)pai->ai_addr;
- if (pai->ai_addr) {
-
- /* AI_PASSIVE means addr must be INADDR_ANY */
- err |= memcmp(&psin6->sin6_addr, &in6addr_any,
- sizeof(struct in6_addr)) != 0;
- err |= psin6->sin6_family != AF_INET6;
- err |= psin6->sin6_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv6 0+service, PASSIVE:"
- " fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin6,
- psin6 ? psin6->sin6_family : 0,
- psin6 ? psin6->sin6_port : 0,
- psin6 ? htons(psin6->sin6_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 0+service, PASSIVE");
- freeaddrinfo(aires);
- } else {
- if (TEST_RETURN == EAI_BADFLAGS) {
- tst_resm(TPASS, "getaddrinfo IPv6 0+service, PASSIVE"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 0+service, PASSIVE"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
- }
- }
+ check_addrinfo(1, "AI_V4MAPPED", NULL, 513, "513",
+ AI_V4MAPPED, 0, 0, NULL);
+}
- /* test 18, IPv6 0+service */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- hints.ai_socktype = SOCK_STREAM;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in6 *psin6 = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET6;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in6);
- err |= pai->ai_addr == 0;
- psin6 = (struct sockaddr_in6 *)pai->ai_addr;
- if (pai->ai_addr) {
- /* hostname not set; addr should be loopback */
- err |= memcmp(&psin6->sin6_addr,
- &in6addr_loopback,
- sizeof(struct in6_addr)) != 0;
- err |= psin6->sin6_family != AF_INET6;
- err |= psin6->sin6_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv6 0+service: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin6,
- psin6 ? psin6->sin6_family : 0,
- psin6 ? psin6->sin6_port : 0,
- psin6 ? htons(psin6->sin6_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 0+service");
- freeaddrinfo(aires);
- } else {
- if (TEST_RETURN == EAI_BADFLAGS) {
- tst_resm(TPASS, "getaddrinfo IPv6 0+service"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 0+service"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
- }
- }
+static struct tcase {
+ sa_family_t family;
+ const char *const addr;
+ const char *const name;
+ const char *const alias;
+} tcases[] = {
+ { AF_INET, "127.0.127.1", "getaddrinfo01.ltp", "getaddrinfo01-ipv4" },
+ { AF_INET6, "::127", "getaddrinfo01.ipv6.ltp", "getaddrinfo01-ipv6" }
+};
- /* test 19, IPv6 host+service, AI_NUMERICSERV */
-#ifndef AI_NUMERICSERV
- tst_resm(TCONF, "getaddrinfo IPv6 host+service, AI_NUMERICSERV: flag "
- "not implemented");
-#else
- memset(&hints, 0, sizeof(hints));
- strcpy(service, "echo");
- servnum = 7;
- hints.ai_family = AF_INET6;
- hints.ai_flags = AI_NUMERICSERV;
- TEST(getaddrinfo(hostname, service, &hints, &aires));
- if (TEST_RETURN != EAI_NONAME) {
- tst_resm(TFAIL,
- "getaddrinfo IPv6 host+service, AI_NUMERICSERV: "
- "returns %ld (\"%s\") expected %d (EAI_NONAME)",
- TEST_RETURN, gai_strerror(TEST_RETURN), EAI_NONAME);
- if (!TEST_RETURN)
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 host+service, AI_NUMERICSERV");
- if (!TEST_RETURN)
- freeaddrinfo(aires);
-#endif /* AI_NUMERICSERV */
+static void setup(void)
+{
+ unsigned int i;
+ int fd;
- /* test 20, IPv6 SOCK_STREAM/IPPROTO_UDP hints */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- hints.ai_socktype = SOCK_STREAM;
- hints.ai_protocol = IPPROTO_UDP;
- strcpy(service, "9462");
- servnum = htons(9462);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- tst_resm(TFAIL, "getaddrinfo IPv6 SOCK_STREAM/IPPROTO_UDP "
- "hints");
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 SOCK_STREAM/IPPROTO_UDP hints");
+ if (access(host_file, W_OK))
+ tst_brk(TCONF | TERRNO, "%s file not available", host_file);
- /* test 21, IPv6 socktype 0, 513 */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- hints.ai_socktype = 0;
- strcpy(service, "513");
- servnum = htons(513);
- TEST(getaddrinfo(0, service, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in6 *psin6 = 0;
- int got_tcp, got_udp;
- int err = 0;
-
- got_tcp = got_udp = 0;
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET6;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in6);
- err |= pai->ai_addr == 0;
- got_tcp |= pai->ai_socktype == SOCK_STREAM;
- got_udp |= pai->ai_socktype == SOCK_DGRAM;
- psin6 = (struct sockaddr_in6 *)pai->ai_addr;
- if (pai->ai_addr) {
- /* hostname not set; addr should be loopback */
- err |= memcmp(&psin6->sin6_addr,
- &in6addr_loopback,
- sizeof(struct in6_addr)) != 0;
- err |= psin6->sin6_family != AF_INET6;
- err |= psin6->sin6_port != servnum;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv6 socktype 0,513: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin6,
- psin6 ? psin6->sin6_family : 0,
- psin6 ? psin6->sin6_port : 0,
- psin6 ? htons(psin6->sin6_port) : 0);
- freeaddrinfo(aires);
- return;
- } else if (got_tcp && got_udp) {
- tst_resm(TPASS, "getaddrinfo IPv6 socktype 0,513");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 socktype 0,513 TCP %d"
- " UDP %d", got_tcp, got_udp);
- freeaddrinfo(aires);
- return;
- }
- } else {
- if (TEST_RETURN == EAI_BADFLAGS) {
- tst_resm(TPASS, "getaddrinfo IPv6 socktype 0,513"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 socktype 0,513"
- " (\"\", \"%s\") returns %ld (\"%s\")", service,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
- }
- }
+ SAFE_CP(host_file, "hosts");
- /* test 22, IPv6 AI_V4MAPPED */
- memset(&hints, 0, sizeof(hints));
- hints.ai_family = AF_INET6;
- hints.ai_flags = AI_V4MAPPED;
- TEST(getaddrinfo(hostname, 0, &hints, &aires));
- if (!TEST_RETURN) {
- struct sockaddr_in6 *psin6 = 0;
- int err = 0;
-
- for (pai = aires; pai; pai = pai->ai_next) {
- err |= pai->ai_family != AF_INET6;
- err |= pai->ai_addrlen != sizeof(struct sockaddr_in6);
- err |= pai->ai_addr == 0;
- psin6 = (struct sockaddr_in6 *)pai->ai_addr;
- if (pai->ai_addr) {
- err |= psin6->sin6_family != AF_INET6;
- err |= psin6->sin6_port != 0;
- }
- if (err)
- break;
- }
- if (err) {
- tst_resm(TFAIL, "getaddrinfo IPv6 AI_V4MAPPED: "
- "fam %d alen %d addr 0x%p addr/fam %d "
- "addr/port %d H[%d]",
- pai->ai_family, pai->ai_addrlen, psin6,
- psin6 ? psin6->sin6_family : 0,
- psin6 ? psin6->sin6_port : 0,
- psin6 ? htons(psin6->sin6_port) : 0);
- freeaddrinfo(aires);
- return;
- }
- tst_resm(TPASS, "getaddrinfo IPv6 AI_V4MAPPED");
- freeaddrinfo(aires);
- } else {
- tst_resm(TFAIL, "getaddrinfo IPv6 "
- "AI_V4MAPPED (\"%s\") returns %ld (\"%s\")", hostname,
- TEST_RETURN, gai_strerror(TEST_RETURN));
- return;
+ host_file_changed = 1;
+ fd = SAFE_OPEN(host_file, O_WRONLY|O_APPEND);
+
+ for (i = 0; i < ARRAY_SIZE(tcases); ++i) {
+ char *entry;
+
+ SAFE_ASPRINTF(&entry, "%s %s %s\n",
+ tcases[i].addr, tcases[i].name, tcases[i].alias);
+ SAFE_WRITE(0, fd, entry, strlen(entry));
+ free(entry);
}
+ SAFE_CLOSE(fd);
+}
+
+static void cleanup(void)
+{
+ if (host_file_changed)
+ SAFE_CP("hosts", host_file);
}
+
+static void do_test(unsigned int i)
+{
+ family = tcases[i].family;
+ hostname = tcases[i].name;
+ shortname = tcases[i].alias;
+ gaiv();
+}
+
+static struct tst_test test = {
+ .needs_root = 1,
+ .needs_tmpdir = 1,
+ .setup = setup,
+ .cleanup = cleanup,
+ .tcnt = ARRAY_SIZE(tcases),
+ .test = do_test,
+};
--
2.25.1
More information about the ltp
mailing list