1 /* 2 * Copyright (C) 2017 Netronome Systems, Inc. 3 * 4 * This software is licensed under the GNU General License Version 2, 5 * June 1991 as shown in the file COPYING in the top-level directory of this 6 * source tree. 7 * 8 * THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM "AS IS" 9 * WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, 10 * BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 11 * FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE 12 * OF THE PROGRAM IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME 13 * THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. 14 */ 15 16 #include <linux/device.h> 17 #include <linux/kernel.h> 18 #include <linux/list.h> 19 #include <linux/netdevice.h> 20 #include <linux/u64_stats_sync.h> 21 #include <net/xdp.h> 22 23 #define DRV_NAME "netdevsim" 24 25 #define NSIM_XDP_MAX_MTU 4000 26 27 #define NSIM_EA(extack, msg) NL_SET_ERR_MSG_MOD((extack), msg) 28 29 struct bpf_prog; 30 struct dentry; 31 struct nsim_vf_config; 32 33 #define NSIM_IPSEC_MAX_SA_COUNT 33 34 #define NSIM_IPSEC_VALID BIT(31) 35 36 struct nsim_sa { 37 struct xfrm_state *xs; 38 __be32 ipaddr[4]; 39 u32 key[4]; 40 u32 salt; 41 bool used; 42 bool crypt; 43 bool rx; 44 }; 45 46 struct nsim_ipsec { 47 struct nsim_sa sa[NSIM_IPSEC_MAX_SA_COUNT]; 48 struct dentry *pfile; 49 u32 count; 50 u32 tx; 51 u32 ok; 52 }; 53 54 struct netdevsim { 55 struct net_device *netdev; 56 57 u64 tx_packets; 58 u64 tx_bytes; 59 struct u64_stats_sync syncp; 60 61 struct device dev; 62 63 struct dentry *ddir; 64 65 unsigned int num_vfs; 66 struct nsim_vf_config *vfconfigs; 67 68 struct bpf_prog *bpf_offloaded; 69 u32 bpf_offloaded_id; 70 71 struct xdp_attachment_info xdp; 72 struct xdp_attachment_info xdp_hw; 73 74 u32 prog_id_gen; 75 76 bool bpf_bind_accept; 77 u32 bpf_bind_verifier_delay; 78 struct dentry *ddir_bpf_bound_progs; 79 struct list_head bpf_bound_progs; 80 81 bool bpf_tc_accept; 82 bool bpf_tc_non_bound_accept; 83 bool bpf_xdpdrv_accept; 84 bool bpf_xdpoffload_accept; 85 86 bool bpf_map_accept; 87 struct list_head bpf_bound_maps; 88 #if IS_ENABLED(CONFIG_NET_DEVLINK) 89 struct devlink *devlink; 90 #endif 91 struct nsim_ipsec ipsec; 92 }; 93 94 extern struct dentry *nsim_ddir; 95 96 #ifdef CONFIG_BPF_SYSCALL 97 int nsim_bpf_init(struct netdevsim *ns); 98 void nsim_bpf_uninit(struct netdevsim *ns); 99 int nsim_bpf(struct net_device *dev, struct netdev_bpf *bpf); 100 int nsim_bpf_disable_tc(struct netdevsim *ns); 101 int nsim_bpf_setup_tc_block_cb(enum tc_setup_type type, 102 void *type_data, void *cb_priv); 103 #else 104 static inline int nsim_bpf_init(struct netdevsim *ns) 105 { 106 return 0; 107 } 108 109 static inline void nsim_bpf_uninit(struct netdevsim *ns) 110 { 111 } 112 113 static inline int nsim_bpf(struct net_device *dev, struct netdev_bpf *bpf) 114 { 115 return bpf->command == XDP_QUERY_PROG ? 0 : -EOPNOTSUPP; 116 } 117 118 static inline int nsim_bpf_disable_tc(struct netdevsim *ns) 119 { 120 return 0; 121 } 122 123 static inline int 124 nsim_bpf_setup_tc_block_cb(enum tc_setup_type type, void *type_data, 125 void *cb_priv) 126 { 127 return -EOPNOTSUPP; 128 } 129 #endif 130 131 #if IS_ENABLED(CONFIG_NET_DEVLINK) 132 enum nsim_resource_id { 133 NSIM_RESOURCE_NONE, /* DEVLINK_RESOURCE_ID_PARENT_TOP */ 134 NSIM_RESOURCE_IPV4, 135 NSIM_RESOURCE_IPV4_FIB, 136 NSIM_RESOURCE_IPV4_FIB_RULES, 137 NSIM_RESOURCE_IPV6, 138 NSIM_RESOURCE_IPV6_FIB, 139 NSIM_RESOURCE_IPV6_FIB_RULES, 140 }; 141 142 int nsim_devlink_setup(struct netdevsim *ns); 143 void nsim_devlink_teardown(struct netdevsim *ns); 144 145 int nsim_devlink_init(void); 146 void nsim_devlink_exit(void); 147 148 int nsim_fib_init(void); 149 void nsim_fib_exit(void); 150 u64 nsim_fib_get_val(struct net *net, enum nsim_resource_id res_id, bool max); 151 int nsim_fib_set_max(struct net *net, enum nsim_resource_id res_id, u64 val, 152 struct netlink_ext_ack *extack); 153 #else 154 static inline int nsim_devlink_setup(struct netdevsim *ns) 155 { 156 return 0; 157 } 158 159 static inline void nsim_devlink_teardown(struct netdevsim *ns) 160 { 161 } 162 163 static inline int nsim_devlink_init(void) 164 { 165 return 0; 166 } 167 168 static inline void nsim_devlink_exit(void) 169 { 170 } 171 #endif 172 173 #if IS_ENABLED(CONFIG_XFRM_OFFLOAD) 174 void nsim_ipsec_init(struct netdevsim *ns); 175 void nsim_ipsec_teardown(struct netdevsim *ns); 176 bool nsim_ipsec_tx(struct netdevsim *ns, struct sk_buff *skb); 177 #else 178 static inline void nsim_ipsec_init(struct netdevsim *ns) 179 { 180 } 181 182 static inline void nsim_ipsec_teardown(struct netdevsim *ns) 183 { 184 } 185 186 static inline bool nsim_ipsec_tx(struct netdevsim *ns, struct sk_buff *skb) 187 { 188 return true; 189 } 190 #endif 191 192 static inline struct netdevsim *to_nsim(struct device *ptr) 193 { 194 return container_of(ptr, struct netdevsim, dev); 195 } 196