longjmp () из обработчика сигнала

Я использую следующий код, чтобы попытаться прочитать ввод от пользователя и тайм-аут и выйти, если прошло более 5 секунд. Это достигается с помощью комбинации setjmp / longjmp и сигнала SIGALRM.

Вот код:

#include <stdio.h>
#include <setjmp.h>
#include <unistd.h>
#include <string.h>
#include <sys/signal.h>

jmp_buf buffer;

// this will cause t_gets() to return -2
void timeout() {
    longjmp(buffer, 1);
}

int t_gets(char* s, int t)
{
    char* ret;
    signal(SIGALRM, timeout);
    if (setjmp(buffer) != 0)
        return -2; // <--- timeout() will jump here
    alarm(t);
    // if fgets() does not return in t seconds, SIGALARM handler timeout()
    // will be called, causing t_gets() to return -2
    ret = fgets(s, 100, stdin);
    alarm(0);
    if (ret == NULL ) return -1;
    return strlen(s);
}

int main()
{
    char s[100];
    int z=t_gets(s, 5);
    printf("%d\n", z); 
}

Теперь мой вопрос: есть ли что-нибудь, что может пойти не так с этой функцией? Я читал, что вызов longjmp () из обработчика сигнала может иметь неопределенное поведение, к чему именно это относится?

Кроме того, что если тревога срабатывает сразу после возврата функции fgets (), но до вызова alarm (0)? Приведет ли это к функции, возвращающей -2, даже если пользователь что-то ввел?

ПОСЛЕДНЕЕ РЕДАКТИРОВАНИЕ: Меня не интересуют способы улучшения кода. Я просто хочу знать, как это может потерпеть неудачу.

Ответы на вопрос(7)

Ваш ответ на вопрос