Xinqi Bao's Git
1 /* See LICENSE file for copyright and license details. */
15 const char *(*func
)();
21 static volatile sig_atomic_t done
;
27 terminate(const int signo
)
34 difftimespec(struct timespec
*res
, struct timespec
*a
, struct timespec
*b
)
36 res
->tv_sec
= a
->tv_sec
- b
->tv_sec
- (a
->tv_nsec
< b
->tv_nsec
);
37 res
->tv_nsec
= a
->tv_nsec
- b
->tv_nsec
+
38 (a
->tv_nsec
< b
->tv_nsec
) * 1E9
;
44 die("usage: %s [-s]", argv0
);
48 main(int argc
, char *argv
[])
51 struct timespec start
, current
, diff
, intspec
, wait
;
70 memset(&act
, 0, sizeof(act
));
71 act
.sa_handler
= terminate
;
72 sigaction(SIGINT
, &act
, NULL
);
73 sigaction(SIGTERM
, &act
, NULL
);
74 act
.sa_flags
|= SA_RESTART
;
75 sigaction(SIGUSR1
, &act
, NULL
);
77 if (!sflag
&& !(dpy
= XOpenDisplay(NULL
))) {
78 die("XOpenDisplay: Failed to open display");
82 if (clock_gettime(CLOCK_MONOTONIC
, &start
) < 0) {
83 die("clock_gettime:");
87 for (i
= len
= 0; i
< LEN(args
); i
++) {
88 if (!(res
= args
[i
].func(args
[i
].args
))) {
91 if ((ret
= esnprintf(status
+ len
, sizeof(status
) - len
,
92 args
[i
].fmt
, res
)) < 0) {
104 if (XStoreName(dpy
, DefaultRootWindow(dpy
), status
)
106 die("XStoreName: Allocation failed");
112 if (clock_gettime(CLOCK_MONOTONIC
, ¤t
) < 0) {
113 die("clock_gettime:");
115 difftimespec(&diff
, ¤t
, &start
);
117 intspec
.tv_sec
= interval
/ 1000;
118 intspec
.tv_nsec
= (interval
% 1000) * 1E6
;
119 difftimespec(&wait
, &intspec
, &diff
);
121 if (wait
.tv_sec
>= 0) {
122 if (nanosleep(&wait
, NULL
) < 0 &&
131 XStoreName(dpy
, DefaultRootWindow(dpy
), NULL
);
132 if (XCloseDisplay(dpy
) < 0) {
133 die("XCloseDisplay: Failed to close display");