BUG/MAJOR: fix listening IP address storage for frontends

When compiled with GCC 6, the IP address specified for a frontend was
ignored and HAProxy was listening on all addresses instead. This is
caused by an incomplete copy of a "struct sockaddr_storage".

With the GNU Libc, "struct sockaddr_storage" is defined as this:

    struct sockaddr_storage
      {
        sa_family_t ss_family;
        unsigned long int __ss_align;
        char __ss_padding[(128 - (2 * sizeof (unsigned long int)))];
      };

Doing an aggregate copy (ss1 = ss2) is different than using memcpy():
only members of the aggregate have to be copied. Notably, padding can be
or not be copied. In GCC 6, some optimizations use this fact and if a
"struct sockaddr_storage" contains a "struct sockaddr_in", the port and
the address are part of the padding (between sa_family and __ss_align)
and can be not copied over.

Therefore, we replace any aggregate copy by a memcpy(). There is another
place using the same pattern. We also fix a function receiving a "struct
sockaddr_storage" by copy instead of by reference. Since it only needs a
read-only copy, the function is converted to request a reference.

This is a backport for 1.5 of 6e6158 and 6e46ff1.
diff --git a/src/cfgparse.c b/src/cfgparse.c
index 39abf6b..9331415 100644
--- a/src/cfgparse.c
+++ b/src/cfgparse.c
@@ -280,7 +280,7 @@
 		}
 
 		/* OK the address looks correct */
-		ss = *ss2;
+		memcpy(&ss, ss2, sizeof(ss));
 
 		for (; port <= end; port++) {
 			l = (struct listener *)calloc(1, sizeof(struct listener));
@@ -291,7 +291,7 @@
 			l->bind_conf = bind_conf;
 
 			l->fd = fd;
-			l->addr = ss;
+			memcpy(&l->addr, &ss, sizeof(ss));
 			l->xprt = &raw_sock;
 			l->state = LI_INIT;
 
diff --git a/src/connection.c b/src/connection.c
index dab1c90..09fd04e 100644
--- a/src/connection.c
+++ b/src/connection.c
@@ -620,7 +620,7 @@
 	const char pp2_signature[] = PP2_SIGNATURE;
 	int ret = 0;
 	struct proxy_hdr_v2 *hdr = (struct proxy_hdr_v2 *)buf;
-	struct sockaddr_storage null_addr = {0};
+	struct sockaddr_storage null_addr = { .ss_family = 0 };
 	struct sockaddr_storage *src = &null_addr;
 	struct sockaddr_storage *dst = &null_addr;
 #ifdef USE_OPENSSL
diff --git a/src/proto_http.c b/src/proto_http.c
index b3aa4d8..0b13c5e 100644
--- a/src/proto_http.c
+++ b/src/proto_http.c
@@ -3220,15 +3220,15 @@
 /* Sets the TOS header in IPv4 and the traffic class header in IPv6 packets
  * (as per RFC3260 #4 and BCP37 #4.2 and #5.2).
  */
-static inline void inet_set_tos(int fd, struct sockaddr_storage from, int tos)
+static inline void inet_set_tos(int fd, struct sockaddr_storage *from, int tos)
 {
 #ifdef IP_TOS
-	if (from.ss_family == AF_INET)
+	if (from->ss_family == AF_INET)
 		setsockopt(fd, IPPROTO_IP, IP_TOS, &tos, sizeof(tos));
 #endif
 #ifdef IPV6_TCLASS
-	if (from.ss_family == AF_INET6) {
-		if (IN6_IS_ADDR_V4MAPPED(&((struct sockaddr_in6 *)&from)->sin6_addr))
+	if (from->ss_family == AF_INET6) {
+		if (IN6_IS_ADDR_V4MAPPED(&((struct sockaddr_in6 *)from)->sin6_addr))
 			/* v4-mapped addresses need IP_TOS */
 			setsockopt(fd, IPPROTO_IP, IP_TOS, &tos, sizeof(tos));
 		else
@@ -3366,7 +3366,7 @@
 
 		case HTTP_REQ_ACT_SET_TOS:
 			if ((cli_conn = objt_conn(s->req->prod->end)) && conn_ctrl_ready(cli_conn))
-				inet_set_tos(cli_conn->t.sock.fd, cli_conn->addr.from, rule->arg.tos);
+				inet_set_tos(cli_conn->t.sock.fd, &cli_conn->addr.from, rule->arg.tos);
 			break;
 
 		case HTTP_REQ_ACT_SET_MARK:
@@ -3563,7 +3563,7 @@
 
 		case HTTP_RES_ACT_SET_TOS:
 			if ((cli_conn = objt_conn(s->req->prod->end)) && conn_ctrl_ready(cli_conn))
-				inet_set_tos(cli_conn->t.sock.fd, cli_conn->addr.from, rule->arg.tos);
+				inet_set_tos(cli_conn->t.sock.fd, &cli_conn->addr.from, rule->arg.tos);
 			break;
 
 		case HTTP_RES_ACT_SET_MARK:
diff --git a/src/proto_tcp.c b/src/proto_tcp.c
index cfa62f7..8c06441 100644
--- a/src/proto_tcp.c
+++ b/src/proto_tcp.c
@@ -394,7 +394,7 @@
 			struct sockaddr_storage sa;
 
 			ret = 1;
-			sa = src->source_addr;
+			memcpy(&sa, &src->source_addr, sizeof(sa));
 
 			do {
 				/* note: in case of retry, we may have to release a previously