Commit 6ebbe97a authored by Ahmed Zaki's avatar Ahmed Zaki Committed by Tony Nguyen

ice: Add a per-VF limit on number of FDIR filters

While the iavf driver adds a s/w limit (128) on the number of FDIR
filters that the VF can request, a malicious VF driver can request more
than that and exhaust the resources for other VFs.

Add a similar limit in ice.

CC: stable@vger.kernel.org
Fixes: 1f7ea1cd ("ice: Enable FDIR Configure for AVF")
Reviewed-by: default avatarPrzemek Kitszel <przemyslaw.kitszel@intel.com>
Suggested-by: default avatarSridhar Samudrala <sridhar.samudrala@intel.com>
Signed-off-by: default avatarAhmed Zaki <ahmed.zaki@intel.com>
Reviewed-by: default avatarWojciech Drewek <wojciech.drewek@intel.com>
Tested-by: default avatarRafal Romanowski <rafal.romanowski@intel.com>
Signed-off-by: default avatarTony Nguyen <anthony.l.nguyen@intel.com>
parent 3ba359c0
...@@ -534,7 +534,7 @@ ice_parse_rx_flow_user_data(struct ethtool_rx_flow_spec *fsp, ...@@ -534,7 +534,7 @@ ice_parse_rx_flow_user_data(struct ethtool_rx_flow_spec *fsp,
* *
* Returns the number of available flow director filters to this VSI * Returns the number of available flow director filters to this VSI
*/ */
static int ice_fdir_num_avail_fltr(struct ice_hw *hw, struct ice_vsi *vsi) int ice_fdir_num_avail_fltr(struct ice_hw *hw, struct ice_vsi *vsi)
{ {
u16 vsi_num = ice_get_hw_vsi_num(hw, vsi->idx); u16 vsi_num = ice_get_hw_vsi_num(hw, vsi->idx);
u16 num_guar; u16 num_guar;
......
...@@ -207,6 +207,8 @@ struct ice_fdir_base_pkt { ...@@ -207,6 +207,8 @@ struct ice_fdir_base_pkt {
const u8 *tun_pkt; const u8 *tun_pkt;
}; };
struct ice_vsi;
int ice_alloc_fd_res_cntr(struct ice_hw *hw, u16 *cntr_id); int ice_alloc_fd_res_cntr(struct ice_hw *hw, u16 *cntr_id);
int ice_free_fd_res_cntr(struct ice_hw *hw, u16 cntr_id); int ice_free_fd_res_cntr(struct ice_hw *hw, u16 cntr_id);
int ice_alloc_fd_guar_item(struct ice_hw *hw, u16 *cntr_id, u16 num_fltr); int ice_alloc_fd_guar_item(struct ice_hw *hw, u16 *cntr_id, u16 num_fltr);
...@@ -218,6 +220,7 @@ int ...@@ -218,6 +220,7 @@ int
ice_fdir_get_gen_prgm_pkt(struct ice_hw *hw, struct ice_fdir_fltr *input, ice_fdir_get_gen_prgm_pkt(struct ice_hw *hw, struct ice_fdir_fltr *input,
u8 *pkt, bool frag, bool tun); u8 *pkt, bool frag, bool tun);
int ice_get_fdir_cnt_all(struct ice_hw *hw); int ice_get_fdir_cnt_all(struct ice_hw *hw);
int ice_fdir_num_avail_fltr(struct ice_hw *hw, struct ice_vsi *vsi);
bool ice_fdir_is_dup_fltr(struct ice_hw *hw, struct ice_fdir_fltr *input); bool ice_fdir_is_dup_fltr(struct ice_hw *hw, struct ice_fdir_fltr *input);
bool ice_fdir_has_frag(enum ice_fltr_ptype flow); bool ice_fdir_has_frag(enum ice_fltr_ptype flow);
struct ice_fdir_fltr * struct ice_fdir_fltr *
......
...@@ -536,6 +536,8 @@ static void ice_vc_fdir_reset_cnt_all(struct ice_vf_fdir *fdir) ...@@ -536,6 +536,8 @@ static void ice_vc_fdir_reset_cnt_all(struct ice_vf_fdir *fdir)
fdir->fdir_fltr_cnt[flow][0] = 0; fdir->fdir_fltr_cnt[flow][0] = 0;
fdir->fdir_fltr_cnt[flow][1] = 0; fdir->fdir_fltr_cnt[flow][1] = 0;
} }
fdir->fdir_fltr_cnt_total = 0;
} }
/** /**
...@@ -1560,6 +1562,7 @@ ice_vc_add_fdir_fltr_post(struct ice_vf *vf, struct ice_vf_fdir_ctx *ctx, ...@@ -1560,6 +1562,7 @@ ice_vc_add_fdir_fltr_post(struct ice_vf *vf, struct ice_vf_fdir_ctx *ctx,
resp->status = status; resp->status = status;
resp->flow_id = conf->flow_id; resp->flow_id = conf->flow_id;
vf->fdir.fdir_fltr_cnt[conf->input.flow_type][is_tun]++; vf->fdir.fdir_fltr_cnt[conf->input.flow_type][is_tun]++;
vf->fdir.fdir_fltr_cnt_total++;
ret = ice_vc_send_msg_to_vf(vf, ctx->v_opcode, v_ret, ret = ice_vc_send_msg_to_vf(vf, ctx->v_opcode, v_ret,
(u8 *)resp, len); (u8 *)resp, len);
...@@ -1624,6 +1627,7 @@ ice_vc_del_fdir_fltr_post(struct ice_vf *vf, struct ice_vf_fdir_ctx *ctx, ...@@ -1624,6 +1627,7 @@ ice_vc_del_fdir_fltr_post(struct ice_vf *vf, struct ice_vf_fdir_ctx *ctx,
resp->status = status; resp->status = status;
ice_vc_fdir_remove_entry(vf, conf, conf->flow_id); ice_vc_fdir_remove_entry(vf, conf, conf->flow_id);
vf->fdir.fdir_fltr_cnt[conf->input.flow_type][is_tun]--; vf->fdir.fdir_fltr_cnt[conf->input.flow_type][is_tun]--;
vf->fdir.fdir_fltr_cnt_total--;
ret = ice_vc_send_msg_to_vf(vf, ctx->v_opcode, v_ret, ret = ice_vc_send_msg_to_vf(vf, ctx->v_opcode, v_ret,
(u8 *)resp, len); (u8 *)resp, len);
...@@ -1790,6 +1794,7 @@ int ice_vc_add_fdir_fltr(struct ice_vf *vf, u8 *msg) ...@@ -1790,6 +1794,7 @@ int ice_vc_add_fdir_fltr(struct ice_vf *vf, u8 *msg)
struct virtchnl_fdir_add *stat = NULL; struct virtchnl_fdir_add *stat = NULL;
struct virtchnl_fdir_fltr_conf *conf; struct virtchnl_fdir_fltr_conf *conf;
enum virtchnl_status_code v_ret; enum virtchnl_status_code v_ret;
struct ice_vsi *vf_vsi;
struct device *dev; struct device *dev;
struct ice_pf *pf; struct ice_pf *pf;
int is_tun = 0; int is_tun = 0;
...@@ -1798,6 +1803,17 @@ int ice_vc_add_fdir_fltr(struct ice_vf *vf, u8 *msg) ...@@ -1798,6 +1803,17 @@ int ice_vc_add_fdir_fltr(struct ice_vf *vf, u8 *msg)
pf = vf->pf; pf = vf->pf;
dev = ice_pf_to_dev(pf); dev = ice_pf_to_dev(pf);
vf_vsi = ice_get_vf_vsi(vf);
#define ICE_VF_MAX_FDIR_FILTERS 128
if (!ice_fdir_num_avail_fltr(&pf->hw, vf_vsi) ||
vf->fdir.fdir_fltr_cnt_total >= ICE_VF_MAX_FDIR_FILTERS) {
v_ret = VIRTCHNL_STATUS_ERR_PARAM;
dev_err(dev, "Max number of FDIR filters for VF %d is reached\n",
vf->vf_id);
goto err_exit;
}
ret = ice_vc_fdir_param_check(vf, fltr->vsi_id); ret = ice_vc_fdir_param_check(vf, fltr->vsi_id);
if (ret) { if (ret) {
v_ret = VIRTCHNL_STATUS_ERR_PARAM; v_ret = VIRTCHNL_STATUS_ERR_PARAM;
......
...@@ -29,6 +29,7 @@ struct ice_vf_fdir_ctx { ...@@ -29,6 +29,7 @@ struct ice_vf_fdir_ctx {
struct ice_vf_fdir { struct ice_vf_fdir {
u16 fdir_fltr_cnt[ICE_FLTR_PTYPE_MAX][ICE_FD_HW_SEG_MAX]; u16 fdir_fltr_cnt[ICE_FLTR_PTYPE_MAX][ICE_FD_HW_SEG_MAX];
int prof_entry_cnt[ICE_FLTR_PTYPE_MAX][ICE_FD_HW_SEG_MAX]; int prof_entry_cnt[ICE_FLTR_PTYPE_MAX][ICE_FD_HW_SEG_MAX];
u16 fdir_fltr_cnt_total;
struct ice_fd_hw_prof **fdir_prof; struct ice_fd_hw_prof **fdir_prof;
struct idr fdir_rule_idr; struct idr fdir_rule_idr;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment