OSDN Git Service

Initial revision
authormrs <mrs@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 18 Dec 1996 02:45:53 +0000 (02:45 +0000)
committermrs <mrs@138bc75d-0d04-0410-961f-82ee72b054a4>
Wed, 18 Dec 1996 02:45:53 +0000 (02:45 +0000)
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@13320 138bc75d-0d04-0410-961f-82ee72b054a4

gcc/cp/g++spec.c [new file with mode: 0644]

diff --git a/gcc/cp/g++spec.c b/gcc/cp/g++spec.c
new file mode 100644 (file)
index 0000000..881e821
--- /dev/null
@@ -0,0 +1,227 @@
+#include <sys/types.h>
+#include <stdio.h>
+#include "gansidecl.h"
+
+/* This bit is set if we saw a `-xfoo' language specification.  */
+#define LANGSPEC       (1<<1)
+/* This bit is set if they did `-lm' or `-lmath'.  */
+#define MATHLIB                (1<<2)
+/* This bit is set if they did `-lc'.  */
+#define WITHLIBC       (1<<3)
+
+#ifndef MATH_LIBRARY
+#define MATH_LIBRARY "-lm"
+#endif
+
+extern char *xmalloc PROTO((size_t));
+
+void
+lang_specific_driver (fn, in_argc, in_argv)
+     void (*fn)();
+     int *in_argc;
+     char ***in_argv;
+{
+  int i, j;
+
+  /* If non-zero, the user gave us the `-v' flag.  */ 
+  int saw_verbose_flag = 0;
+
+  /* This will be 0 if we encounter a situation where we should not
+     link in libstdc++.  */
+  int library = 1;
+
+  /* The number of arguments being added to what's in argv, other than
+     libraries.  We use this to track the number of times we've inserted
+     -xc++/-xnone.  */
+  int added = 2;
+
+  /* Used to track options that take arguments, so we don't go wrapping
+     those with -xc++/-xnone.  */
+  char *quote = NULL;
+
+  /* The new argument list will be contained in this.  */
+  char **arglist;
+
+  /* Non-zero if we saw a `-xfoo' language specification on the
+     command line.  Used to avoid adding our own -xc++ if the user
+     already gave a language for the file.  */
+  int saw_speclang = 0;
+
+  /* "-lm" or "-lmath" if it appears on the command line.  */
+  char *saw_math = 0;
+
+  /* "-lc" if it appears on the command line.  */
+  char *saw_libc = 0;
+
+  /* An array used to flag each argument that needs a bit set for
+     LANGSPEC, MATHLIB, or WITHLIBC.  */
+  int *args;
+
+  /* By default, we throw on the math library.  */
+  int need_math = 1;
+
+  /* The total number of arguments with the new stuff.  */
+  int argc;
+
+  /* The argument list.  */
+  char **argv;
+
+  /* The total number of arguments with the new stuff.  */
+  int num_args = 1;
+
+  argc = *in_argc;
+  argv = *in_argv;
+
+
+  args = (int *) xmalloc (argc * sizeof (int));
+  bzero ((char *) args, argc * sizeof (int));
+
+  /* NOTE: We start at 0 now, not 1.  */
+  for (i = 0; i < argc; i++)
+    {
+      /* If the previous option took an argument, we swallow it here.  */
+      if (quote)
+       {
+         quote = NULL;
+         continue;
+       }
+
+      /* We don't do this anymore, since we don't get them with minus
+        signs on them.  */
+      if (argv[i][0] == '\0' || argv[i][1] == '\0')
+       continue;
+
+      if (argv[i][0] == '-')
+       {
+         if (library != 0 && (strcmp (argv[i], "nostdlib") == 0
+                              || strcmp (argv[i], "nodefaultlibs") == 0))
+           {
+             library = 0;
+           }
+         else if (strcmp (argv[i], "lm") == 0
+                  || strcmp (argv[i], "lmath") == 0
+#ifdef ALT_LIBM
+                  || strcmp (argv[i], ALT_LIBM) == 0
+#endif
+                 )
+           {
+             args[i] |= MATHLIB;
+             need_math = 0;
+           }
+         else if (strcmp (argv[i], "lc") == 0)
+           args[i] |= WITHLIBC;
+         else if (strcmp (argv[i], "v") == 0)
+           {
+             saw_verbose_flag = 1;
+             /* We now see if this is 1, since we are doing the switches
+                differently.  */
+             if (argc == 1)
+               {
+                 /* If they only gave us `-v', don't try to link
+                    in libg++.  */ 
+                 library = 0;
+               }
+           }
+         else if (strncmp (argv[i], "x", 2) == 0)
+           saw_speclang = 1;
+         else if (((argv[i][2] == '\0'
+                    && (char *)strchr ("bBVDUoeTuIYmLiA", argv[i][1]) != NULL)
+                   || strcmp (argv[i], "Tdata") == 0))
+           quote = argv[i];
+         else if (library != 0 && ((argv[i][2] == '\0'
+                    && (char *) strchr ("cSEM", argv[i][1]) != NULL)
+                   || strcmp (argv[i], "MM") == 0))
+           {
+             /* Don't specify libraries if we won't link, since that would
+                cause a warning.  */
+             library = 0;
+             added -= 2;
+           }
+         else
+           /* Pass other options through.  */
+           continue;
+       }
+      else
+       {
+         int len; 
+
+         if (saw_speclang)
+           {
+             saw_speclang = 0;
+             continue;
+           }
+
+         /* If the filename ends in .c or .i, put options around it.
+            But not if a specified -x option is currently active.  */
+         len = strlen (argv[i]);
+         if (len > 2
+             && (argv[i][len - 1] == 'c' || argv[i][len - 1] == 'i')
+             && argv[i][len - 2] == '.')
+           {
+             args[i] |= LANGSPEC;
+             added += 2;
+           }
+       }
+    }
+
+  if (quote)
+    (*fn) ("argument to `%s' missing\n", quote);
+
+  /* If we know we don't have to do anything, bail now.  */
+  if (! added && ! library)
+    {
+      free (args);
+      return;
+    }
+
+  num_args = argc + added + need_math;
+  arglist = (char **) xmalloc (num_args * sizeof (char *));
+
+  /* NOTE: We start at 1 now, not 0.  */
+  for (i = 0, j = 0; i < argc; i++, j++)
+    {
+      arglist[j] = argv[i];
+
+      /* Make sure -lstdc++ is before the math library, since libstdc++
+        itself uses those math routines.  */
+      if (!saw_math && (args[i] & MATHLIB) && library)
+       {
+         --j;
+         saw_math = argv[i];
+       }
+
+      if (!saw_libc && (args[i] & WITHLIBC) && library)
+       {
+         --j;
+         saw_libc = argv[i];
+       }
+
+      /* Wrap foo.c and foo.i files in a language specification to
+        force the gcc compiler driver to run cc1plus on them.  */
+      if (args[i] & LANGSPEC)
+       {
+         int len = strlen (argv[i]);
+         if (argv[i][len - 1] == 'i')
+           arglist[j++] = "-xc++-cpp-output";
+         else
+           arglist[j++] = "-xc++";
+         arglist[j++] = argv[i];
+         arglist[j] = "-xnone";
+       }
+  }
+
+  /* Add `-lstdc++' if we haven't already done so.  */
+  if (library)
+    arglist[j++] = "-lstdc++";
+  if (saw_math)
+    arglist[j++] = saw_math;
+  else if (library)
+    arglist[j++] = MATH_LIBRARY;
+  if (saw_libc)
+    arglist[j++] = saw_libc;
+
+  arglist[j] = NULL;
+
+  *in_argc = j;
+  *in_argv = arglist;
+}