1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
|
#include "timer.h"
#include <assert.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <time.h>
#include <sys/timerfd.h>
#include <sys/eventfd.h>
#include <poll.h>
void timer_init(Timer *t, size_t sec) {
assert(t != NULL);
t->seconds = sec;
t->remaining_seconds = sec;
t->timerfd = timerfd_create(CLOCK_MONOTONIC, TFD_NONBLOCK);
if(t->timerfd == -1) {
fprintf(stdout, "Error: timerfd could not be created!");
exit(1);
}
}
void timer_reset(Timer *t) {
assert(t != NULL);
struct itimerspec spec = {0};
timerfd_settime(t->timerfd, 0, &spec, NULL);
t->remaining_seconds = t->seconds;
size_t mins = t->remaining_seconds / 60;
size_t secs = t->remaining_seconds % 60;
fprintf(stdout, "{\"text\": \"Paused %02d:%02d\"}\n", mins, secs);
fflush(stdout);
}
void timer_start(Timer *t) {
assert(t != NULL);
t->status = T_RUNNING;
struct itimerspec spec;
spec.it_interval.tv_sec = 1;
spec.it_interval.tv_nsec = 0;
spec.it_value.tv_sec = 1;
spec.it_value.tv_nsec = 0;
timerfd_settime(t->timerfd, 0, &spec, NULL);
}
void timer_stop(Timer *t) {
assert(t != NULL);
t->status = T_STOPPED;
struct itimerspec spec = {0};
timerfd_settime(t->timerfd, 0, &spec, NULL);
}
void timer_toggle_state(Timer *t) {
assert(t != NULL);
if(t->status == T_RUNNING)
timer_stop(t);
else if (t->status == T_STOPPED)
timer_start(t);
}
void timer_loop(Timer *t) { // May drift by a couple mili-seconds. However, just a pomodoro app, so that is not important.
assert(t != NULL);
t->remaining_seconds = t->seconds;
size_t mins = t->remaining_seconds / 60;
size_t secs = t->remaining_seconds % 60;
fprintf(stdout, "{\"text\": \"Paused %02d:%02d\"}\n", mins, secs);
fflush(stdout);
struct pollfd fds;
fds.fd = t->timerfd;
fds.events = POLLIN;
while (1) {
if(poll(&fds, 1, -1) == -1) {
printf("Failed to poll events!");
exit(1);
}
if(fds.revents & POLLIN) {
uint64_t tick;
read(t->timerfd, &tick, sizeof(tick));
if(t->remaining_seconds == 0) {
fprintf(stdout,"{\"text\": \"Completed\"}\n");
uint64_t buf;
timer_stop(t);
} else {
t->remaining_seconds--;
size_t mins = t->remaining_seconds / 60;
size_t secs = t->remaining_seconds % 60;
fprintf(stdout,"{\"text\": \"Work %02d:%02d\"}\n", mins, secs);
}
fflush(stdout);
}
}
}
|