Put the clearing of the socket cd interrupt and setting of it under
protection of sc->mtx. Sometimes multiple insert/ejections could cause further insertion/removals to not happen due to racing an ISR...
This commit is contained in:
parent
4aef3fb1c3
commit
da245931e3
@ -1010,15 +1010,6 @@ cbb_event_thread(void *arg)
|
||||
}
|
||||
mtx_unlock(&Giant);
|
||||
|
||||
/*
|
||||
* In our ISR, we turn off the card changed interrupt. Turn
|
||||
* them back on here before we wait for them to happen. We
|
||||
* turn them on/off so that we can tolerate a large latency
|
||||
* between the time we signal cbb_event_thread and it gets
|
||||
* a chance to run.
|
||||
*/
|
||||
cbb_setb(sc, CBB_SOCKET_MASK, CBB_SOCKET_MASK_CD);
|
||||
|
||||
/*
|
||||
* Wait until it has been 1s since the last time we
|
||||
* get an interrupt. We handle the rest of the interrupt
|
||||
@ -1026,8 +1017,15 @@ cbb_event_thread(void *arg)
|
||||
* ISR, we signal sc->cv from the detach path after we've
|
||||
* set the CBB_KTHREAD_DONE bit, so we can't do a simple
|
||||
* 1s sleep here.
|
||||
*
|
||||
* In our ISR, we turn off the card changed interrupt. Turn
|
||||
* them back on here before we wait for them to happen. We
|
||||
* turn them on/off so that we can tolerate a large latency
|
||||
* between the time we signal cbb_event_thread and it gets
|
||||
* a chance to run.
|
||||
*/
|
||||
mtx_lock(&sc->mtx);
|
||||
cbb_setb(sc, CBB_SOCKET_MASK, CBB_SOCKET_MASK_CD);
|
||||
cv_wait(&sc->cv, &sc->mtx);
|
||||
err = 0;
|
||||
while (err != EWOULDBLOCK &&
|
||||
@ -1125,8 +1123,8 @@ cbb_intr(void *arg)
|
||||
* excellent results.
|
||||
*/
|
||||
if (sockevent & CBB_SOCKET_EVENT_CD) {
|
||||
cbb_clrb(sc, CBB_SOCKET_MASK, CBB_SOCKET_MASK_CD);
|
||||
mtx_lock(&sc->mtx);
|
||||
cbb_setb(sc, CBB_SOCKET_MASK, CBB_SOCKET_MASK_CD);
|
||||
sc->flags &= ~CBB_CARD_OK;
|
||||
cbb_disable_func_intr(sc);
|
||||
DPRINTF(("Waking up thread\n"));
|
||||
|
Loading…
x
Reference in New Issue
Block a user