@@ -387,6 +387,57 @@ static int geneve_udp_encap_recv(struct sock *sk, struct sk_buff *skb)
387
387
return 0 ;
388
388
}
389
389
390
+ /* Callback from net/ipv{4,6}/udp.c to check that we have a tunnel for errors */
391
+ static int geneve_udp_encap_err_lookup (struct sock * sk , struct sk_buff * skb )
392
+ {
393
+ struct genevehdr * geneveh ;
394
+ struct geneve_sock * gs ;
395
+ u8 zero_vni [3 ] = { 0 };
396
+ u8 * vni = zero_vni ;
397
+
398
+ if (skb -> len < GENEVE_BASE_HLEN )
399
+ return - EINVAL ;
400
+
401
+ geneveh = geneve_hdr (skb );
402
+ if (geneveh -> ver != GENEVE_VER )
403
+ return - EINVAL ;
404
+
405
+ if (geneveh -> proto_type != htons (ETH_P_TEB ))
406
+ return - EINVAL ;
407
+
408
+ gs = rcu_dereference_sk_user_data (sk );
409
+ if (!gs )
410
+ return - ENOENT ;
411
+
412
+ if (geneve_get_sk_family (gs ) == AF_INET ) {
413
+ struct iphdr * iph = ip_hdr (skb );
414
+ __be32 addr4 = 0 ;
415
+
416
+ if (!gs -> collect_md ) {
417
+ vni = geneve_hdr (skb )-> vni ;
418
+ addr4 = iph -> daddr ;
419
+ }
420
+
421
+ return geneve_lookup (gs , addr4 , vni ) ? 0 : - ENOENT ;
422
+ }
423
+
424
+ #if IS_ENABLED (CONFIG_IPV6 )
425
+ if (geneve_get_sk_family (gs ) == AF_INET6 ) {
426
+ struct ipv6hdr * ip6h = ipv6_hdr (skb );
427
+ struct in6_addr addr6 = { 0 };
428
+
429
+ if (!gs -> collect_md ) {
430
+ vni = geneve_hdr (skb )-> vni ;
431
+ addr6 = ip6h -> daddr ;
432
+ }
433
+
434
+ return geneve6_lookup (gs , addr6 , vni ) ? 0 : - ENOENT ;
435
+ }
436
+ #endif
437
+
438
+ return - EPFNOSUPPORT ;
439
+ }
440
+
390
441
static struct socket * geneve_create_sock (struct net * net , bool ipv6 ,
391
442
__be16 port , bool ipv6_rx_csum )
392
443
{
@@ -544,6 +595,7 @@ static struct geneve_sock *geneve_socket_create(struct net *net, __be16 port,
544
595
tunnel_cfg .gro_receive = geneve_gro_receive ;
545
596
tunnel_cfg .gro_complete = geneve_gro_complete ;
546
597
tunnel_cfg .encap_rcv = geneve_udp_encap_recv ;
598
+ tunnel_cfg .encap_err_lookup = geneve_udp_encap_err_lookup ;
547
599
tunnel_cfg .encap_destroy = NULL ;
548
600
setup_udp_tunnel_sock (net , sock , & tunnel_cfg );
549
601
list_add (& gs -> list , & gn -> sock_list );
0 commit comments