Commit 7b6b6c95 authored by Raghu Vatsavayi's avatar Raghu Vatsavayi Committed by David S. Miller

liquidio: link and control commands

This patch adds work queue support for link status and
control commands.
Signed-off-by: default avatarDerek Chickles <derek.chickles@caviumnetworks.com>
Signed-off-by: default avatarSatanand Burla <satananda.burla@caviumnetworks.com>
Signed-off-by: default avatarFelix Manlunas <felix.manlunas@caviumnetworks.com>
Signed-off-by: default avatarRaghu Vatsavayi <raghu.vatsavayi@caviumnetworks.com>
Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
parent 0cc1f315
...@@ -156,10 +156,9 @@ void liquidio_link_ctrl_cmd_completion(void *nctrl_ptr) ...@@ -156,10 +156,9 @@ void liquidio_link_ctrl_cmd_completion(void *nctrl_ptr)
dev_info(&oct->pci_dev->dev, "%s MTU Changed from %d to %d\n", dev_info(&oct->pci_dev->dev, "%s MTU Changed from %d to %d\n",
netdev->name, netdev->mtu, netdev->name, netdev->mtu,
nctrl->ncmd.s.param1); nctrl->ncmd.s.param1);
rtnl_lock();
netdev->mtu = nctrl->ncmd.s.param1; netdev->mtu = nctrl->ncmd.s.param1;
call_netdevice_notifiers(NETDEV_CHANGEMTU, netdev); queue_delayed_work(lio->link_status_wq.wq,
rtnl_unlock(); &lio->link_status_wq.wk.work, 0);
break; break;
case OCTNET_CMD_GPIO_ACCESS: case OCTNET_CMD_GPIO_ACCESS:
......
...@@ -856,6 +856,52 @@ static void print_link_info(struct net_device *netdev) ...@@ -856,6 +856,52 @@ static void print_link_info(struct net_device *netdev)
} }
} }
/**
* \brief Routine to notify MTU change
* @param work work_struct data structure
*/
static void octnet_link_status_change(struct work_struct *work)
{
struct cavium_wk *wk = (struct cavium_wk *)work;
struct lio *lio = (struct lio *)wk->ctxptr;
rtnl_lock();
call_netdevice_notifiers(NETDEV_CHANGEMTU, lio->netdev);
rtnl_unlock();
}
/**
* \brief Sets up the mtu status change work
* @param netdev network device
*/
static inline int setup_link_status_change_wq(struct net_device *netdev)
{
struct lio *lio = GET_LIO(netdev);
struct octeon_device *oct = lio->oct_dev;
lio->link_status_wq.wq = alloc_workqueue("link-status",
WQ_MEM_RECLAIM, 0);
if (!lio->link_status_wq.wq) {
dev_err(&oct->pci_dev->dev, "unable to create cavium link status wq\n");
return -1;
}
INIT_DELAYED_WORK(&lio->link_status_wq.wk.work,
octnet_link_status_change);
lio->link_status_wq.wk.ctxptr = lio;
return 0;
}
static inline void cleanup_link_status_change_wq(struct net_device *netdev)
{
struct lio *lio = GET_LIO(netdev);
if (lio->link_status_wq.wq) {
cancel_delayed_work_sync(&lio->link_status_wq.wk.work);
destroy_workqueue(lio->link_status_wq.wq);
}
}
/** /**
* \brief Update link status * \brief Update link status
* @param netdev network device * @param netdev network device
...@@ -1385,11 +1431,16 @@ static void liquidio_destroy_nic_device(struct octeon_device *oct, int ifidx) ...@@ -1385,11 +1431,16 @@ static void liquidio_destroy_nic_device(struct octeon_device *oct, int ifidx)
napi_disable(napi); napi_disable(napi);
oct->props[lio->ifidx].napi_enabled = 0; oct->props[lio->ifidx].napi_enabled = 0;
if (OCTEON_CN23XX_PF(oct))
oct->droq[0]->ops.poll_mode = 0;
} }
if (atomic_read(&lio->ifstate) & LIO_IFSTATE_REGISTERED) if (atomic_read(&lio->ifstate) & LIO_IFSTATE_REGISTERED)
unregister_netdev(netdev); unregister_netdev(netdev);
cleanup_link_status_change_wq(netdev);
delete_glists(lio); delete_glists(lio);
free_netdev(netdev); free_netdev(netdev);
...@@ -2267,6 +2318,14 @@ static inline int setup_io_queues(struct octeon_device *octeon_dev, ...@@ -2267,6 +2318,14 @@ static inline int setup_io_queues(struct octeon_device *octeon_dev,
octeon_register_droq_ops(octeon_dev, q_no, &droq_ops); octeon_register_droq_ops(octeon_dev, q_no, &droq_ops);
} }
if (OCTEON_CN23XX_PF(octeon_dev)) {
/* 23XX PF can receive control messages (via the first PF-owned
* droq) from the firmware even if the ethX interface is down,
* so that's why poll_mode must be off for the first droq.
*/
octeon_dev->droq[0]->ops.poll_mode = 0;
}
/* set up IQs. */ /* set up IQs. */
for (q = 0; q < lio->linfo.num_txpciq; q++) { for (q = 0; q < lio->linfo.num_txpciq; q++) {
num_tx_descs = CFG_GET_NUM_TX_DESCS_NIC_IF(octeon_get_conf num_tx_descs = CFG_GET_NUM_TX_DESCS_NIC_IF(octeon_get_conf
...@@ -2351,12 +2410,20 @@ static int liquidio_open(struct net_device *netdev) ...@@ -2351,12 +2410,20 @@ static int liquidio_open(struct net_device *netdev)
napi_enable(napi); napi_enable(napi);
oct->props[lio->ifidx].napi_enabled = 1; oct->props[lio->ifidx].napi_enabled = 1;
if (OCTEON_CN23XX_PF(oct))
oct->droq[0]->ops.poll_mode = 1;
} }
oct_ptp_open(netdev); oct_ptp_open(netdev);
ifstate_set(lio, LIO_IFSTATE_RUNNING); ifstate_set(lio, LIO_IFSTATE_RUNNING);
/* Ready for link status updates */
lio->intf_open = 1;
netif_info(lio, ifup, lio->netdev, "Interface Open, ready for traffic\n");
if (OCTEON_CN23XX_PF(oct)) { if (OCTEON_CN23XX_PF(oct)) {
if (!oct->msix_on) if (!oct->msix_on)
if (setup_tx_poll_fn(netdev)) if (setup_tx_poll_fn(netdev))
...@@ -2368,14 +2435,9 @@ static int liquidio_open(struct net_device *netdev) ...@@ -2368,14 +2435,9 @@ static int liquidio_open(struct net_device *netdev)
start_txq(netdev); start_txq(netdev);
netif_info(lio, ifup, lio->netdev, "Interface Open, ready for traffic\n");
/* tell Octeon to start forwarding packets to host */ /* tell Octeon to start forwarding packets to host */
send_rx_ctrl_cmd(lio, 1); send_rx_ctrl_cmd(lio, 1);
/* Ready for link status updates */
lio->intf_open = 1;
dev_info(&oct->pci_dev->dev, "%s interface is opened\n", dev_info(&oct->pci_dev->dev, "%s interface is opened\n",
netdev->name); netdev->name);
...@@ -3668,6 +3730,9 @@ static int setup_nic_devices(struct octeon_device *octeon_dev) ...@@ -3668,6 +3730,9 @@ static int setup_nic_devices(struct octeon_device *octeon_dev)
liquidio_set_feature(netdev, liquidio_set_feature(netdev,
OCTNET_CMD_VERBOSE_ENABLE, 0); OCTNET_CMD_VERBOSE_ENABLE, 0);
if (setup_link_status_change_wq(netdev))
goto setup_nic_dev_fail;
/* Register the network device with the OS */ /* Register the network device with the OS */
if (register_netdev(netdev)) { if (register_netdev(netdev)) {
dev_err(&octeon_dev->pci_dev->dev, "Device registration failed\n"); dev_err(&octeon_dev->pci_dev->dev, "Device registration failed\n");
......
...@@ -122,6 +122,10 @@ struct lio { ...@@ -122,6 +122,10 @@ struct lio {
/* work queue for txq status */ /* work queue for txq status */
struct cavium_wq txq_status_wq; struct cavium_wq txq_status_wq;
/* work queue for link status */
struct cavium_wq link_status_wq;
}; };
#define LIO_SIZE (sizeof(struct lio)) #define LIO_SIZE (sizeof(struct lio))
......
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