X-Git-Url: https://git.ozlabs.org/?p=ccan;a=blobdiff_plain;f=ccan%2Fnet%2Ftest%2Frun.c;h=bdd5f1de8e49d82d3cb46460098e60cc3955e30a;hp=bff1b6a79e47a47ec0ba994f4a83f980a2d91d27;hb=291237b4fed863be74051274ac5ad9920cb33cc3;hpb=5b189c748dbc4b09e8180ce6fc6c2d0411968c48 diff --git a/ccan/net/test/run.c b/ccan/net/test/run.c index bff1b6a7..bdd5f1de 100644 --- a/ccan/net/test/run.c +++ b/ccan/net/test/run.c @@ -6,7 +6,7 @@ #include #include -static unsigned int server(int protocol, int type) +static int server(int protocol, int type) { int sock; union { @@ -17,9 +17,12 @@ static unsigned int server(int protocol, int type) socklen_t addlen = sizeof(addr); sock = socket(protocol, type, 0); + if (sock < 0) + return -1; /* Bind to free port. */ - listen(sock, 0); + if (listen(sock, 0) != 0) + return -1; /* Figure out what port it gave us. */ getsockname(sock, &addr.addr, &addlen); @@ -43,10 +46,8 @@ static unsigned int server(int protocol, int type) ? addr.ipv4.sin_port : addr.ipv6.sin6_port); } -static bool we_faked_double = false; - -/* Get a localhost on ipv4 and IPv6. Fake it if we have to. */ -static struct addrinfo* double_addr_lookup(char* buf) +/* Get a localhost on ipv4 and IPv6. Fake it if we can. */ +static struct addrinfo* double_addr_lookup(char* buf, bool *fake_double) { struct addrinfo *addr, *addr2; @@ -57,9 +58,8 @@ static struct addrinfo* double_addr_lookup(char* buf) /* If we only got one, we need to fake up the other one. */ if (addr->ai_next) { addr2 = addr->ai_next; + *fake_double = false; } else { - we_faked_double = true; - /* OK, IPv4 only? */ if (addr->ai_family == AF_INET) { /* These are the names I found on my Ubuntu system. */ @@ -77,8 +77,14 @@ static struct addrinfo* double_addr_lookup(char* buf) /* IPv6 only? This is a guess... */ addr2 = net_client_lookup("ip4-localhost", buf, AF_UNSPEC, SOCK_STREAM); - if (!addr2) - return NULL; + + /* Perhaps no support on this system? Go ahead with one. */ + if (!addr2) { + *fake_double = false; + return addr; + } + + *fake_double = true; addr->ai_next = addr2; } @@ -93,16 +99,13 @@ static struct addrinfo* double_addr_lookup(char* buf) return NULL; } -static void double_addr_free(struct addrinfo* addr) +static void double_addr_free(struct addrinfo* addr, bool fake_double) { - struct addrinfo *addr2; - if (we_faked_double) { - addr2 = addr->ai_next; + if (fake_double) { + freeaddrinfo(addr->ai_next); addr->ai_next = NULL; } freeaddrinfo(addr); - if (we_faked_double) - freeaddrinfo(addr2); } int main(void) @@ -112,45 +115,65 @@ int main(void) struct sockaddr saddr; socklen_t slen; char buf[20]; - unsigned int port; + int port; + bool fake_double; plan_tests(14); + port = server(AF_INET, SOCK_STREAM); - sprintf(buf, "%u", port); - - addr = double_addr_lookup(buf); - ok1(addr); - fd = net_connect(addr); - ok1(fd >= 0); - - slen = sizeof(saddr); - ok1(getsockname(fd, &saddr, &slen) == 0); - diag("family = %d", saddr.sa_family); - ok1(saddr.sa_family == AF_INET); - status = read(fd, buf, sizeof(buf)); - ok(status == strlen("Yay!"), - "Read returned %i (%s)", status, strerror(errno)); - ok1(strncmp(buf, "Yay!", strlen("Yay!")) == 0); - close(fd); - double_addr_free(addr); + if (port == -1) { + /* No IPv4 support? Maybe one day this will happen! */ + if (errno == EAFNOSUPPORT) + skip(6, "No IPv4 socket support"); + else + fail("Could not create IPv4 listening socket: %s", + strerror(errno)); + } else { + sprintf(buf, "%u", port); + + addr = double_addr_lookup(buf, &fake_double); + ok1(addr); + fd = net_connect(addr); + ok1(fd >= 0); + + slen = sizeof(saddr); + ok1(getsockname(fd, &saddr, &slen) == 0); + diag("family = %d", saddr.sa_family); + ok1(saddr.sa_family == AF_INET); + status = read(fd, buf, sizeof(buf)); + ok(status == strlen("Yay!"), + "Read returned %i (%s)", status, strerror(errno)); + ok1(strncmp(buf, "Yay!", strlen("Yay!")) == 0); + close(fd); + double_addr_free(addr, fake_double); + } port = server(AF_INET6, SOCK_STREAM); - sprintf(buf, "%u", port); - - addr = double_addr_lookup(buf); - ok1(addr); - fd = net_connect(addr); - ok1(fd >= 0); - - slen = sizeof(saddr); - ok1(getsockname(fd, &saddr, &slen) == 0); - ok1(saddr.sa_family == AF_INET6); - status = read(fd, buf, sizeof(buf)); - ok(status == strlen("Yay!"), - "Read returned %i (%s)", status, strerror(errno)); - ok1(strncmp(buf, "Yay!", strlen("Yay!")) == 0); - close(fd); - double_addr_free(addr); + if (port == -1) { + /* No IPv6 support? */ + if (errno == EAFNOSUPPORT) + skip(6, "No IPv6 socket support"); + else + fail("Could not create IPv6 listening socket: %s", + strerror(errno)); + } else { + sprintf(buf, "%u", port); + + addr = double_addr_lookup(buf, &fake_double); + ok1(addr); + fd = net_connect(addr); + ok1(fd >= 0); + + slen = sizeof(saddr); + ok1(getsockname(fd, &saddr, &slen) == 0); + ok1(saddr.sa_family == AF_INET6); + status = read(fd, buf, sizeof(buf)); + ok(status == strlen("Yay!"), + "Read returned %i (%s)", status, strerror(errno)); + ok1(strncmp(buf, "Yay!", strlen("Yay!")) == 0); + close(fd); + double_addr_free(addr, fake_double); + } wait(&status); ok1(WIFEXITED(status));