¿Qué variables deben ser sig_atomic_t exactamente en el contexto del manejo de la señal?

Aquí hay un programa de juguete simple que usavolatile sig_atomic_t.

#include <stdio.h>
#include <signal.h>
#include <stdlib.h>
#include <unistd.h>

#define UNUSED(x) (void) (x)

volatile sig_atomic_t quit;

void sigusr1_handler(int sig)
{
    UNUSED(sig);
    write(1, "handler\n", 8);
    quit = 1;
}

int main()
{
    struct sigaction sa;

    sa.sa_handler = sigusr1_handler;
    sa.sa_flags = 0;
    sigemptyset(&sa.sa_mask);

    if (sigaction(SIGUSR1, &sa, NULL) == -1) {
        perror("sigaction");
        return 1;
    }

    quit = 0;
    while (!quit)
        ;

    printf("Exiting ...\n");
    return 0;
}

Creo que se porquevolatile sig_atomic_t es necesario para elquit variable en este programa en particular.

Sinvolatile, el compilador puede optimizarwhile (!quit) ; a un bucle infinito. No encuentra el bucle modificandoquit, entonces se supone quequit siempre permanece0.Una actualización dequit o una lectura dequit debe suceder en una sola instrucción de máquina. Si se necesitan varias instrucciones de la máquina para actualizar o leerquit, si se invoca un controlador de señal mientras se realizaba una actualización, una lectura en el controlador de señal puede ver un valor inconsistente enquit.

¿Estoy en lo correcto hasta ahora? Si no, corrígeme en tu respuesta.

Ahora quiero aprender una regla generalizada para cuándosig_atomic_t es necesario en el contexto del manejo de la señal. Jonathan Leffler ha explicado en el comentario que no es fácil proporcionar una generalización.

¿Puede proporcionar una lista de escenarios conocidos donde una variable debe definirse comosig_atomic_t desde la perspectiva estándar C? No necesita ser una lista exhaustiva. Podría ser una lista a la que un desarrollador menos experimentado puede referirse mientras escribe software C con código de manejo de señal.

Respuestas a la pregunta(1)

Su respuesta a la pregunta