main.c 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687
  1. #include <errno.h>
  2. #include <fcntl.h>
  3. #include <stdint.h>
  4. #include <stdio.h>
  5. #include <stdlib.h>
  6. #include <string.h>
  7. #include <sys/eventfd.h>
  8. #include <sys/select.h>
  9. #include <sys/wait.h>
  10. #include <time.h>
  11. #include <unistd.h>
  12. // 创建 eventfd 并返回 fd
  13. int create_eventfd() {
  14. int fd = eventfd(0, EFD_NONBLOCK);
  15. if (fd == -1) {
  16. perror("eventfd");
  17. exit(EXIT_FAILURE);
  18. }
  19. return fd;
  20. }
  21. // 子线程或子进程模拟事件发生
  22. void trigger_event(int efd, unsigned int delay_sec) {
  23. printf("[trigger] Writing eventfd after %u seconds...\n", delay_sec);
  24. sleep(delay_sec);
  25. uint64_t val = 1;
  26. if (write(efd, &val, sizeof(val)) != sizeof(val)) {
  27. perror("write eventfd");
  28. exit(EXIT_FAILURE);
  29. }
  30. printf("[trigger] Event written to eventfd.\n");
  31. }
  32. int main() {
  33. int efd = create_eventfd();
  34. pid_t pid = fork();
  35. if (pid < 0) {
  36. perror("fork");
  37. exit(1);
  38. }
  39. if (pid == 0) {
  40. // 子进程:触发事件
  41. trigger_event(efd, 3);
  42. close(efd);
  43. exit(0);
  44. }
  45. // 父进程:使用 select 等待事件发生
  46. printf("[select_test] Waiting for event...\n");
  47. fd_set rfds;
  48. FD_ZERO(&rfds);
  49. FD_SET(efd, &rfds);
  50. int maxfd = efd + 1;
  51. struct timeval timeout;
  52. timeout.tv_sec = 5;
  53. timeout.tv_usec = 0;
  54. int ret = select(maxfd, &rfds, NULL, NULL, &timeout);
  55. if (ret < 0) {
  56. perror("select");
  57. exit(1);
  58. }
  59. printf("[select_test] select returned: %d\n", ret);
  60. if (FD_ISSET(efd, &rfds)) {
  61. printf("[select_test] Event occurred on eventfd.\n");
  62. uint64_t val;
  63. if (read(efd, &val, sizeof(val)) != sizeof(val)) {
  64. perror("read");
  65. exit(1);
  66. }
  67. printf("[select_test] Received eventfd value: %lu\n", val);
  68. }
  69. // wait for child process to finish
  70. int status;
  71. waitpid(pid, &status, 0);
  72. printf("[parent] Child exited with status: %d\n", WEXITSTATUS(status));
  73. close(efd);
  74. return 0;
  75. }