@@ -238,6 +238,7 @@ static void ip6_dev_free(struct net_device *dev)
238
238
{
239
239
struct ip6_tnl * t = netdev_priv (dev );
240
240
241
+ gro_cells_destroy (& t -> gro_cells );
241
242
dst_cache_destroy (& t -> dst_cache );
242
243
free_percpu (dev -> tstats );
243
244
free_netdev (dev );
@@ -753,97 +754,157 @@ int ip6_tnl_rcv_ctl(struct ip6_tnl *t,
753
754
}
754
755
EXPORT_SYMBOL_GPL (ip6_tnl_rcv_ctl );
755
756
756
- /**
757
- * ip6_tnl_rcv - decapsulate IPv6 packet and retransmit it locally
758
- * @skb: received socket buffer
759
- * @protocol: ethernet protocol ID
760
- * @dscp_ecn_decapsulate: the function to decapsulate DSCP code and ECN
761
- *
762
- * Return: 0
763
- **/
764
-
765
- static int ip6_tnl_rcv (struct sk_buff * skb , __u16 protocol ,
766
- __u8 ipproto ,
767
- int (* dscp_ecn_decapsulate )(const struct ip6_tnl * t ,
768
- const struct ipv6hdr * ipv6h ,
769
- struct sk_buff * skb ))
757
+ static int __ip6_tnl_rcv (struct ip6_tnl * tunnel , struct sk_buff * skb ,
758
+ const struct tnl_ptk_info * tpi ,
759
+ struct metadata_dst * tun_dst ,
760
+ int (* dscp_ecn_decapsulate )(const struct ip6_tnl * t ,
761
+ const struct ipv6hdr * ipv6h ,
762
+ struct sk_buff * skb ),
763
+ bool log_ecn_err )
770
764
{
771
- struct ip6_tnl * t ;
765
+ struct pcpu_sw_netstats * tstats ;
772
766
const struct ipv6hdr * ipv6h = ipv6_hdr (skb );
773
- u8 tproto ;
774
767
int err ;
775
768
776
- rcu_read_lock ();
777
- t = ip6_tnl_lookup (dev_net (skb -> dev ), & ipv6h -> saddr , & ipv6h -> daddr );
778
- if (t ) {
779
- struct pcpu_sw_netstats * tstats ;
769
+ if ((!(tpi -> flags & TUNNEL_CSUM ) &&
770
+ (tunnel -> parms .i_flags & TUNNEL_CSUM )) ||
771
+ ((tpi -> flags & TUNNEL_CSUM ) &&
772
+ !(tunnel -> parms .i_flags & TUNNEL_CSUM ))) {
773
+ tunnel -> dev -> stats .rx_crc_errors ++ ;
774
+ tunnel -> dev -> stats .rx_errors ++ ;
775
+ goto drop ;
776
+ }
780
777
781
- tproto = ACCESS_ONCE (t -> parms .proto );
782
- if (tproto != ipproto && tproto != 0 ) {
783
- rcu_read_unlock ();
784
- goto discard ;
778
+ if (tunnel -> parms .i_flags & TUNNEL_SEQ ) {
779
+ if (!(tpi -> flags & TUNNEL_SEQ ) ||
780
+ (tunnel -> i_seqno &&
781
+ (s32 )(ntohl (tpi -> seq ) - tunnel -> i_seqno ) < 0 )) {
782
+ tunnel -> dev -> stats .rx_fifo_errors ++ ;
783
+ tunnel -> dev -> stats .rx_errors ++ ;
784
+ goto drop ;
785
785
}
786
+ tunnel -> i_seqno = ntohl (tpi -> seq ) + 1 ;
787
+ }
786
788
787
- if (!xfrm6_policy_check (NULL , XFRM_POLICY_IN , skb )) {
788
- rcu_read_unlock ();
789
- goto discard ;
790
- }
789
+ skb -> protocol = tpi -> proto ;
791
790
792
- if (!ip6_tnl_rcv_ctl (t , & ipv6h -> daddr , & ipv6h -> saddr )) {
793
- t -> dev -> stats .rx_dropped ++ ;
794
- rcu_read_unlock ();
795
- goto discard ;
791
+ /* Warning: All skb pointers will be invalidated! */
792
+ if (tunnel -> dev -> type == ARPHRD_ETHER ) {
793
+ if (!pskb_may_pull (skb , ETH_HLEN )) {
794
+ tunnel -> dev -> stats .rx_length_errors ++ ;
795
+ tunnel -> dev -> stats .rx_errors ++ ;
796
+ goto drop ;
796
797
}
797
- skb -> mac_header = skb -> network_header ;
798
- skb_reset_network_header (skb );
799
- skb -> protocol = htons (protocol );
800
- memset (skb -> cb , 0 , sizeof (struct inet6_skb_parm ));
801
-
802
- __skb_tunnel_rx (skb , t -> dev , t -> net );
803
-
804
- err = dscp_ecn_decapsulate (t , ipv6h , skb );
805
- if (unlikely (err )) {
806
- if (log_ecn_error )
807
- net_info_ratelimited ("non-ECT from %pI6 with dsfield=%#x\n" ,
808
- & ipv6h -> saddr ,
809
- ipv6_get_dsfield (ipv6h ));
810
- if (err > 1 ) {
811
- ++ t -> dev -> stats .rx_frame_errors ;
812
- ++ t -> dev -> stats .rx_errors ;
813
- rcu_read_unlock ();
814
- goto discard ;
815
- }
798
+
799
+ ipv6h = ipv6_hdr (skb );
800
+ skb -> protocol = eth_type_trans (skb , tunnel -> dev );
801
+ skb_postpull_rcsum (skb , eth_hdr (skb ), ETH_HLEN );
802
+ } else {
803
+ skb -> dev = tunnel -> dev ;
804
+ }
805
+
806
+ skb_reset_network_header (skb );
807
+ memset (skb -> cb , 0 , sizeof (struct inet6_skb_parm ));
808
+
809
+ __skb_tunnel_rx (skb , tunnel -> dev , tunnel -> net );
810
+
811
+ err = dscp_ecn_decapsulate (tunnel , ipv6h , skb );
812
+ if (unlikely (err )) {
813
+ if (log_ecn_err )
814
+ net_info_ratelimited ("non-ECT from %pI6 with DS=%#x\n" ,
815
+ & ipv6h -> saddr ,
816
+ ipv6_get_dsfield (ipv6h ));
817
+ if (err > 1 ) {
818
+ ++ tunnel -> dev -> stats .rx_frame_errors ;
819
+ ++ tunnel -> dev -> stats .rx_errors ;
820
+ goto drop ;
816
821
}
822
+ }
817
823
818
- tstats = this_cpu_ptr (t -> dev -> tstats );
819
- u64_stats_update_begin (& tstats -> syncp );
820
- tstats -> rx_packets ++ ;
821
- tstats -> rx_bytes += skb -> len ;
822
- u64_stats_update_end (& tstats -> syncp );
824
+ tstats = this_cpu_ptr (tunnel -> dev -> tstats );
825
+ u64_stats_update_begin (& tstats -> syncp );
826
+ tstats -> rx_packets ++ ;
827
+ tstats -> rx_bytes += skb -> len ;
828
+ u64_stats_update_end (& tstats -> syncp );
823
829
824
- netif_rx (skb );
830
+ skb_scrub_packet (skb , ! net_eq ( tunnel -> net , dev_net ( tunnel -> dev )) );
825
831
826
- rcu_read_unlock ();
827
- return 0 ;
832
+ gro_cells_receive (& tunnel -> gro_cells , skb );
833
+ return 0 ;
834
+
835
+ drop :
836
+ kfree_skb (skb );
837
+ return 0 ;
838
+ }
839
+
840
+ int ip6_tnl_rcv (struct ip6_tnl * t , struct sk_buff * skb ,
841
+ const struct tnl_ptk_info * tpi ,
842
+ struct metadata_dst * tun_dst ,
843
+ bool log_ecn_err )
844
+ {
845
+ return __ip6_tnl_rcv (t , skb , tpi , NULL , ip6ip6_dscp_ecn_decapsulate ,
846
+ log_ecn_err );
847
+ }
848
+ EXPORT_SYMBOL (ip6_tnl_rcv );
849
+
850
+ static const struct tnl_ptk_info tpi_v6 = {
851
+ /* no tunnel info required for ipxip6. */
852
+ .proto = htons (ETH_P_IPV6 ),
853
+ };
854
+
855
+ static const struct tnl_ptk_info tpi_v4 = {
856
+ /* no tunnel info required for ipxip6. */
857
+ .proto = htons (ETH_P_IP ),
858
+ };
859
+
860
+ static int ipxip6_rcv (struct sk_buff * skb , u8 ipproto ,
861
+ const struct tnl_ptk_info * tpi ,
862
+ int (* dscp_ecn_decapsulate )(const struct ip6_tnl * t ,
863
+ const struct ipv6hdr * ipv6h ,
864
+ struct sk_buff * skb ))
865
+ {
866
+ struct ip6_tnl * t ;
867
+ const struct ipv6hdr * ipv6h = ipv6_hdr (skb );
868
+ int ret = -1 ;
869
+
870
+ rcu_read_lock ();
871
+ t = ip6_tnl_lookup (dev_net (skb -> dev ), & ipv6h -> saddr , & ipv6h -> daddr );
872
+
873
+ if (t ) {
874
+ u8 tproto = ACCESS_ONCE (t -> parms .proto );
875
+
876
+ if (tproto != ipproto && tproto != 0 )
877
+ goto drop ;
878
+ if (!xfrm6_policy_check (NULL , XFRM_POLICY_IN , skb ))
879
+ goto drop ;
880
+ if (!ip6_tnl_rcv_ctl (t , & ipv6h -> daddr , & ipv6h -> saddr ))
881
+ goto drop ;
882
+ if (iptunnel_pull_header (skb , 0 , tpi -> proto , false))
883
+ goto drop ;
884
+ ret = __ip6_tnl_rcv (t , skb , tpi , NULL , dscp_ecn_decapsulate ,
885
+ log_ecn_error );
828
886
}
887
+
829
888
rcu_read_unlock ();
830
- return 1 ;
831
889
832
- discard :
890
+ return ret ;
891
+
892
+ drop :
893
+ rcu_read_unlock ();
833
894
kfree_skb (skb );
834
895
return 0 ;
835
896
}
836
897
837
898
static int ip4ip6_rcv (struct sk_buff * skb )
838
899
{
839
- return ip6_tnl_rcv (skb , ETH_P_IP , IPPROTO_IPIP ,
840
- ip4ip6_dscp_ecn_decapsulate );
900
+ return ipxip6_rcv (skb , IPPROTO_IP , & tpi_v4 ,
901
+ ip4ip6_dscp_ecn_decapsulate );
841
902
}
842
903
843
904
static int ip6ip6_rcv (struct sk_buff * skb )
844
905
{
845
- return ip6_tnl_rcv (skb , ETH_P_IPV6 , IPPROTO_IPV6 ,
846
- ip6ip6_dscp_ecn_decapsulate );
906
+ return ipxip6_rcv (skb , IPPROTO_IPV6 , & tpi_v6 ,
907
+ ip6ip6_dscp_ecn_decapsulate );
847
908
}
848
909
849
910
struct ipv6_tel_txoption {
@@ -1370,6 +1431,8 @@ ip6_tnl_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
1370
1431
struct net * net = t -> net ;
1371
1432
struct ip6_tnl_net * ip6n = net_generic (net , ip6_tnl_net_id );
1372
1433
1434
+ memset (& p1 , 0 , sizeof (p1 ));
1435
+
1373
1436
switch (cmd ) {
1374
1437
case SIOCGETTUNNEL :
1375
1438
if (dev == ip6n -> fb_tnl_dev ) {
@@ -1549,13 +1612,22 @@ ip6_tnl_dev_init_gen(struct net_device *dev)
1549
1612
return - ENOMEM ;
1550
1613
1551
1614
ret = dst_cache_init (& t -> dst_cache , GFP_KERNEL );
1552
- if (ret ) {
1553
- free_percpu (dev -> tstats );
1554
- dev -> tstats = NULL ;
1555
- return ret ;
1556
- }
1615
+ if (ret )
1616
+ goto free_stats ;
1617
+
1618
+ ret = gro_cells_init (& t -> gro_cells , dev );
1619
+ if (ret )
1620
+ goto destroy_dst ;
1557
1621
1558
1622
return 0 ;
1623
+
1624
+ destroy_dst :
1625
+ dst_cache_destroy (& t -> dst_cache );
1626
+ free_stats :
1627
+ free_percpu (dev -> tstats );
1628
+ dev -> tstats = NULL ;
1629
+
1630
+ return ret ;
1559
1631
}
1560
1632
1561
1633
/**
0 commit comments