Clean up memory handling in spawn_pager(), free(3)ing everything
authorschwarze <schwarze@openbsd.org>
Mon, 4 Oct 2021 21:28:50 +0000 (21:28 +0000)
committerschwarze <schwarze@openbsd.org>
Mon, 4 Oct 2021 21:28:50 +0000 (21:28 +0000)
that is malloc(3)ed.  In addition to being less confusing, the new
code is also shorter by two lines.

usr.bin/mandoc/main.c

index 20ff8a6..280f365 100644 (file)
@@ -1,4 +1,4 @@
-/* $OpenBSD: main.c,v 1.261 2021/10/04 20:24:00 schwarze Exp $ */
+/* $OpenBSD: main.c,v 1.262 2021/10/04 21:28:50 schwarze Exp $ */
 /*
  * Copyright (c) 2010-2012, 2014-2021 Ingo Schwarze <schwarze@openbsd.org>
  * Copyright (c) 2008-2012 Kristaps Dzonsons <kristaps@bsd.lv>
@@ -1262,6 +1262,7 @@ spawn_pager(struct outstate *outst, char *tag_target)
        char            *argv[MAX_PAGER_ARGS];
        const char      *pager;
        char            *cp;
+       size_t           wordlen;
        size_t           cmdlen;
        int              argc, use_ofn;
        pid_t            pager_pid;
@@ -1274,7 +1275,6 @@ spawn_pager(struct outstate *outst, char *tag_target)
                pager = getenv("PAGER");
        if (pager == NULL || *pager == '\0')
                pager = "less";
-       cp = mandoc_strdup(pager);
 
        /*
         * Parse the pager command into words.
@@ -1282,16 +1282,12 @@ spawn_pager(struct outstate *outst, char *tag_target)
         */
 
        argc = 0;
-       while (argc + 5 < MAX_PAGER_ARGS) {
-               argv[argc++] = cp;
-               cp = strchr(cp, ' ');
-               if (cp == NULL)
-                       break;
-               *cp++ = '\0';
-               while (*cp == ' ')
-                       cp++;
-               if (*cp == '\0')
-                       break;
+       while (*pager != '\0' && argc + 5 < MAX_PAGER_ARGS) {
+               wordlen = strcspn(pager, " ");
+               argv[argc++] = mandoc_strndup(pager, wordlen);
+               pager += wordlen;
+               while (*pager == ' ')
+                       pager++;
        }
 
        /* For more(1) and less(1), use the tag file. */
@@ -1302,10 +1298,10 @@ spawn_pager(struct outstate *outst, char *tag_target)
                cp = argv[0] + cmdlen - 4;
                if (strcmp(cp, "less") == 0 || strcmp(cp, "more") == 0) {
                        argv[argc++] = mandoc_strdup("-T");
-                       argv[argc++] = outst->tag_files->tfn;
+                       argv[argc++] = mandoc_strdup(outst->tag_files->tfn);
                        if (tag_target != NULL) {
                                argv[argc++] = mandoc_strdup("-t");
-                               argv[argc++] = tag_target;
+                               argv[argc++] = mandoc_strdup(tag_target);
                                use_ofn = 0;
                        }
                }
@@ -1315,7 +1311,7 @@ spawn_pager(struct outstate *outst, char *tag_target)
                        mandoc_asprintf(&argv[argc], "file://%s#%s",
                            outst->tag_files->ofn, tag_target);
                else
-                       argv[argc] = outst->tag_files->ofn;
+                       argv[argc] = mandoc_strdup(outst->tag_files->ofn);
                argc++;
        }
        argv[argc] = NULL;
@@ -1327,6 +1323,8 @@ spawn_pager(struct outstate *outst, char *tag_target)
        case 0:
                break;
        default:
+               while (argc > 0)
+                       free(argv[--argc]);
                (void)setpgid(pager_pid, 0);
                (void)tcsetpgrp(STDOUT_FILENO, pager_pid);
                if (pledge("stdio rpath tmppath tty proc", NULL) == -1) {