Fix -save-temp leaking files in /tmp
authorBernd Edlinger <bernd.edlinger@hotmail.de>
Mon, 17 Feb 2020 16:40:07 +0000 (17:40 +0100)
committerBernd Edlinger <bernd.edlinger@hotmail.de>
Wed, 19 Feb 2020 11:48:54 +0000 (12:48 +0100)
And avoid signal handler calling signal unsafe functions,
and/or calling unlink with uninitialized memory pointer.

2020-02-19  Bernd Edlinger  <bernd.edlinger@hotmail.de>

* collect2.c (c_file, o_file): Make const again.
(ldout,lderrout, dump_ld_file): Remove.
(tool_cleanup): Avoid calling not signal-safe functions.
(maybe_run_lto_and_relink): Avoid possible signal handler
access to unintialzed memory (lto_o_files).
(main): Avoid leaking temp files in $TMPDIR.
Initialize c_file/o_file with concat, which avoids exposing
uninitialized memory to signal handler, which calls unlink(!).
Avoid calling maybe_unlink when the main function returns,
since the atexit handler is already doing this.
* collect2.h (dump_ld_file, ldout, lderrout): Remove.

gcc/ChangeLog
gcc/collect2.c
gcc/collect2.h

index 7ebeaed..6cd941a 100644 (file)
@@ -1,3 +1,17 @@
+2020-02-19  Bernd Edlinger  <bernd.edlinger@hotmail.de>
+
+       * collect2.c (c_file, o_file): Make const again.
+       (ldout,lderrout, dump_ld_file): Remove.
+       (tool_cleanup): Avoid calling not signal-safe functions.
+       (maybe_run_lto_and_relink): Avoid possible signal handler
+       access to unintialzed memory (lto_o_files).
+       (main): Avoid leaking temp files in $TMPDIR.
+       Initialize c_file/o_file with concat, which avoids exposing
+       uninitialized memory to signal handler, which calls unlink(!).
+       Avoid calling maybe_unlink when the main function returns,
+       since the atexit handler is already doing this.
+       * collect2.h (dump_ld_file, ldout, lderrout): Remove.
+
 2020-02-19  Martin Jambor  <mjambor@suse.cz>
 
        PR tree-optimization/93776
index 502d629..f7d9f10 100644 (file)
@@ -205,14 +205,12 @@ bool helpflag;                    /* true if --help */
 static int shared_obj;                 /* true if -shared */
 static int static_obj;                 /* true if -static */
 
-static char *c_file;           /* <xxx>.c for constructor/destructor list.  */
-static char *o_file;           /* <xxx>.o for constructor/destructor list.  */
+static const char *c_file;             /* <xxx>.c for constructor/destructor list.  */
+static const char *o_file;             /* <xxx>.o for constructor/destructor list.  */
 #ifdef COLLECT_EXPORT_LIST
 static const char *export_file;                /* <xxx>.x for AIX export list.  */
 #endif
 static char **lto_o_files;             /* Output files for LTO.  */
-const char *ldout;                     /* File for ld stdout.  */
-const char *lderrout;                  /* File for ld stderr.  */
 static const char *output_file;                /* Output file for ld.  */
 static const char *nm_file_name;       /* pathname of nm */
 #ifdef LDD_SUFFIX
@@ -384,6 +382,10 @@ static void scan_prog_file (const char *, scanpass, scanfilter);
 void
 tool_cleanup (bool from_signal)
 {
+  /* maybe_unlink may call notice, which is not signal safe.  */
+  if (from_signal)
+    verbose = false;
+
   if (c_file != 0 && c_file[0])
     maybe_unlink (c_file);
 
@@ -397,20 +399,6 @@ tool_cleanup (bool from_signal)
 
   if (lto_o_files)
     maybe_unlink_list (lto_o_files);
-
-  if (ldout != 0 && ldout[0])
-    {
-      if (!from_signal)
-       dump_ld_file (ldout, stdout);
-      maybe_unlink (ldout);
-    }
-
-  if (lderrout != 0 && lderrout[0])
-    {
-      if (!from_signal)
-       dump_ld_file (lderrout, stderr);
-      maybe_unlink (lderrout);
-    }
 }
 
 static void
@@ -476,77 +464,6 @@ extract_string (const char **pp)
   return XOBFINISH (&temporary_obstack, char *);
 }
 \f
-void
-dump_ld_file (const char *name, FILE *to)
-{
-  FILE *stream = fopen (name, "r");
-
-  if (stream == 0)
-    return;
-  while (1)
-    {
-      int c;
-      while (c = getc (stream),
-            c != EOF && (ISIDNUM (c) || c == '$' || c == '.'))
-       obstack_1grow (&temporary_obstack, c);
-      if (obstack_object_size (&temporary_obstack) > 0)
-       {
-         const char *word, *p;
-         char *result;
-         obstack_1grow (&temporary_obstack, '\0');
-         word = XOBFINISH (&temporary_obstack, const char *);
-
-         if (*word == '.')
-           ++word, putc ('.', to);
-         p = word;
-         if (!strncmp (p, USER_LABEL_PREFIX, strlen (USER_LABEL_PREFIX)))
-           p += strlen (USER_LABEL_PREFIX);
-
-#ifdef HAVE_LD_DEMANGLE
-         result = 0;
-#else
-         if (no_demangle)
-           result = 0;
-         else
-           result = cplus_demangle (p, DMGL_PARAMS | DMGL_ANSI | DMGL_VERBOSE);
-#endif
-
-         if (result)
-           {
-             int diff;
-             fputs (result, to);
-
-             diff = strlen (word) - strlen (result);
-             while (diff > 0 && c == ' ')
-               --diff, putc (' ', to);
-             if (diff < 0 && c == ' ')
-               {
-                 while (diff < 0 && c == ' ')
-                   ++diff, c = getc (stream);
-                 if (!ISSPACE (c))
-                   {
-                     /* Make sure we output at least one space, or
-                        the demangled symbol name will run into
-                        whatever text follows.  */
-                     putc (' ', to);
-                   }
-               }
-
-             free (result);
-           }
-         else
-           fputs (word, to);
-
-         fflush (to);
-         obstack_free (&temporary_obstack, temporary_firstobj);
-       }
-      if (c == EOF)
-       break;
-      putc (c, to);
-    }
-  fclose (stream);
-}
-\f
 /* Return the kind of symbol denoted by name S.  */
 
 static symkind
@@ -744,7 +661,10 @@ maybe_run_lto_and_relink (char **lto_ld_argv, char **object_lst,
              ++num_files;
          }
 
-       lto_o_files = XNEWVEC (char *, num_files + 1);
+       /* signal handler may access uninitialized memory
+          and delete whatever it points to, if lto_o_files
+          is not allocatted with calloc.  */
+       lto_o_files = XCNEWVEC (char *, num_files + 1);
        lto_o_files[num_files] = NULL;
        start = XOBFINISH (&temporary_obstack, char *);
        for (i = 0; i < num_files; ++i)
@@ -1262,27 +1182,19 @@ main (int argc, char **argv)
   /* Make temp file names.  */
   if (save_temps)
     {
-      c_file = (char *) xmalloc (strlen (output_file)
-                                 + sizeof (".cdtor.c") + 1);
-      strcpy (c_file, output_file);
-      strcat (c_file, ".cdtor.c");
-      o_file = (char *) xmalloc (strlen (output_file)
-                                 + sizeof (".cdtor.o") + 1);
-      strcpy (o_file, output_file);
-      strcat (o_file, ".cdtor.o");
+      c_file = concat (output_file, ".cdtor.c", NULL);
+      o_file = concat (output_file, ".cdtor.o", NULL);
+#ifdef COLLECT_EXPORT_LIST
+      export_file = concat (output_file, ".x", NULL);
+#endif
     }
   else
     {
       c_file = make_temp_file (".cdtor.c");
       o_file = make_temp_file (".cdtor.o");
-    }
 #ifdef COLLECT_EXPORT_LIST
-  export_file = make_temp_file (".x");
+      export_file = make_temp_file (".x");
 #endif
-  if (!debug)
-    {
-      ldout = make_temp_file (".ld");
-      lderrout = make_temp_file (".le");
     }
   /* Build the command line to compile the ctor/dtor list.  */
   *c_ptr++ = c_file_name;
@@ -1811,9 +1723,6 @@ main (int argc, char **argv)
       maybe_unlink (export_file);
 #endif
       post_ld_pass (/*temp_file*/false);
-
-      maybe_unlink (c_file);
-      maybe_unlink (o_file);
       return 0;
     }
 
@@ -1912,13 +1821,6 @@ main (int argc, char **argv)
   scan_prog_file (output_file, PASS_SECOND, SCAN_ALL);
 #endif
 
-  maybe_unlink (c_file);
-  maybe_unlink (o_file);
-
-#ifdef COLLECT_EXPORT_LIST
-  maybe_unlink (export_file);
-#endif
-
   return 0;
 }
 
index ab5fcdf..aa8a03e 100644 (file)
@@ -25,12 +25,8 @@ extern struct pex_obj *collect_execute (const char *, char **, const char *,
 
 extern int collect_wait (const char *, struct pex_obj *);
 
-extern void dump_ld_file (const char *, FILE *);
-
 extern int file_exists (const char *);
 
-extern const char *ldout;
-extern const char *lderrout;
 extern const char *c_file_name;
 extern struct obstack temporary_obstack;
 extern char *temporary_firstobj;