diff --git a/include/common/standard.h b/include/common/standard.h index e7a105284..008208733 100644 --- a/include/common/standard.h +++ b/include/common/standard.h @@ -525,6 +525,20 @@ static inline int get_host_port(struct sockaddr_storage *addr) return 0; } +/* returns address len for 's family, 0 for unknown families */ +static inline int get_addr_len(const struct sockaddr_storage *addr) +{ + switch (addr->ss_family) { + case AF_INET: + return sizeof(struct sockaddr_in); + case AF_INET6: + return sizeof(struct sockaddr_in6); + case AF_UNIX: + return sizeof(struct sockaddr_un); + } + return 0; +} + /* set port in host byte order */ static inline int set_net_port(struct sockaddr_storage *addr, int port) { diff --git a/src/checks.c b/src/checks.c index 147a7abd6..4285624cf 100644 --- a/src/checks.c +++ b/src/checks.c @@ -817,16 +817,9 @@ static int event_srv_chk_w(int fd) else sa = s->addr; - switch (s->check_addr.ss_family) { - case AF_INET: - ((struct sockaddr_in *)&sa)->sin_port = htons(s->check_port); - break; - case AF_INET6: - ((struct sockaddr_in6 *)&sa)->sin6_port = htons(s->check_port); - break; - } + set_host_port(&sa, s->check_port); - if (connect(fd, (struct sockaddr *)&sa, sizeof(sa)) == 0) + if (connect(fd, (struct sockaddr *)&sa, get_addr_len(&sa)) == 0) errno = 0; if (errno == EALREADY || errno == EINPROGRESS) @@ -1377,7 +1370,7 @@ struct task *process_chk(struct task *t) if (s->proxy->options2 & PR_O2_SMARTCON) setsockopt(fd, IPPROTO_TCP, TCP_QUICKACK, (char *) &zero, sizeof(zero)); #endif - if ((connect(fd, (struct sockaddr *)&sa, sizeof(sa)) != -1) || (errno == EINPROGRESS)) { + if ((connect(fd, (struct sockaddr *)&sa, get_addr_len(&sa)) != -1) || (errno == EINPROGRESS)) { /* OK, connection in progress or established */ //fprintf(stderr, "process_chk: 4\n"); @@ -1390,7 +1383,7 @@ struct task *process_chk(struct task *t) fdtab[fd].cb[DIR_WR].f = &event_srv_chk_w; fdtab[fd].cb[DIR_WR].b = NULL; fdinfo[fd].peeraddr = (struct sockaddr *)&sa; - fdinfo[fd].peerlen = sizeof(sa); + fdinfo[fd].peerlen = get_addr_len(&sa); fdtab[fd].state = FD_STCONN; /* connection in progress */ fdtab[fd].flags = FD_FL_TCP | FD_FL_TCP_NODELAY; EV_FD_SET(fd, DIR_WR); /* for connect status */ diff --git a/src/log.c b/src/log.c index eba9adf0e..58d884a54 100644 --- a/src/log.c +++ b/src/log.c @@ -289,7 +289,8 @@ void send_log(struct proxy *p, int level, const char *message, ...) /* the total syslog message now starts at logptr, for dataptr+data_len-logptr */ sent = sendto(*plogfd, log_ptr, dataptr + data_len - log_ptr, - MSG_DONTWAIT | MSG_NOSIGNAL, (struct sockaddr *)&logsrv->addr, sizeof(logsrv->addr)); + MSG_DONTWAIT | MSG_NOSIGNAL, + (struct sockaddr *)&logsrv->addr, get_addr_len(&logsrv->addr)); if (sent < 0) { Alert("sendto logger #%d failed: %s (errno=%d)\n", nblogger, strerror(errno), errno); diff --git a/src/proto_tcp.c b/src/proto_tcp.c index ca993a6fc..13ea2103c 100644 --- a/src/proto_tcp.c +++ b/src/proto_tcp.c @@ -150,12 +150,12 @@ int tcp_bind_socket(int fd, int flags, struct sockaddr_storage *local, struct so setsockopt(fd, SOL_SOCKET, SO_REUSEADDR, (char *) &one, sizeof(one)); if (foreign_ok) { - ret = bind(fd, (struct sockaddr *)&bind_addr, sizeof(bind_addr)); + ret = bind(fd, (struct sockaddr *)&bind_addr, get_addr_len(&bind_addr)); if (ret < 0) return 2; } else { - ret = bind(fd, (struct sockaddr *)local, sizeof(*local)); + ret = bind(fd, (struct sockaddr *)local, get_addr_len(local)); if (ret < 0) return 1; } @@ -406,7 +406,7 @@ int tcp_connect_server(struct stream_interface *si) if (global.tune.server_rcvbuf) setsockopt(fd, SOL_SOCKET, SO_RCVBUF, &global.tune.server_rcvbuf, sizeof(global.tune.server_rcvbuf)); - if ((connect(fd, (struct sockaddr *)&si->addr.s.to, sizeof(struct sockaddr_storage)) == -1) && + if ((connect(fd, (struct sockaddr *)&si->addr.s.to, get_addr_len(&si->addr.s.to)) == -1) && (errno != EINPROGRESS) && (errno != EALREADY) && (errno != EISCONN)) { if (errno == EAGAIN || errno == EADDRINUSE) { @@ -449,7 +449,7 @@ int tcp_connect_server(struct stream_interface *si) fdtab[fd].cb[DIR_WR].b = si->ob; fdinfo[fd].peeraddr = (struct sockaddr *)&si->addr.s.to; - fdinfo[fd].peerlen = sizeof(struct sockaddr_storage); + fdinfo[fd].peerlen = get_addr_len(&si->addr.s.to); fd_insert(fd); EV_FD_SET(fd, DIR_WR); /* for connect status */