#include <unistd.h>
#include <string.h>
#include <stdio.h>
#include <sys/types.h>
#include <sys/epoll.h>
#include <sys/inotify.h>
#include <dirent.h>
#include <stdlib.h>
int main(int argc, char **argv)
{
int *fd, *wd;
int len, path_num, current_path_num;
int select_ret;
int event_pos, event_size;
char buf[256];
struct inotify_event *event;
fd_set read_fds, tmp_fds;
if (argc < 2) {
printf("please input correct dir name\n");
return -1;
}
path_num = current_path_num = argc - 1;
for (int i = 1; i < argc; i++) {
if (access(argv[i], F_OK) != 0) {
printf("path: %s is not existed\n", argv[i]);
return -1;
}
}
wd = (int *)calloc(argc-1, sizeof(int));
fd = (int *)calloc(argc-1, sizeof(int));
if (wd == NULL) {
printf("calloc fail\n");
return -1;
}
if (fd == NULL) {
printf("calloc fail\n");
free(wd);
return -1;
}
for (int i = 1; i < argc; i++) {
fd[i - 1] = inotify_init();
if (fd[i - 1] == -1) {
printf("inotify_init error!\n");
free(fd);
free(wd);
return -1;
}
wd[i - 1] = inotify_add_watch(fd[i-1], argv[i], IN_CREATE | IN_DELETE | IN_MODIFY | IN_DELETE_SELF);
if (wd[i - 1] < 0) {
printf("inotify_add_watch error\n");
free(fd);
free(wd);
return -1;
}
}
FD_ZERO(&read_fds);
FD_ZERO(&tmp_fds);
for (int i = 0; i < argc -1; i++) {
FD_SET(fd[i], &read_fds);
}
while (1) {
tmp_fds = read_fds;
select_ret = select(FD_SETSIZE, &tmp_fds, (fd_set *)0, (fd_set *)0, (struct timeval *) 0);
if (select_ret < 1) {
perror("select error");
free(fd);
free(wd);
exit(1);
}
for (int i = 0; i < FD_SETSIZE; i++) {
if (FD_ISSET(i, &tmp_fds)) {
event_pos = 0;
len = read(i, buf, sizeof(buf) - 1);
while (len >= (int)sizeof(struct inotify_event) ) {
event = (struct inotify_event*)(buf + event_pos);
if (strncmp(event->name, ".", strlen(".")) != 0
&& strncmp(event->name, "..", strlen("..")) != 0
&& strncmp(&event->name[len-1], "~", strlen("~")) != 0) {
switch (event->mask) {
case IN_CREATE:
printf("create file: %s\n",event->name);
break;
case IN_DELETE:
printf("delete file: %s\n",event->name);
break;
case IN_MODIFY:
printf("modify file: %s\n",event->name);
break;
case IN_DELETE_SELF:
printf("watched path has been deleted\n");
FD_CLR(i, &read_fds);
path_num -= 1;
break;
default:
printf("error watch type\n");
FD_CLR(i, &read_fds);
path_num -= 1;
break;
}
}
if (path_num <= 0) {
printf("all watched path has been deleted\n");
free(fd);
free(wd);
exit(1);
}
if (path_num < current_path_num) {
current_path_num = path_num;
break;
}
event_size = sizeof(struct inotify_event) + event->len;
len -= event_size;
event_pos += event_size;
}
}
}
}
return 0;
}
监视test1、test2运行结果