diff options
author | Paul Eggert <eggert@cs.ucla.edu> | 2023-03-11 00:38:24 -0800 |
---|---|---|
committer | Alejandro Colomar <alx@kernel.org> | 2023-04-18 18:42:04 +0200 |
commit | 025e2e0769f3f345842412742da0276c865b9e6b (patch) | |
tree | a2faacdd690297dc6eb9d38b8bd1b6c208f2c2d2 | |
parent | 97f79e3b2715d78c9342cbb292e1a3e72a23fe62 (diff) |
Avoid silent truncation of console file datapaul
* libmisc/console.c (is_listed): Rework so that there is no
fixed-size buffer, and no need to use fgets or strlcpy or strtok.
Instead, the code works with arbitrary-sized input,
without silently truncating data or mishandling NUL
bytes in the console file.
Signed-off-by: Paul Eggert <eggert@cs.ucla.edu>
-rw-r--r-- | libmisc/console.c | 41 |
1 files changed, 20 insertions, 21 deletions
diff --git a/libmisc/console.c b/libmisc/console.c index 7e2132dd..8264e1a3 100644 --- a/libmisc/console.c +++ b/libmisc/console.c @@ -24,7 +24,6 @@ static bool is_listed (const char *cfgin, const char *tty, bool def) { FILE *fp; - char buf[1024], *s; const char *cons; /* @@ -43,17 +42,17 @@ static bool is_listed (const char *cfgin, const char *tty, bool def) */ if (*cons != '/') { - char *pbuf; - strlcpy (buf, cons, sizeof (buf)); - pbuf = &buf[0]; - while ((s = strtok (pbuf, ":")) != NULL) { - if (strcmp (s, tty) == 0) { + size_t ttylen = strlen (tty); + for (;;) { + if (strncmp (cons, tty, ttylen) == 0 + && (cons[ttylen] == ':' || !cons[ttylen])) { return true; } - - pbuf = NULL; + cons = strchr (cons, ':'); + if (!cons) + return false; + cons++; } - return false; } /* @@ -70,21 +69,22 @@ static bool is_listed (const char *cfgin, const char *tty, bool def) * See if this tty is listed in the console file. */ - while (fgets (buf, sizeof (buf), fp) != NULL) { - /* Remove optional trailing '\n'. */ - buf[strcspn (buf, "\n")] = '\0'; - if (strcmp (buf, tty) == 0) { - (void) fclose (fp); - return true; + const char *tp = tty; + bool listed = false; + for (int c; 0 <= (c = getc (fp)); ) { + if (c == '\n') { + if (tp && !*tp) { + listed = true; + break; + } + tp = tty; + } else if (tp) { + tp = *tp == c && c ? tp + 1 : NULL; } } - /* - * This tty isn't a console. - */ - (void) fclose (fp); - return false; + return listed; } /* @@ -105,4 +105,3 @@ bool console (const char *tty) return is_listed ("CONSOLE", tty, true); } - |