ncurses in a multithreaded application - c

I have a multi threaded application which uses ncurses on a single thread to report information to the user. My code basically looks like this:
const unsigned int refresh_cycle = 180;
unsigned int refresh_count = refresh_cycle;
while(killswitch != 1) {
if (refresh_count >= refresh_cycle) {
// critical section which obtains some data worked on by a thread. only does this once every refresh cycle times
// mtx lock, fetch, mtx unlock
refresh_count = 0;
}
refresh_count++;
// get input
// draw some stuff
// refresh
}
What I notice is that the ncurses window gets refreshed lots and lots of times. Way more than is really needed for a user who could probably get by with only 15-30 refreshes in a second.
But now I am worrying this might 'steal' unnecesary processing power from one of the threads that is doing work. Is this a reasonable assertion?
Should I build in a sort of frame limiter with usleep() or would that be going overboard?

As per the comments, if in between the refreshes you need to deal with user input, then the easiest way is probably to call select() on STDIN_FILENO with a suitably small timeout. When select() returns, either because there is user input or because it timed out, do a refresh at that point.
Here's an example that'll let you see how to set this up, and shows when when and how many times select() is returning so you can visualize what's going on. Try letting it sit and run for a while, and then try holding down a key, and watch how the select() has returned [n] times message behaves in each case. The comments in the code explain what's happening:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <unistd.h>
#include <time.h>
#include <sys/select.h>
#include <ncurses.h>
/* struct to store curses info for cleanup */
struct curinfo {
WINDOW * main_window;
int old_cursor;
};
/* curses helper functions */
void start_curses(struct curinfo * info);
void stop_curses(struct curinfo * info);
/* main function */
int main(int argc, char * argv[])
{
/* Set default timeout */
int secs = 0;
int usecs = 500000;
/* Set timeout based on command line args, if provided */
if ( argc > 1 ) {
if ( !strcmp(argv[1], "veryshort") ) {
secs = 0;
usecs = 200000;
}
else if ( !strcmp(argv[1], "short") ) {
secs = 1;
usecs = 0;
}
else if ( !strcmp(argv[1], "medium") ) {
secs = 2;
usecs = 0;
}
else if ( !strcmp(argv[1], "long") ) {
secs = 5;
usecs = 0;
}
}
struct curinfo cinfo;
start_curses(&cinfo);
int input = '0'; /* Set to something printable */
int num_sel = 0; /* Number of times select() has returned */
while ( input != 'q' && input != 'Q' ) {
/* Output messages */
mvprintw(3, 3, "select() has returned %d times", num_sel);
mvprintw(4, 3, "Last character input was %c", input);
mvprintw(5, 3, "Press 'q' to quit");
refresh();
/* select() modifies the fd_sets passed to it,
* so zero and set them prior to each call. */
fd_set fds;
FD_ZERO(&fds);
FD_SET(STDIN_FILENO, &fds);
/* Same deal for the struct timeval, select() may
* modify it, it may not, so recreate to be portable. */
struct timeval tv;
tv.tv_sec = secs;
tv.tv_usec = usecs;
/* Store the return so we can check it */
int status = select(STDIN_FILENO + 1, &fds, NULL, NULL, &tv);
/* Check for error */
if ( status == -1 ) {
/* select() returned with an error. */
if ( errno != EINTR ) {
/* If interrupted by a signal, no problem,
* keep going. Otherwise, let's just quit. */
stop_curses(&cinfo);
perror("error calling select()");
return EXIT_FAILURE;
}
}
else if ( FD_ISSET(STDIN_FILENO, &fds) ) {
/* Only call getch() if input is ready.
* getch() will not block when we do it this way. */
if ( (input = getch()) == ERR ) {
stop_curses(&cinfo);
fprintf(stderr, "ERR returned from getch()\n");
return EXIT_FAILURE;
}
}
/* Increment number of times select() has returned */
++num_sel;
}
stop_curses(&cinfo);
return 0;
}
/* Starts curses and populates the passed struct */
void start_curses(struct curinfo * info)
{
if ( (info->main_window = initscr()) == NULL ) {
fprintf(stderr, "Error calling initscr()\n");
exit(EXIT_FAILURE);
}
keypad(stdscr, TRUE);
timeout(0);
raw();
nonl();
noecho();
info->old_cursor = curs_set(0);
refresh();
}
/* Stops curses and cleans up */
void stop_curses(struct curinfo * info)
{
delwin(info->main_window);
curs_set(info->old_cursor);
endwin();
refresh();
}

Related

Is there any way to change sigaction flags during execution?

I have this child process in infinite loop and i want it to stop the loop when recive SIGUSR1 from parent pid.
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <signal.h>
int GameOver = 0;
jmp_buf here; // <------- After Joshua's Answer
void trataSIGUSR1(int sig, siginfo_t *info, void *extra);
int main(int argc, char** argv){
int someNumber = 0, score = 0;
char word[15],c;
struct sigaction new_action;
// new_action.sa_flags = SA_SIGINFO; // <------- Before Joshua's Answer
new_action.sa_flags = SA_SIGINFO | SA_RESTART; // <------- After Joshua's Answer
new_action.sa_sigaction = &trataSIGUSR1;
sigfillset(&new_action.sa_mask);
if (sigaction(SIGUSR1, &new_action, NULL) == -1){
perror("Error: cannot handle SIGUSR1"); // não deve acontecer
return EXIT_FAILURE;
}
FILE *f;
f = fopen("randomfile.txt", "r");
if (f == NULL){
printf("Errr Opening File!\n");
return EXIT_FAILURE;
}
// setjmp(here); // <------- After Joshua's Answer
sigsetjmp(here,1); // <-- After wildplasser's Answer
while (!GameOver){
fscanf(f, "%s", word);
printf("\nWord -> %s\n", word);
if(!scanf("%d", &someNumber)){
puts("Invalid Value!");
while ((c = getchar()) != '\n' && c != EOF);
continue;
}
if(someNumber == strlen(word) && !GameOver)
score ++;
if(feof(f)){
printf("\nEnd of file.\n");
break;
}
}
if( GameOver )
puts("\nAcabou o tempo!"); // <-- After wildplasser's Answer
fclose(f);
return score;
}
void trataSIGUSR1(int sig, siginfo_t *info, void *extra){
if (info->si_pid == getppid()){ // only end when parent send SIGUSR1
// puts("\nAcabou o tempo!"); // <-- Before wildplasser's Answer
GameOver = 1;
// longjmp(here,1); // <------- After Joshua's Answer
siglongjmp(here,1); // <---- After wildplasser's Answer
}
}
It works fine but if i send SIGUSR1 to child pid from another process scanf get interupted... I want to interupt the scanf and automaticly stop the loop only when signal come from parent, in other case just ignore. Is there any way to change the flag to new_action.sa_flags = SA_RESTART; when signal comes from other process?!
There are several possibilities, ranging from a huge hack, to proper (but complicated).
The simplest thing is to have the SIGUSR1 from parent reopen standard input to /dev/null. Then, when scanf() fails, instead of complaining and retrying, you can break out of the loop if feof(stdin) is true. Unfortunately, freopen() is not async-signal safe, so this is not a standards (POSIX, in this case) compliant way of doing things.
The standards-compliant way of doing things is to implement your own read input line into a dynamically allocated string -type of function, which detects when the signal handler sets the flag. The flag should also be of volatile sig_atomic_t type, not an int; the volatile in particular tells the compiler that the value may be changed unexpectedly (by the signal handler), so whenever referenced, the compiler must re-read the variable value, instead of remembering it from a previous access. The sig_atomic_t type is an atomic integer type: the process and the signal handler will only ever see either the new, or the old value, never a mix of the two, but might have as small valid range as 0 to 127, inclusive.
Signal delivery to an userspace handler (installed without SA_RESTART) does interrupt a blocking I/O operation (like read or write; in the thread used for signal delivery – you only have one, so that will always be used), but it might occur between the flag check and the scanf(), so in this case, it is not reliable.
The proper solution here is to not use stdin at all, and instead use the low-level <unistd.h> I/O for this. Note that it is imperative to not mix stdin/scanf() and low-level I/O for the same stream. You can safely use printf(), fprintf(stdout, ...), fprintf(stderr, ...), and so on. The reason is that the C library internal stdin stream structure will not be updated correctly by our low-level access, and will be out-of-sync with reality if we mix both (for the same stream).
Here is an example program showing one implementation (licensed under Creative Commons Zero v1.0 International – do as you wish with it, no guarantees though):
// SPDX-License-Identifier: CC0-1.0
#define _POSIX_C_SOURCE 200809L
#include <stdlib.h>
#include <unistd.h>
#include <sys/types.h>
#include <fcntl.h>
#include <poll.h>
#include <signal.h>
#include <time.h>
#include <string.h>
#include <stdio.h>
#include <errno.h>
/* Maximum poll() timeout, in milliseconds, so that done flag is checked often enough.
*/
#ifndef DONE_POLL_INTERVAL_MS
#define DONE_POLL_INTERVAL_MS 100
#endif
static volatile sig_atomic_t done = 0;
static void handle_done(int signum, siginfo_t *info, void *context)
{
/* This silences warnings about context not being used. It does nothing. */
(void)context;
if (signum == SIGUSR1 && info->si_pid == getppid()) {
/* SIGUSR1 is only accepted if it comes from the parent process */
done = 1;
} else {
/* All other signals are accepted from all processes (that have the necessary privileges) */
done = 1;
}
}
static int install_done(const int signum)
{
struct sigaction act;
memset(&act, 0, sizeof act);
sigemptyset(&(act.sa_mask));
act.sa_sigaction = handle_done;
act.sa_flags = SA_SIGINFO;
return sigaction(signum, &act, NULL);
}
/* Our own input stream structure type. */
struct input {
int descriptor;
char *data;
size_t size;
size_t head;
size_t tail;
};
/* Associating an input stream with a file descriptor.
Do not mix stdin use and input stream on descriptor STDIN_FILENO!
*/
static int input_use(struct input *const in, const int descriptor)
{
/* Check that the parameters are not obviously invalid. */
if (!in || descriptor == -1) {
errno = EINVAL;
return -1;
}
/* Set the descriptor nonblocking. */
{
int flags = fcntl(descriptor, F_GETFL);
if (flags == -1) {
/* errno set by fcntl(). */
return -1;
}
if (fcntl(descriptor, F_SETFL, flags | O_NONBLOCK) == -1) {
/* errno set by fcntl(). */
return -1;
}
}
/* Initialize the stream structure. */
in->descriptor = descriptor;
in->data = NULL;
in->size = 0;
in->head = 0;
in->tail = 0;
/* Success. */
return 0;
}
/* Read until delimiter from an input stream.
* If 'done' is set at any point, will return 0 with errno==EINTR.
* Returns 0 if an error occurs, with errno set.
* Returns 0 with errno==0 when end of input stream.
*/
static size_t input_getdelim(struct input *const in,
int const delim,
char **const dataptr,
size_t *const sizeptr,
const double timeout)
{
const clockid_t timeout_clk = CLOCK_BOOTTIME;
struct timespec then;
/* Verify none of the pointers are NULL. */
if (!in || !dataptr || !sizeptr) {
errno = EINVAL;
return 0;
}
/* Record current time for timeout measurement. */
clock_gettime(timeout_clk, &then);
char *line_data = *dataptr;
size_t line_size = *sizeptr;
/* If (*sizeptr) is zero, then we ignore dataptr value, like getline() does. */
if (!line_size)
line_data = NULL;
while (1) {
struct timespec now;
struct pollfd fds[1];
ssize_t n;
int ms = DONE_POLL_INTERVAL_MS;
/* Done flag set? */
if (done) {
errno = EINTR;
return 0;
}
/* Is there a complete line in the input buffer? */
if (in->tail > in->head) {
const char *ptr = memchr(in->data + in->head, delim, in->tail - in->head);
if (ptr) {
const size_t len = ptr - (in->data + in->head);
if (len + 2 > line_size) {
/* Since we do not have any meaningful data in line_data,
and it would be overwritten anyway if there was,
instead of reallocating it we just free an allocate it. */
free(line_data); /* Note: free(null) is safe. */
line_size = len + 2;
line_data = malloc(line_size);
if (!line_data) {
/* Oops, we lost the buffer. */
*dataptr = NULL;
*sizeptr = 0;
errno = ENOMEM;
return 0;
}
*dataptr = line_data;
*sizeptr = line_size;
}
/* Copy the line, including the separator, */
memcpy(line_data, in->data + in->head, len + 1);
/* add a terminating nul char, */
line_data[len + 1] = '\0';
/* and update stream buffer state. */
in->head += len + 1;
return len + 1;
}
/* No, we shall read more data. Prepare the buffer. */
if (in->head > 0) {
memmove(in->data, in->data + in->head, in->tail - in->head);
in->tail -= in->head;
in->head = 0;
}
} else {
/* Input buffer is empty. */
in->head = 0;
in->tail = 0;
}
/* Do we need to grow input stream buffer? */
if (in->head >= in->tail) {
/* TODO: Better buffer size growth policy! */
const size_t size = (in->tail + 65535) | 65537;
char *data;
data = realloc(in->data, size);
if (!data) {
errno = ENOMEM;
return 0;
}
in->data = data;
in->size = size;
}
/* Try to read additional data. It is imperative that the descriptor
has been marked nonblocking, as otherwise this will block. */
n = read(in->descriptor, in->data + in->tail, in->size - in->tail);
if (n > 0) {
/* We read more data without blocking. */
in->tail += n;
continue;
} else
if (n == 0) {
/* End of input mark (Ctrl+D at the beginning of line, if a terminal) */
const size_t len = in->tail - in->head;
if (len < 1) {
/* No data buffered, read end of input. */
if (line_size < 1) {
line_size = 1;
line_data = malloc(line_size);
if (!line_data) {
errno = ENOMEM;
return 0;
}
*dataptr = line_data;
*sizeptr = line_size;
}
line_data[0] = '\0';
errno = 0;
return 0;
}
if (len + 1 > line_size) {
/* Since we do not have any meaningful data in line_data,
and it would be overwritten anyway if there was,
instead of reallocating it we just free an allocate it. */
free(line_data); /* Note: free(null) is safe. */
line_size = len + 1;
line_data = malloc(line_size);
if (!line_data) {
/* Oops, we lost the buffer. */
*dataptr = NULL;
*sizeptr = 0;
errno = ENOMEM;
return 0;
}
*dataptr = line_data;
*sizeptr = line_size;
}
memmove(line_data, in->data, len);
line_data[len] = '\0';
in->head = 0;
in->tail = 0;
return 0;
} else
if (n != -1) {
/* This should never occur; it would be a C library bug. */
errno = EIO;
return 0;
} else {
const int err = errno;
if (err != EAGAIN && err != EWOULDBLOCK && err != EINTR)
return 0;
/* EAGAIN, EWOULDBLOCK, and EINTR are not real errors. */
}
/* Nonblocking operation, with timeout == 0.0? */
if (timeout == 0.0) {
errno = ETIMEDOUT;
return 0;
} else
if (timeout > 0.0) {
/* Obtain current time. */
clock_gettime(timeout_clk, &now);
const double elapsed = (double)(now.tv_sec - then.tv_sec)
+ (double)(now.tv_nsec - then.tv_nsec) / 1000000000.0;
/* Timed out? */
if (elapsed >= (double)timeout / 1000.0) {
errno = ETIMEDOUT;
return 0;
}
if (timeout - elapsed < (double)DONE_POLL_INTERVAL_MS / 1000.0) {
ms = (int)(1000 * (timeout - elapsed));
if (ms < 1) {
errno = ETIMEDOUT;
return 0;
}
}
}
/* Negative timeout values means no timeout check,
and ms retains its initialized value. */
/* Another done check; it's cheap. */
if (done) {
errno = 0;
return EINTR;
}
/* Wait for input, but not longer than ms milliseconds. */
fds[0].fd = in->descriptor;
fds[0].events = POLLIN;
fds[0].revents = 0;
poll(fds, 1, ms);
/* We don't actually care about the result at this point. */
}
/* Never reached. */
}
static inline size_t input_getline(struct input *const in,
char **const dataptr,
size_t *const sizeptr,
const double timeout)
{
return input_getdelim(in, '\n', dataptr, sizeptr, timeout);
}
int main(void)
{
struct input in;
char *line = NULL;
size_t size = 0;
size_t len;
if (install_done(SIGINT) == -1 ||
install_done(SIGHUP) == -1 ||
install_done(SIGTERM) == -1 ||
install_done(SIGUSR1) == -1) {
fprintf(stderr, "Cannot install signal handlers: %s.\n", strerror(errno));
return EXIT_FAILURE;
}
if (input_use(&in, STDIN_FILENO)) {
fprintf(stderr, "BUG in input_use(): %s.\n", strerror(errno));
return EXIT_FAILURE;
}
while (!done) {
/* Wait for input for five seconds. */
len = input_getline(&in, &line, &size, 5000);
if (len > 0) {
/* Remove the newline at end, if any. */
line[strcspn(line, "\n")] = '\0';
printf("Received: \"%s\" (%zu chars)\n", line, len);
fflush(stdout);
continue;
} else
if (errno == 0) {
/* This is the special case: input_getline() returns 0 with
errno == 0 when there is no more input. */
fprintf(stderr, "End of standard input.\n");
return EXIT_SUCCESS;
} else
if (errno == ETIMEDOUT) {
printf("(No input for five seconds.)\n");
fflush(stdout);
} else
if (errno == EINTR) {
/* Break or continue works here, since input_getline() only
returns 0 with errno==EINTR if done==1. */
break;
} else {
fprintf(stderr, "Error reading from standard input: %s.\n", strerror(errno));
return EXIT_FAILURE;
}
}
printf("Signal received; done.\n");
return EXIT_SUCCESS;
}
Save it as e.g. example.c, compile using e.g. gcc -Wall -Wextra -O2 example.c -o example, and run using ./example. Type input and enter to supply lines, or Ctrl+D at the beginning of a line to end input, or Ctrl+C to send the process a SIGINT signal.
Note the compile-time constant DONE_POLL_INTERVAL_MS. If the signal is delivered between a done check and poll(), this is the maximum delay, in milliseconds (1000ths of a second), that the poll may block; and therefore is roughly the maximum delay from receiving the signal and acting upon it.
To make the example more interesting, it also implements a timeout on reading a full line also. The above example prints when it is reached, but that messes up how the user sees the input they're typing. (It does not affect the input.)
This is by no means a perfect example of such functions, but I hope it is a readable one, with the comments explaining the reasoning behind each code block.
Historically we solved this problem by always setting SA_RESTART and calling longjump() to get out of the signal handler when the condition is met.
The standard makes this undefined but I think this does the right thing when stdin is connected to the keyboard. Don't try it with redirected handles. It won't work well. At least you can check for this condition with isatty(0).
If it doesn't work and you are bent on using signals like this, you'll need to abandon scanf() and friends and get all your input using read().

Pthread runtime errors

I'm having trouble debugging the following program I wrote. The idea is to have two seperate threads; one thread executes a 5 second countdown while the other waits for key input from the user. Whichever thread completes first should cancel the sibling thread and exit the program. However, the following code just hangs.
Any help would be appreciated, but I would be most grateful for an explanation as to the problem.
#include <pthread.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h> // For sleep()
#define NUM_THREADS 2
// The stuct to be passed as an argument to the countdown routine
typedef struct countdown_struct {
pthread_t *thread;
signed int num_secs;
} CountdownStruct;
// Struct for passing to the input wait routine
typedef struct wait_struct {
pthread_t *thread;
int *key;
} WaitStruct;
// Countdown routine; simply acts as a timer counting down
void * countdown(void *args)
{
CountdownStruct *cd_str = (CountdownStruct *)args;
signed int secs = cd_str->num_secs;
printf("Will use default setting in %d seconds...", secs);
while (secs >= 0)
{
sleep(1);
secs -= 1;
printf("Will use default setting in %d seconds...", secs);
}
// Cancel the other struct
pthread_cancel(*(cd_str->thread));
return NULL;
}
// Waits for the user to pass input through the tty
void * wait_for_input(void *args)
{
WaitStruct *wait_str = (WaitStruct *) args;
int c = 0;
do {
c = getchar();
} while (!(c == '1' || c == '2'));
*(wait_str->key) = c;
// Cancel the other thread
pthread_cancel(*(wait_str->thread));
return NULL;
}
int main(int argc, char **argv)
{
pthread_t wait_thread;
pthread_t countdown_thread;
pthread_attr_t attr;
int key=0;
long numMillis=5000;
int rc=0;
int status=0;
// Create the structs to be passe as paramaters to both routines
CountdownStruct *cd_str = (CountdownStruct *) malloc(sizeof(CountdownStruct));
if (cd_str == NULL)
{
printf("Couldn't create the countdown struct. Aborting...");
return -1;
}
cd_str->thread = &wait_thread;
cd_str->num_secs = 5;
WaitStruct *wait_str = (WaitStruct *) malloc(sizeof(WaitStruct));
if (wait_str == NULL)
{
printf("Couldn't create the iput wait struct. Aborting...");
return -1;
}
wait_str->thread = &countdown_thread;
wait_str->key = &key;
// Create the joinable attribute
pthread_attr_init(&attr);
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
// Create both threads
rc = pthread_create(&countdown_thread, &attr, countdown, (void *) cd_str);
if (rc) { printf("Error with the thread creation!"); exit(-1); }
rc = pthread_create(&wait_thread, &attr, wait_for_input, (void *) wait_str);
if (rc) { printf("Error with the thread creation!"); exit(-1); }
// Destroy the pthread_attribute
pthread_attr_destroy(&attr);
// now join on the threads and wait for main
pthread_join(wait_thread, NULL);
pthread_join(countdown_thread, NULL);
// Call pthread_exit
pthread_exit(NULL);
// Free the function structs
free(cd_str);
free(wait_str);
}
Getchar is not required to be a cancellation point. Select and pselect are. Even if you want to continue to use a countdown thread you could still provide a cancellation point in the opposing thread by use of select.
I had reasonable behavior with the following modified wait_for_input()
// Waits for the user to pass input through the tty
void * wait_for_input(void *args)
{
WaitStruct *wait_str = (WaitStruct *) args;
int c = 0;
fd_set readFds;
int numFds=0;
FD_ZERO(&readFds);
do {
struct timeval timeout={.tv_sec=8,.tv_usec=0};
/* select here is primarily to serve as a cancellation
* point. Though there is a possible race condition
* still between getchar() getting called right as the
* the timeout thread calls cancel.().
* Using the timeout option on select would at least
* cover that, but not done here while testing.
*******************************************************/
FD_ZERO(&readFds);
FD_SET(STDOUT_FILENO,&readFds);
numFds=select(STDOUT_FILENO+1,&readFds,NULL,NULL,&timeout);
if(numFds==0 )
{
/* must be timeout if no FD's selected */
break;
}
if(FD_ISSET(STDOUT_FILENO,&readFds))
{
printf("Only get here if key pressed\n");
c = getchar();
}
} while (!(c == '1' || c == '2'));
*(wait_str->key) = c;
// Cancel the other thread
pthread_cancel(*(wait_str->thread));
return NULL;
}

How do you make a precise countdown timer using clock_gettime?

Could somebody please explain how to make a countdown timer using clock_gettime, under Linux. I know you can use the clock() function to get cpu time, and multiply it by CLOCKS_PER_SEC to get actual time, but I'm told the clock() function is not well suited for this.
So far I have attempted this (a billion is to pause for one second)
#include <stdio.h>
#include <time.h>
#define BILLION 1000000000
int main()
{
struct timespec rawtime;
clock_gettime(CLOCK_MONOTONIC_RAW, &rawtime);
unsigned long int current = ( rawtime.tv_sec + rawtime.tv_nsec );
unsigned long int end = (( rawtime.tv_sec + rawtime.tv_nsec ) + BILLION );
while ( current < end )
{
clock_gettime(CLOCK_MONOTONIC_RAW, &rawtime);
current = ( rawtime.tv_sec + rawtime.tv_nsec );
}
return 0;
}
I know this wouldn't be very useful on its own, but once I've found out how to time correctly I can use this in my projects. I know that sleep() can be used for this purpose, but I want to code the timer myself so that I can better integrate it in my projects - such as the possibility of it returning the time left, as opposed to pausing the whole program.
Please, do not do that. You're burning CPU power for nothing in a busy loop.
Why not use the nanosleep() function instead? It's perfectly suited to the use case you outlined. Or, if you want an easier interface, perhaps something like
#define _POSIX_C_SOURCE 200809L
#include <time.h>
#include <errno.h>
/* Sleep for the specified number of seconds,
* and return the time left over.
*/
double dsleep(const double seconds)
{
struct timespec req, rem;
/* No sleep? */
if (seconds <= 0.0)
return 0.0;
/* Convert to seconds and nanoseconds. */
req.tv_sec = (time_t)seconds;
req.tv_nsec = (long)((seconds - (double)req.tv_sec) * 1000000000.0);
/* Take care of any rounding errors. */
if (req.tv_nsec < 0L)
req.tv_nsec = 0L;
else
if (req.tv_nsec > 999999999L)
req.tv_nsec = 999999999L;
/* Do the nanosleep. */
if (nanosleep(&req, &rem) != -1)
return 0.0;
/* Error? */
if (errno != EINTR)
return 0.0;
/* Return remainder. */
return (double)rem.tv_sec + (double)rem.tv_nsec / 1000000000.0;
}
The difference is that using this one the CPU is free to do something else, rather than spin like a crazed squirrel on speed.
This is not an answer, but an example of how to use signals and a POSIX timer to implement a timeout timer; intended as a response to the OP's followup question in a comment to the accepted answer.
#define _POSIX_C_SOURCE 200809L
#include <stdlib.h>
#include <signal.h>
#include <time.h>
#include <errno.h>
#include <string.h>
#include <stdio.h>
/* Timeout timer.
*/
static timer_t timeout_timer;
static volatile sig_atomic_t timeout_state = 0;
static volatile sig_atomic_t timeout_armed = 2;
static const int timeout_signo = SIGALRM;
#define TIMEDOUT() (timeout_state != 0)
/* Timeout signal handler.
*/
static void timeout_handler(int signo, siginfo_t *info, void *context __attribute__((unused)))
{
if (timeout_armed == 1)
if (signo == timeout_signo && info && info->si_code == SI_TIMER)
timeout_state = ~0;
}
/* Unset timeout.
* Returns nonzero if timeout had expired, zero otherwise.
*/
static int timeout_unset(void)
{
struct itimerspec t;
const int retval = timeout_state;
/* Not armed? */
if (timeout_armed != 1)
return retval;
/* Disarm. */
t.it_value.tv_sec = 0;
t.it_value.tv_nsec = 0;
t.it_interval.tv_sec = 0;
t.it_interval.tv_nsec = 0;
timer_settime(timeout_timer, 0, &t, NULL);
return retval;
}
/* Set timeout (in wall clock seconds).
* Cancels any pending timeouts.
*/
static int timeout_set(const double seconds)
{
struct itimerspec t;
/* Uninitialized yet? */
if (timeout_armed == 2) {
struct sigaction act;
struct sigevent evt;
/* Use timeout_handler() for timeout_signo signal. */
sigemptyset(&act.sa_mask);
act.sa_sigaction = timeout_handler;
act.sa_flags = SA_SIGINFO;
if (sigaction(timeout_signo, &act, NULL) == -1)
return errno;
/* Create a monotonic timer, delivering timeout_signo signal. */
evt.sigev_value.sival_ptr = NULL;
evt.sigev_signo = timeout_signo;
evt.sigev_notify = SIGEV_SIGNAL;
if (timer_create(CLOCK_MONOTONIC, &evt, &timeout_timer) == -1)
return errno;
/* Timeout is initialzied but unarmed. */
timeout_armed = 0;
}
/* Disarm timer, if armed. */
if (timeout_armed == 1) {
/* Set zero timeout, disarming the timer. */
t.it_value.tv_sec = 0;
t.it_value.tv_nsec = 0;
t.it_interval.tv_sec = 0;
t.it_interval.tv_nsec = 0;
if (timer_settime(timeout_timer, 0, &t, NULL) == -1)
return errno;
timeout_armed = 0;
}
/* Clear timeout state. It should be safe (no pending signals). */
timeout_state = 0;
/* Invalid timeout? */
if (seconds <= 0.0)
return errno = EINVAL;
/* Set new timeout. Check for underflow/overflow. */
t.it_value.tv_sec = (time_t)seconds;
t.it_value.tv_nsec = (long)((seconds - (double)t.it_value.tv_sec) * 1000000000.0);
if (t.it_value.tv_nsec < 0L)
t.it_value.tv_nsec = 0L;
else
if (t.it_value.tv_nsec > 999999999L)
t.it_value.tv_nsec = 999999999L;
/* Set it repeat once every millisecond, just in case the initial
* interrupt is missed. */
t.it_interval.tv_sec = 0;
t.it_interval.tv_nsec = 1000000L;
if (timer_settime(timeout_timer, 0, &t, NULL) == -1)
return errno;
timeout_armed = 1;
return 0;
}
int main(void)
{
char *line = NULL;
size_t size = 0;
ssize_t len;
fprintf(stderr, "Please supply input. The program will exit automatically if\n");
fprintf(stderr, "it takes more than five seconds for the next line to arrive.\n");
fflush(stderr);
while (1) {
if (timeout_set(5.0)) {
const char *const errmsg = strerror(errno);
fprintf(stderr, "Cannot set timeout: %s.\n", errmsg);
return 1;
}
len = getline(&line, &size, stdin);
if (len == (ssize_t)-1)
break;
if (len < (ssize_t)1) {
/* This should never occur (except for -1, of course). */
errno = EIO;
break;
}
/* We do not want *output* to be interrupted,
* so we cancel the timeout. */
timeout_unset();
if (fwrite(line, (size_t)len, 1, stdout) != 1) {
fprintf(stderr, "Error writing to standard output.\n");
fflush(stderr);
return 1;
}
fflush(stdout);
/* Next line. */
}
/* Remember to cancel the timeout. Also check it. */
if (timeout_unset())
fprintf(stderr, "Timed out.\n");
else
if (ferror(stdin) || !feof(stdin))
fprintf(stderr, "Error reading standard input.\n");
else
fprintf(stderr, "End of input.\n");
fflush(stderr);
/* Free line buffer. */
free(line);
line = NULL;
size = 0;
/* Done. */
return 0;
}
If you save the above as timer.c, you can compile it using e.g.
gcc -W -Wall -O3 -std=c99 -pedantic timer.c -lrt -o timer
and run it using ./timer.
If you read the code above carefully, you'll see that it is actually a periodic timer signal (at millisecond intervals), with a variable delay before the first signal. That is just a technique I like to use to make sure I don't miss the signal. (The signal repeats until the timeout is unset.)
Note that although you can do computation in an signal handler, you should only use functions that are async-signal-safe; see man 7 signal. Also, only the sig_atomic_t type is atomic wrt. normal single-threaded code and a signal handler. So, it is better to just use the signal as an indicator, and do the actual code in your own program.
If you wanted to e.g. update monster coordinates in a signal handler, it is possible but a bit tricky. I'd use three arrays containing the monster information, and use GCC __sync_bool_compare_and_swap() to update the array pointers -- very much the same technique as triple-buffering in graphics.
If you need more than one concurrent timeout, you could use multiple timers (there is a number of them available), but the best option is to define timeout slots. (You can use generation counters to detect "forgotten" timeouts, and so on.) Whenever a new timeout is set or unset, you update the timeout to reflect the next timeout that expires. It's a bit more code, but really a straightforward extension of the above.

timers in linux in c [duplicate]

This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Loops/timers in C
I've been reading about timers for the last 3 days and I'm unable to find anything useful, I'm trying to understand it in real example, can somebody help me figure out how to setup an alarm for the below program.
How can I set a a timer so that it will send 2 args, one is the array name, and the second one is the number to be deleted, I know the below is not safe in anyway, I'm just trying to understand how use alarms with args to call a function.
please note that the environment is Linux, and also I appreciate any link with a working C example.
#include<stdio.h>
int delete_from_array(int arg) ;
int main()
{
int a[10000], i, y ;
//how to set timer here for to delete any number in array after half a second
for (y=0; y < 100; y++) {
for (i=0; i<sizeof(a) / sizeof(int); i++)
a[i] = i;
sleep(1);
printf("wake\n");
}
}
int delete_from_array(int arg)
{
int i, a[1000], number_to_delete=0;
//number_to_delete = arg->number;
for (i=0; i<sizeof(a); i++)
if (a[i] == number_to_delete)
a[i] = 0;
printf("deleted\n");
}
What I'm trying to do is that I have a hash which has has values to be expired after 1 seconds, so after I insert the value into the hash, I need to create a timer so that it will delete that value after let's say 1 second, and IF I got a response from the server before the that interval (1 second) then I delete the value from the hash and delete the timer, almost like retransmission in tcp
Do you want to use signals or threads?
First, set up the signal handler or prepare a suitable thread function; see man 7 sigevent for details.
Next, create a suitable timer, using timer_create(). See man 2 timer_create for details.
Depending on what you do when the timer fires, you may wish to set the timer to either one-shot, or to repeat at a short interval afterwards. You use timer_settime() to both arm, and to disarm, the timer; see man 2 timer_settime for details.
In practical applications you usually need to multiplex the timer. Even though a process can create multiple timers, they are a limited resource. Especially timeout timers -- which are trivial, either setting a flag and/or sending a signal to a specific thread -- should use a single timer, which fires at the next timeout, sets the related timeout flag, and optionally send a signal (with an empty-body handler) to the desired thread to make sure it is interrupted. (For a single-thread process, the original signal delivery will interrupt blocking I/O calls.) Consider a server, responding to some request: the request itself might have a timeout on the order of a minute or so, while processing the request might need connection timeouts, I/O timeouts, and so on.
Now, the original question is interesting, because timers are powerful when used effectively. However, the example program is basically nonsense. Why don't you create say a program that sets one or more timers, each for example outputting something to standard output? Remember to use write() et al from unistd.h as they are async-signal safe, whereas printf() et cetera from stdio.h are not. (If your signal handlers use non-async-signal safe functions, the results are undefined. It usually works, but it's not guaranteed at all; it may just as well crash as work. Testing will not tell, as it is undefined.)
Edited to add: Here is a bare-bones example of multiplexed timeouts.
(To the extent possible under law, I dedicate all copyright and related and neighboring rights to the code snippets shown below to the public domain worldwide; see CC0 Public Domain Dedication. In other words, feel free to use the code below in any way you wish, just don't blame me for any problems with it.)
I used old-style GCC atomic built-ins, so it should be thread-safe. With a few additions, it should work for multithreaded code too. (You cannot use for example mutexes, because pthread_mutex_lock() is not async-signal safe. Atomically manipulating the timeout states should work, although there might be some races left if you disable a timeout just when it fires.)
#define _POSIX_C_SOURCE 200809L
#include <unistd.h>
#include <signal.h>
#include <time.h>
#include <errno.h>
#define TIMEOUTS 16
#define TIMEOUT_SIGNAL (SIGRTMIN+0)
#define TIMEOUT_USED 1
#define TIMEOUT_ARMED 2
#define TIMEOUT_PASSED 4
static timer_t timeout_timer;
static volatile sig_atomic_t timeout_state[TIMEOUTS] = { 0 };
static struct timespec timeout_time[TIMEOUTS];
/* Return the number of seconds between before and after, (after - before).
* This must be async-signal safe, so it cannot use difftime().
*/
static inline double timespec_diff(const struct timespec after, const struct timespec before)
{
return (double)(after.tv_sec - before.tv_sec)
+ (double)(after.tv_nsec - before.tv_nsec) / 1000000000.0;
}
/* Add positive seconds to a timespec, nothing if seconds is negative.
* This must be async-signal safe.
*/
static inline void timespec_add(struct timespec *const to, const double seconds)
{
if (to && seconds > 0.0) {
long s = (long)seconds;
long ns = (long)(0.5 + 1000000000.0 * (seconds - (double)s));
/* Adjust for rounding errors. */
if (ns < 0L)
ns = 0L;
else
if (ns > 999999999L)
ns = 999999999L;
to->tv_sec += (time_t)s;
to->tv_nsec += ns;
if (to->tv_nsec >= 1000000000L) {
to->tv_nsec -= 1000000000L;
to->tv_sec++;
}
}
}
/* Set the timespec to the specified number of seconds, or zero if negative seconds.
*/
static inline void timespec_set(struct timespec *const to, const double seconds)
{
if (to) {
if (seconds > 0.0) {
const long s = (long)seconds;
long ns = (long)(0.5 + 1000000000.0 * (seconds - (double)s));
if (ns < 0L)
ns = 0L;
else
if (ns > 999999999L)
ns = 999999999L;
to->tv_sec = (time_t)s;
to->tv_nsec = ns;
} else {
to->tv_sec = (time_t)0;
to->tv_nsec = 0L;
}
}
}
/* Return nonzero if the timeout has occurred.
*/
static inline int timeout_passed(const int timeout)
{
if (timeout >= 0 && timeout < TIMEOUTS) {
const int state = __sync_or_and_fetch(&timeout_state[timeout], 0);
/* Refers to an unused timeout? */
if (!(state & TIMEOUT_USED))
return -1;
/* Not armed? */
if (!(state & TIMEOUT_ARMED))
return -1;
/* Return 1 if timeout passed, 0 otherwise. */
return (state & TIMEOUT_PASSED) ? 1 : 0;
} else {
/* Invalid timeout number. */
return -1;
}
}
/* Release the timeout.
* Returns 0 if the timeout had not fired yet, 1 if it had.
*/
static inline int timeout_unset(const int timeout)
{
if (timeout >= 0 && timeout < TIMEOUTS) {
/* Obtain the current timeout state to 'state',
* then clear all but the TIMEOUT_PASSED flag
* for the specified timeout.
* Thanks to Bylos for catching this bug. */
const int state = __sync_fetch_and_and(&timeout_state[timeout], TIMEOUT_PASSED);
/* Invalid timeout? */
if (!(state & TIMEOUT_USED))
return -1;
/* Not armed? */
if (!(state & TIMEOUT_ARMED))
return -1;
/* Return 1 if passed, 0 otherwise. */
return (state & TIMEOUT_PASSED) ? 1 : 0;
} else {
/* Invalid timeout number. */
return -1;
}
}
int timeout_set(const double seconds)
{
struct timespec now, then;
struct itimerspec when;
double next;
int timeout, i;
/* Timeout must be in the future. */
if (seconds <= 0.0)
return -1;
/* Get current time, */
if (clock_gettime(CLOCK_REALTIME, &now))
return -1;
/* and calculate when the timeout should fire. */
then = now;
timespec_add(&then, seconds);
/* Find an unused timeout. */
for (timeout = 0; timeout < TIMEOUTS; timeout++)
if (!(__sync_fetch_and_or(&timeout_state[timeout], TIMEOUT_USED) & TIMEOUT_USED))
break;
/* No unused timeouts? */
if (timeout >= TIMEOUTS)
return -1;
/* Clear all but TIMEOUT_USED from the state, */
__sync_and_and_fetch(&timeout_state[timeout], TIMEOUT_USED);
/* update the timeout details, */
timeout_time[timeout] = then;
/* and mark the timeout armable. */
__sync_or_and_fetch(&timeout_state[timeout], TIMEOUT_ARMED);
/* How long till the next timeout? */
next = seconds;
for (i = 0; i < TIMEOUTS; i++)
if ((__sync_fetch_and_or(&timeout_state[i], 0) & (TIMEOUT_USED | TIMEOUT_ARMED | TIMEOUT_PASSED)) == (TIMEOUT_USED | TIMEOUT_ARMED)) {
const double secs = timespec_diff(timeout_time[i], now);
if (secs >= 0.0 && secs < next)
next = secs;
}
/* Calculate duration when to fire the timeout next, */
timespec_set(&when.it_value, next);
when.it_interval.tv_sec = 0;
when.it_interval.tv_nsec = 0L;
/* and arm the timer. */
if (timer_settime(timeout_timer, 0, &when, NULL)) {
/* Failed. */
__sync_and_and_fetch(&timeout_state[timeout], 0);
return -1;
}
/* Return the timeout number. */
return timeout;
}
static void timeout_signal_handler(int signum __attribute__((unused)), siginfo_t *info, void *context __attribute__((unused)))
{
struct timespec now;
struct itimerspec when;
int saved_errno, i;
double next;
/* Not a timer signal? */
if (!info || info->si_code != SI_TIMER)
return;
/* Save errno; some of the functions used may modify errno. */
saved_errno = errno;
if (clock_gettime(CLOCK_REALTIME, &now)) {
errno = saved_errno;
return;
}
/* Assume no next timeout. */
next = -1.0;
/* Check all timeouts that are used and armed, but not passed yet. */
for (i = 0; i < TIMEOUTS; i++)
if ((__sync_or_and_fetch(&timeout_state[i], 0) & (TIMEOUT_USED | TIMEOUT_ARMED | TIMEOUT_PASSED)) == (TIMEOUT_USED | TIMEOUT_ARMED)) {
const double seconds = timespec_diff(timeout_time[i], now);
if (seconds <= 0.0) {
/* timeout [i] fires! */
__sync_or_and_fetch(&timeout_state[i], TIMEOUT_PASSED);
} else
if (next <= 0.0 || seconds < next) {
/* This is the soonest timeout in the future. */
next = seconds;
}
}
/* Note: timespec_set() will set the time to zero if next <= 0.0,
* which in turn will disarm the timer.
* The timer is one-shot; it_interval == 0.
*/
timespec_set(&when.it_value, next);
when.it_interval.tv_sec = 0;
when.it_interval.tv_nsec = 0L;
timer_settime(timeout_timer, 0, &when, NULL);
/* Restore errno. */
errno = saved_errno;
}
int timeout_init(void)
{
struct sigaction act;
struct sigevent evt;
struct itimerspec arm;
/* Install timeout_signal_handler. */
sigemptyset(&act.sa_mask);
act.sa_sigaction = timeout_signal_handler;
act.sa_flags = SA_SIGINFO;
if (sigaction(TIMEOUT_SIGNAL, &act, NULL))
return errno;
/* Create a timer that will signal to timeout_signal_handler. */
evt.sigev_notify = SIGEV_SIGNAL;
evt.sigev_signo = TIMEOUT_SIGNAL;
evt.sigev_value.sival_ptr = NULL;
if (timer_create(CLOCK_REALTIME, &evt, &timeout_timer))
return errno;
/* Disarm the timeout timer (for now). */
arm.it_value.tv_sec = 0;
arm.it_value.tv_nsec = 0L;
arm.it_interval.tv_sec = 0;
arm.it_interval.tv_nsec = 0L;
if (timer_settime(timeout_timer, 0, &arm, NULL))
return errno;
return 0;
}
int timeout_done(void)
{
struct sigaction act;
struct itimerspec arm;
int errors = 0;
/* Ignore the timeout signals. */
sigemptyset(&act.sa_mask);
act.sa_handler = SIG_IGN;
if (sigaction(TIMEOUT_SIGNAL, &act, NULL))
if (!errors) errors = errno;
/* Disarm any current timeouts. */
arm.it_value.tv_sec = 0;
arm.it_value.tv_nsec = 0L;
arm.it_interval.tv_sec = 0;
arm.it_interval.tv_nsec = 0;
if (timer_settime(timeout_timer, 0, &arm, NULL))
if (!errors) errors = errno;
/* Destroy the timer itself. */
if (timer_delete(timeout_timer))
if (!errors) errors = errno;
/* If any errors occurred, set errno. */
if (errors)
errno = errors;
/* Return 0 if success, errno otherwise. */
return errors;
}
Remember to include the rt library when compiling, i.e. use gcc -W -Wall *source*.c -lrt -o *binary* to compile.
The idea is that the main program first calls timeout_init() to install all the necessary handlers et cetera, and may call timeout_done() to deistall it before exiting (or in a child process after fork()ing).
To set a timeout, you call timeout_set(seconds). The return value is a timeout descriptor. Currently there is just a flag you can check using timeout_passed(), but the delivery of the timeout signal also interrupts any blocking I/O calls. Thus, you can expect the timeout to interrupt any blocking I/O call.
If you want to do anything more than set a flag at timeout, you cannot do it in the signal handler; remember, in a signal handler, you're limited to async-signal safe functions. The easiest way around that is to use a separate thread with an endless loop over sigwaitinfo(), with the TIMEOUT_SIGNAL signal blocked in all other threads. That way the dedicated thread is guaranteed to catch the signal, but at the same time, is not limited to async-signal safe functions. It can, for example, do much more work, or even send a signal to a specific thread using pthread_kill(). (As long as that signal has a handler, even one with an empty body, its delivery will interrupt any blocking I/O call in that thread.)
Here is a simple example main() for using the timeouts. It is silly, and relies on fgets() not retrying (when interrupted by a signal), but it seems to work.
#include <string.h>
#include <stdio.h>
int main(void)
{
char buffer[1024], *line;
int t1, t2, warned1;
if (timeout_init()) {
fprintf(stderr, "timeout_init(): %s.\n", strerror(errno));
return 1;
}
printf("You have five seconds to type something.\n");
t1 = timeout_set(2.5); warned1 = 0;
t2 = timeout_set(5.0);
line = NULL;
while (1) {
if (timeout_passed(t1)) {
/* Print only the first time we notice. */
if (!warned1++)
printf("\nTwo and a half seconds left, buddy.\n");
}
if (timeout_passed(t2)) {
printf("\nAw, just forget it, then.\n");
break;
}
line = fgets(buffer, sizeof buffer, stdin);
if (line) {
printf("\nOk, you typed: %s\n", line);
break;
}
}
/* The two timeouts are no longer needed. */
timeout_unset(t1);
timeout_unset(t2);
/* Note: 'line' is non-NULL if the user did type a line. */
if (timeout_done()) {
fprintf(stderr, "timeout_done(): %s.\n", strerror(errno));
return 1;
}
return 0;
}
A useful read is the time(7) man page. Notice that Linux also provides the timerfd_create(2) Linux specific syscall, often used with a multiplexing syscall like poll(2) (or ppoll(2) or the older select(2) syscall).
If you want to use signals don't forget to read carefully signal(7) man page (there are restrictions about coding signal handlers; you might want to set a volatile sigatomic_t variable in your signal handlers; you should not do any new or delete -or malloc & free- memory menagenment operations inside a signal handler, where only async-safe function calls are permitted.).
Notice also that event-oriented programming, such as GUI applications, often provide ways (in Gtk, in Qt, with libevent, ....) to manage timers in their event loop.

How to loop select() to poll for data ad infinitum

#include <stdio.h>
#include <unistd.h>
#include <sys/time.h>
#include <sys/types.h>
int main ()
{
char name[20];
fd_set input_set;
struct timeval timeout;
int ready_for_reading = 0;
int read_bytes = 0;
/* Empty the FD Set */
FD_ZERO(&input_set );
/* Listen to the input descriptor */
FD_SET(0, &input_set);
/* Waiting for some seconds */
timeout.tv_sec = 10; // 10 seconds
timeout.tv_usec = 0; // 0 milliseconds
/* Invitation for the user to write something */
printf("Enter Username: (in 15 seconds)\n");
printf("Time start now!!!\n");
/* Listening for input stream for any activity */
ready_for_reading = select(1, &input_set, NULL, NULL, &timeout);
/* Here, first parameter is value of the socket descriptor + 1 (STDIN descriptor is 0, so
* 0 +1 = 1)
* in the set, second is our FD set for reading,
* third is the FD set in which any write activity needs to updated, which is not required
* in this case. Fourth is timeout
*/
if (ready_for_reading == -1) {
/* Some error has occured in input */
printf("Unable to read your input\n");
return -1;
} else {
if (ready_for_reading) {
read_bytes = read(0, name, 19);
printf("Read, %d bytes from input : %s \n", read_bytes, name);
} else {
printf(" 10 Seconds are over - no data input \n");
}
}
return 0;
}
How to do the same, but not just once, but in infinite loop which breaks after encountering 'quit' string (for example). Every way I tried - failed.
So if no data has been inputed after 10 seconds program just prints "10 secs are over - no data input" and then starts waiting again. Same after input - just begins again and behave the same every time in infinite loop.
Am little desperate already, please - help.
Thanks.
I don't really see the problem here. Basically just put everything you want in the loop, and let it run. Did you try this?
int main ()
{
/* Declarations and stuff */
/* ... */
/* The loop */
int break_condition = 0;
while (!break_condition)
{
/* Selection */
FD_ZERO(&input_set ); /* Empty the FD Set */
FD_SET(0, &input_set); /* Listen to the input descriptor */
ready_for_reading = select(1, &input_set, NULL, NULL, &timeout);
/* Selection handling */
if (ready_for_reading)
{
/* Do something clever with the input */
}
else
{
/* Handle the error */
}
/* Test the breaking condition */
break_condition = some_calculation();
}
return 0;
}
Note that you have to have keep resetting the selection inside the loop so that it will respond again in the next iteration.
The select() function can be told to block indefinitely by setting timeout to NULL. See select(2) man page:
timeout is an upper bound on the amount of time elapsed before select() returns. If both fields of the timeval stucture are zero, then select() returns immediately. (This is useful for polling.) If timeout is NULL (no timeout), select() can block indefinitely.
So what you want is:
...
ready_for_reading = select(1, &input_set, NULL, NULL, NULL);
...

Resources