Страницы

Поиск по вопросам

воскресенье, 12 января 2020 г.

Linux таймеры и сигналы реального времени

#linux #c


Есть несколько таймеров, которые генерируют один и тот же сигнал SIGRTMIN дополнительно
передавая в sival_int значение. Есть несколько обработчиков сигнала таймера. Правильно
ли я понимаю, что сигнал гарантировано дойдет до всех обработчиков сигнала? А если
сигнал сгенерируется одновременно несколькими таймерами?

Корректно ли в обработчике проверять sival_int ?

#define TIMER_EVENT_ID_1 1
#define TIMER_EVENT_ID_2 2

void timer_handler(int signo, siginfo_t *info, void *context)
{
    if(info->si_value.sival_int==TIMER_EVENT_ID_1)
    {
        sem_post(&sem1); //будим трид 
    }   

    if(info->si_value.sival_int==TIMER_EVENT_ID_2)
    {
        sem_post(&sem2); //будим трид 
    }
}


В разных потоках я создаю, а потом сбрасываю и устанавливаю значения таймеров:

typedef struct 
{
    struct sigevent sigev;
    struct sigaction sa;
    struct itimerspec ival;
    timer_t tid;
} timer_data_t;

int init_timer(timer_data_t *timer_data, void *handler, UNS8 sigNum, UNS8 eventNum)
{
    timer_data->sa.sa_flags = SA_SIGINFO;
    sigemptyset(&timer_data->sa.sa_mask);
    sigaddset(&timer_data->sa.sa_mask, sigNum);
    timer_data->sa.sa_sigaction=handler;   

    if(sigaction(sigNum, &timer_data->sa, NULL)==-1)
    {
        perror("sigaction failed");
        return -1;
    }

    timer_data->sigev.sigev_notify = SIGEV_SIGNAL;
    timer_data->sigev.sigev_signo = sigNum;
    timer_data->sigev.sigev_value.sival_int=eventNum;

    //создаем таймер
    if( timer_create(CLOCK_REALTIME, &timer_data->sigev, &timer_data->tid)==-1)
    {
        printf("init_timer: не могу создать таймер! \n");
        perror("timer_create");
        return -1;
    }

    return 0;       
}

int set_timer(timer_data_t *timer_data, UNS32 timeSec, UNS64 timeNsec)
{
    timer_data->ival.it_value.tv_sec=timeSec;
    timer_data->ival.it_value.tv_nsec =timeNsec;
    timer_data->ival.it_interval.tv_sec=0;
    timer_data->ival.it_interval.tv_nsec=0;

    if(timer_settime(timer_data->tid, 0, &timer_data->ival, NULL) == -1)
    {
        perror("timer_settime");
        return -1;
    }

    return 0;
}


Т.е. вызывая init_timer, я просто изменяю обработчик для конкретного сигнала, т.к.
он может быть только один?
    


Ответы

Ответ 1



Не очень понимаю Ваш вопрос: Правильно ли я понимаю, что сигнал гарантировано дойдет до всех обработчиков сигнала?" Что значит "до всех" ? Сигнал всегда доходит до обработчика сигнала, там обрабатывается и ИСЧЕЗАЕТ! Один сигнал не может дойти до двух обработчиков. В руководстве по сигналам написано, что если сигнал ожидают несколько обработчиков, то кто именно его получит - определяется реализацией.

Комментариев нет:

Отправить комментарий