Skip to content
/ linux Public
forked from torvalds/linux

Commit

Permalink
l3mdev: add infrastructure for table to VRF mapping
Browse files Browse the repository at this point in the history
Add infrastructure to l3mdev (the core code for Layer 3 master devices) in
order to find out the corresponding VRF device for a given table id.
Therefore, the l3mdev implementations:
 - can register a callback that returns the device index of the l3mdev
   associated with a given table id;
 - can offer the lookup function (table to VRF device).

Signed-off-by: Andrea Mayer <[email protected]>
Signed-off-by: David S. Miller <[email protected]>
  • Loading branch information
skorpion17 authored and davem330 committed Jun 21, 2020
1 parent c5eb179 commit 49042c2
Show file tree
Hide file tree
Showing 2 changed files with 132 additions and 0 deletions.
39 changes: 39 additions & 0 deletions include/net/l3mdev.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,16 @@
#include <net/dst.h>
#include <net/fib_rules.h>

enum l3mdev_type {
L3MDEV_TYPE_UNSPEC,
L3MDEV_TYPE_VRF,
__L3MDEV_TYPE_MAX
};

#define L3MDEV_TYPE_MAX (__L3MDEV_TYPE_MAX - 1)

typedef int (*lookup_by_table_id_t)(struct net *net, u32 table_d);

/**
* struct l3mdev_ops - l3mdev operations
*
Expand Down Expand Up @@ -37,6 +47,15 @@ struct l3mdev_ops {

#ifdef CONFIG_NET_L3_MASTER_DEV

int l3mdev_table_lookup_register(enum l3mdev_type l3type,
lookup_by_table_id_t fn);

void l3mdev_table_lookup_unregister(enum l3mdev_type l3type,
lookup_by_table_id_t fn);

int l3mdev_ifindex_lookup_by_table_id(enum l3mdev_type l3type, struct net *net,
u32 table_id);

int l3mdev_fib_rule_match(struct net *net, struct flowi *fl,
struct fib_lookup_arg *arg);

Expand Down Expand Up @@ -280,6 +299,26 @@ struct sk_buff *l3mdev_ip6_out(struct sock *sk, struct sk_buff *skb)
return skb;
}

static inline
int l3mdev_table_lookup_register(enum l3mdev_type l3type,
lookup_by_table_id_t fn)
{
return -EOPNOTSUPP;
}

static inline
void l3mdev_table_lookup_unregister(enum l3mdev_type l3type,
lookup_by_table_id_t fn)
{
}

static inline
int l3mdev_ifindex_lookup_by_table_id(enum l3mdev_type l3type, struct net *net,
u32 table_id)
{
return -ENODEV;
}

static inline
int l3mdev_fib_rule_match(struct net *net, struct flowi *fl,
struct fib_lookup_arg *arg)
Expand Down
93 changes: 93 additions & 0 deletions net/l3mdev/l3mdev.c
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,99 @@
#include <net/fib_rules.h>
#include <net/l3mdev.h>

static DEFINE_SPINLOCK(l3mdev_lock);

struct l3mdev_handler {
lookup_by_table_id_t dev_lookup;
};

static struct l3mdev_handler l3mdev_handlers[L3MDEV_TYPE_MAX + 1];

static int l3mdev_check_type(enum l3mdev_type l3type)
{
if (l3type <= L3MDEV_TYPE_UNSPEC || l3type > L3MDEV_TYPE_MAX)
return -EINVAL;

return 0;
}

int l3mdev_table_lookup_register(enum l3mdev_type l3type,
lookup_by_table_id_t fn)
{
struct l3mdev_handler *hdlr;
int res;

res = l3mdev_check_type(l3type);
if (res)
return res;

hdlr = &l3mdev_handlers[l3type];

spin_lock(&l3mdev_lock);

if (hdlr->dev_lookup) {
res = -EBUSY;
goto unlock;
}

hdlr->dev_lookup = fn;
res = 0;

unlock:
spin_unlock(&l3mdev_lock);

return res;
}
EXPORT_SYMBOL_GPL(l3mdev_table_lookup_register);

void l3mdev_table_lookup_unregister(enum l3mdev_type l3type,
lookup_by_table_id_t fn)
{
struct l3mdev_handler *hdlr;

if (l3mdev_check_type(l3type))
return;

hdlr = &l3mdev_handlers[l3type];

spin_lock(&l3mdev_lock);

if (hdlr->dev_lookup == fn)
hdlr->dev_lookup = NULL;

spin_unlock(&l3mdev_lock);
}
EXPORT_SYMBOL_GPL(l3mdev_table_lookup_unregister);

int l3mdev_ifindex_lookup_by_table_id(enum l3mdev_type l3type,
struct net *net, u32 table_id)
{
lookup_by_table_id_t lookup;
struct l3mdev_handler *hdlr;
int ifindex = -EINVAL;
int res;

res = l3mdev_check_type(l3type);
if (res)
return res;

hdlr = &l3mdev_handlers[l3type];

spin_lock(&l3mdev_lock);

lookup = hdlr->dev_lookup;
if (!lookup)
goto unlock;

ifindex = lookup(net, table_id);

unlock:
spin_unlock(&l3mdev_lock);

return ifindex;
}
EXPORT_SYMBOL_GPL(l3mdev_ifindex_lookup_by_table_id);

/**
* l3mdev_master_ifindex - get index of L3 master device
* @dev: targeted interface
Expand Down

0 comments on commit 49042c2

Please sign in to comment.