timer_settime()
builds timer every second. The signal handler is traffic_measurement_handler
. Does traffic_measurement_handler
run in a new thread? How to let callback
stop when the handler is running?
#define CLOCKID CLOCK_REALTIME
#define SIG SIGUSR1
timer_t timerid;
int main(void)
{
..
build_timer();
pcap_loop(pcap_handle, -1, callback, NULL);
}
void callback() // callback of Libpcap API: pcap_loop()
{
detect_network_traffic(); // stop when timer expires, and then continue
// to run when traffic_measurement_handler has finished.
}
// timer handler runs every second to update database
void traffic_measurement_handler()
{
.. // This block will fetch global variables, so I want to
// let callback stop when this handler is running.
// rebuild the timer
build_timer();
}
// set timer
void build_timer()
{
sa.sa_flags = SA_SIGINFO;
sa.sa_sigaction = traffic_measurement_handler;
sigemptyset(&sa.sa_mask);
sigaction(SIG, &sa, NULL);
sev.sigev_notify = SIGEV_SIGNAL;
sev.sigev_signo = SIG;
sev.sigev_value.sival_ptr = &timerid;
timer_create(CLOCKID, &sev, &timerid);
its.it_value.tv_sec = 1;
its.it_value.tv_nsec = 0;
its.it_interval.tv_sec = its.it_value.tv_sec;
its.it_interval.tv_nsec = its.it_value.tv_nsec;
timer_settime(timerid, 0, &its, NULL);
}
Is signal handler safe in a process where only one thread exists?
Added: second version
Is this right?
pthread_t thread_global;
int main(void)
{
// register SIGUSR1 handler
sa.sa_flags = SA_SIGINFO;
sa.sa_sigaction = traffic_measurement_handler;
sigemptyset(&sa.sa_mask);
sigaction(SIG, &sa, NULL);
pthread_create(&thread1, NULL, processing_thread, (void *) thread_id1);
pthread_create(&thread2, NULL, timer_thread, (void *) thread_id2);
pthread_join(thread1, NULL);
pthread_join(thread2, NULL);
}
void *processing_thread(void *thread_id)
{
pcap_loop(pcap_handle, -1, callback, NULL);
}
void callback() // callback of Libpcap API: pcap_loop()
{
thread_global = pthread_self();
detect_network_traffic(); // stop when SIGUSR1 is caught, and then continue
// to run when traffic_measurement_handler has finished.
}
//update database every second when SIGUSR1 is caught
void traffic_measurement_handler()
{
..
}
//This thread is used to notify updating database every second.
void *timer_thread(void *thread_id)
{
for (; ;) {
sleep(1);
pthread_kill(thread_global, SIGUSR1);
}
}