The loop that splits a PATH_SEPARATOR separated environment variable and
adds each directory as a prefix was written out three times, for
COMPILER_PATH, LIBRARY_PATH and LPATH, differing only in which prefix
list each directory is added to.

Factor it out into for_each_env_path, a sibling of for_each_path that
takes a callback the same way.  Handling a null value in the helper also
lets the two startfile users share one 'cross_compile' test and one
callback, rather than repeating both.

No functional change.

gcc/ChangeLog:

        * gcc.cc (for_each_env_path): New function template.
        (process_command): Use it for COMPILER_PATH, LIBRARY_PATH and
        LPATH.

Signed-off-by: John Ericson <[email protected]>
---
 gcc/gcc.cc | 148 +++++++++++++++++++++--------------------------------
 1 file changed, 57 insertions(+), 91 deletions(-)

diff --git a/gcc/gcc.cc b/gcc/gcc.cc
index 973a3402330..08a192ade76 100644
--- a/gcc/gcc.cc
+++ b/gcc/gcc.cc
@@ -2983,6 +2983,51 @@ for_each_path (const struct path_prefix *paths,
   return ret;
 }
 
+/* Call CALLBACK once per directory named in VALUE, a PATH_SEPARATOR
+   separated list such as the value of COMPILER_PATH or PATH.  VALUE may be
+   null, in which case CALLBACK is not called at all.
+
+   An empty element denotes the current directory.  Each directory is passed
+   with a trailing directory separator, as add_prefix expects.  The buffer
+   handed to CALLBACK is reused between iterations, so CALLBACK must copy
+   anything it wants to keep -- add_prefix does.  */
+
+template<typename fun>
+static void
+for_each_env_path (const char *value, fun callback)
+{
+  if (!value)
+    return;
+
+  char *nstore = (char *) alloca (strlen (value) + 3);
+
+  for (const char *startp = value, *endp = value; ; endp++)
+    {
+      if (*endp != PATH_SEPARATOR && *endp != 0)
+       continue;
+
+      if (endp == startp)
+       strcpy (nstore, concat (".", dir_separator_str, NULL));
+      else
+       {
+         strncpy (nstore, startp, endp - startp);
+         if (!IS_DIR_SEPARATOR (endp[-1]))
+           {
+             nstore[endp - startp] = DIR_SEPARATOR;
+             nstore[endp - startp + 1] = 0;
+           }
+         else
+           nstore[endp - startp] = 0;
+       }
+
+      callback (nstore);
+
+      if (*endp == 0)
+       break;
+      startp = endp + 1;
+    }
+}
+
 /* Add or change the value of an environment variable, outputting the
    change to standard error if in verbose mode.  */
 static void
@@ -4962,103 +5007,24 @@ process_command (unsigned int decoded_options_count,
   /* COMPILER_PATH and LIBRARY_PATH have values
      that are lists of directory names with colons.  */
 
-  temp = env.get ("COMPILER_PATH");
-  if (temp)
+  for_each_env_path (env.get ("COMPILER_PATH"), [] (const char *dir)
     {
-      const char *startp, *endp;
-      char *nstore = (char *) alloca (strlen (temp) + 3);
-
-      startp = endp = temp;
-      while (1)
-       {
-         if (*endp == PATH_SEPARATOR || *endp == 0)
-           {
-             strncpy (nstore, startp, endp - startp);
-             if (endp == startp)
-               strcpy (nstore, concat (".", dir_separator_str, NULL));
-             else if (!IS_DIR_SEPARATOR (endp[-1]))
-               {
-                 nstore[endp - startp] = DIR_SEPARATOR;
-                 nstore[endp - startp + 1] = 0;
-               }
-             else
-               nstore[endp - startp] = 0;
-             add_prefix (&exec_prefixes, nstore, 0,
-                         PREFIX_PRIORITY_LAST, 0, 0);
-             add_prefix (&include_prefixes, nstore, 0,
-                         PREFIX_PRIORITY_LAST, 0, 0);
-             if (*endp == 0)
-               break;
-             endp = startp = endp + 1;
-           }
-         else
-           endp++;
-       }
-    }
+      add_prefix (&exec_prefixes, dir, 0, PREFIX_PRIORITY_LAST, 0, 0);
+      add_prefix (&include_prefixes, dir, 0, PREFIX_PRIORITY_LAST, 0, 0);
+    });
 
-  temp = env.get (LIBRARY_PATH_ENV);
-  if (temp && *cross_compile == '0')
+  if (*cross_compile == '0')
     {
-      const char *startp, *endp;
-      char *nstore = (char *) alloca (strlen (temp) + 3);
-
-      startp = endp = temp;
-      while (1)
+      auto add_startfile_prefix = [] (const char *dir)
        {
-         if (*endp == PATH_SEPARATOR || *endp == 0)
-           {
-             strncpy (nstore, startp, endp - startp);
-             if (endp == startp)
-               strcpy (nstore, concat (".", dir_separator_str, NULL));
-             else if (!IS_DIR_SEPARATOR (endp[-1]))
-               {
-                 nstore[endp - startp] = DIR_SEPARATOR;
-                 nstore[endp - startp + 1] = 0;
-               }
-             else
-               nstore[endp - startp] = 0;
-             add_prefix (&startfile_prefixes, nstore, NULL,
-                         PREFIX_PRIORITY_LAST, 0, 1);
-             if (*endp == 0)
-               break;
-             endp = startp = endp + 1;
-           }
-         else
-           endp++;
-       }
-    }
+         add_prefix (&startfile_prefixes, dir, NULL,
+                     PREFIX_PRIORITY_LAST, 0, 1);
+       };
 
-  /* Use LPATH like LIBRARY_PATH (for the CMU build program).  */
-  temp = env.get ("LPATH");
-  if (temp && *cross_compile == '0')
-    {
-      const char *startp, *endp;
-      char *nstore = (char *) alloca (strlen (temp) + 3);
+      for_each_env_path (env.get (LIBRARY_PATH_ENV), add_startfile_prefix);
 
-      startp = endp = temp;
-      while (1)
-       {
-         if (*endp == PATH_SEPARATOR || *endp == 0)
-           {
-             strncpy (nstore, startp, endp - startp);
-             if (endp == startp)
-               strcpy (nstore, concat (".", dir_separator_str, NULL));
-             else if (!IS_DIR_SEPARATOR (endp[-1]))
-               {
-                 nstore[endp - startp] = DIR_SEPARATOR;
-                 nstore[endp - startp + 1] = 0;
-               }
-             else
-               nstore[endp - startp] = 0;
-             add_prefix (&startfile_prefixes, nstore, NULL,
-                         PREFIX_PRIORITY_LAST, 0, 1);
-             if (*endp == 0)
-               break;
-             endp = startp = endp + 1;
-           }
-         else
-           endp++;
-       }
+      /* Use LPATH like LIBRARY_PATH (for the CMU build program).  */
+      for_each_env_path (env.get ("LPATH"), add_startfile_prefix);
     }
 
   /* Process the options and store input files and switches in their

base-commit: c31b7a09eea3c33bccca12bab4a7bb6b01da1ff6
-- 
2.54.0

Reply via email to