diff options
Diffstat (limited to 'net/ipv4/tcp_input.c')
-rw-r--r-- | net/ipv4/tcp_input.c | 25 |
1 files changed, 15 insertions, 10 deletions
diff --git a/net/ipv4/tcp_input.c b/net/ipv4/tcp_input.c index 4e4617e90417..196b4388116c 100644 --- a/net/ipv4/tcp_input.c +++ b/net/ipv4/tcp_input.c | |||
@@ -5876,20 +5876,22 @@ static inline void pr_drop_req(struct request_sock *req, __u16 port, int family) | |||
5876 | */ | 5876 | */ |
5877 | static void tcp_ecn_create_request(struct request_sock *req, | 5877 | static void tcp_ecn_create_request(struct request_sock *req, |
5878 | const struct sk_buff *skb, | 5878 | const struct sk_buff *skb, |
5879 | const struct sock *listen_sk) | 5879 | const struct sock *listen_sk, |
5880 | const struct dst_entry *dst) | ||
5880 | { | 5881 | { |
5881 | const struct tcphdr *th = tcp_hdr(skb); | 5882 | const struct tcphdr *th = tcp_hdr(skb); |
5882 | const struct net *net = sock_net(listen_sk); | 5883 | const struct net *net = sock_net(listen_sk); |
5883 | bool th_ecn = th->ece && th->cwr; | 5884 | bool th_ecn = th->ece && th->cwr; |
5884 | bool ect, need_ecn; | 5885 | bool ect, need_ecn, ecn_ok; |
5885 | 5886 | ||
5886 | if (!th_ecn) | 5887 | if (!th_ecn) |
5887 | return; | 5888 | return; |
5888 | 5889 | ||
5889 | ect = !INET_ECN_is_not_ect(TCP_SKB_CB(skb)->ip_dsfield); | 5890 | ect = !INET_ECN_is_not_ect(TCP_SKB_CB(skb)->ip_dsfield); |
5890 | need_ecn = tcp_ca_needs_ecn(listen_sk); | 5891 | need_ecn = tcp_ca_needs_ecn(listen_sk); |
5892 | ecn_ok = net->ipv4.sysctl_tcp_ecn || dst_feature(dst, RTAX_FEATURE_ECN); | ||
5891 | 5893 | ||
5892 | if (!ect && !need_ecn && net->ipv4.sysctl_tcp_ecn) | 5894 | if (!ect && !need_ecn && ecn_ok) |
5893 | inet_rsk(req)->ecn_ok = 1; | 5895 | inet_rsk(req)->ecn_ok = 1; |
5894 | else if (ect && need_ecn) | 5896 | else if (ect && need_ecn) |
5895 | inet_rsk(req)->ecn_ok = 1; | 5897 | inet_rsk(req)->ecn_ok = 1; |
@@ -5954,13 +5956,7 @@ int tcp_conn_request(struct request_sock_ops *rsk_ops, | |||
5954 | if (security_inet_conn_request(sk, skb, req)) | 5956 | if (security_inet_conn_request(sk, skb, req)) |
5955 | goto drop_and_free; | 5957 | goto drop_and_free; |
5956 | 5958 | ||
5957 | if (!want_cookie || tmp_opt.tstamp_ok) | 5959 | if (!want_cookie && !isn) { |
5958 | tcp_ecn_create_request(req, skb, sk); | ||
5959 | |||
5960 | if (want_cookie) { | ||
5961 | isn = cookie_init_sequence(af_ops, sk, skb, &req->mss); | ||
5962 | req->cookie_ts = tmp_opt.tstamp_ok; | ||
5963 | } else if (!isn) { | ||
5964 | /* VJ's idea. We save last timestamp seen | 5960 | /* VJ's idea. We save last timestamp seen |
5965 | * from the destination in peer table, when entering | 5961 | * from the destination in peer table, when entering |
5966 | * state TIME-WAIT, and check against it before | 5962 | * state TIME-WAIT, and check against it before |
@@ -6008,6 +6004,15 @@ int tcp_conn_request(struct request_sock_ops *rsk_ops, | |||
6008 | goto drop_and_free; | 6004 | goto drop_and_free; |
6009 | } | 6005 | } |
6010 | 6006 | ||
6007 | tcp_ecn_create_request(req, skb, sk, dst); | ||
6008 | |||
6009 | if (want_cookie) { | ||
6010 | isn = cookie_init_sequence(af_ops, sk, skb, &req->mss); | ||
6011 | req->cookie_ts = tmp_opt.tstamp_ok; | ||
6012 | if (!tmp_opt.tstamp_ok) | ||
6013 | inet_rsk(req)->ecn_ok = 0; | ||
6014 | } | ||
6015 | |||
6011 | tcp_rsk(req)->snt_isn = isn; | 6016 | tcp_rsk(req)->snt_isn = isn; |
6012 | tcp_openreq_init_rwin(req, sk, dst); | 6017 | tcp_openreq_init_rwin(req, sk, dst); |
6013 | fastopen = !want_cookie && | 6018 | fastopen = !want_cookie && |