summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorjfv <jfv@FreeBSD.org>2010-01-27 20:12:04 +0000
committerjfv <jfv@FreeBSD.org>2010-01-27 20:12:04 +0000
commitf3b3ede9be1a20d78ac5f23b94dde56dd83faee2 (patch)
treee890e089de0e0553d8a220b6a620982f84d49fb1
parent37cc0bd2abcf0afd8ba8923846fba6f69c0a3232 (diff)
downloadFreeBSD-src-f3b3ede9be1a20d78ac5f23b94dde56dd83faee2.zip
FreeBSD-src-f3b3ede9be1a20d78ac5f23b94dde56dd83faee2.tar.gz
Add a link tasklet so updates can be sleepable.
-rw-r--r--sys/dev/e1000/if_igb.c28
-rw-r--r--sys/dev/e1000/if_igb.h3
2 files changed, 24 insertions, 7 deletions
diff --git a/sys/dev/e1000/if_igb.c b/sys/dev/e1000/if_igb.c
index 92ccdae..70fc661 100644
--- a/sys/dev/e1000/if_igb.c
+++ b/sys/dev/e1000/if_igb.c
@@ -244,6 +244,7 @@ static void igb_add_rx_process_limit(struct adapter *, const char *,
const char *, int *, int);
static void igb_handle_rxtx(void *context, int pending);
static void igb_handle_que(void *context, int pending);
+static void igb_handle_link(void *context, int pending);
/* These are MSIX only irq handlers */
static void igb_msix_que(void *);
@@ -1203,6 +1204,15 @@ igb_handle_que(void *context, int pending)
E1000_WRITE_REG(&adapter->hw, E1000_EIMS, que->eims);
}
+/* Deal with link in a sleepable context */
+static void
+igb_handle_link(void *context, int pending)
+{
+ struct adapter *adapter = context;
+
+ adapter->hw.mac.get_link_status = 1;
+ igb_update_link_status(adapter);
+}
/*********************************************************************
*
@@ -1239,10 +1249,8 @@ igb_irq_fast(void *arg)
taskqueue_enqueue(adapter->tq, &adapter->rxtx_task);
/* Link status change */
- if (reg_icr & (E1000_ICR_RXSEQ | E1000_ICR_LSC)) {
- adapter->hw.mac.get_link_status = 1;
- igb_update_link_status(adapter);
- }
+ if (reg_icr & (E1000_ICR_RXSEQ | E1000_ICR_LSC))
+ taskqueue_enqueue(adapter->tq, &adapter->link_task);
if (reg_icr & E1000_ICR_RXO)
adapter->rx_overruns++;
@@ -1352,8 +1360,7 @@ igb_msix_link(void *arg)
icr = E1000_READ_REG(&adapter->hw, E1000_ICR);
if (!(icr & E1000_ICR_LSC))
goto spurious;
- adapter->hw.mac.get_link_status = 1;
- igb_update_link_status(adapter);
+ taskqueue_enqueue(adapter->tq, &adapter->link_task);
spurious:
/* Rearm */
@@ -1986,6 +1993,8 @@ igb_allocate_legacy(struct adapter *adapter)
* processing contexts.
*/
TASK_INIT(&adapter->rxtx_task, 0, igb_handle_rxtx, adapter);
+ /* Make tasklet for deferred link handling */
+ TASK_INIT(&adapter->link_task, 0, igb_handle_link, adapter);
adapter->tq = taskqueue_create_fast("igb_taskq", M_NOWAIT,
taskqueue_thread_enqueue, &adapter->tq);
taskqueue_start_threads(&adapter->tq, 1, PI_NET, "%s taskq",
@@ -2072,6 +2081,13 @@ igb_allocate_msix(struct adapter *adapter)
}
adapter->linkvec = vector;
+ /* Make tasklet for deferred handling */
+ TASK_INIT(&adapter->link_task, 0, igb_handle_link, adapter);
+ adapter->tq = taskqueue_create_fast("igb_link", M_NOWAIT,
+ taskqueue_thread_enqueue, &adapter->tq);
+ taskqueue_start_threads(&adapter->tq, 1, PI_NET, "%s link",
+ device_get_nameunit(adapter->dev));
+
return (0);
}
diff --git a/sys/dev/e1000/if_igb.h b/sys/dev/e1000/if_igb.h
index f14d734..fbcf4a0 100644
--- a/sys/dev/e1000/if_igb.h
+++ b/sys/dev/e1000/if_igb.h
@@ -372,6 +372,7 @@ struct adapter {
int linkvec;
int link_mask;
+ struct task link_task;
int link_irq;
struct ifmedia media;
@@ -383,7 +384,7 @@ struct adapter {
struct mtx core_mtx;
int igb_insert_vlan_header;
struct task rxtx_task;
- struct taskqueue *tq; /* private task queue */
+ struct taskqueue *tq; /* adapter task queue */
u16 num_queues;
eventhandler_tag vlan_attach;
OpenPOWER on IntegriCloud