Condividi tramite


Prevenire errori e deadlock durante l'uso degli spin lock

Mentre una routine driver detiene un spin lock, non può causare un'eccezione hardware o generare un'eccezione software senza arrestare il sistema. In altre parole, l'ISR di un driver e qualsiasi routine SynchCritSection fornita dal driver in una chiamata a KeSynchronizeExecution non deve causare errori o trap, ad esempio un errore di pagina o un'eccezione aritmetica, e non può generare un'eccezione software. Una routine che chiama KeAcquireSpinLock o KeAcquireInStackQueuedSpinLock non può anche causare un'eccezione hardware o generare un'eccezione software fino a quando non ha rilasciato il blocco spin esecutivo e non è più in esecuzione in IRQL = DISPATCH_LEVEL.

Routine di dati e supporto paginabili

Tenendo uno spin lock, i driver non devono chiamare routine che accedono a dati paginabili. Tenere presente che i driver possono chiamare determinate routine di supporto che accedono ai dati paginabili se e solo se le chiamate si verificano durante l'esecuzione a un IRQL rigorosamente inferiore a DISPATCH_LEVEL. Questa restrizione IRQL impedisce di chiamare queste routine di supporto mantenendo un blocco di selezione. Per i requisiti IRQL per qualsiasi routine di supporto specifica, vedere la pagina di riferimento della routine.

Ricorsione

Il tentativo di acquisire un blocco di rotazione in modo ricorsivo è garantito che causi un deadlock: la creazione di un'istanza di una routine ricorsiva non può rilasciare il blocco di rotazione mentre una seconda rotazione di istanze tenta di acquisire lo stesso blocco di rotazione.

Le linee guida seguenti descrivono come usare i blocchi di selezione con routine ricorsive:

  • La routine ricorsiva non deve chiamare se stessa tenendo premuto un blocco di selezione o non deve tentare di acquisire lo stesso blocco di selezione nelle chiamate successive.

  • Mentre la routine ricorsiva contiene un blocco di rotazione, un'altra routine del driver non deve chiamare la routine ricorsiva se la ricorsione potrebbe causare un deadlock o potrebbe causare il blocco di rotazione per più di 25 microsecondi.

Per ulteriori informazioni sulle routine del driver ricorsive, vedere Utilizzo dello stack del kernel.

Acquisizioni di blocchi spin annidati

Il tentativo di acquisire un secondo spin lock mantenendo un altro spin lock può anche causare deadlock o scarse prestazioni del driver.

Le linee guida seguenti descrivono come i driver devono contenere blocchi di selezione:

  • Il driver non deve chiamare una routine di supporto che utilizza un blocco spin, a meno che non si verifichi un deadlock.

  • Anche se non è possibile eseguire un deadlock, il driver non deve chiamare una routine di supporto che usa un blocco spin, a meno che le tecniche di codifica alternative non possano fornire prestazioni e funzionalità simili al driver.

  • Se un driver effettua chiamate annidate per acquisire blocchi di selezione, deve sempre acquisire i blocchi di rotazione nello stesso ordine ogni volta che vengono acquisiti. Questo ordine consente di evitare deadlock.

In generale, evitare di usare blocchi di selezione annidati per proteggere subset sovrapposti o set discreti di dati e risorse condivisi. Considera cosa può accadere se un driver usa due spin lock esecutivi per proteggere le risorse discrete, ad esempio una coppia di oggetti timer che possono essere impostati individualmente o collettivamente da varie routine del driver. Il driver si bloccava in modo intermittente in un computer SMP, ogni volta che una delle due routine, ciascuna con uno spin lock, tentava di acquisire l'altro spin lock.

Per ulteriori informazioni sull'acquisizione di spin lock annidati, vedere Blocchi, deadlock e sincronizzazione.