From 0eb62b93cbe0e8dea4cfe5ee761755e982663727 Mon Sep 17 00:00:00 2001 From: Rony Efraim Date: Thu, 25 Apr 2013 05:22:26 +0000 Subject: [PATCH] net/mlx4: Add structures to keep VF Ethernet ports information This patch add struct mlx4_vport_state where all the parameters related to management of VFs port (virtual ports of the NIC eswitch) are kept. The driver keeps an administrative and operational copy of the settings. The current administrative copy becomes operational on the event of probing a VF either on a VM or on the host. Signed-off-by: Rony Efraim Signed-off-by: Or Gerlitz Signed-off-by: David S. Miller --- drivers/net/ethernet/mellanox/mlx4/cmd.c | 32 +++++++++++++++++++++++ drivers/net/ethernet/mellanox/mlx4/fw.c | 4 +++ drivers/net/ethernet/mellanox/mlx4/mlx4.h | 26 ++++++++++++++++++ 3 files changed, 62 insertions(+) diff --git a/drivers/net/ethernet/mellanox/mlx4/cmd.c b/drivers/net/ethernet/mellanox/mlx4/cmd.c index 05267d716e86..0a301e1a0635 100644 --- a/drivers/net/ethernet/mellanox/mlx4/cmd.c +++ b/drivers/net/ethernet/mellanox/mlx4/cmd.c @@ -1490,6 +1490,16 @@ out: return ret; } +static int mlx4_master_activate_admin_state(struct mlx4_priv *priv, int slave) +{ + int port; + for (port = 1; port <= MLX4_MAX_PORTS; port++) { + priv->mfunc.master.vf_oper[slave].vport[port].state = + priv->mfunc.master.vf_admin[slave].vport[port]; + } + return 0; +} + static void mlx4_master_do_cmd(struct mlx4_dev *dev, int slave, u8 cmd, u16 param, u8 toggle) { @@ -1556,6 +1566,7 @@ static void mlx4_master_do_cmd(struct mlx4_dev *dev, int slave, u8 cmd, if (slave_state[slave].last_cmd != MLX4_COMM_CMD_VHCR2) goto reset_slave; slave_state[slave].vhcr_dma |= param; + mlx4_master_activate_admin_state(priv, slave); slave_state[slave].active = true; mlx4_dispatch_event(dev, MLX4_DEV_EVENT_SLAVE_INIT, slave); break; @@ -1732,6 +1743,18 @@ int mlx4_multi_func_init(struct mlx4_dev *dev) if (!priv->mfunc.master.slave_state) goto err_comm; + priv->mfunc.master.vf_admin = + kzalloc(dev->num_slaves * + sizeof(struct mlx4_vf_admin_state), GFP_KERNEL); + if (!priv->mfunc.master.vf_admin) + goto err_comm_admin; + + priv->mfunc.master.vf_oper = + kzalloc(dev->num_slaves * + sizeof(struct mlx4_vf_oper_state), GFP_KERNEL); + if (!priv->mfunc.master.vf_oper) + goto err_comm_oper; + for (i = 0; i < dev->num_slaves; ++i) { s_state = &priv->mfunc.master.slave_state[i]; s_state->last_cmd = MLX4_COMM_CMD_RESET; @@ -1752,6 +1775,9 @@ int mlx4_multi_func_init(struct mlx4_dev *dev) goto err_slaves; } INIT_LIST_HEAD(&s_state->mcast_filters[port]); + priv->mfunc.master.vf_admin[i].vport[port].default_vlan = MLX4_VGT; + priv->mfunc.master.vf_oper[i].vport[port].vlan_idx = NO_INDX; + priv->mfunc.master.vf_oper[i].vport[port].mac_idx = NO_INDX; } spin_lock_init(&s_state->lock); } @@ -1800,6 +1826,10 @@ err_slaves: for (port = 1; port <= MLX4_MAX_PORTS; port++) kfree(priv->mfunc.master.slave_state[i].vlan_filter[port]); } + kfree(priv->mfunc.master.vf_oper); +err_comm_oper: + kfree(priv->mfunc.master.vf_admin); +err_comm_admin: kfree(priv->mfunc.master.slave_state); err_comm: iounmap(priv->mfunc.comm); @@ -1874,6 +1904,8 @@ void mlx4_multi_func_cleanup(struct mlx4_dev *dev) kfree(priv->mfunc.master.slave_state[i].vlan_filter[port]); } kfree(priv->mfunc.master.slave_state); + kfree(priv->mfunc.master.vf_admin); + kfree(priv->mfunc.master.vf_oper); } iounmap(priv->mfunc.comm); diff --git a/drivers/net/ethernet/mellanox/mlx4/fw.c b/drivers/net/ethernet/mellanox/mlx4/fw.c index 1f6c3e9128ef..70d44adddc39 100644 --- a/drivers/net/ethernet/mellanox/mlx4/fw.c +++ b/drivers/net/ethernet/mellanox/mlx4/fw.c @@ -816,6 +816,7 @@ int mlx4_QUERY_PORT_wrapper(struct mlx4_dev *dev, int slave, struct mlx4_cmd_mailbox *outbox, struct mlx4_cmd_info *cmd) { + struct mlx4_priv *priv = mlx4_priv(dev); u64 def_mac; u8 port_type; u16 short_field; @@ -833,6 +834,9 @@ int mlx4_QUERY_PORT_wrapper(struct mlx4_dev *dev, int slave, /* set slave default_mac address */ MLX4_GET(def_mac, outbox->buf, QUERY_PORT_MAC_OFFSET); def_mac += slave << 8; + /* if config MAC in DB use it */ + if (priv->mfunc.master.vf_oper[slave].vport[vhcr->in_modifier].state.mac) + def_mac = priv->mfunc.master.vf_oper[slave].vport[vhcr->in_modifier].state.mac; MLX4_PUT(outbox->buf, def_mac, QUERY_PORT_MAC_OFFSET); /* get port type - currently only eth is enabled */ diff --git a/drivers/net/ethernet/mellanox/mlx4/mlx4.h b/drivers/net/ethernet/mellanox/mlx4/mlx4.h index 0567f01938ed..7e1d10059eda 100644 --- a/drivers/net/ethernet/mellanox/mlx4/mlx4.h +++ b/drivers/net/ethernet/mellanox/mlx4/mlx4.h @@ -473,6 +473,30 @@ struct mlx4_slave_state { enum slave_port_state port_state[MLX4_MAX_PORTS + 1]; }; +#define MLX4_VGT 4095 +#define NO_INDX (-1) + +struct mlx4_vport_state { + u64 mac; + u16 default_vlan; + u8 default_qos; + u32 tx_rate; + bool spoofchk; +}; + +struct mlx4_vf_admin_state { + struct mlx4_vport_state vport[MLX4_MAX_PORTS + 1]; +}; + +struct mlx4_vport_oper_state { + struct mlx4_vport_state state; + int mac_idx; + int vlan_idx; +}; +struct mlx4_vf_oper_state { + struct mlx4_vport_oper_state vport[MLX4_MAX_PORTS + 1]; +}; + struct slave_list { struct mutex mutex; struct list_head res_list[MLX4_NUM_OF_RESOURCE_TYPE]; @@ -503,6 +527,8 @@ struct mlx4_master_qp0_state { struct mlx4_mfunc_master_ctx { struct mlx4_slave_state *slave_state; + struct mlx4_vf_admin_state *vf_admin; + struct mlx4_vf_oper_state *vf_oper; struct mlx4_master_qp0_state qp0_state[MLX4_MAX_PORTS + 1]; int init_port_ref[MLX4_MAX_PORTS + 1]; u16 max_mtu[MLX4_MAX_PORTS + 1]; -- 2.20.1