#if !defined(_GNU_SOURCE) #define _GNU_SOURCE #endif #include #include #include #include #include #include #include #include #include #include #include #define ARRAYSIZE(x) (sizeof(x) / sizeof(*x)) static int fd_tty_write; static int fd_tty_read; static int fd_log; int LLVMFuzzerInitialize(int* argc, char*** argv) { fd_tty_write = open("/dev/tty", O_RDWR | O_DSYNC); if (fd_tty_write == -1) { perror("open('/dev/tty'), O_RDWR | O_DSYNC"); exit(EXIT_FAILURE); } fd_tty_read = open("/dev/tty", O_RDWR | O_NONBLOCK); if (fd_tty_read == -1) { perror("open('/dev/tty'), O_RDWR | O_NONBLOCK"); exit(EXIT_FAILURE); } fd_log = open("./term.log", O_WRONLY | O_CREAT | O_APPEND, 0644); if (fd_log == -1) { perror("open('./term.log')"); exit(EXIT_FAILURE); } return 0; } static bool isInteresting(const char* s, size_t len) { for (size_t i = 0; i < len; i++) { if (s[i] == '[') { continue; } if (s[i] == ']') { continue; } if (s[i] == '?') { continue; } if (s[i] == ';') { continue; } if (s[i] == 'c') { continue; } if (s[i] == 'R') { continue; } if (s[i] == '\0') { continue; } if (s[i] == '\x1b') { continue; } if (isdigit(s[i])) { continue; } return true; } return false; } int LLVMFuzzerTestOneInput(const uint8_t* buf, size_t len) { write(fd_tty_write, buf, len); for (;;) { char read_buf[1024 * 1024]; ssize_t sz = read(fd_tty_read, read_buf, sizeof(read_buf)); if (sz <= 0) { break; } static const char msg_in[] = "\n============ IN ============\n"; static const char msg_out[] = "\n============ OUT ===========\n"; static const char msg_end[] = "\n============================\n"; struct iovec iov[] = { { .iov_base = (void*)msg_in, .iov_len = sizeof(msg_in), }, { .iov_base = (void*)buf, .iov_len = len, }, { .iov_base = (void*)msg_out, .iov_len = sizeof(msg_out), }, { .iov_base = (void*)read_buf, .iov_len = sz, }, { .iov_base = (void*)msg_end, .iov_len = sizeof(msg_end), }, }; writev(fd_log, iov, ARRAYSIZE(iov)); } return 0; }