aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/ethernet/mellanox
diff options
context:
space:
mode:
authorRony Efraim <ronye@mellanox.com>2013-06-13 06:19:11 -0400
committerDavid S. Miller <davem@davemloft.net>2013-06-13 20:51:04 -0400
commit948e306d7d645af80ea331b60495710fe4fe12bb (patch)
treec66b8872cbc566df779b454d78c9c181c94440c8 /drivers/net/ethernet/mellanox
parent1d8faf48c74b8329a0322dc4b2a2030ae5003c86 (diff)
net/mlx4: Add VF link state support
Add support to change the link state of VF (vPort) Signed-off-by: Rony Efraim <ronye@mellanox.com> Signed-off-by: Or Gerlitz <ogerlitz@mellanox.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/ethernet/mellanox')
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/cmd.c48
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/en_netdev.c8
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/eq.c9
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/fw.c8
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/mlx4.h1
5 files changed, 72 insertions, 2 deletions
diff --git a/drivers/net/ethernet/mellanox/mlx4/cmd.c b/drivers/net/ethernet/mellanox/mlx4/cmd.c
index 0e572a527154..ea1e03896353 100644
--- a/drivers/net/ethernet/mellanox/mlx4/cmd.c
+++ b/drivers/net/ethernet/mellanox/mlx4/cmd.c
@@ -39,6 +39,7 @@
39#include <linux/errno.h> 39#include <linux/errno.h>
40 40
41#include <linux/mlx4/cmd.h> 41#include <linux/mlx4/cmd.h>
42#include <linux/mlx4/device.h>
42#include <linux/semaphore.h> 43#include <linux/semaphore.h>
43#include <rdma/ib_smi.h> 44#include <rdma/ib_smi.h>
44 45
@@ -2178,7 +2179,54 @@ int mlx4_get_vf_config(struct mlx4_dev *dev, int port, int vf, struct ifla_vf_in
2178 ivf->qos = s_info->default_qos; 2179 ivf->qos = s_info->default_qos;
2179 ivf->tx_rate = s_info->tx_rate; 2180 ivf->tx_rate = s_info->tx_rate;
2180 ivf->spoofchk = s_info->spoofchk; 2181 ivf->spoofchk = s_info->spoofchk;
2182 ivf->linkstate = s_info->link_state;
2181 2183
2182 return 0; 2184 return 0;
2183} 2185}
2184EXPORT_SYMBOL_GPL(mlx4_get_vf_config); 2186EXPORT_SYMBOL_GPL(mlx4_get_vf_config);
2187
2188int mlx4_set_vf_link_state(struct mlx4_dev *dev, int port, int vf, int link_state)
2189{
2190 struct mlx4_priv *priv = mlx4_priv(dev);
2191 struct mlx4_vport_state *s_info;
2192 struct mlx4_vport_oper_state *vp_oper;
2193 int slave;
2194 u8 link_stat_event;
2195
2196 slave = mlx4_get_slave_indx(dev, vf);
2197 if (slave < 0)
2198 return -EINVAL;
2199
2200 switch (link_state) {
2201 case IFLA_VF_LINK_STATE_AUTO:
2202 /* get current link state */
2203 if (!priv->sense.do_sense_port[port])
2204 link_stat_event = MLX4_PORT_CHANGE_SUBTYPE_ACTIVE;
2205 else
2206 link_stat_event = MLX4_PORT_CHANGE_SUBTYPE_DOWN;
2207 break;
2208
2209 case IFLA_VF_LINK_STATE_ENABLE:
2210 link_stat_event = MLX4_PORT_CHANGE_SUBTYPE_ACTIVE;
2211 break;
2212
2213 case IFLA_VF_LINK_STATE_DISABLE:
2214 link_stat_event = MLX4_PORT_CHANGE_SUBTYPE_DOWN;
2215 break;
2216
2217 default:
2218 mlx4_warn(dev, "unknown value for link_state %02x on slave %d port %d\n",
2219 link_state, slave, port);
2220 return -EINVAL;
2221 };
2222 /* update the admin & oper state on the link state */
2223 s_info = &priv->mfunc.master.vf_admin[slave].vport[port];
2224 vp_oper = &priv->mfunc.master.vf_oper[slave].vport[port];
2225 s_info->link_state = link_state;
2226 vp_oper->state.link_state = link_state;
2227
2228 /* send event */
2229 mlx4_gen_port_state_change_eqe(dev, slave, port, link_stat_event);
2230 return 0;
2231}
2232EXPORT_SYMBOL_GPL(mlx4_set_vf_link_state);
diff --git a/drivers/net/ethernet/mellanox/mlx4/en_netdev.c b/drivers/net/ethernet/mellanox/mlx4/en_netdev.c
index 89c47ea84b50..ade276cca0e6 100644
--- a/drivers/net/ethernet/mellanox/mlx4/en_netdev.c
+++ b/drivers/net/ethernet/mellanox/mlx4/en_netdev.c
@@ -2061,6 +2061,13 @@ static int mlx4_en_get_vf_config(struct net_device *dev, int vf, struct ifla_vf_
2061 return mlx4_get_vf_config(mdev->dev, en_priv->port, vf, ivf); 2061 return mlx4_get_vf_config(mdev->dev, en_priv->port, vf, ivf);
2062} 2062}
2063 2063
2064static int mlx4_en_set_vf_link_state(struct net_device *dev, int vf, int link_state)
2065{
2066 struct mlx4_en_priv *en_priv = netdev_priv(dev);
2067 struct mlx4_en_dev *mdev = en_priv->mdev;
2068
2069 return mlx4_set_vf_link_state(mdev->dev, en_priv->port, vf, link_state);
2070}
2064static const struct net_device_ops mlx4_netdev_ops = { 2071static const struct net_device_ops mlx4_netdev_ops = {
2065 .ndo_open = mlx4_en_open, 2072 .ndo_open = mlx4_en_open,
2066 .ndo_stop = mlx4_en_close, 2073 .ndo_stop = mlx4_en_close,
@@ -2101,6 +2108,7 @@ static const struct net_device_ops mlx4_netdev_ops_master = {
2101 .ndo_set_vf_mac = mlx4_en_set_vf_mac, 2108 .ndo_set_vf_mac = mlx4_en_set_vf_mac,
2102 .ndo_set_vf_vlan = mlx4_en_set_vf_vlan, 2109 .ndo_set_vf_vlan = mlx4_en_set_vf_vlan,
2103 .ndo_set_vf_spoofchk = mlx4_en_set_vf_spoofchk, 2110 .ndo_set_vf_spoofchk = mlx4_en_set_vf_spoofchk,
2111 .ndo_set_vf_link_state = mlx4_en_set_vf_link_state,
2104 .ndo_get_vf_config = mlx4_en_get_vf_config, 2112 .ndo_get_vf_config = mlx4_en_get_vf_config,
2105#ifdef CONFIG_NET_POLL_CONTROLLER 2113#ifdef CONFIG_NET_POLL_CONTROLLER
2106 .ndo_poll_controller = mlx4_en_netpoll, 2114 .ndo_poll_controller = mlx4_en_netpoll,
diff --git a/drivers/net/ethernet/mellanox/mlx4/eq.c b/drivers/net/ethernet/mellanox/mlx4/eq.c
index 6000342f9725..7e042869ef0c 100644
--- a/drivers/net/ethernet/mellanox/mlx4/eq.c
+++ b/drivers/net/ethernet/mellanox/mlx4/eq.c
@@ -448,6 +448,7 @@ static int mlx4_eq_int(struct mlx4_dev *dev, struct mlx4_eq *eq)
448 int i; 448 int i;
449 enum slave_port_gen_event gen_event; 449 enum slave_port_gen_event gen_event;
450 unsigned long flags; 450 unsigned long flags;
451 struct mlx4_vport_state *s_info;
451 452
452 while ((eqe = next_eqe_sw(eq, dev->caps.eqe_factor))) { 453 while ((eqe = next_eqe_sw(eq, dev->caps.eqe_factor))) {
453 /* 454 /*
@@ -556,7 +557,9 @@ static int mlx4_eq_int(struct mlx4_dev *dev, struct mlx4_eq *eq)
556 mlx4_dbg(dev, "%s: Sending MLX4_PORT_CHANGE_SUBTYPE_DOWN" 557 mlx4_dbg(dev, "%s: Sending MLX4_PORT_CHANGE_SUBTYPE_DOWN"
557 " to slave: %d, port:%d\n", 558 " to slave: %d, port:%d\n",
558 __func__, i, port); 559 __func__, i, port);
559 mlx4_slave_event(dev, i, eqe); 560 s_info = &priv->mfunc.master.vf_oper[slave].vport[port].state;
561 if (IFLA_VF_LINK_STATE_AUTO == s_info->link_state)
562 mlx4_slave_event(dev, i, eqe);
560 } else { /* IB port */ 563 } else { /* IB port */
561 set_and_calc_slave_port_state(dev, i, port, 564 set_and_calc_slave_port_state(dev, i, port,
562 MLX4_PORT_STATE_DEV_EVENT_PORT_DOWN, 565 MLX4_PORT_STATE_DEV_EVENT_PORT_DOWN,
@@ -580,7 +583,9 @@ static int mlx4_eq_int(struct mlx4_dev *dev, struct mlx4_eq *eq)
580 for (i = 0; i < dev->num_slaves; i++) { 583 for (i = 0; i < dev->num_slaves; i++) {
581 if (i == mlx4_master_func_num(dev)) 584 if (i == mlx4_master_func_num(dev))
582 continue; 585 continue;
583 mlx4_slave_event(dev, i, eqe); 586 s_info = &priv->mfunc.master.vf_oper[slave].vport[port].state;
587 if (IFLA_VF_LINK_STATE_AUTO == s_info->link_state)
588 mlx4_slave_event(dev, i, eqe);
584 } 589 }
585 else /* IB port */ 590 else /* IB port */
586 /* port-up event will be sent to a slave when the 591 /* port-up event will be sent to a slave when the
diff --git a/drivers/net/ethernet/mellanox/mlx4/fw.c b/drivers/net/ethernet/mellanox/mlx4/fw.c
index 2c97901c6a6d..569bbe3e7403 100644
--- a/drivers/net/ethernet/mellanox/mlx4/fw.c
+++ b/drivers/net/ethernet/mellanox/mlx4/fw.c
@@ -830,8 +830,10 @@ int mlx4_QUERY_PORT_wrapper(struct mlx4_dev *dev, int slave,
830 u8 port_type; 830 u8 port_type;
831 u16 short_field; 831 u16 short_field;
832 int err; 832 int err;
833 int admin_link_state;
833 834
834#define MLX4_VF_PORT_NO_LINK_SENSE_MASK 0xE0 835#define MLX4_VF_PORT_NO_LINK_SENSE_MASK 0xE0
836#define MLX4_PORT_LINK_UP_MASK 0x80
835#define QUERY_PORT_CUR_MAX_PKEY_OFFSET 0x0c 837#define QUERY_PORT_CUR_MAX_PKEY_OFFSET 0x0c
836#define QUERY_PORT_CUR_MAX_GID_OFFSET 0x0e 838#define QUERY_PORT_CUR_MAX_GID_OFFSET 0x0e
837 839
@@ -861,6 +863,12 @@ int mlx4_QUERY_PORT_wrapper(struct mlx4_dev *dev, int slave,
861 /* set port type to currently operating port type */ 863 /* set port type to currently operating port type */
862 port_type |= (dev->caps.port_type[vhcr->in_modifier] & 0x3); 864 port_type |= (dev->caps.port_type[vhcr->in_modifier] & 0x3);
863 865
866 admin_link_state = priv->mfunc.master.vf_oper[slave].vport[vhcr->in_modifier].state.link_state;
867 if (IFLA_VF_LINK_STATE_ENABLE == admin_link_state)
868 port_type |= MLX4_PORT_LINK_UP_MASK;
869 else if (IFLA_VF_LINK_STATE_DISABLE == admin_link_state)
870 port_type &= ~MLX4_PORT_LINK_UP_MASK;
871
864 MLX4_PUT(outbox->buf, port_type, 872 MLX4_PUT(outbox->buf, port_type,
865 QUERY_PORT_SUPPORTED_TYPE_OFFSET); 873 QUERY_PORT_SUPPORTED_TYPE_OFFSET);
866 874
diff --git a/drivers/net/ethernet/mellanox/mlx4/mlx4.h b/drivers/net/ethernet/mellanox/mlx4/mlx4.h
index df15bb6631cc..75272935a3f7 100644
--- a/drivers/net/ethernet/mellanox/mlx4/mlx4.h
+++ b/drivers/net/ethernet/mellanox/mlx4/mlx4.h
@@ -482,6 +482,7 @@ struct mlx4_vport_state {
482 u8 default_qos; 482 u8 default_qos;
483 u32 tx_rate; 483 u32 tx_rate;
484 bool spoofchk; 484 bool spoofchk;
485 u32 link_state;
485}; 486};
486 487
487struct mlx4_vf_admin_state { 488struct mlx4_vf_admin_state {