xref: /openbmc/linux/drivers/net/ethernet/mellanox/mlx5/core/en_accel/ipsec.h (revision c900529f3d9161bfde5cca0754f83b4d3c3e0220)
1  /*
2   * Copyright (c) 2017 Mellanox Technologies. All rights reserved.
3   *
4   * This software is available to you under a choice of one of two
5   * licenses.  You may choose to be licensed under the terms of the GNU
6   * General Public License (GPL) Version 2, available from the file
7   * COPYING in the main directory of this source tree, or the
8   * OpenIB.org BSD license below:
9   *
10   *     Redistribution and use in source and binary forms, with or
11   *     without modification, are permitted provided that the following
12   *     conditions are met:
13   *
14   *      - Redistributions of source code must retain the above
15   *        copyright notice, this list of conditions and the following
16   *        disclaimer.
17   *
18   *      - Redistributions in binary form must reproduce the above
19   *        copyright notice, this list of conditions and the following
20   *        disclaimer in the documentation and/or other materials
21   *        provided with the distribution.
22   *
23   * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
24   * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
25   * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
26   * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
27   * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
28   * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
29   * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
30   * SOFTWARE.
31   *
32   */
33  
34  #ifndef __MLX5E_IPSEC_H__
35  #define __MLX5E_IPSEC_H__
36  
37  #include <linux/mlx5/device.h>
38  #include <net/xfrm.h>
39  #include <linux/idr.h>
40  #include "lib/aso.h"
41  
42  #define MLX5E_IPSEC_SADB_RX_BITS 10
43  #define MLX5E_IPSEC_ESN_SCOPE_MID 0x80000000L
44  
45  struct aes_gcm_keymat {
46  	u64   seq_iv;
47  
48  	u32   salt;
49  	u32   icv_len;
50  
51  	u32   key_len;
52  	u32   aes_key[256 / 32];
53  };
54  
55  struct upspec {
56  	u16 dport;
57  	u16 dport_mask;
58  	u16 sport;
59  	u16 sport_mask;
60  	u8 proto;
61  };
62  
63  struct mlx5_ipsec_lft {
64  	u64 hard_packet_limit;
65  	u64 soft_packet_limit;
66  	u64 numb_rounds_hard;
67  	u64 numb_rounds_soft;
68  };
69  
70  struct mlx5_replay_esn {
71  	u32 replay_window;
72  	u32 esn;
73  	u32 esn_msb;
74  	u8 overlap : 1;
75  	u8 trigger : 1;
76  };
77  
78  struct mlx5_accel_esp_xfrm_attrs {
79  	u32   spi;
80  	u32   mode;
81  	struct aes_gcm_keymat aes_gcm;
82  
83  	union {
84  		__be32 a4;
85  		__be32 a6[4];
86  	} saddr;
87  
88  	union {
89  		__be32 a4;
90  		__be32 a6[4];
91  	} daddr;
92  
93  	struct upspec upspec;
94  	u8 dir : 2;
95  	u8 type : 2;
96  	u8 drop : 1;
97  	u8 encap : 1;
98  	u8 family;
99  	struct mlx5_replay_esn replay_esn;
100  	u32 authsize;
101  	u32 reqid;
102  	struct mlx5_ipsec_lft lft;
103  	union {
104  		u8 smac[ETH_ALEN];
105  		__be16 sport;
106  	};
107  	union {
108  		u8 dmac[ETH_ALEN];
109  		__be16 dport;
110  	};
111  };
112  
113  enum mlx5_ipsec_cap {
114  	MLX5_IPSEC_CAP_CRYPTO		= 1 << 0,
115  	MLX5_IPSEC_CAP_ESN		= 1 << 1,
116  	MLX5_IPSEC_CAP_PACKET_OFFLOAD	= 1 << 2,
117  	MLX5_IPSEC_CAP_ROCE             = 1 << 3,
118  	MLX5_IPSEC_CAP_PRIO             = 1 << 4,
119  	MLX5_IPSEC_CAP_TUNNEL           = 1 << 5,
120  	MLX5_IPSEC_CAP_ESPINUDP         = 1 << 6,
121  };
122  
123  struct mlx5e_priv;
124  
125  struct mlx5e_ipsec_hw_stats {
126  	u64 ipsec_rx_pkts;
127  	u64 ipsec_rx_bytes;
128  	u64 ipsec_rx_drop_pkts;
129  	u64 ipsec_rx_drop_bytes;
130  	u64 ipsec_tx_pkts;
131  	u64 ipsec_tx_bytes;
132  	u64 ipsec_tx_drop_pkts;
133  	u64 ipsec_tx_drop_bytes;
134  };
135  
136  struct mlx5e_ipsec_sw_stats {
137  	atomic64_t ipsec_rx_drop_sp_alloc;
138  	atomic64_t ipsec_rx_drop_sadb_miss;
139  	atomic64_t ipsec_rx_drop_syndrome;
140  	atomic64_t ipsec_tx_drop_bundle;
141  	atomic64_t ipsec_tx_drop_no_state;
142  	atomic64_t ipsec_tx_drop_not_ip;
143  	atomic64_t ipsec_tx_drop_trailer;
144  };
145  
146  struct mlx5e_ipsec_fc;
147  struct mlx5e_ipsec_tx;
148  
149  struct mlx5e_ipsec_work {
150  	struct work_struct work;
151  	struct mlx5e_ipsec_sa_entry *sa_entry;
152  	void *data;
153  };
154  
155  struct mlx5e_ipsec_netevent_data {
156  	u8 addr[ETH_ALEN];
157  };
158  
159  struct mlx5e_ipsec_dwork {
160  	struct delayed_work dwork;
161  	struct mlx5e_ipsec_sa_entry *sa_entry;
162  };
163  
164  struct mlx5e_ipsec_aso {
165  	u8 __aligned(64) ctx[MLX5_ST_SZ_BYTES(ipsec_aso)];
166  	dma_addr_t dma_addr;
167  	struct mlx5_aso *aso;
168  	/* Protect ASO WQ access, as it is global to whole IPsec */
169  	spinlock_t lock;
170  };
171  
172  struct mlx5e_ipsec_rx_create_attr {
173  	struct mlx5_flow_namespace *ns;
174  	struct mlx5_ttc_table *ttc;
175  	u32 family;
176  	int prio;
177  	int pol_level;
178  	int sa_level;
179  	int status_level;
180  	enum mlx5_flow_namespace_type chains_ns;
181  };
182  
183  struct mlx5e_ipsec_ft {
184  	struct mutex mutex; /* Protect changes to this struct */
185  	struct mlx5_flow_table *pol;
186  	struct mlx5_flow_table *sa;
187  	struct mlx5_flow_table *status;
188  	u32 refcnt;
189  };
190  
191  struct mlx5e_ipsec_rule {
192  	struct mlx5_flow_handle *rule;
193  	struct mlx5_modify_hdr *modify_hdr;
194  	struct mlx5_pkt_reformat *pkt_reformat;
195  	struct mlx5_fc *fc;
196  };
197  
198  struct mlx5e_ipsec_miss {
199  	struct mlx5_flow_group *group;
200  	struct mlx5_flow_handle *rule;
201  };
202  
203  struct mlx5e_ipsec_rx {
204  	struct mlx5e_ipsec_ft ft;
205  	struct mlx5e_ipsec_miss pol;
206  	struct mlx5e_ipsec_miss sa;
207  	struct mlx5e_ipsec_rule status;
208  	struct mlx5e_ipsec_miss status_drop;
209  	struct mlx5_fc *status_drop_cnt;
210  	struct mlx5e_ipsec_fc *fc;
211  	struct mlx5_fs_chains *chains;
212  	u8 allow_tunnel_mode : 1;
213  	struct xarray ipsec_obj_id_map;
214  };
215  
216  struct mlx5e_ipsec_tx_create_attr {
217  	int prio;
218  	int pol_level;
219  	int sa_level;
220  	int cnt_level;
221  	enum mlx5_flow_namespace_type chains_ns;
222  };
223  
224  struct mlx5e_ipsec {
225  	struct mlx5_core_dev *mdev;
226  	struct xarray sadb;
227  	struct mlx5e_ipsec_sw_stats sw_stats;
228  	struct mlx5e_ipsec_hw_stats hw_stats;
229  	struct workqueue_struct *wq;
230  	struct mlx5e_flow_steering *fs;
231  	struct mlx5e_ipsec_rx *rx_ipv4;
232  	struct mlx5e_ipsec_rx *rx_ipv6;
233  	struct mlx5e_ipsec_rx *rx_esw;
234  	struct mlx5e_ipsec_tx *tx;
235  	struct mlx5e_ipsec_tx *tx_esw;
236  	struct mlx5e_ipsec_aso *aso;
237  	struct notifier_block nb;
238  	struct notifier_block netevent_nb;
239  	struct mlx5_ipsec_fs *roce;
240  	u8 is_uplink_rep: 1;
241  };
242  
243  struct mlx5e_ipsec_esn_state {
244  	u32 esn;
245  	u32 esn_msb;
246  	u8 overlap: 1;
247  };
248  
249  struct mlx5e_ipsec_limits {
250  	u64 round;
251  	u8 soft_limit_hit : 1;
252  	u8 fix_limit : 1;
253  };
254  
255  struct mlx5e_ipsec_sa_entry {
256  	struct mlx5e_ipsec_esn_state esn_state;
257  	struct xfrm_state *x;
258  	struct mlx5e_ipsec *ipsec;
259  	struct mlx5_accel_esp_xfrm_attrs attrs;
260  	void (*set_iv_op)(struct sk_buff *skb, struct xfrm_state *x,
261  			  struct xfrm_offload *xo);
262  	u32 ipsec_obj_id;
263  	u32 enc_key_id;
264  	struct mlx5e_ipsec_rule ipsec_rule;
265  	struct mlx5e_ipsec_work *work;
266  	struct mlx5e_ipsec_dwork *dwork;
267  	struct mlx5e_ipsec_limits limits;
268  	u32 rx_mapped_id;
269  };
270  
271  struct mlx5_accel_pol_xfrm_attrs {
272  	union {
273  		__be32 a4;
274  		__be32 a6[4];
275  	} saddr;
276  
277  	union {
278  		__be32 a4;
279  		__be32 a6[4];
280  	} daddr;
281  
282  	struct upspec upspec;
283  	u8 family;
284  	u8 action;
285  	u8 type : 2;
286  	u8 dir : 2;
287  	u32 reqid;
288  	u32 prio;
289  };
290  
291  struct mlx5e_ipsec_pol_entry {
292  	struct xfrm_policy *x;
293  	struct mlx5e_ipsec *ipsec;
294  	struct mlx5e_ipsec_rule ipsec_rule;
295  	struct mlx5_accel_pol_xfrm_attrs attrs;
296  };
297  
298  #ifdef CONFIG_MLX5_EN_IPSEC
299  
300  void mlx5e_ipsec_init(struct mlx5e_priv *priv);
301  void mlx5e_ipsec_cleanup(struct mlx5e_priv *priv);
302  void mlx5e_ipsec_build_netdev(struct mlx5e_priv *priv);
303  
304  void mlx5e_accel_ipsec_fs_cleanup(struct mlx5e_ipsec *ipsec);
305  int mlx5e_accel_ipsec_fs_init(struct mlx5e_ipsec *ipsec);
306  int mlx5e_accel_ipsec_fs_add_rule(struct mlx5e_ipsec_sa_entry *sa_entry);
307  void mlx5e_accel_ipsec_fs_del_rule(struct mlx5e_ipsec_sa_entry *sa_entry);
308  int mlx5e_accel_ipsec_fs_add_pol(struct mlx5e_ipsec_pol_entry *pol_entry);
309  void mlx5e_accel_ipsec_fs_del_pol(struct mlx5e_ipsec_pol_entry *pol_entry);
310  void mlx5e_accel_ipsec_fs_modify(struct mlx5e_ipsec_sa_entry *sa_entry);
311  bool mlx5e_ipsec_fs_tunnel_enabled(struct mlx5e_ipsec_sa_entry *sa_entry);
312  
313  int mlx5_ipsec_create_sa_ctx(struct mlx5e_ipsec_sa_entry *sa_entry);
314  void mlx5_ipsec_free_sa_ctx(struct mlx5e_ipsec_sa_entry *sa_entry);
315  
316  u32 mlx5_ipsec_device_caps(struct mlx5_core_dev *mdev);
317  
318  void mlx5_accel_esp_modify_xfrm(struct mlx5e_ipsec_sa_entry *sa_entry,
319  				const struct mlx5_accel_esp_xfrm_attrs *attrs);
320  
321  int mlx5e_ipsec_aso_init(struct mlx5e_ipsec *ipsec);
322  void mlx5e_ipsec_aso_cleanup(struct mlx5e_ipsec *ipsec);
323  
324  int mlx5e_ipsec_aso_query(struct mlx5e_ipsec_sa_entry *sa_entry,
325  			  struct mlx5_wqe_aso_ctrl_seg *data);
326  void mlx5e_accel_ipsec_fs_read_stats(struct mlx5e_priv *priv,
327  				     void *ipsec_stats);
328  
329  void mlx5e_ipsec_build_accel_xfrm_attrs(struct mlx5e_ipsec_sa_entry *sa_entry,
330  					struct mlx5_accel_esp_xfrm_attrs *attrs);
331  static inline struct mlx5_core_dev *
mlx5e_ipsec_sa2dev(struct mlx5e_ipsec_sa_entry * sa_entry)332  mlx5e_ipsec_sa2dev(struct mlx5e_ipsec_sa_entry *sa_entry)
333  {
334  	return sa_entry->ipsec->mdev;
335  }
336  
337  static inline struct mlx5_core_dev *
mlx5e_ipsec_pol2dev(struct mlx5e_ipsec_pol_entry * pol_entry)338  mlx5e_ipsec_pol2dev(struct mlx5e_ipsec_pol_entry *pol_entry)
339  {
340  	return pol_entry->ipsec->mdev;
341  }
342  
addr6_all_zero(__be32 * addr6)343  static inline bool addr6_all_zero(__be32 *addr6)
344  {
345  	static const __be32 zaddr6[4] = {};
346  
347  	return !memcmp(addr6, zaddr6, sizeof(zaddr6));
348  }
349  #else
mlx5e_ipsec_init(struct mlx5e_priv * priv)350  static inline void mlx5e_ipsec_init(struct mlx5e_priv *priv)
351  {
352  }
353  
mlx5e_ipsec_cleanup(struct mlx5e_priv * priv)354  static inline void mlx5e_ipsec_cleanup(struct mlx5e_priv *priv)
355  {
356  }
357  
mlx5e_ipsec_build_netdev(struct mlx5e_priv * priv)358  static inline void mlx5e_ipsec_build_netdev(struct mlx5e_priv *priv)
359  {
360  }
361  
mlx5_ipsec_device_caps(struct mlx5_core_dev * mdev)362  static inline u32 mlx5_ipsec_device_caps(struct mlx5_core_dev *mdev)
363  {
364  	return 0;
365  }
366  #endif
367  
368  #endif	/* __MLX5E_IPSEC_H__ */
369