Skip to content

Commit 3714694

Browse files
committed
sq12: formalize logging
As with pcoul, we write a start line, a progress line (every 600s) and a finish line. We do not attempt recovery at this point: an interrupted run should be manually restarted after inspecting progress made.
1 parent f30519e commit 3714694

File tree

1 file changed

+90
-17
lines changed

1 file changed

+90
-17
lines changed

sq12.c

Lines changed: 90 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -34,51 +34,90 @@ ulong pmin, pmax;
3434
prime_iterator ip, iq, ir;
3535
t_divisors *divisors;
3636

37-
uint diag_delay = 1;
38-
timer_t diag_timerid;
37+
uint diag_delay = 1, log_delay = 600;
38+
timer_t diag_timerid, log_timerid;
3939
volatile bool need_work = 0;
4040
bool clock_is_realtime = 0;
41+
struct rusage rusage_buf;
42+
static inline double utime(void) {
43+
getrusage(RUSAGE_SELF, &rusage_buf);
44+
return (double)rusage_buf.ru_utime.tv_sec
45+
+ (double)rusage_buf.ru_utime.tv_usec / 1000000;
46+
}
47+
48+
char *rpath = NULL; /* path to log file */
49+
FILE *rfp = NULL; /* file handle to log file */
4150

4251
void fail(char *format, ...) {
4352
va_list ap;
4453
va_start(ap, format);
4554
vfprintf(stderr, format, ap);
4655
fprintf(stderr, "\n");
4756
va_end(ap);
57+
if (rfp)
58+
fclose(rfp);
4859
exit(1);
4960
}
5061

62+
void report(char *format, ...) {
63+
keep_diag();
64+
va_list ap;
65+
va_start(ap, format);
66+
gmp_vfprintf(stdout, format, ap);
67+
va_end(ap);
68+
69+
if (rfp) {
70+
va_start(ap, format);
71+
gmp_vfprintf(rfp, format, ap);
72+
va_end(ap);
73+
fflush(rfp);
74+
}
75+
}
76+
5177
char buf[256];
78+
void do_diag(void) {
79+
if (need_work & 1) {
80+
diag(buf);
81+
need_work &= ~1;
82+
}
83+
if (rfp && (need_work & 2)) {
84+
fprintf(rfp, "305 %s (%.2fs)\n", buf, utime());
85+
need_work &= ~2;
86+
}
87+
}
88+
5289
void diag_p(ulong p) {
5390
sprintf(buf, "%lu", p);
54-
diag(buf);
55-
need_work = 0;
91+
do_diag();
5692
}
5793
void diag_pq(ulong p, ulong q) {
5894
sprintf(buf, "%lu %lu", p, q);
59-
diag(buf);
60-
need_work = 0;
95+
do_diag();
6196
}
6297
void diag_pqr(ulong p, ulong q, ulong r) {
6398
sprintf(buf, "%lu %lu %lu", p, q, r);
64-
diag(buf);
65-
need_work = 0;
99+
do_diag();
66100
}
67101

68102
void handle_sig(int sig) {
69-
need_work = 1;
103+
if (sig == SIGUSR1)
104+
need_work |= 1;
105+
else
106+
need_work |= 2;
70107
}
71108

72109
void init_time(void) {
73110
struct sigaction sa;
74111
struct sigevent sev;
75-
struct itimerspec diag_timer;
112+
struct itimerspec diag_timer, log_timer;
76113

77114
sa.sa_handler = &handle_sig;
78115
sa.sa_flags = SA_RESTART;
79116
sigemptyset(&sa.sa_mask);
80117
if (sigaction(SIGUSR1, &sa, NULL))
81118
fail("Could not set USR1 handler: %s\n", strerror(errno));
119+
if (sigaction(SIGUSR2, &sa, NULL))
120+
fail("Could not set USR2 handler: %s\n", strerror(errno));
82121

83122
sev.sigev_notify = SIGEV_SIGNAL;
84123
sev.sigev_signo = SIGUSR1;
@@ -91,12 +130,25 @@ void init_time(void) {
91130
clock_is_realtime = 1;
92131
}
93132

133+
sev.sigev_signo = SIGUSR2;
134+
sev.sigev_value.sival_ptr = &log_timerid;
135+
clockid_t clock = clock_is_realtime
136+
? CLOCK_REALTIME : CLOCK_PROCESS_CPUTIME_ID;
137+
if (timer_create(clock, &sev, &log_timerid))
138+
fail("Could not create log timer: %s\n", strerror(errno));
139+
94140
diag_timer.it_value.tv_sec = diag_delay;
95141
diag_timer.it_value.tv_nsec = 0;
96142
diag_timer.it_interval.tv_sec = diag_delay;
97143
diag_timer.it_interval.tv_nsec = 0;
98144
if (timer_settime(diag_timerid, 0, &diag_timer, NULL))
99145
fail("Could not set diag timer: %s\n", strerror(errno));
146+
log_timer.it_value.tv_sec = log_delay;
147+
log_timer.it_value.tv_nsec = 0;
148+
log_timer.it_interval.tv_sec = log_delay;
149+
log_timer.it_interval.tv_nsec = 0;
150+
if (timer_settime(log_timerid, 0, &log_timer, NULL))
151+
fail("Could not set log timer: %s\n", strerror(errno));
100152
}
101153

102154
void init(void) {
@@ -191,7 +243,7 @@ void tryvalue(mpz_t zv) {
191243
if (!is_taux(Z(temp), 12, 1))
192244
return;
193245
keep_diag();
194-
gmp_printf("hit near %Zu\n", Z(v));
246+
report("209 hit near %Zu (%.2fs)\n", Z(v), utime());
195247
}
196248

197249
void tryp(ulong p) {
@@ -232,14 +284,33 @@ void tryp(ulong p) {
232284
}
233285

234286
int main(int argc, char **argv, char **envp) {
287+
int i = 1;
235288
init();
236-
if (argc != 4)
289+
while (i < argc && argv[i][0] == '-') {
290+
char *arg = argv[i++];
291+
if (arg[1] == 'r') {
292+
rpath = (char *)malloc(strlen(&arg[2]) + 1);
293+
strcpy(rpath, &arg[2]);
294+
} else
295+
fail("unknown option '%s'", arg);
296+
}
297+
if (i + 3 != argc)
237298
fail("wrong number of arguments");
238-
ston(Z(lim), argv[1]);
239-
ulong pmin = ulston(argv[2]);
240-
ulong pmax = ulston(argv[3]);
299+
ston(Z(lim), argv[i++]);
300+
ulong pmin = ulston(argv[i++]);
301+
ulong pmax = ulston(argv[i++]);
302+
303+
if (rpath) {
304+
printf("path %s\n", rpath);
305+
rfp = fopen(rpath, "a");
306+
if (rfp == NULL)
307+
fail("%s: %s", rpath, strerror(errno));
308+
setlinebuf(rfp);
309+
}
310+
report("001 sq12 %Zu %lu %lu\n", Z(lim), pmin, pmax);
241311

242-
prime_iterator_setprime(&ip, pmax + 1);
312+
prime_iterator_setprime(&ip, pmax);
313+
prime_iterator_next(&ip);
243314
while (1) {
244315
ulong p = prime_iterator_prev(&ip);
245316
if (p < pmin)
@@ -248,6 +319,8 @@ int main(int argc, char **argv, char **envp) {
248319
diag_p(p);
249320
tryp(p);
250321
}
251-
keep_diag();
322+
report("200 sq12 %Zu %lu %lu (%.2fs)\n", Z(lim), pmin, pmax, utime());
323+
if (rfp)
324+
fclose(rfp);
252325
return 0;
253326
}

0 commit comments

Comments
 (0)