Codebase list entr / b0a99e5
Update upstream source from tag 'upstream/4.2' Update to upstream version '4.2' with Debian dir 0b775797009df624378b8808766ee34bd8ff762a Otto Kekäläinen 4 years ago
7 changed file(s) with 63 addition(s) and 19 deletion(s). Raw diff Collapse all Expand all
00 PREFIX ?= /usr/local
11 MANPREFIX ?= ${PREFIX}/man
2 RELEASE = 4.1
2 RELEASE = 4.2
33 CPPFLAGS += -DRELEASE=\"${RELEASE}\"
44
55 all: versioncheck entr
00 = Release History
1
2 == 4.2: March 28, 2019
3
4 - Use pledge(2) on OpenBSD
5 - New '-a' option enables response to events that occur while the utility is
6 running
7 - Error messages direct users to http://eradman.com/entrproject/limits.html
8 - Correctly report error when a file cannot be reopened
19
210 == 4.1: June 13, 2018
311
1212 .\" ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
1313 .\" OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
1414 .\"
15 .Dd April 17 2018 $
15 .Dd March 28, 2019
1616 .Dt ENTR 1
1717 .Os
1818 .Sh NAME
2020 .Nd run arbitrary commands when files change
2121 .Sh SYNOPSIS
2222 .Nm
23 .Op Fl cdprs
23 .Op Fl acdprs
2424 .Ar utility
2525 .Op Ar argument /_ ...
2626 .Sh DESCRIPTION
3535 .Pp
3636 The arguments are as follows:
3737 .Bl -tag -width Ds
38 .It Fl a
39 Respond to all events which occur while the
40 .Ar utility
41 is running.
42 Without this option
43 .Nm
44 consolidates events in order to avoid looping.
45 This option has no effect in conjunction with the
46 .Fl r
47 flag.
3848 .It Fl c
3949 Execute
4050 .Pa /usr/bin/clear
7272 WatchFile *leading_edge;
7373 int child_pid;
7474
75 int aggressive_opt;
7576 int clear_opt;
7677 int dirwatch_opt;
78 int noninteractive_opt;
79 int postpone_opt;
7780 int restart_opt;
78 int postpone_opt;
7981 int shell_opt;
80 int noninteractive_opt;
8182 struct termios canonical_tty;
8283
8384 /* forwards */
126127 xlist_dir = list_dir;
127128 xtcsetattr = tcsetattr;
128129
130 if (pledge("stdio rpath tty proc exec", NULL) == -1)
131 err(1, "pledge");
132
129133 /* call usage() if no command is supplied */
130134 if (argc < 2) usage();
131135 argv_index = set_options(argv);
137141 if (sigemptyset(&act.sa_mask) & (sigaction(SIGINT, &act, NULL) != 0))
138142 err(1, "Failed to set SIGINT handler");
139143 if (sigemptyset(&act.sa_mask) & (sigaction(SIGTERM, &act, NULL) != 0))
140 err(1, "Failed to set TERM handler");
144 err(1, "Failed to set SIGTERM handler");
141145
142146 /* raise soft limit */
143147 getrlimit(RLIMIT_NOFILE, &rl);
168172 if (n_files == -1)
169173 errx(1, "Too many files listed; the hard limit for your login"
170174 " class is %d. Please consult"
171 " http://entrproject.org/limits.html", (int)rl.rlim_cur);
175 " http://eradman.com/entrproject/limits.html", (int)rl.rlim_cur);
172176 for (i=0; i<n_files; i++)
173177 watch_file(kq, files[i]);
174178
199203 void
200204 usage() {
201205 fprintf(stderr, "release: %s\n", RELEASE);
202 fprintf(stderr, "usage: entr [-cdnprs] utility [argument [/_] ...] < filenames\n");
206 fprintf(stderr, "usage: entr [-acdnprs] utility [argument [/_] ...] < filenames\n");
203207 exit(1);
204208 }
205209
225229 }
226230
227231 /*
228 * Read lines from a file stream (normally STDIN)
229 * Returns the number of regular files to be watched or -1 if max_files is
230 * exceeded
232 * Read lines from a file stream (normally STDIN). Returns the number of
233 * regular files to be watched or -1 if max_files is exceeded.
231234 */
232235 int
233236 process_input(FILE *file, WatchFile *files[], int max_files) {
308311
309312 /* read arguments until we reach a command */
310313 for (argc=1; argv[argc] != 0 && argv[argc][0] == '-'; argc++);
311 while ((ch = getopt(argc, argv, "cdnprs")) != -1) {
314 while ((ch = getopt(argc, argv, "acdnprs")) != -1) {
312315 switch (ch) {
316 case 'a':
317 aggressive_opt = 1;
318 break;
313319 case 'c':
314320 clear_opt = 1;
315321 break;
440446 else break;
441447 }
442448 if (file->fd == -1) {
449 warn("cannot open '%s'", file->fn);
443450 terminate_utility();
444 err(1, "cannot open '%s'", file->fn);
451 exit(1);
445452 }
446453
447454 EV_SET(&evSet, file->fd, EVFILT_VNODE, EV_ADD | EV_CLEAR, NOTE_ALL, 0,
450457 if (errno == ENOSPC)
451458 errx(1, "Unable to allocate memory for kernel queue."
452459 " Please consult"
453 " http://entrproject.org/limits.html");
460 " http://eradman.com/entrproject/limits.html");
454461 else
455462 err(1, "failed to register VNODE event");
456463 }
494501 WatchFile *file;
495502 int i;
496503 struct timespec evTimeout = { 0, 1000000 };
497 int reopen_only = 0;
504 int reopen_only = !aggressive_opt;
498505 int collate_only = 0;
499506 int do_exec = 0;
500507 int dir_modified = 0;
516523
517524 main:
518525 if (!noninteractive_opt)
519 xtcsetattr(STDIN_FILENO, TCSADRAIN, &character_tty);
526 xtcsetattr(0, TCSADRAIN, &character_tty);
520527 if ((reopen_only == 1) || (collate_only == 1)) {
521528 nev = xkevent(kq, NULL, 0, evList, 32, &evTimeout);
522529 }
631638 if (do_exec == 1) {
632639 do_exec = 0;
633640 run_utility(argv);
634 reopen_only = 1;
641 if (!aggressive_opt)
642 reopen_only = 1;
635643 leading_edge_set = 0;
636644 }
637645 if (dir_modified > 0) {
7979 optind = 1;
8080
8181 /* initialize global data */
82 aggressive_opt = 1;
8283 clear_opt = 0;
8384 dirwatch_opt = 0;
85 noninteractive_opt = 0;
8486 postpone_opt = 0;
8587 restart_opt = 0;
8688 shell_opt = 0;
87 noninteractive_opt = 0;
89
8890 leading_edge = 0;
8991 files = calloc(max_files, sizeof(WatchFile *));
9092 for (i=0; i<max_files; i++)
9193 files[i] = calloc(1, sizeof(WatchFile));
94
9295 /* initialize test context */
9396 memset(&ctx, 0, sizeof(ctx));
9497
377380 int kq = kqueue();
378381 static char *argv[] = { "prog", "arg1", "arg2", NULL };
379382
383 aggressive_opt = 0;
380384 postpone_opt = 1;
381385 strlcpy(files[0]->fn, "main.py", sizeof(files[0]->fn));
382386 watch_file(kq, files[0]);
1414 #endif
1515
1616 #if !defined(ARG_MAX)
17 #define ARG_MAX 2097152
17 #define ARG_MAX (256 * 1024)
1818 #endif
19
20 #ifndef __OpenBSD__
21 #define pledge(s, p) (0)
22 #endif
370370
371371 # extra slow tests that rely on timeouts
372372
373 try "respond to events that occur while the utility is running"
374 setup
375 ls $tmp/file* | ./entr -a sh -c 'echo "vroom"; sleep 0.5' > $tmp/exec.out &
376 bgpid=$! ; zz
377 echo "123" > $tmp/file1
378 sleep 1
379 kill -INT $bgpid
380 wait $bgpid || assert "$?" "130"
381 assert "$(cat $tmp/exec.out)" "$(printf 'vroom\nvroom\n')"
382
373383 try "ensure that all subprocesses are terminated in restart mode when a file is removed"
374384 setup
375385 cat <<-SCRIPT > $tmp/go.sh