Skip to content

Commit 1c1e761

Browse files
Zashasborkmann
authored andcommitted
ipv6: sr: export function lookup_nexthop
The function lookup_nexthop is essential to implement most of the seg6local actions. As we want to provide a BPF helper allowing to apply some of these actions on the packet being processed, the helper should be able to call this function, hence the need to make it public. Moreover, if one argument is incorrect or if the next hop can not be found, an error should be returned by the BPF helper so the BPF program can adapt its processing of the packet (return an error, properly force the drop, ...). This patch hence makes this function return dst->error to indicate a possible error. Signed-off-by: Mathieu Xhonneux <[email protected]> Acked-by: David Lebrun <[email protected]> Signed-off-by: Daniel Borkmann <[email protected]>
1 parent 63526e1 commit 1c1e761

File tree

3 files changed

+37
-10
lines changed

3 files changed

+37
-10
lines changed

include/net/seg6.h

+2-1
Original file line numberDiff line numberDiff line change
@@ -67,5 +67,6 @@ extern bool seg6_validate_srh(struct ipv6_sr_hdr *srh, int len);
6767
extern int seg6_do_srh_encap(struct sk_buff *skb, struct ipv6_sr_hdr *osrh,
6868
int proto);
6969
extern int seg6_do_srh_inline(struct sk_buff *skb, struct ipv6_sr_hdr *osrh);
70-
70+
extern int seg6_lookup_nexthop(struct sk_buff *skb, struct in6_addr *nhaddr,
71+
u32 tbl_id);
7172
#endif

include/net/seg6_local.h

+24
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
/*
2+
* SR-IPv6 implementation
3+
*
4+
* Authors:
5+
* David Lebrun <[email protected]>
6+
* eBPF support: Mathieu Xhonneux <[email protected]>
7+
*
8+
*
9+
* This program is free software; you can redistribute it and/or
10+
* modify it under the terms of the GNU General Public License
11+
* as published by the Free Software Foundation; either version
12+
* 2 of the License, or (at your option) any later version.
13+
*/
14+
15+
#ifndef _NET_SEG6_LOCAL_H
16+
#define _NET_SEG6_LOCAL_H
17+
18+
#include <linux/net.h>
19+
#include <linux/ipv6.h>
20+
21+
extern int seg6_lookup_nexthop(struct sk_buff *skb, struct in6_addr *nhaddr,
22+
u32 tbl_id);
23+
24+
#endif

net/ipv6/seg6_local.c

+11-9
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030
#ifdef CONFIG_IPV6_SEG6_HMAC
3131
#include <net/seg6_hmac.h>
3232
#endif
33+
#include <net/seg6_local.h>
3334
#include <linux/etherdevice.h>
3435

3536
struct seg6_local_lwt;
@@ -140,8 +141,8 @@ static void advance_nextseg(struct ipv6_sr_hdr *srh, struct in6_addr *daddr)
140141
*daddr = *addr;
141142
}
142143

143-
static void lookup_nexthop(struct sk_buff *skb, struct in6_addr *nhaddr,
144-
u32 tbl_id)
144+
int seg6_lookup_nexthop(struct sk_buff *skb, struct in6_addr *nhaddr,
145+
u32 tbl_id)
145146
{
146147
struct net *net = dev_net(skb->dev);
147148
struct ipv6hdr *hdr = ipv6_hdr(skb);
@@ -187,6 +188,7 @@ static void lookup_nexthop(struct sk_buff *skb, struct in6_addr *nhaddr,
187188

188189
skb_dst_drop(skb);
189190
skb_dst_set(skb, dst);
191+
return dst->error;
190192
}
191193

192194
/* regular endpoint function */
@@ -200,7 +202,7 @@ static int input_action_end(struct sk_buff *skb, struct seg6_local_lwt *slwt)
200202

201203
advance_nextseg(srh, &ipv6_hdr(skb)->daddr);
202204

203-
lookup_nexthop(skb, NULL, 0);
205+
seg6_lookup_nexthop(skb, NULL, 0);
204206

205207
return dst_input(skb);
206208

@@ -220,7 +222,7 @@ static int input_action_end_x(struct sk_buff *skb, struct seg6_local_lwt *slwt)
220222

221223
advance_nextseg(srh, &ipv6_hdr(skb)->daddr);
222224

223-
lookup_nexthop(skb, &slwt->nh6, 0);
225+
seg6_lookup_nexthop(skb, &slwt->nh6, 0);
224226

225227
return dst_input(skb);
226228

@@ -239,7 +241,7 @@ static int input_action_end_t(struct sk_buff *skb, struct seg6_local_lwt *slwt)
239241

240242
advance_nextseg(srh, &ipv6_hdr(skb)->daddr);
241243

242-
lookup_nexthop(skb, NULL, slwt->table);
244+
seg6_lookup_nexthop(skb, NULL, slwt->table);
243245

244246
return dst_input(skb);
245247

@@ -331,7 +333,7 @@ static int input_action_end_dx6(struct sk_buff *skb,
331333
if (!ipv6_addr_any(&slwt->nh6))
332334
nhaddr = &slwt->nh6;
333335

334-
lookup_nexthop(skb, nhaddr, 0);
336+
seg6_lookup_nexthop(skb, nhaddr, 0);
335337

336338
return dst_input(skb);
337339
drop:
@@ -380,7 +382,7 @@ static int input_action_end_dt6(struct sk_buff *skb,
380382
if (!pskb_may_pull(skb, sizeof(struct ipv6hdr)))
381383
goto drop;
382384

383-
lookup_nexthop(skb, NULL, slwt->table);
385+
seg6_lookup_nexthop(skb, NULL, slwt->table);
384386

385387
return dst_input(skb);
386388

@@ -406,7 +408,7 @@ static int input_action_end_b6(struct sk_buff *skb, struct seg6_local_lwt *slwt)
406408
ipv6_hdr(skb)->payload_len = htons(skb->len - sizeof(struct ipv6hdr));
407409
skb_set_transport_header(skb, sizeof(struct ipv6hdr));
408410

409-
lookup_nexthop(skb, NULL, 0);
411+
seg6_lookup_nexthop(skb, NULL, 0);
410412

411413
return dst_input(skb);
412414

@@ -438,7 +440,7 @@ static int input_action_end_b6_encap(struct sk_buff *skb,
438440
ipv6_hdr(skb)->payload_len = htons(skb->len - sizeof(struct ipv6hdr));
439441
skb_set_transport_header(skb, sizeof(struct ipv6hdr));
440442

441-
lookup_nexthop(skb, NULL, 0);
443+
seg6_lookup_nexthop(skb, NULL, 0);
442444

443445
return dst_input(skb);
444446

0 commit comments

Comments
 (0)