net: fix saving TX flow hash in sock for outgoing connections
The commit "net: Save TX flow hash in sock and set in skbuf on xmit" introduced the inet_set_txhash() and ip6_set_txhash() routines to calculate and record flow hash(sk_txhash) in the socket structure. sk_txhash is used to set skb->hash which is used to spread flows across multiple TXQs. But, the above routines are invoked before the source port of the connection is created. Because of this all outgoing connections that just differ in the source port get hashed into the same TXQ. This patch fixes this problem for IPv4/6 by invoking the the above routines after the source port is available for the socket. Fixes: b73c3d0e4("net: Save TX flow hash in sock and set in skbuf on xmit") Signed-off-by: Sathya Perla <sathya.perla@emulex.com> Acked-by: Eric Dumazet <edumazet@google.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
789f202326
commit
9e7ceb0607
|
@ -206,8 +206,6 @@ int tcp_v4_connect(struct sock *sk, struct sockaddr *uaddr, int addr_len)
|
||||||
inet->inet_dport = usin->sin_port;
|
inet->inet_dport = usin->sin_port;
|
||||||
inet->inet_daddr = daddr;
|
inet->inet_daddr = daddr;
|
||||||
|
|
||||||
inet_set_txhash(sk);
|
|
||||||
|
|
||||||
inet_csk(sk)->icsk_ext_hdr_len = 0;
|
inet_csk(sk)->icsk_ext_hdr_len = 0;
|
||||||
if (inet_opt)
|
if (inet_opt)
|
||||||
inet_csk(sk)->icsk_ext_hdr_len = inet_opt->opt.optlen;
|
inet_csk(sk)->icsk_ext_hdr_len = inet_opt->opt.optlen;
|
||||||
|
@ -224,6 +222,8 @@ int tcp_v4_connect(struct sock *sk, struct sockaddr *uaddr, int addr_len)
|
||||||
if (err)
|
if (err)
|
||||||
goto failure;
|
goto failure;
|
||||||
|
|
||||||
|
inet_set_txhash(sk);
|
||||||
|
|
||||||
rt = ip_route_newports(fl4, rt, orig_sport, orig_dport,
|
rt = ip_route_newports(fl4, rt, orig_sport, orig_dport,
|
||||||
inet->inet_sport, inet->inet_dport, sk);
|
inet->inet_sport, inet->inet_dport, sk);
|
||||||
if (IS_ERR(rt)) {
|
if (IS_ERR(rt)) {
|
||||||
|
|
|
@ -200,8 +200,6 @@ static int tcp_v6_connect(struct sock *sk, struct sockaddr *uaddr,
|
||||||
sk->sk_v6_daddr = usin->sin6_addr;
|
sk->sk_v6_daddr = usin->sin6_addr;
|
||||||
np->flow_label = fl6.flowlabel;
|
np->flow_label = fl6.flowlabel;
|
||||||
|
|
||||||
ip6_set_txhash(sk);
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* TCP over IPv4
|
* TCP over IPv4
|
||||||
*/
|
*/
|
||||||
|
@ -297,6 +295,8 @@ static int tcp_v6_connect(struct sock *sk, struct sockaddr *uaddr,
|
||||||
if (err)
|
if (err)
|
||||||
goto late_failure;
|
goto late_failure;
|
||||||
|
|
||||||
|
ip6_set_txhash(sk);
|
||||||
|
|
||||||
if (!tp->write_seq && likely(!tp->repair))
|
if (!tp->write_seq && likely(!tp->repair))
|
||||||
tp->write_seq = secure_tcpv6_sequence_number(np->saddr.s6_addr32,
|
tp->write_seq = secure_tcpv6_sequence_number(np->saddr.s6_addr32,
|
||||||
sk->sk_v6_daddr.s6_addr32,
|
sk->sk_v6_daddr.s6_addr32,
|
||||||
|
|
Loading…
Reference in New Issue