aboutsummaryrefslogtreecommitdiffstats
path: root/net/ipv4/tcp_ipv4.c
diff options
context:
space:
mode:
Diffstat (limited to 'net/ipv4/tcp_ipv4.c')
-rw-r--r--net/ipv4/tcp_ipv4.c91
1 files changed, 50 insertions, 41 deletions
diff --git a/net/ipv4/tcp_ipv4.c b/net/ipv4/tcp_ipv4.c
index c34f01513945..a7443159c400 100644
--- a/net/ipv4/tcp_ipv4.c
+++ b/net/ipv4/tcp_ipv4.c
@@ -92,7 +92,7 @@ EXPORT_SYMBOL(sysctl_tcp_low_latency);
92static struct tcp_md5sig_key *tcp_v4_md5_do_lookup(struct sock *sk, 92static struct tcp_md5sig_key *tcp_v4_md5_do_lookup(struct sock *sk,
93 __be32 addr); 93 __be32 addr);
94static int tcp_v4_md5_hash_hdr(char *md5_hash, struct tcp_md5sig_key *key, 94static int tcp_v4_md5_hash_hdr(char *md5_hash, struct tcp_md5sig_key *key,
95 __be32 daddr, __be32 saddr, struct tcphdr *th); 95 __be32 daddr, __be32 saddr, const struct tcphdr *th);
96#else 96#else
97static inline 97static inline
98struct tcp_md5sig_key *tcp_v4_md5_do_lookup(struct sock *sk, __be32 addr) 98struct tcp_md5sig_key *tcp_v4_md5_do_lookup(struct sock *sk, __be32 addr)
@@ -104,7 +104,7 @@ struct tcp_md5sig_key *tcp_v4_md5_do_lookup(struct sock *sk, __be32 addr)
104struct inet_hashinfo tcp_hashinfo; 104struct inet_hashinfo tcp_hashinfo;
105EXPORT_SYMBOL(tcp_hashinfo); 105EXPORT_SYMBOL(tcp_hashinfo);
106 106
107static inline __u32 tcp_v4_init_sequence(struct sk_buff *skb) 107static inline __u32 tcp_v4_init_sequence(const struct sk_buff *skb)
108{ 108{
109 return secure_tcp_sequence_number(ip_hdr(skb)->daddr, 109 return secure_tcp_sequence_number(ip_hdr(skb)->daddr,
110 ip_hdr(skb)->saddr, 110 ip_hdr(skb)->saddr,
@@ -552,7 +552,7 @@ static void __tcp_v4_send_check(struct sk_buff *skb,
552/* This routine computes an IPv4 TCP checksum. */ 552/* This routine computes an IPv4 TCP checksum. */
553void tcp_v4_send_check(struct sock *sk, struct sk_buff *skb) 553void tcp_v4_send_check(struct sock *sk, struct sk_buff *skb)
554{ 554{
555 struct inet_sock *inet = inet_sk(sk); 555 const struct inet_sock *inet = inet_sk(sk);
556 556
557 __tcp_v4_send_check(skb, inet->inet_saddr, inet->inet_daddr); 557 __tcp_v4_send_check(skb, inet->inet_saddr, inet->inet_daddr);
558} 558}
@@ -590,7 +590,7 @@ int tcp_v4_gso_send_check(struct sk_buff *skb)
590 590
591static void tcp_v4_send_reset(struct sock *sk, struct sk_buff *skb) 591static void tcp_v4_send_reset(struct sock *sk, struct sk_buff *skb)
592{ 592{
593 struct tcphdr *th = tcp_hdr(skb); 593 const struct tcphdr *th = tcp_hdr(skb);
594 struct { 594 struct {
595 struct tcphdr th; 595 struct tcphdr th;
596#ifdef CONFIG_TCP_MD5SIG 596#ifdef CONFIG_TCP_MD5SIG
@@ -652,6 +652,7 @@ static void tcp_v4_send_reset(struct sock *sk, struct sk_buff *skb)
652 arg.flags = (sk && inet_sk(sk)->transparent) ? IP_REPLY_ARG_NOSRCCHECK : 0; 652 arg.flags = (sk && inet_sk(sk)->transparent) ? IP_REPLY_ARG_NOSRCCHECK : 0;
653 653
654 net = dev_net(skb_dst(skb)->dev); 654 net = dev_net(skb_dst(skb)->dev);
655 arg.tos = ip_hdr(skb)->tos;
655 ip_send_reply(net->ipv4.tcp_sock, skb, ip_hdr(skb)->saddr, 656 ip_send_reply(net->ipv4.tcp_sock, skb, ip_hdr(skb)->saddr,
656 &arg, arg.iov[0].iov_len); 657 &arg, arg.iov[0].iov_len);
657 658
@@ -666,9 +667,9 @@ static void tcp_v4_send_reset(struct sock *sk, struct sk_buff *skb)
666static void tcp_v4_send_ack(struct sk_buff *skb, u32 seq, u32 ack, 667static void tcp_v4_send_ack(struct sk_buff *skb, u32 seq, u32 ack,
667 u32 win, u32 ts, int oif, 668 u32 win, u32 ts, int oif,
668 struct tcp_md5sig_key *key, 669 struct tcp_md5sig_key *key,
669 int reply_flags) 670 int reply_flags, u8 tos)
670{ 671{
671 struct tcphdr *th = tcp_hdr(skb); 672 const struct tcphdr *th = tcp_hdr(skb);
672 struct { 673 struct {
673 struct tcphdr th; 674 struct tcphdr th;
674 __be32 opt[(TCPOLEN_TSTAMP_ALIGNED >> 2) 675 __be32 opt[(TCPOLEN_TSTAMP_ALIGNED >> 2)
@@ -726,7 +727,7 @@ static void tcp_v4_send_ack(struct sk_buff *skb, u32 seq, u32 ack,
726 arg.csumoffset = offsetof(struct tcphdr, check) / 2; 727 arg.csumoffset = offsetof(struct tcphdr, check) / 2;
727 if (oif) 728 if (oif)
728 arg.bound_dev_if = oif; 729 arg.bound_dev_if = oif;
729 730 arg.tos = tos;
730 ip_send_reply(net->ipv4.tcp_sock, skb, ip_hdr(skb)->saddr, 731 ip_send_reply(net->ipv4.tcp_sock, skb, ip_hdr(skb)->saddr,
731 &arg, arg.iov[0].iov_len); 732 &arg, arg.iov[0].iov_len);
732 733
@@ -743,7 +744,8 @@ static void tcp_v4_timewait_ack(struct sock *sk, struct sk_buff *skb)
743 tcptw->tw_ts_recent, 744 tcptw->tw_ts_recent,
744 tw->tw_bound_dev_if, 745 tw->tw_bound_dev_if,
745 tcp_twsk_md5_key(tcptw), 746 tcp_twsk_md5_key(tcptw),
746 tw->tw_transparent ? IP_REPLY_ARG_NOSRCCHECK : 0 747 tw->tw_transparent ? IP_REPLY_ARG_NOSRCCHECK : 0,
748 tw->tw_tos
747 ); 749 );
748 750
749 inet_twsk_put(tw); 751 inet_twsk_put(tw);
@@ -757,7 +759,8 @@ static void tcp_v4_reqsk_send_ack(struct sock *sk, struct sk_buff *skb,
757 req->ts_recent, 759 req->ts_recent,
758 0, 760 0,
759 tcp_v4_md5_do_lookup(sk, ip_hdr(skb)->daddr), 761 tcp_v4_md5_do_lookup(sk, ip_hdr(skb)->daddr),
760 inet_rsk(req)->no_srccheck ? IP_REPLY_ARG_NOSRCCHECK : 0); 762 inet_rsk(req)->no_srccheck ? IP_REPLY_ARG_NOSRCCHECK : 0,
763 ip_hdr(skb)->tos);
761} 764}
762 765
763/* 766/*
@@ -927,18 +930,21 @@ int tcp_v4_md5_do_add(struct sock *sk, __be32 addr,
927 } 930 }
928 sk_nocaps_add(sk, NETIF_F_GSO_MASK); 931 sk_nocaps_add(sk, NETIF_F_GSO_MASK);
929 } 932 }
930 if (tcp_alloc_md5sig_pool(sk) == NULL) { 933
934 md5sig = tp->md5sig_info;
935 if (md5sig->entries4 == 0 &&
936 tcp_alloc_md5sig_pool(sk) == NULL) {
931 kfree(newkey); 937 kfree(newkey);
932 return -ENOMEM; 938 return -ENOMEM;
933 } 939 }
934 md5sig = tp->md5sig_info;
935 940
936 if (md5sig->alloced4 == md5sig->entries4) { 941 if (md5sig->alloced4 == md5sig->entries4) {
937 keys = kmalloc((sizeof(*keys) * 942 keys = kmalloc((sizeof(*keys) *
938 (md5sig->entries4 + 1)), GFP_ATOMIC); 943 (md5sig->entries4 + 1)), GFP_ATOMIC);
939 if (!keys) { 944 if (!keys) {
940 kfree(newkey); 945 kfree(newkey);
941 tcp_free_md5sig_pool(); 946 if (md5sig->entries4 == 0)
947 tcp_free_md5sig_pool();
942 return -ENOMEM; 948 return -ENOMEM;
943 } 949 }
944 950
@@ -982,6 +988,7 @@ int tcp_v4_md5_do_del(struct sock *sk, __be32 addr)
982 kfree(tp->md5sig_info->keys4); 988 kfree(tp->md5sig_info->keys4);
983 tp->md5sig_info->keys4 = NULL; 989 tp->md5sig_info->keys4 = NULL;
984 tp->md5sig_info->alloced4 = 0; 990 tp->md5sig_info->alloced4 = 0;
991 tcp_free_md5sig_pool();
985 } else if (tp->md5sig_info->entries4 != i) { 992 } else if (tp->md5sig_info->entries4 != i) {
986 /* Need to do some manipulation */ 993 /* Need to do some manipulation */
987 memmove(&tp->md5sig_info->keys4[i], 994 memmove(&tp->md5sig_info->keys4[i],
@@ -989,7 +996,6 @@ int tcp_v4_md5_do_del(struct sock *sk, __be32 addr)
989 (tp->md5sig_info->entries4 - i) * 996 (tp->md5sig_info->entries4 - i) *
990 sizeof(struct tcp4_md5sig_key)); 997 sizeof(struct tcp4_md5sig_key));
991 } 998 }
992 tcp_free_md5sig_pool();
993 return 0; 999 return 0;
994 } 1000 }
995 } 1001 }
@@ -1087,7 +1093,7 @@ static int tcp_v4_md5_hash_pseudoheader(struct tcp_md5sig_pool *hp,
1087} 1093}
1088 1094
1089static int tcp_v4_md5_hash_hdr(char *md5_hash, struct tcp_md5sig_key *key, 1095static int tcp_v4_md5_hash_hdr(char *md5_hash, struct tcp_md5sig_key *key,
1090 __be32 daddr, __be32 saddr, struct tcphdr *th) 1096 __be32 daddr, __be32 saddr, const struct tcphdr *th)
1091{ 1097{
1092 struct tcp_md5sig_pool *hp; 1098 struct tcp_md5sig_pool *hp;
1093 struct hash_desc *desc; 1099 struct hash_desc *desc;
@@ -1119,12 +1125,12 @@ clear_hash_noput:
1119} 1125}
1120 1126
1121int tcp_v4_md5_hash_skb(char *md5_hash, struct tcp_md5sig_key *key, 1127int tcp_v4_md5_hash_skb(char *md5_hash, struct tcp_md5sig_key *key,
1122 struct sock *sk, struct request_sock *req, 1128 const struct sock *sk, const struct request_sock *req,
1123 struct sk_buff *skb) 1129 const struct sk_buff *skb)
1124{ 1130{
1125 struct tcp_md5sig_pool *hp; 1131 struct tcp_md5sig_pool *hp;
1126 struct hash_desc *desc; 1132 struct hash_desc *desc;
1127 struct tcphdr *th = tcp_hdr(skb); 1133 const struct tcphdr *th = tcp_hdr(skb);
1128 __be32 saddr, daddr; 1134 __be32 saddr, daddr;
1129 1135
1130 if (sk) { 1136 if (sk) {
@@ -1169,7 +1175,7 @@ clear_hash_noput:
1169} 1175}
1170EXPORT_SYMBOL(tcp_v4_md5_hash_skb); 1176EXPORT_SYMBOL(tcp_v4_md5_hash_skb);
1171 1177
1172static int tcp_v4_inbound_md5_hash(struct sock *sk, struct sk_buff *skb) 1178static int tcp_v4_inbound_md5_hash(struct sock *sk, const struct sk_buff *skb)
1173{ 1179{
1174 /* 1180 /*
1175 * This gets called for each TCP segment that arrives 1181 * This gets called for each TCP segment that arrives
@@ -1179,10 +1185,10 @@ static int tcp_v4_inbound_md5_hash(struct sock *sk, struct sk_buff *skb)
1179 * o MD5 hash and we're not expecting one. 1185 * o MD5 hash and we're not expecting one.
1180 * o MD5 hash and its wrong. 1186 * o MD5 hash and its wrong.
1181 */ 1187 */
1182 __u8 *hash_location = NULL; 1188 const __u8 *hash_location = NULL;
1183 struct tcp_md5sig_key *hash_expected; 1189 struct tcp_md5sig_key *hash_expected;
1184 const struct iphdr *iph = ip_hdr(skb); 1190 const struct iphdr *iph = ip_hdr(skb);
1185 struct tcphdr *th = tcp_hdr(skb); 1191 const struct tcphdr *th = tcp_hdr(skb);
1186 int genhash; 1192 int genhash;
1187 unsigned char newhash[16]; 1193 unsigned char newhash[16];
1188 1194
@@ -1245,7 +1251,7 @@ int tcp_v4_conn_request(struct sock *sk, struct sk_buff *skb)
1245{ 1251{
1246 struct tcp_extend_values tmp_ext; 1252 struct tcp_extend_values tmp_ext;
1247 struct tcp_options_received tmp_opt; 1253 struct tcp_options_received tmp_opt;
1248 u8 *hash_location; 1254 const u8 *hash_location;
1249 struct request_sock *req; 1255 struct request_sock *req;
1250 struct inet_request_sock *ireq; 1256 struct inet_request_sock *ireq;
1251 struct tcp_sock *tp = tcp_sk(sk); 1257 struct tcp_sock *tp = tcp_sk(sk);
@@ -1504,6 +1510,7 @@ exit:
1504 NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_LISTENDROPS); 1510 NET_INC_STATS_BH(sock_net(sk), LINUX_MIB_LISTENDROPS);
1505 return NULL; 1511 return NULL;
1506put_and_exit: 1512put_and_exit:
1513 bh_unlock_sock(newsk);
1507 sock_put(newsk); 1514 sock_put(newsk);
1508 goto exit; 1515 goto exit;
1509} 1516}
@@ -1585,7 +1592,7 @@ int tcp_v4_do_rcv(struct sock *sk, struct sk_buff *skb)
1585#endif 1592#endif
1586 1593
1587 if (sk->sk_state == TCP_ESTABLISHED) { /* Fast path */ 1594 if (sk->sk_state == TCP_ESTABLISHED) { /* Fast path */
1588 sock_rps_save_rxhash(sk, skb->rxhash); 1595 sock_rps_save_rxhash(sk, skb);
1589 if (tcp_rcv_established(sk, skb, tcp_hdr(skb), skb->len)) { 1596 if (tcp_rcv_established(sk, skb, tcp_hdr(skb), skb->len)) {
1590 rsk = sk; 1597 rsk = sk;
1591 goto reset; 1598 goto reset;
@@ -1602,7 +1609,7 @@ int tcp_v4_do_rcv(struct sock *sk, struct sk_buff *skb)
1602 goto discard; 1609 goto discard;
1603 1610
1604 if (nsk != sk) { 1611 if (nsk != sk) {
1605 sock_rps_save_rxhash(nsk, skb->rxhash); 1612 sock_rps_save_rxhash(nsk, skb);
1606 if (tcp_child_process(sk, nsk, skb)) { 1613 if (tcp_child_process(sk, nsk, skb)) {
1607 rsk = nsk; 1614 rsk = nsk;
1608 goto reset; 1615 goto reset;
@@ -1610,7 +1617,7 @@ int tcp_v4_do_rcv(struct sock *sk, struct sk_buff *skb)
1610 return 0; 1617 return 0;
1611 } 1618 }
1612 } else 1619 } else
1613 sock_rps_save_rxhash(sk, skb->rxhash); 1620 sock_rps_save_rxhash(sk, skb);
1614 1621
1615 if (tcp_rcv_state_process(sk, skb, tcp_hdr(skb), skb->len)) { 1622 if (tcp_rcv_state_process(sk, skb, tcp_hdr(skb), skb->len)) {
1616 rsk = sk; 1623 rsk = sk;
@@ -1642,7 +1649,7 @@ EXPORT_SYMBOL(tcp_v4_do_rcv);
1642int tcp_v4_rcv(struct sk_buff *skb) 1649int tcp_v4_rcv(struct sk_buff *skb)
1643{ 1650{
1644 const struct iphdr *iph; 1651 const struct iphdr *iph;
1645 struct tcphdr *th; 1652 const struct tcphdr *th;
1646 struct sock *sk; 1653 struct sock *sk;
1647 int ret; 1654 int ret;
1648 struct net *net = dev_net(skb->dev); 1655 struct net *net = dev_net(skb->dev);
@@ -1677,7 +1684,7 @@ int tcp_v4_rcv(struct sk_buff *skb)
1677 skb->len - th->doff * 4); 1684 skb->len - th->doff * 4);
1678 TCP_SKB_CB(skb)->ack_seq = ntohl(th->ack_seq); 1685 TCP_SKB_CB(skb)->ack_seq = ntohl(th->ack_seq);
1679 TCP_SKB_CB(skb)->when = 0; 1686 TCP_SKB_CB(skb)->when = 0;
1680 TCP_SKB_CB(skb)->flags = iph->tos; 1687 TCP_SKB_CB(skb)->ip_dsfield = ipv4_get_dsfield(iph);
1681 TCP_SKB_CB(skb)->sacked = 0; 1688 TCP_SKB_CB(skb)->sacked = 0;
1682 1689
1683 sk = __inet_lookup_skb(&tcp_hashinfo, skb, th->source, th->dest); 1690 sk = __inet_lookup_skb(&tcp_hashinfo, skb, th->source, th->dest);
@@ -1806,7 +1813,7 @@ EXPORT_SYMBOL(tcp_v4_get_peer);
1806 1813
1807void *tcp_v4_tw_get_peer(struct sock *sk) 1814void *tcp_v4_tw_get_peer(struct sock *sk)
1808{ 1815{
1809 struct inet_timewait_sock *tw = inet_twsk(sk); 1816 const struct inet_timewait_sock *tw = inet_twsk(sk);
1810 1817
1811 return inet_getpeer_v4(tw->tw_daddr, 1); 1818 return inet_getpeer_v4(tw->tw_daddr, 1);
1812} 1819}
@@ -2333,7 +2340,7 @@ static void tcp_seq_stop(struct seq_file *seq, void *v)
2333 } 2340 }
2334} 2341}
2335 2342
2336static int tcp_seq_open(struct inode *inode, struct file *file) 2343int tcp_seq_open(struct inode *inode, struct file *file)
2337{ 2344{
2338 struct tcp_seq_afinfo *afinfo = PDE(inode)->data; 2345 struct tcp_seq_afinfo *afinfo = PDE(inode)->data;
2339 struct tcp_iter_state *s; 2346 struct tcp_iter_state *s;
@@ -2349,23 +2356,19 @@ static int tcp_seq_open(struct inode *inode, struct file *file)
2349 s->last_pos = 0; 2356 s->last_pos = 0;
2350 return 0; 2357 return 0;
2351} 2358}
2359EXPORT_SYMBOL(tcp_seq_open);
2352 2360
2353int tcp_proc_register(struct net *net, struct tcp_seq_afinfo *afinfo) 2361int tcp_proc_register(struct net *net, struct tcp_seq_afinfo *afinfo)
2354{ 2362{
2355 int rc = 0; 2363 int rc = 0;
2356 struct proc_dir_entry *p; 2364 struct proc_dir_entry *p;
2357 2365
2358 afinfo->seq_fops.open = tcp_seq_open;
2359 afinfo->seq_fops.read = seq_read;
2360 afinfo->seq_fops.llseek = seq_lseek;
2361 afinfo->seq_fops.release = seq_release_net;
2362
2363 afinfo->seq_ops.start = tcp_seq_start; 2366 afinfo->seq_ops.start = tcp_seq_start;
2364 afinfo->seq_ops.next = tcp_seq_next; 2367 afinfo->seq_ops.next = tcp_seq_next;
2365 afinfo->seq_ops.stop = tcp_seq_stop; 2368 afinfo->seq_ops.stop = tcp_seq_stop;
2366 2369
2367 p = proc_create_data(afinfo->name, S_IRUGO, net->proc_net, 2370 p = proc_create_data(afinfo->name, S_IRUGO, net->proc_net,
2368 &afinfo->seq_fops, afinfo); 2371 afinfo->seq_fops, afinfo);
2369 if (!p) 2372 if (!p)
2370 rc = -ENOMEM; 2373 rc = -ENOMEM;
2371 return rc; 2374 return rc;
@@ -2378,7 +2381,7 @@ void tcp_proc_unregister(struct net *net, struct tcp_seq_afinfo *afinfo)
2378} 2381}
2379EXPORT_SYMBOL(tcp_proc_unregister); 2382EXPORT_SYMBOL(tcp_proc_unregister);
2380 2383
2381static void get_openreq4(struct sock *sk, struct request_sock *req, 2384static void get_openreq4(const struct sock *sk, const struct request_sock *req,
2382 struct seq_file *f, int i, int uid, int *len) 2385 struct seq_file *f, int i, int uid, int *len)
2383{ 2386{
2384 const struct inet_request_sock *ireq = inet_rsk(req); 2387 const struct inet_request_sock *ireq = inet_rsk(req);
@@ -2408,9 +2411,9 @@ static void get_tcp4_sock(struct sock *sk, struct seq_file *f, int i, int *len)
2408{ 2411{
2409 int timer_active; 2412 int timer_active;
2410 unsigned long timer_expires; 2413 unsigned long timer_expires;
2411 struct tcp_sock *tp = tcp_sk(sk); 2414 const struct tcp_sock *tp = tcp_sk(sk);
2412 const struct inet_connection_sock *icsk = inet_csk(sk); 2415 const struct inet_connection_sock *icsk = inet_csk(sk);
2413 struct inet_sock *inet = inet_sk(sk); 2416 const struct inet_sock *inet = inet_sk(sk);
2414 __be32 dest = inet->inet_daddr; 2417 __be32 dest = inet->inet_daddr;
2415 __be32 src = inet->inet_rcv_saddr; 2418 __be32 src = inet->inet_rcv_saddr;
2416 __u16 destp = ntohs(inet->inet_dport); 2419 __u16 destp = ntohs(inet->inet_dport);
@@ -2459,7 +2462,7 @@ static void get_tcp4_sock(struct sock *sk, struct seq_file *f, int i, int *len)
2459 len); 2462 len);
2460} 2463}
2461 2464
2462static void get_timewait4_sock(struct inet_timewait_sock *tw, 2465static void get_timewait4_sock(const struct inet_timewait_sock *tw,
2463 struct seq_file *f, int i, int *len) 2466 struct seq_file *f, int i, int *len)
2464{ 2467{
2465 __be32 dest, src; 2468 __be32 dest, src;
@@ -2514,12 +2517,18 @@ out:
2514 return 0; 2517 return 0;
2515} 2518}
2516 2519
2520static const struct file_operations tcp_afinfo_seq_fops = {
2521 .owner = THIS_MODULE,
2522 .open = tcp_seq_open,
2523 .read = seq_read,
2524 .llseek = seq_lseek,
2525 .release = seq_release_net
2526};
2527
2517static struct tcp_seq_afinfo tcp4_seq_afinfo = { 2528static struct tcp_seq_afinfo tcp4_seq_afinfo = {
2518 .name = "tcp", 2529 .name = "tcp",
2519 .family = AF_INET, 2530 .family = AF_INET,
2520 .seq_fops = { 2531 .seq_fops = &tcp_afinfo_seq_fops,
2521 .owner = THIS_MODULE,
2522 },
2523 .seq_ops = { 2532 .seq_ops = {
2524 .show = tcp4_seq_show, 2533 .show = tcp4_seq_show,
2525 }, 2534 },