diff options
Diffstat (limited to 'net/ipv4/tcp_ipv4.c')
-rw-r--r-- | net/ipv4/tcp_ipv4.c | 32 |
1 files changed, 24 insertions, 8 deletions
diff --git a/net/ipv4/tcp_ipv4.c b/net/ipv4/tcp_ipv4.c index a9db4b1a2215..fd54c5f8a255 100644 --- a/net/ipv4/tcp_ipv4.c +++ b/net/ipv4/tcp_ipv4.c | |||
@@ -73,6 +73,7 @@ | |||
73 | #include <net/xfrm.h> | 73 | #include <net/xfrm.h> |
74 | #include <net/netdma.h> | 74 | #include <net/netdma.h> |
75 | #include <net/secure_seq.h> | 75 | #include <net/secure_seq.h> |
76 | #include <net/tcp_memcontrol.h> | ||
76 | 77 | ||
77 | #include <linux/inet.h> | 78 | #include <linux/inet.h> |
78 | #include <linux/ipv6.h> | 79 | #include <linux/ipv6.h> |
@@ -630,7 +631,7 @@ static void tcp_v4_send_reset(struct sock *sk, struct sk_buff *skb) | |||
630 | arg.iov[0].iov_len = sizeof(rep.th); | 631 | arg.iov[0].iov_len = sizeof(rep.th); |
631 | 632 | ||
632 | #ifdef CONFIG_TCP_MD5SIG | 633 | #ifdef CONFIG_TCP_MD5SIG |
633 | key = sk ? tcp_v4_md5_do_lookup(sk, ip_hdr(skb)->daddr) : NULL; | 634 | key = sk ? tcp_v4_md5_do_lookup(sk, ip_hdr(skb)->saddr) : NULL; |
634 | if (key) { | 635 | if (key) { |
635 | rep.opt[0] = htonl((TCPOPT_NOP << 24) | | 636 | rep.opt[0] = htonl((TCPOPT_NOP << 24) | |
636 | (TCPOPT_NOP << 16) | | 637 | (TCPOPT_NOP << 16) | |
@@ -650,6 +651,11 @@ static void tcp_v4_send_reset(struct sock *sk, struct sk_buff *skb) | |||
650 | arg.iov[0].iov_len, IPPROTO_TCP, 0); | 651 | arg.iov[0].iov_len, IPPROTO_TCP, 0); |
651 | arg.csumoffset = offsetof(struct tcphdr, check) / 2; | 652 | arg.csumoffset = offsetof(struct tcphdr, check) / 2; |
652 | arg.flags = (sk && inet_sk(sk)->transparent) ? IP_REPLY_ARG_NOSRCCHECK : 0; | 653 | arg.flags = (sk && inet_sk(sk)->transparent) ? IP_REPLY_ARG_NOSRCCHECK : 0; |
654 | /* When socket is gone, all binding information is lost. | ||
655 | * routing might fail in this case. using iif for oif to | ||
656 | * make sure we can deliver it | ||
657 | */ | ||
658 | arg.bound_dev_if = sk ? sk->sk_bound_dev_if : inet_iif(skb); | ||
653 | 659 | ||
654 | net = dev_net(skb_dst(skb)->dev); | 660 | net = dev_net(skb_dst(skb)->dev); |
655 | arg.tos = ip_hdr(skb)->tos; | 661 | arg.tos = ip_hdr(skb)->tos; |
@@ -1460,9 +1466,13 @@ struct sock *tcp_v4_syn_recv_sock(struct sock *sk, struct sk_buff *skb, | |||
1460 | inet_csk(newsk)->icsk_ext_hdr_len = inet_opt->opt.optlen; | 1466 | inet_csk(newsk)->icsk_ext_hdr_len = inet_opt->opt.optlen; |
1461 | newinet->inet_id = newtp->write_seq ^ jiffies; | 1467 | newinet->inet_id = newtp->write_seq ^ jiffies; |
1462 | 1468 | ||
1463 | if (!dst && (dst = inet_csk_route_child_sock(sk, newsk, req)) == NULL) | 1469 | if (!dst) { |
1464 | goto put_and_exit; | 1470 | dst = inet_csk_route_child_sock(sk, newsk, req); |
1465 | 1471 | if (!dst) | |
1472 | goto put_and_exit; | ||
1473 | } else { | ||
1474 | /* syncookie case : see end of cookie_v4_check() */ | ||
1475 | } | ||
1466 | sk_setup_caps(newsk, dst); | 1476 | sk_setup_caps(newsk, dst); |
1467 | 1477 | ||
1468 | tcp_mtup_init(newsk); | 1478 | tcp_mtup_init(newsk); |
@@ -1511,6 +1521,7 @@ exit: | |||
1511 | return NULL; | 1521 | return NULL; |
1512 | put_and_exit: | 1522 | put_and_exit: |
1513 | tcp_clear_xmit_timers(newsk); | 1523 | tcp_clear_xmit_timers(newsk); |
1524 | tcp_cleanup_congestion_control(newsk); | ||
1514 | bh_unlock_sock(newsk); | 1525 | bh_unlock_sock(newsk); |
1515 | sock_put(newsk); | 1526 | sock_put(newsk); |
1516 | goto exit; | 1527 | goto exit; |
@@ -1916,7 +1927,8 @@ static int tcp_v4_init_sock(struct sock *sk) | |||
1916 | sk->sk_rcvbuf = sysctl_tcp_rmem[1]; | 1927 | sk->sk_rcvbuf = sysctl_tcp_rmem[1]; |
1917 | 1928 | ||
1918 | local_bh_disable(); | 1929 | local_bh_disable(); |
1919 | percpu_counter_inc(&tcp_sockets_allocated); | 1930 | sock_update_memcg(sk); |
1931 | sk_sockets_allocated_inc(sk); | ||
1920 | local_bh_enable(); | 1932 | local_bh_enable(); |
1921 | 1933 | ||
1922 | return 0; | 1934 | return 0; |
@@ -1972,7 +1984,8 @@ void tcp_v4_destroy_sock(struct sock *sk) | |||
1972 | tp->cookie_values = NULL; | 1984 | tp->cookie_values = NULL; |
1973 | } | 1985 | } |
1974 | 1986 | ||
1975 | percpu_counter_dec(&tcp_sockets_allocated); | 1987 | sk_sockets_allocated_dec(sk); |
1988 | sock_release_memcg(sk); | ||
1976 | } | 1989 | } |
1977 | EXPORT_SYMBOL(tcp_v4_destroy_sock); | 1990 | EXPORT_SYMBOL(tcp_v4_destroy_sock); |
1978 | 1991 | ||
@@ -2619,7 +2632,6 @@ struct proto tcp_prot = { | |||
2619 | .orphan_count = &tcp_orphan_count, | 2632 | .orphan_count = &tcp_orphan_count, |
2620 | .memory_allocated = &tcp_memory_allocated, | 2633 | .memory_allocated = &tcp_memory_allocated, |
2621 | .memory_pressure = &tcp_memory_pressure, | 2634 | .memory_pressure = &tcp_memory_pressure, |
2622 | .sysctl_mem = sysctl_tcp_mem, | ||
2623 | .sysctl_wmem = sysctl_tcp_wmem, | 2635 | .sysctl_wmem = sysctl_tcp_wmem, |
2624 | .sysctl_rmem = sysctl_tcp_rmem, | 2636 | .sysctl_rmem = sysctl_tcp_rmem, |
2625 | .max_header = MAX_TCP_HEADER, | 2637 | .max_header = MAX_TCP_HEADER, |
@@ -2633,10 +2645,14 @@ struct proto tcp_prot = { | |||
2633 | .compat_setsockopt = compat_tcp_setsockopt, | 2645 | .compat_setsockopt = compat_tcp_setsockopt, |
2634 | .compat_getsockopt = compat_tcp_getsockopt, | 2646 | .compat_getsockopt = compat_tcp_getsockopt, |
2635 | #endif | 2647 | #endif |
2648 | #ifdef CONFIG_CGROUP_MEM_RES_CTLR_KMEM | ||
2649 | .init_cgroup = tcp_init_cgroup, | ||
2650 | .destroy_cgroup = tcp_destroy_cgroup, | ||
2651 | .proto_cgroup = tcp_proto_cgroup, | ||
2652 | #endif | ||
2636 | }; | 2653 | }; |
2637 | EXPORT_SYMBOL(tcp_prot); | 2654 | EXPORT_SYMBOL(tcp_prot); |
2638 | 2655 | ||
2639 | |||
2640 | static int __net_init tcp_sk_init(struct net *net) | 2656 | static int __net_init tcp_sk_init(struct net *net) |
2641 | { | 2657 | { |
2642 | return inet_ctl_sock_create(&net->ipv4.tcp_sock, | 2658 | return inet_ctl_sock_create(&net->ipv4.tcp_sock, |