Merge branch 'master' into upstream
[powerpc.git] / net / ipv6 / tcp_ipv6.c
index 81dbc9c..923989d 100644 (file)
@@ -269,9 +269,8 @@ static int tcp_v6_connect(struct sock *sk, struct sockaddr *uaddr,
        ipv6_addr_copy(&np->saddr, saddr);
        inet->rcv_saddr = LOOPBACK4_IPV6;
 
+       sk->sk_gso_type = SKB_GSO_TCPV6;
        ip6_dst_store(sk, dst, NULL);
-       sk->sk_route_caps = dst->dev->features &
-               ~(NETIF_F_IP_CSUM | NETIF_F_TSO);
 
        icsk->icsk_ext_hdr_len = 0;
        if (np->opt)
@@ -553,6 +552,24 @@ static void tcp_v6_send_check(struct sock *sk, int len, struct sk_buff *skb)
        }
 }
 
+static int tcp_v6_gso_send_check(struct sk_buff *skb)
+{
+       struct ipv6hdr *ipv6h;
+       struct tcphdr *th;
+
+       if (!pskb_may_pull(skb, sizeof(*th)))
+               return -EINVAL;
+
+       ipv6h = skb->nh.ipv6h;
+       th = skb->h.th;
+
+       th->check = 0;
+       th->check = ~csum_ipv6_magic(&ipv6h->saddr, &ipv6h->daddr, skb->len,
+                                    IPPROTO_TCP, 0);
+       skb->csum = offsetof(struct tcphdr, check);
+       skb->ip_summed = CHECKSUM_HW;
+       return 0;
+}
 
 static void tcp_v6_send_reset(struct sk_buff *skb)
 {
@@ -929,9 +946,8 @@ static struct sock * tcp_v6_syn_recv_sock(struct sock *sk, struct sk_buff *skb,
         * comment in that function for the gory details. -acme
         */
 
+       sk->sk_gso_type = SKB_GSO_TCPV6;
        ip6_dst_store(newsk, dst, NULL);
-       newsk->sk_route_caps = dst->dev->features &
-               ~(NETIF_F_IP_CSUM | NETIF_F_TSO);
 
        newtcp6sk = (struct tcp6_sock *)newsk;
        inet_sk(newsk)->pinet6 = &newtcp6sk->inet6;
@@ -1605,6 +1621,8 @@ struct proto tcpv6_prot = {
 static struct inet6_protocol tcpv6_protocol = {
        .handler        =       tcp_v6_rcv,
        .err_handler    =       tcp_v6_err,
+       .gso_send_check =       tcp_v6_gso_send_check,
+       .gso_segment    =       tcp_tso_segment,
        .flags          =       INET6_PROTO_NOPOLICY|INET6_PROTO_FINAL,
 };