blob: e41641aca23ee02e2d5cd83316a8bda203222bbc (
plain)
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
|
// SPDX-License-Identifier: GPL-2.0-only
/*
* console_countdown - contdown on the console - interruptible by a keypress
*
* Copyright (c) 2007 Sascha Hauer <s.hauer@pengutronix.de>, Pengutronix
*/
#include <clock.h>
#include <command.h>
#include <errno.h>
#include <console_countdown.h>
#include <stdio.h>
static bool console_countdown_timeout_abort;
void console_countdown_abort(void)
{
console_countdown_timeout_abort = true;
}
static int key_in_list(char key, const char *keys)
{
if (!keys)
return false;
while (*keys) {
if (key == *keys)
return true;
keys++;
}
return false;
}
int console_countdown(int timeout_s, unsigned flags, const char *keys,
char *out_key)
{
uint64_t start, second;
int countdown, ret = -EINTR;
int key = 0;
start = get_time_ns();
second = start;
countdown = timeout_s;
if (!(flags & CONSOLE_COUNTDOWN_SILENT))
printf("%4d", countdown--);
do {
if (tstc()) {
key = getchar();
if (key >= 0) {
if (key_in_list(key, keys))
goto out;
if (flags & CONSOLE_COUNTDOWN_ANYKEY)
goto out;
if (flags & CONSOLE_COUNTDOWN_RETURN && (key == '\n' || key == '\r'))
goto out;
if (flags & CONSOLE_COUNTDOWN_CTRLC && key == 3)
goto out;
}
key = 0;
}
if ((flags & CONSOLE_COUNTDOWN_EXTERN) &&
console_countdown_timeout_abort)
goto out;
if (!(flags & CONSOLE_COUNTDOWN_SILENT) &&
is_timeout(second, SECOND)) {
printf("\b\b\b\b%4d", countdown--);
second += SECOND;
}
} while (!is_timeout(start, timeout_s * SECOND));
if ((flags & CONSOLE_COUNTDOWN_EXTERN) &&
console_countdown_timeout_abort)
goto out;
ret = 0;
out:
if (!(flags & CONSOLE_COUNTDOWN_SILENT))
printf("\n");
if (key && out_key)
*out_key = key;
console_countdown_timeout_abort = false;
return ret;
}
|