Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/usr.bin/indent indent: don't read out-of-bounds memory in pr...



details:   https://anonhg.NetBSD.org/src/rev/ed423062b540
branches:  trunk
changeset: 375912:ed423062b540
user:      rillig <rillig%NetBSD.org@localhost>
date:      Sun May 21 10:05:20 2023 +0000

description:
indent: don't read out-of-bounds memory in preprocessing lines

(Since a few minutes.)

If a line '#if 0' was followed by an unlikely line '#', the second line
was interpreted as '#if' as well.

To detect this bug automatically, a dynamic analysis tool would need to
know that only the memory between lab.mem and lab.mem + lab.len has
defined content.  This constraint, in turn, would throw up at the bottom
of copy_comment_wrap, which for a brief moment intentionally violates
this constraint.

diffstat:

 usr.bin/indent/indent.c |  16 ++++++++--------
 1 files changed, 8 insertions(+), 8 deletions(-)

diffs (50 lines):

diff -r 56b72f7ef868 -r ed423062b540 usr.bin/indent/indent.c
--- a/usr.bin/indent/indent.c   Sun May 21 09:48:22 2023 +0000
+++ b/usr.bin/indent/indent.c   Sun May 21 10:05:20 2023 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: indent.c,v 1.301 2023/05/21 09:48:22 rillig Exp $      */
+/*     $NetBSD: indent.c,v 1.302 2023/05/21 10:05:20 rillig Exp $      */
 
 /*-
  * SPDX-License-Identifier: BSD-4-Clause
@@ -38,7 +38,7 @@
  */
 
 #include <sys/cdefs.h>
-__RCSID("$NetBSD: indent.c,v 1.301 2023/05/21 09:48:22 rillig Exp $");
+__RCSID("$NetBSD: indent.c,v 1.302 2023/05/21 10:05:20 rillig Exp $");
 
 #include <sys/param.h>
 #include <err.h>
@@ -948,25 +948,25 @@ process_preprocessing(void)
        const char *dir = lab.st + 1;
        while (dir < end && ch_isblank(*dir))
                dir++;
-       const char *dir_end = dir;
-       while (dir_end < end && ch_isalpha(*dir_end))
-               dir_end++;
+       size_t dir_len = 0;
+       while (dir + dir_len < end && ch_isalpha(dir[dir_len]))
+               dir_len++;
 
-       if (strncmp(dir, "if", 2) == 0) {       /* also ifdef, ifndef */
+       if (dir_len >= 2 && memcmp(dir, "if", 2) == 0) {
                if ((size_t)ifdef_level < array_length(state_stack))
                        state_stack[ifdef_level++] = ps;
                else
                        diag(1, "#if stack overflow");
                out.line_kind = lk_if;
 
-       } else if (strncmp(dir, "el", 2) == 0) {        /* else, elif */
+       } else if (dir_len >= 2 && memcmp(dir, "el", 2) == 0) {
                if (ifdef_level <= 0)
                        diag(1, dir[2] == 'i'
                            ? "Unmatched #elif" : "Unmatched #else");
                else
                        ps = state_stack[ifdef_level - 1];
 
-       } else if (dir_end - dir == 5 && memcmp(dir, "endif", 5) == 0) {
+       } else if (dir_len == 5 && memcmp(dir, "endif", 5) == 0) {
                if (ifdef_level <= 0)
                        diag(1, "Unmatched #endif");
                else



Home | Main Index | Thread Index | Old Index