aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net/sfc/efx.c
diff options
context:
space:
mode:
authorSteve Hodgson <shodgson@solarflare.com>2009-11-28 05:34:05 +0000
committerDavid S. Miller <davem@davemloft.net>2009-11-28 23:58:50 -0800
commitfdaa9aed21c8c8b529f3c94a5ffa138bf3360b75 (patch)
tree6db7fd76481b3f87f0f4e94e1bd55c0624fba296 /drivers/net/sfc/efx.c
parentvlan: support "loose binding" to the underlying network device (diff)
downloadlinux-dev-fdaa9aed21c8c8b529f3c94a5ffa138bf3360b75.tar.xz
linux-dev-fdaa9aed21c8c8b529f3c94a5ffa138bf3360b75.zip
sfc: Simplify PHY polling
Falcon can generate events for LASI interrupts from the PHY, but in practice we have never implemented this in reference designs. Instead we have polled, inserted the appropriate events, and then handled the events later. This is a waste of time and code. Instead, make PHY poll functions update the link state synchronously and report whether it changed. We can still make use of the LASI registers as a shortcut on the SFT9001. Signed-off-by: Ben Hutchings <bhutchings@solarflare.com> Signed-off-by: David S. Miller <davem@davemloft.net>
Diffstat (limited to 'drivers/net/sfc/efx.c')
-rw-r--r--drivers/net/sfc/efx.c35
1 files changed, 8 insertions, 27 deletions
diff --git a/drivers/net/sfc/efx.c b/drivers/net/sfc/efx.c
index 1009d1eeba82..b5a7e91590dc 100644
--- a/drivers/net/sfc/efx.c
+++ b/drivers/net/sfc/efx.c
@@ -583,7 +583,7 @@ void efx_schedule_slow_fill(struct efx_rx_queue *rx_queue, int delay)
* netif_carrier_on/off) of the link status, and also maintains the
* link status's stop on the port's TX queue.
*/
-static void efx_link_status_changed(struct efx_nic *efx)
+void efx_link_status_changed(struct efx_nic *efx)
{
struct efx_link_state *link_state = &efx->link_state;
@@ -675,19 +675,6 @@ void efx_reconfigure_port(struct efx_nic *efx)
mutex_unlock(&efx->mac_lock);
}
-/* Asynchronous efx_reconfigure_port work item. To speed up efx_flush_all()
- * we don't efx_reconfigure_port() if the port is disabled. Care is taken
- * in efx_stop_all() and efx_start_port() to prevent PHY events being lost */
-static void efx_phy_work(struct work_struct *data)
-{
- struct efx_nic *efx = container_of(data, struct efx_nic, phy_work);
-
- mutex_lock(&efx->mac_lock);
- if (efx->port_enabled)
- __efx_reconfigure_port(efx);
- mutex_unlock(&efx->mac_lock);
-}
-
/* Asynchronous work item for changing MAC promiscuity and multicast
* hash. Avoid a drain/rx_ingress enable by reconfiguring the current
* MAC directly. */
@@ -768,9 +755,6 @@ fail1:
return rc;
}
-/* Allow efx_reconfigure_port() to be scheduled, and close the window
- * between efx_stop_port and efx_flush_all whereby a previously scheduled
- * efx_phy_work()/efx_mac_work() may have been cancelled */
static void efx_start_port(struct efx_nic *efx)
{
EFX_LOG(efx, "start port\n");
@@ -787,10 +771,7 @@ static void efx_start_port(struct efx_nic *efx)
mutex_unlock(&efx->mac_lock);
}
-/* Prevent efx_phy_work, efx_mac_work, and efx_monitor() from executing,
- * and efx_set_multicast_list() from scheduling efx_phy_work. efx_phy_work
- * and efx_mac_work may still be scheduled via NAPI processing until
- * efx_flush_all() is called */
+/* Prevent efx_mac_work() and efx_monitor() from working */
static void efx_stop_port(struct efx_nic *efx)
{
EFX_LOG(efx, "stop port\n");
@@ -1188,8 +1169,6 @@ static void efx_flush_all(struct efx_nic *efx)
/* Stop scheduled port reconfigurations */
cancel_work_sync(&efx->mac_work);
- cancel_work_sync(&efx->phy_work);
-
}
/* Quiesce hardware and software without bringing the link down.
@@ -1227,7 +1206,7 @@ static void efx_stop_all(struct efx_nic *efx)
* window to loose phy events */
efx_stop_port(efx);
- /* Flush efx_phy_work, efx_mac_work, refill_workqueue, monitor_work */
+ /* Flush efx_mac_work(), refill_workqueue, monitor_work */
efx_flush_all(efx);
/* Isolate the MAC from the TX and RX engines, so that queue
@@ -1907,6 +1886,10 @@ void efx_port_dummy_op_void(struct efx_nic *efx) {}
void efx_port_dummy_op_set_id_led(struct efx_nic *efx, enum efx_led_mode mode)
{
}
+bool efx_port_dummy_op_poll(struct efx_nic *efx)
+{
+ return false;
+}
static struct efx_mac_operations efx_dummy_mac_operations = {
.reconfigure = efx_port_dummy_op_void,
@@ -1915,9 +1898,8 @@ static struct efx_mac_operations efx_dummy_mac_operations = {
static struct efx_phy_operations efx_dummy_phy_operations = {
.init = efx_port_dummy_op_int,
.reconfigure = efx_port_dummy_op_void,
- .poll = efx_port_dummy_op_void,
+ .poll = efx_port_dummy_op_poll,
.fini = efx_port_dummy_op_void,
- .clear_interrupt = efx_port_dummy_op_void,
};
/**************************************************************************
@@ -1957,7 +1939,6 @@ static int efx_init_struct(struct efx_nic *efx, struct efx_nic_type *type,
efx->mac_op = &efx_dummy_mac_operations;
efx->phy_op = &efx_dummy_phy_operations;
efx->mdio.dev = net_dev;
- INIT_WORK(&efx->phy_work, efx_phy_work);
INIT_WORK(&efx->mac_work, efx_mac_work);
atomic_set(&efx->netif_stop_count, 1);