aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorTodd C. Miller <Todd.Miller@courtesan.com>2017-11-14 15:29:41 -0700
committerBruce A. Mah <bmah@kitchenlab.org>2017-11-14 14:29:41 -0800
commitb6072241bf0a4ce767f1843536a36715516fd23d (patch)
treeab627f13b4a01e25c457dab2e62041ce2492f440
parent34f878a2c0efb19129a72591905c11a80044fabb (diff)
downloadiperf3-b6072241bf0a4ce767f1843536a36715516fd23d.tar.gz
Add missing saved_errno dance around some close(2) calls. (#669)
-rw-r--r--src/iperf_client_api.c6
-rw-r--r--src/iperf_sctp.c27
-rw-r--r--src/iperf_server_api.c6
-rw-r--r--src/net.c16
4 files changed, 49 insertions, 6 deletions
diff --git a/src/iperf_client_api.c b/src/iperf_client_api.c
index 4d56e0a..94beeeb 100644
--- a/src/iperf_client_api.c
+++ b/src/iperf_client_api.c
@@ -53,7 +53,7 @@
int
iperf_create_streams(struct iperf_test *test)
{
- int i, s;
+ int i, s, saved_errno;
struct iperf_stream *sp;
int orig_bind_port = test->bind_port;
@@ -69,7 +69,9 @@ iperf_create_streams(struct iperf_test *test)
if (test->protocol->id == Ptcp) {
if (test->congestion) {
if (setsockopt(s, IPPROTO_TCP, TCP_CONGESTION, test->congestion, strlen(test->congestion)) < 0) {
+ saved_errno = errno;
close(s);
+ errno = saved_errno;
i_errno = IESETCONGESTION;
return -1;
}
@@ -78,7 +80,9 @@ iperf_create_streams(struct iperf_test *test)
socklen_t len = TCP_CA_NAME_MAX;
char ca[TCP_CA_NAME_MAX + 1];
if (getsockopt(s, IPPROTO_TCP, TCP_CONGESTION, ca, &len) < 0) {
+ saved_errno = errno;
close(s);
+ errno = saved_errno;
i_errno = IESETCONGESTION;
return -1;
}
diff --git a/src/iperf_sctp.c b/src/iperf_sctp.c
index cc10919..28b98a7 100644
--- a/src/iperf_sctp.c
+++ b/src/iperf_sctp.c
@@ -152,7 +152,7 @@ iperf_sctp_listen(struct iperf_test *test)
#if defined(HAVE_SCTP)
struct addrinfo hints, *res;
char portstr[6];
- int s, opt;
+ int s, opt, saved_errno;
close(test->listener);
@@ -180,8 +180,10 @@ iperf_sctp_listen(struct iperf_test *test)
opt = 1;
if (setsockopt(s, IPPROTO_IPV6, IPV6_V6ONLY,
(char *) &opt, sizeof(opt)) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(res);
+ errno = saved_errno;
i_errno = IEPROTOCOL;
return -1;
}
@@ -190,8 +192,10 @@ iperf_sctp_listen(struct iperf_test *test)
opt = 1;
if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt)) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(res);
+ errno = saved_errno;
i_errno = IEREUSEADDR;
return -1;
}
@@ -203,8 +207,10 @@ iperf_sctp_listen(struct iperf_test *test)
return -1;
} else
if (bind(s, (struct sockaddr *) res->ai_addr, res->ai_addrlen) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(res);
+ errno = saved_errno;
i_errno = IESTREAMLISTEN;
return -1;
}
@@ -234,7 +240,7 @@ int
iperf_sctp_connect(struct iperf_test *test)
{
#if defined(HAVE_SCTP)
- int s, opt;
+ int s, opt, saved_errno;
char portstr[6];
struct addrinfo hints, *local_res, *server_res;
@@ -271,8 +277,10 @@ iperf_sctp_connect(struct iperf_test *test)
if (test->no_delay != 0) {
opt = 1;
if (setsockopt(s, IPPROTO_SCTP, SCTP_NODELAY, &opt, sizeof(opt)) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(server_res);
+ errno = saved_errno;
i_errno = IESETNODELAY;
return -1;
}
@@ -302,8 +310,10 @@ iperf_sctp_connect(struct iperf_test *test)
av.assoc_value = test->settings->mss;
if (setsockopt(s, IPPROTO_SCTP, SCTP_MAXSEG, &av, sizeof(av)) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(server_res);
+ errno = saved_errno;
i_errno = IESETMSS;
return -1;
}
@@ -316,8 +326,10 @@ iperf_sctp_connect(struct iperf_test *test)
*/
if (setsockopt(s, IPPROTO_SCTP, SCTP_MAXSEG, &opt, sizeof(opt)) < 0 &&
errno != ENOPROTOOPT) {
+ saved_errno = errno;
close(s);
freeaddrinfo(server_res);
+ errno = saved_errno;
i_errno = IESETMSS;
return -1;
}
@@ -331,8 +343,10 @@ iperf_sctp_connect(struct iperf_test *test)
initmsg.sinit_num_ostreams = test->settings->num_ostreams;
if (setsockopt(s, IPPROTO_SCTP, SCTP_INITMSG, &initmsg, sizeof(struct sctp_initmsg)) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(server_res);
+ errno = saved_errno;
i_errno = IESETSCTPNSTREAM;
return -1;
}
@@ -346,8 +360,10 @@ iperf_sctp_connect(struct iperf_test *test)
/* TODO support sctp_connectx() to avoid heartbeating. */
if (connect(s, (struct sockaddr *) server_res->ai_addr, server_res->ai_addrlen) < 0 && errno != EINPROGRESS) {
+ saved_errno = errno;
close(s);
freeaddrinfo(server_res);
+ errno = saved_errno;
i_errno = IESTREAMCONNECT;
return -1;
}
@@ -355,7 +371,9 @@ iperf_sctp_connect(struct iperf_test *test)
/* Send cookie for verification */
if (Nwrite(s, test->cookie, COOKIE_SIZE, Psctp) < 0) {
+ saved_errno = errno;
close(s);
+ errno = saved_errno;
i_errno = IESENDCOOKIE;
return -1;
}
@@ -370,8 +388,10 @@ iperf_sctp_connect(struct iperf_test *test)
opt = 0;
if (setsockopt(s, IPPROTO_SCTP, SCTP_DISABLE_FRAGMENTS, &opt, sizeof(opt)) < 0 &&
errno != ENOPROTOOPT) {
+ saved_errno = errno;
close(s);
freeaddrinfo(server_res);
+ errno = saved_errno;
i_errno = IESETSCTPDISABLEFRAG;
return -1;
}
@@ -417,6 +437,7 @@ iperf_sctp_bindx(struct iperf_test *test, int s, int is_server)
int nxaddrs;
int retval;
int domain;
+ int saved_errno;
domain = test->settings->domain;
xbe0 = NULL;
@@ -525,8 +546,10 @@ iperf_sctp_bindx(struct iperf_test *test, int s, int is_server)
}
if (sctp_bindx(s, xaddrs, nxaddrs, SCTP_BINDX_ADD_ADDR) == -1) {
+ saved_errno = errno;
close(s);
free(xaddrs);
+ errno = saved_errno;
i_errno = IESETSCTPBINDX;
retval = -1;
goto out;
diff --git a/src/iperf_server_api.c b/src/iperf_server_api.c
index d19d350..4283dc3 100644
--- a/src/iperf_server_api.c
+++ b/src/iperf_server_api.c
@@ -385,7 +385,7 @@ cleanup_server(struct iperf_test *test)
int
iperf_run_server(struct iperf_test *test)
{
- int result, s, streams_accepted;
+ int result, s, streams_accepted, saved_errno;
fd_set read_set, write_set;
struct iperf_stream *sp;
struct timeval now;
@@ -476,8 +476,10 @@ iperf_run_server(struct iperf_test *test)
warning("TCP congestion control algorithm not supported");
}
else {
+ saved_errno = errno;
close(s);
cleanup_server(test);
+ errno = saved_errno;
i_errno = IESETCONGESTION;
return -1;
}
@@ -487,8 +489,10 @@ iperf_run_server(struct iperf_test *test)
socklen_t len = TCP_CA_NAME_MAX;
char ca[TCP_CA_NAME_MAX + 1];
if (getsockopt(s, IPPROTO_TCP, TCP_CONGESTION, ca, &len) < 0) {
+ saved_errno = errno;
close(s);
cleanup_server(test);
+ errno = saved_errno;
i_errno = IESETCONGESTION;
return -1;
}
diff --git a/src/net.c b/src/net.c
index 290da77..34d7435 100644
--- a/src/net.c
+++ b/src/net.c
@@ -115,7 +115,7 @@ int
netdial(int domain, int proto, char *local, int local_port, char *server, int port, int timeout)
{
struct addrinfo hints, *local_res, *server_res;
- int s;
+ int s, saved_errno;
if (local) {
memset(&hints, 0, sizeof(hints));
@@ -148,9 +148,11 @@ netdial(int domain, int proto, char *local, int local_port, char *server, int po
}
if (bind(s, (struct sockaddr *) local_res->ai_addr, local_res->ai_addrlen) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(local_res);
freeaddrinfo(server_res);
+ errno = saved_errno;
return -1;
}
freeaddrinfo(local_res);
@@ -158,8 +160,10 @@ netdial(int domain, int proto, char *local, int local_port, char *server, int po
((struct sockaddr_in *) server_res->ai_addr)->sin_port = htons(port);
if (timeout_connect(s, (struct sockaddr *) server_res->ai_addr, server_res->ai_addrlen, timeout) < 0 && errno != EINPROGRESS) {
+ saved_errno = errno;
close(s);
freeaddrinfo(server_res);
+ errno = saved_errno;
return -1;
}
@@ -174,7 +178,7 @@ netannounce(int domain, int proto, char *local, int port)
{
struct addrinfo hints, *res;
char portstr[6];
- int s, opt;
+ int s, opt, saved_errno;
snprintf(portstr, 6, "%d", port);
memset(&hints, 0, sizeof(hints));
@@ -210,8 +214,10 @@ netannounce(int domain, int proto, char *local, int port)
opt = 1;
if (setsockopt(s, SOL_SOCKET, SO_REUSEADDR,
(char *) &opt, sizeof(opt)) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(res);
+ errno = saved_errno;
return -1;
}
/*
@@ -230,16 +236,20 @@ netannounce(int domain, int proto, char *local, int port)
opt = 1;
if (setsockopt(s, IPPROTO_IPV6, IPV6_V6ONLY,
(char *) &opt, sizeof(opt)) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(res);
+ errno = saved_errno;
return -1;
}
}
#endif /* IPV6_V6ONLY */
if (bind(s, (struct sockaddr *) res->ai_addr, res->ai_addrlen) < 0) {
+ saved_errno = errno;
close(s);
freeaddrinfo(res);
+ errno = saved_errno;
return -1;
}
@@ -247,7 +257,9 @@ netannounce(int domain, int proto, char *local, int port)
if (proto == SOCK_STREAM) {
if (listen(s, 5) < 0) {
+ saved_errno = errno;
close(s);
+ errno = saved_errno;
return -1;
}
}