mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux.git
synced 2024-08-26 02:39:48 +00:00
![Nikolay Aleksandrov](/assets/img/avatar_default.png)
In preparation for hardware offloading of ipmr/ip6mr we need an interface that allows to check (and later update) the age of entries. Relying on stats alone can show activity but not actual age of the entry, furthermore when there're tens of thousands of entries a lot of the hardware implementations only support "hit" bits which are cleared on read to denote that the entry was active and shouldn't be aged out, these can then be naturally translated into age timestamp and will be compatible with the software forwarding age. Using a lastuse entry doesn't affect performance because the members in that cache line are written to along with the age. Since all new users are encouraged to use ipmr via netlink, this is exported via the RTA_EXPIRES attribute. Also do a minor local variable declaration style adjustment - arrange them longest to shortest. Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com> CC: Roopa Prabhu <roopa@cumulusnetworks.com> CC: Shrijeet Mukherjee <shm@cumulusnetworks.com> CC: Satish Ashok <sashok@cumulusnetworks.com> CC: Donald Sharp <sharpd@cumulusnetworks.com> CC: David S. Miller <davem@davemloft.net> CC: Alexey Kuznetsov <kuznet@ms2.inr.ac.ru> CC: James Morris <jmorris@namei.org> CC: Hideaki YOSHIFUJI <yoshfuji@linux-ipv6.org> CC: Patrick McHardy <kaber@trash.net> Signed-off-by: David S. Miller <davem@davemloft.net>
124 lines
3.1 KiB
C
124 lines
3.1 KiB
C
#ifndef __LINUX_MROUTE_H
|
|
#define __LINUX_MROUTE_H
|
|
|
|
#include <linux/in.h>
|
|
#include <linux/pim.h>
|
|
#include <net/sock.h>
|
|
#include <uapi/linux/mroute.h>
|
|
|
|
#ifdef CONFIG_IP_MROUTE
|
|
static inline int ip_mroute_opt(int opt)
|
|
{
|
|
return opt >= MRT_BASE && opt <= MRT_MAX;
|
|
}
|
|
|
|
int ip_mroute_setsockopt(struct sock *, int, char __user *, unsigned int);
|
|
int ip_mroute_getsockopt(struct sock *, int, char __user *, int __user *);
|
|
int ipmr_ioctl(struct sock *sk, int cmd, void __user *arg);
|
|
int ipmr_compat_ioctl(struct sock *sk, unsigned int cmd, void __user *arg);
|
|
int ip_mr_init(void);
|
|
#else
|
|
static inline int ip_mroute_setsockopt(struct sock *sock, int optname,
|
|
char __user *optval, unsigned int optlen)
|
|
{
|
|
return -ENOPROTOOPT;
|
|
}
|
|
|
|
static inline int ip_mroute_getsockopt(struct sock *sock, int optname,
|
|
char __user *optval, int __user *optlen)
|
|
{
|
|
return -ENOPROTOOPT;
|
|
}
|
|
|
|
static inline int ipmr_ioctl(struct sock *sk, int cmd, void __user *arg)
|
|
{
|
|
return -ENOIOCTLCMD;
|
|
}
|
|
|
|
static inline int ip_mr_init(void)
|
|
{
|
|
return 0;
|
|
}
|
|
|
|
static inline int ip_mroute_opt(int opt)
|
|
{
|
|
return 0;
|
|
}
|
|
#endif
|
|
|
|
struct vif_device {
|
|
struct net_device *dev; /* Device we are using */
|
|
unsigned long bytes_in,bytes_out;
|
|
unsigned long pkt_in,pkt_out; /* Statistics */
|
|
unsigned long rate_limit; /* Traffic shaping (NI) */
|
|
unsigned char threshold; /* TTL threshold */
|
|
unsigned short flags; /* Control flags */
|
|
__be32 local,remote; /* Addresses(remote for tunnels)*/
|
|
int link; /* Physical interface index */
|
|
};
|
|
|
|
#define VIFF_STATIC 0x8000
|
|
|
|
#define VIF_EXISTS(_mrt, _idx) ((_mrt)->vif_table[_idx].dev != NULL)
|
|
#define MFC_LINES 64
|
|
|
|
struct mr_table {
|
|
struct list_head list;
|
|
possible_net_t net;
|
|
u32 id;
|
|
struct sock __rcu *mroute_sk;
|
|
struct timer_list ipmr_expire_timer;
|
|
struct list_head mfc_unres_queue;
|
|
struct list_head mfc_cache_array[MFC_LINES];
|
|
struct vif_device vif_table[MAXVIFS];
|
|
int maxvif;
|
|
atomic_t cache_resolve_queue_len;
|
|
bool mroute_do_assert;
|
|
bool mroute_do_pim;
|
|
int mroute_reg_vif_num;
|
|
};
|
|
|
|
/* mfc_flags:
|
|
* MFC_STATIC - the entry was added statically (not by a routing daemon)
|
|
*/
|
|
enum {
|
|
MFC_STATIC = BIT(0),
|
|
};
|
|
|
|
struct mfc_cache {
|
|
struct list_head list;
|
|
__be32 mfc_mcastgrp; /* Group the entry belongs to */
|
|
__be32 mfc_origin; /* Source of packet */
|
|
vifi_t mfc_parent; /* Source interface */
|
|
int mfc_flags; /* Flags on line */
|
|
|
|
union {
|
|
struct {
|
|
unsigned long expires;
|
|
struct sk_buff_head unresolved; /* Unresolved buffers */
|
|
} unres;
|
|
struct {
|
|
unsigned long last_assert;
|
|
int minvif;
|
|
int maxvif;
|
|
unsigned long bytes;
|
|
unsigned long pkt;
|
|
unsigned long wrong_if;
|
|
unsigned long lastuse;
|
|
unsigned char ttls[MAXVIFS]; /* TTL thresholds */
|
|
} res;
|
|
} mfc_un;
|
|
struct rcu_head rcu;
|
|
};
|
|
|
|
#ifdef __BIG_ENDIAN
|
|
#define MFC_HASH(a,b) (((((__force u32)(__be32)a)>>24)^(((__force u32)(__be32)b)>>26))&(MFC_LINES-1))
|
|
#else
|
|
#define MFC_HASH(a,b) ((((__force u32)(__be32)a)^(((__force u32)(__be32)b)>>2))&(MFC_LINES-1))
|
|
#endif
|
|
|
|
struct rtmsg;
|
|
int ipmr_get_route(struct net *net, struct sk_buff *skb,
|
|
__be32 saddr, __be32 daddr,
|
|
struct rtmsg *rtm, int nowait);
|
|
#endif
|