aboutsummaryrefslogtreecommitdiffstats
path: root/gcc-4.2.1/gcc/config/alpha/vms-cc.c
diff options
context:
space:
mode:
Diffstat (limited to 'gcc-4.2.1/gcc/config/alpha/vms-cc.c')
-rw-r--r--gcc-4.2.1/gcc/config/alpha/vms-cc.c356
1 files changed, 356 insertions, 0 deletions
diff --git a/gcc-4.2.1/gcc/config/alpha/vms-cc.c b/gcc-4.2.1/gcc/config/alpha/vms-cc.c
new file mode 100644
index 000000000..0dcf1508f
--- /dev/null
+++ b/gcc-4.2.1/gcc/config/alpha/vms-cc.c
@@ -0,0 +1,356 @@
+/* VMS DEC C wrapper.
+ Copyright (C) 2001, 2003 Free Software Foundation, Inc.
+ Contributed by Douglas B. Rupp (rupp@gnat.com).
+
+This file is part of GCC.
+
+GCC is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GCC is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GCC; see the file COPYING. If not, write to
+the Free Software Foundation, 51 Franklin Street, Fifth Floor,
+Boston, MA 02110-1301, USA. */
+
+/* This program is a wrapper around the VMS DEC C compiler.
+ It translates Unix style command line options into corresponding
+ VMS style qualifiers and then spawns the DEC C compiler. */
+
+#include "config.h"
+#include "system.h"
+#include "coretypes.h"
+#include "tm.h"
+
+#undef PATH_SEPARATOR
+#undef PATH_SEPARATOR_STR
+#define PATH_SEPARATOR ','
+#define PATH_SEPARATOR_STR ","
+
+/* These can be set by command line arguments */
+static int verbose = 0;
+static int save_temps = 0;
+
+static int comp_arg_max = -1;
+static const char **comp_args = 0;
+static int comp_arg_index = -1;
+static char *objfilename = 0;
+
+static char *system_search_dirs = (char *) "";
+static char *search_dirs;
+
+static char *default_defines = (char *) "";
+static char *defines;
+
+/* Translate a Unix syntax directory specification into VMS syntax.
+ If indicators of VMS syntax found, return input string. */
+static char *to_host_dir_spec (char *);
+
+/* Translate a Unix syntax file specification into VMS syntax.
+ If indicators of VMS syntax found, return input string. */
+static char *to_host_file_spec (char *);
+
+/* Add a translated arg to the list to be passed to DEC CC. */
+static void addarg (const char *);
+
+/* Preprocess the number of args in P_ARGC and contained in ARGV.
+ Look for special flags, etc. that must be handled first. */
+static void preprocess_args (int *, char **);
+
+/* Process the number of args in P_ARGC and contained in ARGV. Look
+ for special flags, etc. that must be handled for the VMS compiler. */
+static void process_args (int *, char **);
+
+/* Action routine called by decc$to_vms */
+static int translate_unix (char *, int);
+
+/* Add the argument contained in STR to the list of arguments to pass to the
+ compiler. */
+
+static void
+addarg (const char *str)
+{
+ int i;
+
+ if (++comp_arg_index >= comp_arg_max)
+ {
+ const char **new_comp_args
+ = (const char **) xcalloc (comp_arg_max + 1000, sizeof (char *));
+
+ for (i = 0; i <= comp_arg_max; i++)
+ new_comp_args [i] = comp_args [i];
+
+ if (comp_args)
+ free (comp_args);
+
+ comp_arg_max += 1000;
+ comp_args = new_comp_args;
+ }
+
+ comp_args [comp_arg_index] = str;
+}
+
+static void
+preprocess_args (int *p_argc, char *argv[])
+{
+ int i;
+
+ for (i = 1; i < *p_argc; i++)
+ {
+ if (strcmp (argv[i], "-o") == 0)
+ {
+ char *buff, *ptr;
+
+ i++;
+ ptr = to_host_file_spec (argv[i]);
+ objfilename = xstrdup (ptr);
+ buff = concat ("/obj=", ptr, NULL);
+ addarg (buff);
+ }
+ }
+}
+
+static void
+process_args (int *p_argc, char *argv[])
+{
+ int i;
+
+ for (i = 1; i < *p_argc; i++)
+ {
+ if (strlen (argv[i]) < 2)
+ continue;
+
+ if (strncmp (argv[i], "-I", 2) == 0)
+ {
+ char *ptr;
+ int new_len, search_dirs_len;
+
+ ptr = to_host_dir_spec (&argv[i][2]);
+ new_len = strlen (ptr);
+ search_dirs_len = strlen (search_dirs);
+
+ search_dirs = xrealloc (search_dirs, search_dirs_len + new_len + 2);
+ if (search_dirs_len > 0)
+ strcat (search_dirs, PATH_SEPARATOR_STR);
+ strcat (search_dirs, ptr);
+ }
+ else if (strncmp (argv[i], "-D", 2) == 0)
+ {
+ char *ptr;
+ int new_len, defines_len;
+
+ ptr = &argv[i][2];
+ new_len = strlen (ptr);
+ defines_len = strlen (defines);
+
+ defines = xrealloc (defines, defines_len + new_len + 4);
+ if (defines_len > 0)
+ strcat (defines, ",");
+
+ strcat (defines, "\"");
+ strcat (defines, ptr);
+ strcat (defines, "\"");
+ }
+ else if (strcmp (argv[i], "-v") == 0)
+ verbose = 1;
+ else if (strcmp (argv[i], "-g0") == 0)
+ addarg ("/nodebug");
+ else if (strcmp (argv[i], "-O0") == 0)
+ addarg ("/noopt");
+ else if (strncmp (argv[i], "-g", 2) == 0)
+ addarg ("/debug");
+ else if (strcmp (argv[i], "-E") == 0)
+ addarg ("/preprocess");
+ else if (strcmp (argv[i], "-save-temps") == 0)
+ save_temps = 1;
+ }
+}
+
+/* The main program. Spawn the VMS DEC C compiler after fixing up the
+ Unix-like flags and args to be what VMS DEC C wants. */
+
+typedef struct dsc {unsigned short len, mbz; char *adr; } Descr;
+
+int
+main (int argc, char **argv)
+{
+ int i;
+ char cwdev [128], *devptr;
+ int devlen;
+ char *cwd = getcwd (0, 1024);
+
+ devptr = strchr (cwd, ':');
+ devlen = (devptr - cwd) + 1;
+ strncpy (cwdev, cwd, devlen);
+ cwdev [devlen] = '\0';
+
+ search_dirs = xstrdup (system_search_dirs);
+ defines = xstrdup (default_defines);
+
+ addarg ("cc");
+ preprocess_args (&argc , argv);
+ process_args (&argc , argv);
+
+ if (strlen (search_dirs) > 0)
+ {
+ addarg ("/include=(");
+ addarg (search_dirs);
+ addarg (")");
+ }
+
+ if (strlen (defines) > 0)
+ {
+ addarg ("/define=(");
+ addarg (defines);
+ addarg (")");
+ }
+
+ for (i = 1; i < argc; i++)
+ {
+ int arg_len = strlen (argv[i]);
+
+ if (strcmp (argv[i], "-o") == 0)
+ i++;
+ else if (strcmp (argv[i], "-v" ) == 0
+ || strcmp (argv[i], "-E") == 0
+ || strcmp (argv[i], "-c") == 0
+ || strncmp (argv[i], "-g", 2 ) == 0
+ || strncmp (argv[i], "-O", 2 ) == 0
+ || strcmp (argv[i], "-save-temps") == 0
+ || (arg_len > 2 && strncmp (argv[i], "-I", 2) == 0)
+ || (arg_len > 2 && strncmp (argv[i], "-D", 2) == 0))
+ ;
+
+ /* Unix style file specs and VMS style switches look alike, so assume
+ an arg consisting of one and only one slash, and that being first, is
+ really a switch. */
+ else if ((argv[i][0] == '/') && (strchr (&argv[i][1], '/') == 0))
+ addarg (argv[i]);
+ else
+ {
+ /* Assume filename arg */
+ char buff [256], *ptr;
+
+ ptr = to_host_file_spec (argv[i]);
+ arg_len = strlen (ptr);
+
+ if (ptr[0] == '[')
+ sprintf (buff, "%s%s", cwdev, ptr);
+ else if (strchr (ptr, ':'))
+ sprintf (buff, "%s", ptr);
+ else
+ sprintf (buff, "%s%s", cwd, ptr);
+
+ ptr = xstrdup (buff);
+ addarg (ptr);
+ }
+ }
+
+ addarg (NULL);
+
+ if (verbose)
+ {
+ int i;
+
+ for (i = 0; i < comp_arg_index; i++)
+ printf ("%s ", comp_args [i]);
+
+ putchar ('\n');
+ }
+
+ {
+ int i;
+ int len = 0;
+
+ for (i = 0; comp_args[i]; i++)
+ len = len + strlen (comp_args[i]) + 1;
+
+ {
+ char *allargs = (char *) alloca (len + 1);
+ Descr cmd;
+ int status;
+ int status1 = 1;
+
+ for (i = 0; i < len + 1; i++)
+ allargs [i] = 0;
+
+ for (i = 0; comp_args [i]; i++)
+ {
+ strcat (allargs, comp_args [i]);
+ strcat (allargs, " ");
+ }
+
+ cmd.adr = allargs;
+ cmd.len = len;
+ cmd.mbz = 0;
+
+ i = LIB$SPAWN (&cmd, 0, 0, 0, 0, 0, &status);
+
+ if ((i & 1) != 1)
+ {
+ LIB$SIGNAL (i);
+ exit (1);
+ }
+
+ if ((status & 1) == 1 && (status1 & 1) == 1)
+ exit (0);
+
+ exit (1);
+ }
+ }
+}
+
+static char new_host_filespec [255];
+static char new_host_dirspec [255];
+static char filename_buff [256];
+
+static int
+translate_unix (char *name, int type ATTRIBUTE_UNUSED)
+{
+ strcpy (filename_buff, name);
+ return 0;
+}
+
+static char *
+to_host_dir_spec (char *dirspec)
+{
+ int len = strlen (dirspec);
+
+ strcpy (new_host_dirspec, dirspec);
+
+ if (strchr (new_host_dirspec, ']') || strchr (new_host_dirspec, ':'))
+ return new_host_dirspec;
+
+ while (len > 1 && new_host_dirspec [len-1] == '/')
+ {
+ new_host_dirspec [len-1] = 0;
+ len--;
+ }
+
+ decc$to_vms (new_host_dirspec, translate_unix, 1, 2);
+ strcpy (new_host_dirspec, filename_buff);
+
+ return new_host_dirspec;
+
+}
+
+static char *
+to_host_file_spec (char *filespec)
+{
+ strcpy (new_host_filespec, "");
+ if (strchr (filespec, ']') || strchr (filespec, ':'))
+ strcpy (new_host_filespec, filespec);
+ else
+ {
+ decc$to_vms (filespec, translate_unix, 1, 1);
+ strcpy (new_host_filespec, filename_buff);
+ }
+
+ return new_host_filespec;
+}