Estoy trabajando en una aplicación de espacio de usuario para un proyecto de Linux incrustado utilizando el kernel 2.6.24.3. Mi aplicación pasa datos entre dos nodos de archivos al crear 2 pthreads que cada uno duerme hasta que se completa una operación IO asincrónica en qué punto se activa y ejecuta un controlador de finalización.¿Puedo evitar que un espacio de usuario de Linux genere pthread en código crítico?
Los controladores de finalización necesitan realizar un seguimiento de la cantidad de transferencias pendientes y mantener un puñado de listas vinculadas que un subproceso agregará y el otro eliminará.
// sleep here until events arrive or time out expires
for(;;) {
no_of_events = io_getevents(ctx, 1, num_events, events, &timeout);
// Process each aio event that has completed or thrown an error
for (i=0; i<no_of_events; i++) {
// Get pointer to completion handler
io_complete = (io_callback_t) events[i].data;
// Get pointer to data object
iocb = (struct iocb *) events[i].obj;
// Call completion handler and pass it the data object
io_complete(ctx, iocb, events[i].res, events[i].res2);
}
}
Mi pregunta es la siguiente ...
¿Existe una manera sencilla puedo evitar que el hilo activo en ese momento de ceder mientras se ejecuta el manejador de finalización en lugar de ir por el camino de bloqueo mutex/vuelta?
O, en su defecto, ¿puede Linux configurarse para evitar producir un pthread cuando se mantiene un bloqueo mutex/spin?
El requisito es principalmente tratar de mantener el código simple, hay varios elementos que requerirían mutex dentro de los manejadores de finalización, pero si pudiera asegurar que solo se producirían fuera de los manejadores, no creo que necesite ningún código . Supongo que la otra opción es simplemente poner un mutex grueso alrededor de todo el controlador. – KermitG
@KermitG: Si le preocupa que el código del manejador de finalización compita con el código en otro hilo, entonces simplemente evitar el adelantamiento no ayudará. El otro subproceso ya podría estar dentro de la sección crítica cuando se inicia el controlador de finalización; incluso si lo pausa mientras se ejecuta el controlador de finalización, aún verá que los datos en los que está trabajando cambian. En general, si el código en el controlador puede competir, el manejador en sí mismo debería ser responsable de bloquearlo. – caf