As Basile Starynkevitch alluded to, I needed to update the terminal configuration via termios(3).
I have provided the revised code below for reference. For the changes required, please see the code between the // TERMINAL SETUP
and // EPOLL SETUP
comments.
#include <errno.h>
#include <linux/input.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <sys/epoll.h>
#include <termios.h>
#include <unistd.h>
int main(void) {
// TERMINAL SETUP
struct termios tty_cfg, tty_cfg_cache;
// Check that fd is a TTY
if (!isatty(STDIN_FILENO)) {
fprintf(stderr, "Standard input is not a terminal.\n");
return EXIT_FAILURE;
}
// Save old terminal configuration
if (tcgetattr(STDIN_FILENO, &tty_cfg_cache) == -1 ||
tcgetattr(STDIN_FILENO, &tty_cfg) == -1) {
fprintf(stderr, "Cannot get terminal settings: %s.\n", strerror(errno));
return EXIT_FAILURE;
}
// Set new terminal configuration
tty_cfg.c_iflag &= ~(IGNBRK | BRKINT | PARMRK);
tty_cfg.c_lflag &= ~(ICANON | ISIG | ECHO | IEXTEN | TOSTOP);
tty_cfg.c_cc[VMIN] = 0;
tty_cfg.c_cc[VTIME] = 0;
tty_cfg.c_cc[VSTART] = 0;
tty_cfg.c_cc[VSTOP] = 0;
if (tcsetattr(STDIN_FILENO, TCSANOW, &tty_cfg) == -1) {
const int saved_errno = errno;
tcsetattr(STDIN_FILENO, TCSANOW, &tty_cfg_cache);
fprintf(stderr, "Cannot set terminal settings: %s.\n", strerror(saved_errno));
return EXIT_FAILURE;
}
// EPOLL SETUP
// Create epoll
int epfd = epoll_create1(EPOLL_CLOEXEC);
// Add stdin control interface to epoll
struct epoll_event event;
int ctl_ret;
event.events = EPOLLIN;
event.data.fd = STDIN_FILENO;
ctl_ret = epoll_ctl(epfd, EPOLL_CTL_ADD, STDIN_FILENO, &event);
if (ctl_ret) {
perror("epoll_ctl");
return 1;
}
// LOOP AND MONITOR EPOLL
int nr_event;
unsigned char keys[16];
ssize_t n;
size_t i, done;
done = 0;
while (!done) {
// Start epoll_wait
nr_event = epoll_wait(epfd, &event, 1, -1);
if (nr_event < 0) {
perror("epoll_wait");
return 1;
}
// Read STDIN_FILENO
n = read(STDIN_FILENO, keys, sizeof keys);
if (n > 0) {
for (i = 0; i < n; i++) {
// Quit if 'q' or 'Q' is pressed
if (keys[i] == 'q' || keys[i] == 'Q')
done = 1;
if (keys[i] >= 32 && keys[i] <= 126)
printf("Key '%c' = 0x%02x = %u pressed\n", keys[i], keys[i], keys[i]);
else
if (keys[i])
printf("Key '\\%03o' = 0x%02x = %u pressed\n", keys[i], keys[i], keys[i]);
else
printf("NUL key (0) pressed\n");
}
fflush(stdout);
}
}
// RESTORE TERMINAL SETTINGS
tcsetattr(STDIN_FILENO, TCSAFLUSH, &tty_cfg_cache);
return EXIT_SUCCESS;
}