[RFA] toplev.c cleanup, part 1

Neil Booth neil@daikokuya.demon.co.uk
Wed Nov 7 23:38:00 GMT 2001


I tried to fix the Debug + preprocessed CPP initialization issue.
However, I got tangled in the chaos that is initialization in
toplev.c.  If that is cleaned up, fixing CPP should be straight
forward.

So, this is part of an attempt to structure it better.  Sadly, the
generated diff is not particularly comprehensible, since diff chooses
to make it look like I moved code I didn't, and code I did move stayed
where it was 8-( The context diff was no better.  So, I'll explain it
here.

Firstly, I moved a routine that was amongst the variables at the top of
toplev.c to the bottom of the variables.

Secondly, decode options code was split, with most in the middle of
the file, but some at the very end.  I moved the stuff at the very end
to be in the same place as the rest.

Thirdly, and what I really wanted to do, is all initialization code is
now together at the end of the file.  toplev_main() is at the bottom,
with most of its old body gutted and separated out into a few
well-defined tasks (I enclose it here for clarity).

int
toplev_main (argc, argv)
     int argc;
     char **argv;
{
  /* Save in case md file wants to emit args as a comment.  */
  save_argc = argc;
  save_argv = argv;

  /* Initialization of GCC's environment.  */
  general_init (argv [0]);

  /* Parse the options and do minimal processing; basically just
     enough to default flags appropriately.  */
  parse_options_and_default_flags (argc, argv);

  /* Exit early if we can (e.g. -help).  */
  if (exit_after_options)
    exit (0);

  /* The bulk of command line switch processing.  */
  process_options ();

  /* Language-independent initialization.  */
  independent_init ();

  compile_file (filename);

  if (errorcount || sorrycount)
    return (FATAL_EXIT_CODE);

  return (SUCCESS_EXIT_CODE);
}

I have not yet sorted out the initialization done in compile_file ().
Most of the confusion is there; I will do that in follow up patches.
I imagine that a lot of its init code will move to independent_init(),
which is currently fairly empty.

Bootstrapped x86 Linux for C, ObjC, C++ and F77.  OK to commit?

Neil.

	* toplev.c (set_Wunused): Move out of variable section.
	(general_init, parse_options_and_default_flags, process_options,
	independent_init): New routines; separated out from the old
	toplev_main.
	(toplev_main): Move most of body elsewhere; give it a clear
	structure.

Index: toplev.c
===================================================================
RCS file: /cvs/gcc/gcc/gcc/toplev.c,v
retrieving revision 1.533
diff -u -p -r1.533 toplev.c
--- toplev.c	2001/11/06 21:12:07	1.533
+++ toplev.c	2001/11/08 07:31:52
@@ -161,6 +161,11 @@ extern char **environ;
 extern int size_directive_output;
 extern tree last_assemble_variable_decl;
 
+static void general_init PARAMS ((char *));
+static void parse_options_and_default_flags PARAMS ((int, char **));
+static void process_options PARAMS ((void));
+static void independent_init PARAMS ((void));
+
 static void set_target_switch PARAMS ((const char *));
 static const char *decl_name PARAMS ((tree, int));
 
@@ -1435,23 +1440,6 @@ int warn_unused_parameter;
 int warn_unused_variable;
 int warn_unused_value;
 
-void
-set_Wunused (setting)
-     int setting;
-{
-  warn_unused_function = setting;
-  warn_unused_label = setting;
-  /* Unused function parameter warnings are reported when either ``-W
-     -Wunused'' or ``-Wunused-parameter'' is specified.  Differentiate
-     -Wunused by setting WARN_UNUSED_PARAMETER to -1.  */
-  if (!setting)
-    warn_unused_parameter = 0;
-  else if (!warn_unused_parameter)
-    warn_unused_parameter = -1;
-  warn_unused_variable = setting;
-  warn_unused_value = setting;
-}
-
 /* Nonzero to warn about code which is never reached.  */
 
 int warn_notreached;
@@ -1553,6 +1541,23 @@ lang_independent_options W_options[] =
    N_("Warn about functions which might be candidates for attribute noreturn") }
 };
 
+void
+set_Wunused (setting)
+     int setting;
+{
+  warn_unused_function = setting;
+  warn_unused_label = setting;
+  /* Unused function parameter warnings are reported when either ``-W
+     -Wunused'' or ``-Wunused-parameter'' is specified.  Differentiate
+     -Wunused by setting WARN_UNUSED_PARAMETER to -1.  */
+  if (!setting)
+    warn_unused_parameter = 0;
+  else if (!warn_unused_parameter)
+    warn_unused_parameter = -1;
+  warn_unused_variable = setting;
+  warn_unused_value = setting;
+}
+
 /* The following routines are useful in setting all the flags that
    -ffast-math and -fno-fast-math imply.  */
 
@@ -4588,27 +4593,186 @@ independent_decode_option (argc, argv)
   return 1;
 }
 
-/* Entry point of cc1, cc1plus, jc1, f771, etc.
-   Decode command args, then call compile_file.
-   Exit code is FATAL_EXIT_CODE if can't open files or if there were
-   any errors, or SUCCESS_EXIT_CODE if compilation succeeded.
+/* Decode -m switches.  */
+/* Decode the switch -mNAME.  */
 
-   It is not safe to call this function more than once.  */
+static void
+set_target_switch (name)
+     const char *name;
+{
+  size_t j;
+  int valid_target_option = 0;
 
-int
-toplev_main (argc, argv)
-     int argc;
-     char **argv;
+  for (j = 0; j < ARRAY_SIZE (target_switches); j++)
+    if (!strcmp (target_switches[j].name, name))
+      {
+	if (target_switches[j].value < 0)
+	  target_flags &= ~-target_switches[j].value;
+	else
+	  target_flags |= target_switches[j].value;
+	valid_target_option = 1;
+      }
+
+#ifdef TARGET_OPTIONS
+  if (!valid_target_option)
+    for (j = 0; j < ARRAY_SIZE (target_options); j++)
+      {
+	int len = strlen (target_options[j].prefix);
+	if (!strncmp (target_options[j].prefix, name, len))
+	  {
+	    *target_options[j].variable = name + len;
+	    valid_target_option = 1;
+	  }
+      }
+#endif
+
+  if (!valid_target_option)
+    error ("Invalid option `%s'", name);
+}
+
+/* Print version information to FILE.
+   Each line begins with INDENT (for the case where FILE is the
+   assembler output file).  */
+
+static void
+print_version (file, indent)
+     FILE *file;
+     const char *indent;
 {
-  int i;
-  char *p;
+#ifndef __VERSION__
+#define __VERSION__ "[?]"
+#endif
+  fnotice (file,
+#ifdef __GNUC__
+	   "%s%s%s version %s (%s)\n%s\tcompiled by GNU C version %s.\n"
+#else
+	   "%s%s%s version %s (%s) compiled by CC.\n"
+#endif
+	   , indent, *indent != 0 ? " " : "",
+	   language_string, version_string, TARGET_NAME,
+	   indent, __VERSION__);
+}
 
-  /* save in case md file wants to emit args as a comment.  */
-  save_argc = argc;
-  save_argv = argv;
+/* Print an option value and return the adjusted position in the line.
+   ??? We don't handle error returns from fprintf (disk full); presumably
+   other code will catch a disk full though.  */
+
+static int
+print_single_switch (file, pos, max, indent, sep, term, type, name)
+     FILE *file;
+     int pos, max;
+     const char *indent, *sep, *term, *type, *name;
+{
+  /* The ultrix fprintf returns 0 on success, so compute the result we want
+     here since we need it for the following test.  */
+  int len = strlen (sep) + strlen (type) + strlen (name);
+
+  if (pos != 0
+      && pos + len > max)
+    {
+      fprintf (file, "%s", term);
+      pos = 0;
+    }
+  if (pos == 0)
+    {
+      fprintf (file, "%s", indent);
+      pos = strlen (indent);
+    }
+  fprintf (file, "%s%s%s", sep, type, name);
+  pos += len;
+  return pos;
+}
 
-  p = argv[0] + strlen (argv[0]);
-  while (p != argv[0] && !IS_DIR_SEPARATOR (p[-1]))
+/* Print active target switches to FILE.
+   POS is the current cursor position and MAX is the size of a "line".
+   Each line begins with INDENT and ends with TERM.
+   Each switch is separated from the next by SEP.  */
+
+static void
+print_switch_values (file, pos, max, indent, sep, term)
+     FILE *file;
+     int pos, max;
+     const char *indent, *sep, *term;
+{
+  size_t j;
+  char **p;
+
+  /* Print the options as passed.  */
+
+  pos = print_single_switch (file, pos, max, indent, *indent ? " " : "", term,
+			     _("options passed: "), "");
+
+  for (p = &save_argv[1]; *p != NULL; p++)
+    if (**p == '-')
+      {
+	/* Ignore these.  */
+	if (strcmp (*p, "-o") == 0)
+	  {
+	    if (p[1] != NULL)
+	      p++;
+	    continue;
+	  }
+	if (strcmp (*p, "-quiet") == 0)
+	  continue;
+	if (strcmp (*p, "-version") == 0)
+	  continue;
+	if ((*p)[1] == 'd')
+	  continue;
+
+	pos = print_single_switch (file, pos, max, indent, sep, term, *p, "");
+      }
+  if (pos > 0)
+    fprintf (file, "%s", term);
+
+  /* Print the -f and -m options that have been enabled.
+     We don't handle language specific options but printing argv
+     should suffice.  */
+
+  pos = print_single_switch (file, 0, max, indent, *indent ? " " : "", term,
+			     _("options enabled: "), "");
+
+  for (j = 0; j < ARRAY_SIZE (f_options); j++)
+    if (*f_options[j].variable == f_options[j].on_value)
+      pos = print_single_switch (file, pos, max, indent, sep, term,
+				 "-f", f_options[j].string);
+
+  /* Print target specific options.  */
+
+  for (j = 0; j < ARRAY_SIZE (target_switches); j++)
+    if (target_switches[j].name[0] != '\0'
+	&& target_switches[j].value > 0
+	&& ((target_switches[j].value & target_flags)
+	    == target_switches[j].value))
+      {
+	pos = print_single_switch (file, pos, max, indent, sep, term,
+				   "-m", target_switches[j].name);
+      }
+
+#ifdef TARGET_OPTIONS
+  for (j = 0; j < ARRAY_SIZE (target_options); j++)
+    if (*target_options[j].variable != NULL)
+      {
+	char prefix[256];
+	sprintf (prefix, "-m%s", target_options[j].prefix);
+	pos = print_single_switch (file, pos, max, indent, sep, term,
+				   prefix, *target_options[j].variable);
+      }
+#endif
+
+  fprintf (file, "%s", term);
+}
+
+/* Initialization of the front end environment, before command line
+   options are parsed.  Signal handlers, internationalization etc.
+   ARGV0 is main's argv[0].  */
+static void
+general_init (argv0)
+     char *argv0;
+{
+  char *p;
+
+  p = argv0 + strlen (argv0);
+  while (p != argv0 && !IS_DIR_SEPARATOR (p[-1]))
     --p;
   progname = p;
 
@@ -4637,25 +4801,33 @@ toplev_main (argc, argv)
   signal (SIGIOT, crash_signal);
 #endif
 
-  decl_printable_name = decl_name;
-  lang_expand_expr = (lang_expand_expr_t) do_abort;
-
-  /* Initialize whether `char' is signed.  */
-  flag_signed_char = DEFAULT_SIGNED_CHAR;
-#ifdef DEFAULT_SHORT_ENUMS
-  /* Initialize how much space enums occupy, by default.  */
-  flag_short_enums = DEFAULT_SHORT_ENUMS;
-#endif
+  /* Initialize the diagnostics reporting machinery.  */
+  diagnostic_initialize (global_dc);
 
-  /* Initialize the garbage-collector.  */
+  /* Initialize the garbage-collector, and string pools.  FIXME: We
+     should do this later, in independent_init () when we know we
+     actually want to compile something, but cpplib currently wants to
+     use the hash table immediately in cpp_create_reader.  */
   init_ggc ();
-  init_stringpool ();
   ggc_add_rtx_root (&stack_limit_rtx, 1);
   ggc_add_tree_root (&current_function_decl, 1);
   ggc_add_tree_root (&current_function_func_begin_label, 1);
 
-  /* Initialize the diagnostics reporting machinery.  */
-  diagnostic_initialize (global_dc);
+  init_stringpool ();
+}
+
+/* Parse command line options and set default flag values, called
+   after language-independent option-independent intialization.  Do
+   minimal options processing.  */
+static void
+parse_options_and_default_flags (argc, argv)
+     int argc;
+     char **argv;
+{
+  int i;
+
+  /* Initialize register usage now so switches may override.  */
+  init_reg_sets ();
 
   /* Register the language-independent parameters.  */
   add_params (lang_independent_params, LAST_PARAM);
@@ -4751,6 +4923,13 @@ toplev_main (argc, argv)
       align_functions = 1;
     }
 
+  /* Initialize whether `char' is signed.  */
+  flag_signed_char = DEFAULT_SIGNED_CHAR;
+#ifdef DEFAULT_SHORT_ENUMS
+  /* Initialize how much space enums occupy, by default.  */
+  flag_short_enums = DEFAULT_SHORT_ENUMS;
+#endif
+
   /* Initialize target_flags before OPTIMIZATION_OPTIONS so the latter can
      modify it.  */
   target_flags = 0;
@@ -4767,9 +4946,6 @@ toplev_main (argc, argv)
   OPTIMIZATION_OPTIONS (optimize, optimize_size);
 #endif
 
-  /* Initialize register usage now so switches may override.  */
-  init_reg_sets ();
-
   /* Perform normal command line switch decoding.  */
   for (i = 1; i < argc;)
     {
@@ -4837,10 +5013,12 @@ toplev_main (argc, argv)
 
   /* All command line options have been processed.  */
   (*lang_hooks.post_options) ();
-
-  if (exit_after_options)
-    exit (0);
-
+}
+
+/* Process the options that have been parsed.  */
+static void
+process_options ()
+{
   /* Checker uses the frame pointer.  */
   if (flag_check_memory_usage)
     flag_omit_frame_pointer = 0;
@@ -4949,181 +5127,53 @@ toplev_main (argc, argv)
       if (! quiet_flag)
 	print_switch_values (stderr, 0, MAX_LINE, "", " ", "\n");
     }
-
-  compile_file (filename);
-
-  if (errorcount)
-    return (FATAL_EXIT_CODE);
-  if (sorrycount)
-    return (FATAL_EXIT_CODE);
-  return (SUCCESS_EXIT_CODE);
 }
-
-/* Decode -m switches.  */
-/* Decode the switch -mNAME.  */
 
+/* Language-independent initialization, before compiling a file.  */
 static void
-set_target_switch (name)
-     const char *name;
+independent_init ()
 {
-  size_t j;
-  int valid_target_option = 0;
-
-  for (j = 0; j < ARRAY_SIZE (target_switches); j++)
-    if (!strcmp (target_switches[j].name, name))
-      {
-	if (target_switches[j].value < 0)
-	  target_flags &= ~-target_switches[j].value;
-	else
-	  target_flags |= target_switches[j].value;
-	valid_target_option = 1;
-      }
-
-#ifdef TARGET_OPTIONS
-  if (!valid_target_option)
-    for (j = 0; j < ARRAY_SIZE (target_options); j++)
-      {
-	int len = strlen (target_options[j].prefix);
-	if (!strncmp (target_options[j].prefix, name, len))
-	  {
-	    *target_options[j].variable = name + len;
-	    valid_target_option = 1;
-	  }
-      }
-#endif
-
-  if (!valid_target_option)
-    error ("Invalid option `%s'", name);
-}
-
-/* Print version information to FILE.
-   Each line begins with INDENT (for the case where FILE is the
-   assembler output file).  */
-
-static void
-print_version (file, indent)
-     FILE *file;
-     const char *indent;
-{
-#ifndef __VERSION__
-#define __VERSION__ "[?]"
-#endif
-  fnotice (file,
-#ifdef __GNUC__
-	   "%s%s%s version %s (%s)\n%s\tcompiled by GNU C version %s.\n"
-#else
-	   "%s%s%s version %s (%s) compiled by CC.\n"
-#endif
-	   , indent, *indent != 0 ? " " : "",
-	   language_string, version_string, TARGET_NAME,
-	   indent, __VERSION__);
+  decl_printable_name = decl_name;
+  lang_expand_expr = (lang_expand_expr_t) do_abort;
 }
-
-/* Print an option value and return the adjusted position in the line.
-   ??? We don't handle error returns from fprintf (disk full); presumably
-   other code will catch a disk full though.  */
 
-static int
-print_single_switch (file, pos, max, indent, sep, term, type, name)
-     FILE *file;
-     int pos, max;
-     const char *indent, *sep, *term, *type, *name;
-{
-  /* The ultrix fprintf returns 0 on success, so compute the result we want
-     here since we need it for the following test.  */
-  int len = strlen (sep) + strlen (type) + strlen (name);
-
-  if (pos != 0
-      && pos + len > max)
-    {
-      fprintf (file, "%s", term);
-      pos = 0;
-    }
-  if (pos == 0)
-    {
-      fprintf (file, "%s", indent);
-      pos = strlen (indent);
-    }
-  fprintf (file, "%s%s%s", sep, type, name);
-  pos += len;
-  return pos;
-}
+/* Entry point of cc1, cc1plus, jc1, f771, etc.
+   Decode command args, then call compile_file.
+   Exit code is FATAL_EXIT_CODE if can't open files or if there were
+   any errors, or SUCCESS_EXIT_CODE if compilation succeeded.
 
-/* Print active target switches to FILE.
-   POS is the current cursor position and MAX is the size of a "line".
-   Each line begins with INDENT and ends with TERM.
-   Each switch is separated from the next by SEP.  */
+   It is not safe to call this function more than once.  */
 
-static void
-print_switch_values (file, pos, max, indent, sep, term)
-     FILE *file;
-     int pos, max;
-     const char *indent, *sep, *term;
+int
+toplev_main (argc, argv)
+     int argc;
+     char **argv;
 {
-  size_t j;
-  char **p;
-
-  /* Print the options as passed.  */
-
-  pos = print_single_switch (file, pos, max, indent, *indent ? " " : "", term,
-			     _("options passed: "), "");
-
-  for (p = &save_argv[1]; *p != NULL; p++)
-    if (**p == '-')
-      {
-	/* Ignore these.  */
-	if (strcmp (*p, "-o") == 0)
-	  {
-	    if (p[1] != NULL)
-	      p++;
-	    continue;
-	  }
-	if (strcmp (*p, "-quiet") == 0)
-	  continue;
-	if (strcmp (*p, "-version") == 0)
-	  continue;
-	if ((*p)[1] == 'd')
-	  continue;
+  /* Save in case md file wants to emit args as a comment.  */
+  save_argc = argc;
+  save_argv = argv;
 
-	pos = print_single_switch (file, pos, max, indent, sep, term, *p, "");
-      }
-  if (pos > 0)
-    fprintf (file, "%s", term);
+  /* Initialization of GCC's environment.  */
+  general_init (argv [0]);
 
-  /* Print the -f and -m options that have been enabled.
-     We don't handle language specific options but printing argv
-     should suffice.  */
+  /* Parse the options and do minimal processing; basically just
+     enough to default flags appropriately.  */
+  parse_options_and_default_flags (argc, argv);
 
-  pos = print_single_switch (file, 0, max, indent, *indent ? " " : "", term,
-			     _("options enabled: "), "");
+  /* Exit early if we can (e.g. -help).  */
+  if (exit_after_options)
+    exit (0);
 
-  for (j = 0; j < ARRAY_SIZE (f_options); j++)
-    if (*f_options[j].variable == f_options[j].on_value)
-      pos = print_single_switch (file, pos, max, indent, sep, term,
-				 "-f", f_options[j].string);
+  /* The bulk of command line switch processing.  */
+  process_options ();
 
-  /* Print target specific options.  */
+  /* Language-independent initialization.  */
+  independent_init ();
 
-  for (j = 0; j < ARRAY_SIZE (target_switches); j++)
-    if (target_switches[j].name[0] != '\0'
-	&& target_switches[j].value > 0
-	&& ((target_switches[j].value & target_flags)
-	    == target_switches[j].value))
-      {
-	pos = print_single_switch (file, pos, max, indent, sep, term,
-				   "-m", target_switches[j].name);
-      }
+  compile_file (filename);
 
-#ifdef TARGET_OPTIONS
-  for (j = 0; j < ARRAY_SIZE (target_options); j++)
-    if (*target_options[j].variable != NULL)
-      {
-	char prefix[256];
-	sprintf (prefix, "-m%s", target_options[j].prefix);
-	pos = print_single_switch (file, pos, max, indent, sep, term,
-				   prefix, *target_options[j].variable);
-      }
-#endif
+  if (errorcount || sorrycount)
+    return (FATAL_EXIT_CODE);
 
-  fprintf (file, "%s", term);
+  return (SUCCESS_EXIT_CODE);
 }



More information about the Gcc-patches mailing list