1*58997Selan /* Compiler driver program that can handle many languages. 2*58997Selan Copyright (C) 1987, 1989, 1992 Free Software Foundation, Inc. 3*58997Selan 4*58997Selan This file is part of GNU CC. 5*58997Selan 6*58997Selan GNU CC is free software; you can redistribute it and/or modify 7*58997Selan it under the terms of the GNU General Public License as published by 8*58997Selan the Free Software Foundation; either version 2, or (at your option) 9*58997Selan any later version. 10*58997Selan 11*58997Selan GNU CC is distributed in the hope that it will be useful, 12*58997Selan but WITHOUT ANY WARRANTY; without even the implied warranty of 13*58997Selan MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14*58997Selan GNU General Public License for more details. 15*58997Selan 16*58997Selan You should have received a copy of the GNU General Public License 17*58997Selan along with GNU CC; see the file COPYING. If not, write to 18*58997Selan the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. 19*58997Selan 20*58997Selan This paragraph is here to try to keep Sun CC from dying. 21*58997Selan The number of chars here seems crucial!!!! */ 22*58997Selan 23*58997Selan /* This program is the user interface to the C compiler and possibly to 24*58997Selan other compilers. It is used because compilation is a complicated procedure 25*58997Selan which involves running several programs and passing temporary files between 26*58997Selan them, forwarding the users switches to those programs selectively, 27*58997Selan and deleting the temporary files at the end. 28*58997Selan 29*58997Selan CC recognizes how to compile each input file by suffixes in the file names. 30*58997Selan Once it knows which kind of compilation to perform, the procedure for 31*58997Selan compilation is specified by a string called a "spec". */ 32*58997Selan 33*58997Selan #include <sys/types.h> 34*58997Selan #include <ctype.h> 35*58997Selan #include <signal.h> 36*58997Selan #include <sys/stat.h> 37*58997Selan #include <sys/file.h> /* May get R_OK, etc. on some systems. */ 38*58997Selan 39*58997Selan #include "config.h" 40*58997Selan #include "obstack.h" 41*58997Selan #include "gvarargs.h" 42*58997Selan #include <stdio.h> 43*58997Selan 44*58997Selan #ifndef R_OK 45*58997Selan #define R_OK 4 46*58997Selan #define W_OK 2 47*58997Selan #define X_OK 1 48*58997Selan #endif 49*58997Selan 50*58997Selan /* Define a generic NULL if one hasn't already been defined. */ 51*58997Selan 52*58997Selan #ifndef NULL 53*58997Selan #define NULL 0 54*58997Selan #endif 55*58997Selan 56*58997Selan #ifndef GENERIC_PTR 57*58997Selan #if defined (USE_PROTOTYPES) ? USE_PROTOTYPES : defined (__STDC__) 58*58997Selan #define GENERIC_PTR void * 59*58997Selan #else 60*58997Selan #define GENERIC_PTR char * 61*58997Selan #endif 62*58997Selan #endif 63*58997Selan 64*58997Selan #ifndef NULL_PTR 65*58997Selan #define NULL_PTR ((GENERIC_PTR)0) 66*58997Selan #endif 67*58997Selan 68*58997Selan #ifdef USG 69*58997Selan #define vfork fork 70*58997Selan #endif /* USG */ 71*58997Selan 72*58997Selan /* On MSDOS, write temp files in current dir 73*58997Selan because there's no place else we can expect to use. */ 74*58997Selan #if __MSDOS__ 75*58997Selan #ifndef P_tmpdir 76*58997Selan #define P_tmpdir "./" 77*58997Selan #endif 78*58997Selan #endif 79*58997Selan 80*58997Selan /* Test if something is a normal file. */ 81*58997Selan #ifndef S_ISREG 82*58997Selan #define S_ISREG(m) (((m) & S_IFMT) == S_IFREG) 83*58997Selan #endif 84*58997Selan 85*58997Selan /* Test if something is a directory. */ 86*58997Selan #ifndef S_ISDIR 87*58997Selan #define S_ISDIR(m) (((m) & S_IFMT) == S_IFDIR) 88*58997Selan #endif 89*58997Selan 90*58997Selan /* By default there is no special suffix for executables. */ 91*58997Selan #ifndef EXECUTABLE_SUFFIX 92*58997Selan #define EXECUTABLE_SUFFIX "" 93*58997Selan #endif 94*58997Selan 95*58997Selan /* By default, colon separates directories in a path. */ 96*58997Selan #ifndef PATH_SEPARATOR 97*58997Selan #define PATH_SEPARATOR ':' 98*58997Selan #endif 99*58997Selan 100*58997Selan #define obstack_chunk_alloc xmalloc 101*58997Selan #define obstack_chunk_free free 102*58997Selan 103*58997Selan extern void free (); 104*58997Selan extern char *getenv (); 105*58997Selan 106*58997Selan extern int errno, sys_nerr; 107*58997Selan extern char *sys_errlist[]; 108*58997Selan 109*58997Selan extern int execv (), execvp (); 110*58997Selan 111*58997Selan /* If a stage of compilation returns an exit status >= 1, 112*58997Selan compilation of that file ceases. */ 113*58997Selan 114*58997Selan #define MIN_FATAL_STATUS 1 115*58997Selan 116*58997Selan /* Flag saying to print the full filename of libgcc.a 117*58997Selan as found through our usual search mechanism. */ 118*58997Selan 119*58997Selan static int print_libgcc_file_name; 120*58997Selan 121*58997Selan /* Flag indicating whether we should print the command and arguments */ 122*58997Selan 123*58997Selan static int verbose_flag; 124*58997Selan 125*58997Selan /* Nonzero means write "temp" files in source directory 126*58997Selan and use the source file's name in them, and don't delete them. */ 127*58997Selan 128*58997Selan static int save_temps_flag; 129*58997Selan 130*58997Selan /* The compiler version specified with -V */ 131*58997Selan 132*58997Selan static char *spec_version; 133*58997Selan 134*58997Selan /* The target machine specified with -b. */ 135*58997Selan 136*58997Selan static char *spec_machine = DEFAULT_TARGET_MACHINE; 137*58997Selan 138*58997Selan /* Nonzero if cross-compiling. 139*58997Selan When -b is used, the value comes from the `specs' file. */ 140*58997Selan 141*58997Selan #ifdef CROSS_COMPILE 142*58997Selan static int cross_compile = 1; 143*58997Selan #else 144*58997Selan static int cross_compile = 0; 145*58997Selan #endif 146*58997Selan 147*58997Selan /* This is the obstack which we use to allocate many strings. */ 148*58997Selan 149*58997Selan static struct obstack obstack; 150*58997Selan 151*58997Selan /* This is the obstack to build an environment variable to pass to 152*58997Selan collect2 that describes all of the relevant switches of what to 153*58997Selan pass the compiler in building the list of pointers to constructors 154*58997Selan and destructors. */ 155*58997Selan 156*58997Selan static struct obstack collect_obstack; 157*58997Selan 158*58997Selan extern char *version_string; 159*58997Selan 160*58997Selan static void set_spec (); 161*58997Selan static struct compiler *lookup_compiler (); 162*58997Selan static char *find_a_file (); 163*58997Selan static void add_prefix (); 164*58997Selan static char *skip_whitespace (); 165*58997Selan static void record_temp_file (); 166*58997Selan static char *handle_braces (); 167*58997Selan static char *save_string (); 168*58997Selan static char *concat (); 169*58997Selan static int do_spec (); 170*58997Selan static int do_spec_1 (); 171*58997Selan static char *find_file (); 172*58997Selan static int is_linker_dir (); 173*58997Selan static void validate_switches (); 174*58997Selan static void validate_all_switches (); 175*58997Selan static void give_switch (); 176*58997Selan static void pfatal_with_name (); 177*58997Selan static void perror_with_name (); 178*58997Selan static void perror_exec (); 179*58997Selan static void fatal (); 180*58997Selan static void error (); 181*58997Selan void fancy_abort (); 182*58997Selan char *xmalloc (); 183*58997Selan char *xrealloc (); 184*58997Selan 185*58997Selan /* Specs are strings containing lines, each of which (if not blank) 186*58997Selan is made up of a program name, and arguments separated by spaces. 187*58997Selan The program name must be exact and start from root, since no path 188*58997Selan is searched and it is unreliable to depend on the current working directory. 189*58997Selan Redirection of input or output is not supported; the subprograms must 190*58997Selan accept filenames saying what files to read and write. 191*58997Selan 192*58997Selan In addition, the specs can contain %-sequences to substitute variable text 193*58997Selan or for conditional text. Here is a table of all defined %-sequences. 194*58997Selan Note that spaces are not generated automatically around the results of 195*58997Selan expanding these sequences; therefore, you can concatenate them together 196*58997Selan or with constant text in a single argument. 197*58997Selan 198*58997Selan %% substitute one % into the program name or argument. 199*58997Selan %i substitute the name of the input file being processed. 200*58997Selan %b substitute the basename of the input file being processed. 201*58997Selan This is the substring up to (and not including) the last period 202*58997Selan and not including the directory. 203*58997Selan %g substitute the temporary-file-name-base. This is a string chosen 204*58997Selan once per compilation. Different temporary file names are made by 205*58997Selan concatenation of constant strings on the end, as in `%g.s'. 206*58997Selan %g also has the same effect of %d. 207*58997Selan %u like %g, but make the temporary file name unique. 208*58997Selan %U returns the last file name generated with %u. 209*58997Selan %d marks the argument containing or following the %d as a 210*58997Selan temporary file name, so that that file will be deleted if CC exits 211*58997Selan successfully. Unlike %g, this contributes no text to the argument. 212*58997Selan %w marks the argument containing or following the %w as the 213*58997Selan "output file" of this compilation. This puts the argument 214*58997Selan into the sequence of arguments that %o will substitute later. 215*58997Selan %W{...} 216*58997Selan like %{...} but mark last argument supplied within 217*58997Selan as a file to be deleted on failure. 218*58997Selan %o substitutes the names of all the output files, with spaces 219*58997Selan automatically placed around them. You should write spaces 220*58997Selan around the %o as well or the results are undefined. 221*58997Selan %o is for use in the specs for running the linker. 222*58997Selan Input files whose names have no recognized suffix are not compiled 223*58997Selan at all, but they are included among the output files, so they will 224*58997Selan be linked. 225*58997Selan %p substitutes the standard macro predefinitions for the 226*58997Selan current target machine. Use this when running cpp. 227*58997Selan %P like %p, but puts `__' before and after the name of each macro. 228*58997Selan (Except macros that already have __.) 229*58997Selan This is for ANSI C. 230*58997Selan %I Substitute a -iprefix option made from GCC_EXEC_PREFIX. 231*58997Selan %s current argument is the name of a library or startup file of some sort. 232*58997Selan Search for that file in a standard list of directories 233*58997Selan and substitute the full name found. 234*58997Selan %eSTR Print STR as an error message. STR is terminated by a newline. 235*58997Selan Use this when inconsistent options are detected. 236*58997Selan %x{OPTION} Accumulate an option for %X. 237*58997Selan %X Output the accumulated linker options specified by compilations. 238*58997Selan %Y Output the accumulated assembler options specified by compilations. 239*58997Selan %a process ASM_SPEC as a spec. 240*58997Selan This allows config.h to specify part of the spec for running as. 241*58997Selan %A process ASM_FINAL_SPEC as a spec. A capital A is actually 242*58997Selan used here. This can be used to run a post-processor after the 243*58997Selan assembler has done it's job. 244*58997Selan %D Dump out a -L option for each directory in library_prefix, 245*58997Selan followed by a -L option for each directory in startfile_prefix. 246*58997Selan %l process LINK_SPEC as a spec. 247*58997Selan %L process LIB_SPEC as a spec. 248*58997Selan %S process STARTFILE_SPEC as a spec. A capital S is actually used here. 249*58997Selan %E process ENDFILE_SPEC as a spec. A capital E is actually used here. 250*58997Selan %c process SIGNED_CHAR_SPEC as a spec. 251*58997Selan %C process CPP_SPEC as a spec. A capital C is actually used here. 252*58997Selan %1 process CC1_SPEC as a spec. 253*58997Selan %2 process CC1PLUS_SPEC as a spec. 254*58997Selan %* substitute the variable part of a matched option. (See below.) 255*58997Selan Note that each comma in the substituted string is replaced by 256*58997Selan a single space. 257*58997Selan %{S} substitutes the -S switch, if that switch was given to CC. 258*58997Selan If that switch was not specified, this substitutes nothing. 259*58997Selan Here S is a metasyntactic variable. 260*58997Selan %{S*} substitutes all the switches specified to CC whose names start 261*58997Selan with -S. This is used for -o, -D, -I, etc; switches that take 262*58997Selan arguments. CC considers `-o foo' as being one switch whose 263*58997Selan name starts with `o'. %{o*} would substitute this text, 264*58997Selan including the space; thus, two arguments would be generated. 265*58997Selan %{S*:X} substitutes X if one or more switches whose names start with -S are 266*58997Selan specified to CC. Note that the tail part of the -S option 267*58997Selan (i.e. the part matched by the `*') will be substituted for each 268*58997Selan occurrence of %* within X. 269*58997Selan %{S:X} substitutes X, but only if the -S switch was given to CC. 270*58997Selan %{!S:X} substitutes X, but only if the -S switch was NOT given to CC. 271*58997Selan %{|S:X} like %{S:X}, but if no S switch, substitute `-'. 272*58997Selan %{|!S:X} like %{!S:X}, but if there is an S switch, substitute `-'. 273*58997Selan %{.S:X} substitutes X, but only if processing a file with suffix S. 274*58997Selan %{!.S:X} substitutes X, but only if NOT processing a file with suffix S. 275*58997Selan %(Spec) processes a specification defined in a specs file as *Spec: 276*58997Selan %[Spec] as above, but put __ around -D arguments 277*58997Selan 278*58997Selan The conditional text X in a %{S:X} or %{!S:X} construct may contain 279*58997Selan other nested % constructs or spaces, or even newlines. They are 280*58997Selan processed as usual, as described above. 281*58997Selan 282*58997Selan The character | is used to indicate that a command should be piped to 283*58997Selan the following command, but only if -pipe is specified. 284*58997Selan 285*58997Selan Note that it is built into CC which switches take arguments and which 286*58997Selan do not. You might think it would be useful to generalize this to 287*58997Selan allow each compiler's spec to say which switches take arguments. But 288*58997Selan this cannot be done in a consistent fashion. CC cannot even decide 289*58997Selan which input files have been specified without knowing which switches 290*58997Selan take arguments, and it must know which input files to compile in order 291*58997Selan to tell which compilers to run. 292*58997Selan 293*58997Selan CC also knows implicitly that arguments starting in `-l' are to be 294*58997Selan treated as compiler output files, and passed to the linker in their 295*58997Selan proper position among the other output files. */ 296*58997Selan 297*58997Selan /* Define the macros used for specs %a, %l, %L, %S, %c, %C, %1. */ 298*58997Selan 299*58997Selan /* config.h can define ASM_SPEC to provide extra args to the assembler 300*58997Selan or extra switch-translations. */ 301*58997Selan #ifndef ASM_SPEC 302*58997Selan #define ASM_SPEC "" 303*58997Selan #endif 304*58997Selan 305*58997Selan /* config.h can define ASM_FINAL_SPEC to run a post processor after 306*58997Selan the assembler has run. */ 307*58997Selan #ifndef ASM_FINAL_SPEC 308*58997Selan #define ASM_FINAL_SPEC "" 309*58997Selan #endif 310*58997Selan 311*58997Selan /* config.h can define CPP_SPEC to provide extra args to the C preprocessor 312*58997Selan or extra switch-translations. */ 313*58997Selan #ifndef CPP_SPEC 314*58997Selan #define CPP_SPEC "" 315*58997Selan #endif 316*58997Selan 317*58997Selan /* config.h can define CC1_SPEC to provide extra args to cc1 and cc1plus 318*58997Selan or extra switch-translations. */ 319*58997Selan #ifndef CC1_SPEC 320*58997Selan #define CC1_SPEC "" 321*58997Selan #endif 322*58997Selan 323*58997Selan /* config.h can define CC1PLUS_SPEC to provide extra args to cc1plus 324*58997Selan or extra switch-translations. */ 325*58997Selan #ifndef CC1PLUS_SPEC 326*58997Selan #define CC1PLUS_SPEC "" 327*58997Selan #endif 328*58997Selan 329*58997Selan /* config.h can define LINK_SPEC to provide extra args to the linker 330*58997Selan or extra switch-translations. */ 331*58997Selan #ifndef LINK_SPEC 332*58997Selan #define LINK_SPEC "" 333*58997Selan #endif 334*58997Selan 335*58997Selan /* config.h can define LIB_SPEC to override the default libraries. */ 336*58997Selan #ifndef LIB_SPEC 337*58997Selan #define LIB_SPEC "%{g*:-lg} %{!p:%{!pg:-lc}}%{p:-lc_p}%{pg:-lc_p}" 338*58997Selan #endif 339*58997Selan 340*58997Selan /* config.h can define STARTFILE_SPEC to override the default crt0 files. */ 341*58997Selan #ifndef STARTFILE_SPEC 342*58997Selan #define STARTFILE_SPEC \ 343*58997Selan "%{pg:gcrt0.o%s}%{!pg:%{p:mcrt0.o%s}%{!p:crt0.o%s}}" 344*58997Selan #endif 345*58997Selan 346*58997Selan /* config.h can define SWITCHES_NEED_SPACES to control passing -o and -L. 347*58997Selan Make the string nonempty to require spaces there. */ 348*58997Selan #ifndef SWITCHES_NEED_SPACES 349*58997Selan #define SWITCHES_NEED_SPACES "" 350*58997Selan #endif 351*58997Selan 352*58997Selan /* config.h can define ENDFILE_SPEC to override the default crtn files. */ 353*58997Selan #ifndef ENDFILE_SPEC 354*58997Selan #define ENDFILE_SPEC "" 355*58997Selan #endif 356*58997Selan 357*58997Selan /* This spec is used for telling cpp whether char is signed or not. */ 358*58997Selan #ifndef SIGNED_CHAR_SPEC 359*58997Selan /* Use #if rather than ?: 360*58997Selan because MIPS C compiler rejects like ?: in initializers. */ 361*58997Selan #if DEFAULT_SIGNED_CHAR 362*58997Selan #define SIGNED_CHAR_SPEC "%{funsigned-char:-D__CHAR_UNSIGNED__}" 363*58997Selan #else 364*58997Selan #define SIGNED_CHAR_SPEC "%{!fsigned-char:-D__CHAR_UNSIGNED__}" 365*58997Selan #endif 366*58997Selan #endif 367*58997Selan 368*58997Selan static char *cpp_spec = CPP_SPEC; 369*58997Selan static char *cpp_predefines = CPP_PREDEFINES; 370*58997Selan static char *cc1_spec = CC1_SPEC; 371*58997Selan static char *cc1plus_spec = CC1PLUS_SPEC; 372*58997Selan static char *signed_char_spec = SIGNED_CHAR_SPEC; 373*58997Selan static char *asm_spec = ASM_SPEC; 374*58997Selan static char *asm_final_spec = ASM_FINAL_SPEC; 375*58997Selan static char *link_spec = LINK_SPEC; 376*58997Selan static char *lib_spec = LIB_SPEC; 377*58997Selan static char *endfile_spec = ENDFILE_SPEC; 378*58997Selan static char *startfile_spec = STARTFILE_SPEC; 379*58997Selan static char *switches_need_spaces = SWITCHES_NEED_SPACES; 380*58997Selan 381*58997Selan /* This defines which switch letters take arguments. */ 382*58997Selan 383*58997Selan #ifndef SWITCH_TAKES_ARG 384*58997Selan #define SWITCH_TAKES_ARG(CHAR) \ 385*58997Selan ((CHAR) == 'D' || (CHAR) == 'U' || (CHAR) == 'o' \ 386*58997Selan || (CHAR) == 'e' || (CHAR) == 'T' || (CHAR) == 'u' \ 387*58997Selan || (CHAR) == 'I' || (CHAR) == 'm' \ 388*58997Selan || (CHAR) == 'L' || (CHAR) == 'A') 389*58997Selan #endif 390*58997Selan 391*58997Selan /* This defines which multi-letter switches take arguments. */ 392*58997Selan 393*58997Selan #ifndef WORD_SWITCH_TAKES_ARG 394*58997Selan #define WORD_SWITCH_TAKES_ARG(STR) \ 395*58997Selan (!strcmp (STR, "Tdata") || !strcmp (STR, "Ttext") \ 396*58997Selan || !strcmp (STR, "Tbss") || !strcmp (STR, "include") \ 397*58997Selan || !strcmp (STR, "imacros") || !strcmp (STR, "aux-info")) 398*58997Selan #endif 399*58997Selan 400*58997Selan /* Record the mapping from file suffixes for compilation specs. */ 401*58997Selan 402*58997Selan struct compiler 403*58997Selan { 404*58997Selan char *suffix; /* Use this compiler for input files 405*58997Selan whose names end in this suffix. */ 406*58997Selan 407*58997Selan char *spec[4]; /* To use this compiler, concatenate these 408*58997Selan specs and pass to do_spec. */ 409*58997Selan }; 410*58997Selan 411*58997Selan /* Pointer to a vector of `struct compiler' that gives the spec for 412*58997Selan compiling a file, based on its suffix. 413*58997Selan A file that does not end in any of these suffixes will be passed 414*58997Selan unchanged to the loader and nothing else will be done to it. 415*58997Selan 416*58997Selan An entry containing two 0s is used to terminate the vector. 417*58997Selan 418*58997Selan If multiple entries match a file, the last matching one is used. */ 419*58997Selan 420*58997Selan static struct compiler *compilers; 421*58997Selan 422*58997Selan /* Number of entries in `compilers', not counting the null terminator. */ 423*58997Selan 424*58997Selan static int n_compilers; 425*58997Selan 426*58997Selan /* The default list of file name suffixes and their compilation specs. */ 427*58997Selan 428*58997Selan static struct compiler default_compilers[] = 429*58997Selan { 430*58997Selan {".c", "@c"}, 431*58997Selan {"@c", 432*58997Selan "cpp -lang-c %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\ 433*58997Selan %{C:%{!E:%eGNU C does not support -C without using -E}}\ 434*58997Selan %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d}\ 435*58997Selan -undef -D__GNUC__=2 %{ansi:-trigraphs -$ -D__STRICT_ANSI__}\ 436*58997Selan %{!undef:%{!ansi:%p} %P} %{trigraphs} \ 437*58997Selan %c %{O*:-D__OPTIMIZE__} %{traditional} %{ftraditional:-traditional}\ 438*58997Selan %{traditional-cpp:-traditional}\ 439*58997Selan %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*}\ 440*58997Selan %i %{!M:%{!MM:%{!E:%{!pipe:%g.i}}}}%{E:%W{o*}}%{M:%W{o*}}%{MM:%W{o*}} |\n", 441*58997Selan "%{!M:%{!MM:%{!E:cc1 %{!pipe:%g.i} %1 \ 442*58997Selan %{!Q:-quiet} -dumpbase %b.c %{d*} %{m*} %{a}\ 443*58997Selan %{g*} %{O*} %{W*} %{w} %{pedantic*} %{ansi} \ 444*58997Selan %{traditional} %{v:-version} %{pg:-p} %{p} %{f*}\ 445*58997Selan %{aux-info*}\ 446*58997Selan %{pg:%{fomit-frame-pointer:%e-pg and -fomit-frame-pointer are incompatible}}\ 447*58997Selan %{S:%W{o*}%{!o*:-o %b.s}}%{!S:-o %{|!pipe:%g.s}} |\n\ 448*58997Selan %{!S:as %{R} %{j} %{J} %{h} %{d2} %a %Y\ 449*58997Selan %{c:%W{o*}%{!o*:-o %w%b.o}}%{!c:-o %d%w%u.o}\ 450*58997Selan %{!pipe:%g.s} %A\n }}}}"}, 451*58997Selan {"-", 452*58997Selan "%{E:cpp -lang-c %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\ 453*58997Selan %{C:%{!E:%eGNU C does not support -C without using -E}}\ 454*58997Selan %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d}\ 455*58997Selan -undef -D__GNUC__=2 %{ansi:-trigraphs -$ -D__STRICT_ANSI__}\ 456*58997Selan %{!undef:%{!ansi:%p} %P} %{trigraphs}\ 457*58997Selan %c %{O*:-D__OPTIMIZE__} %{traditional} %{ftraditional:-traditional}\ 458*58997Selan %{traditional-cpp:-traditional}\ 459*58997Selan %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*}\ 460*58997Selan %i %W{o*}}\ 461*58997Selan %{!E:%e-E required when input is from standard input}"}, 462*58997Selan {".m", "@objective-c"}, 463*58997Selan {"@objective-c", 464*58997Selan "cpp -lang-objc %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\ 465*58997Selan %{C:%{!E:%eGNU C does not support -C without using -E}}\ 466*58997Selan %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d}\ 467*58997Selan -undef -D__OBJC__ -D__GNUC__=2 %{ansi:-trigraphs -$ -D__STRICT_ANSI__}\ 468*58997Selan %{!undef:%{!ansi:%p} %P} %{trigraphs}\ 469*58997Selan %c %{O*:-D__OPTIMIZE__} %{traditional} %{ftraditional:-traditional}\ 470*58997Selan %{traditional-cpp:-traditional}\ 471*58997Selan %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*}\ 472*58997Selan %i %{!M:%{!MM:%{!E:%{!pipe:%g.i}}}}%{E:%W{o*}}%{M:%W{o*}}%{MM:%W{o*}} |\n", 473*58997Selan "%{!M:%{!MM:%{!E:cc1obj %{!pipe:%g.i} %1 \ 474*58997Selan %{!Q:-quiet} -dumpbase %b.m %{d*} %{m*} %{a}\ 475*58997Selan %{g*} %{O*} %{W*} %{w} %{pedantic*} %{ansi} \ 476*58997Selan %{traditional} %{v:-version} %{pg:-p} %{p} %{f*} \ 477*58997Selan -lang-objc %{gen-decls} \ 478*58997Selan %{aux-info*}\ 479*58997Selan %{pg:%{fomit-frame-pointer:%e-pg and -fomit-frame-pointer are incompatible}}\ 480*58997Selan %{S:%W{o*}%{!o*:-o %b.s}}%{!S:-o %{|!pipe:%g.s}} |\n\ 481*58997Selan %{!S:as %{R} %{j} %{J} %{h} %{d2} %a %Y\ 482*58997Selan %{c:%W{o*}%{!o*:-o %w%b.o}}%{!c:-o %d%w%u.o}\ 483*58997Selan %{!pipe:%g.s} %A\n }}}}"}, 484*58997Selan {".h", "@c-header"}, 485*58997Selan {"@c-header", 486*58997Selan "%{!E:%eCompilation of header file requested} \ 487*58997Selan cpp %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\ 488*58997Selan %{C:%{!E:%eGNU C does not support -C without using -E}}\ 489*58997Selan %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} \ 490*58997Selan -undef -D__GNUC__=2 %{ansi:-trigraphs -$ -D__STRICT_ANSI__}\ 491*58997Selan %{!undef:%{!ansi:%p} %P} %{trigraphs}\ 492*58997Selan %c %{O*:-D__OPTIMIZE__} %{traditional} %{ftraditional:-traditional}\ 493*58997Selan %{traditional-cpp:-traditional}\ 494*58997Selan %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*}\ 495*58997Selan %i %W{o*}"}, 496*58997Selan {".cc", "@c++"}, 497*58997Selan {".cxx", "@c++"}, 498*58997Selan {".C", "@c++"}, 499*58997Selan {"@c++", 500*58997Selan "cpp -lang-c++ %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\ 501*58997Selan %{C:%{!E:%eGNU C++ does not support -C without using -E}}\ 502*58997Selan %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} \ 503*58997Selan -undef -D__GNUC__=2 -D__GNUG__=2 -D__cplusplus \ 504*58997Selan %{ansi:-trigraphs -$ -D__STRICT_ANSI__} %{!undef:%{!ansi:%p} %P}\ 505*58997Selan %c %{O*:-D__OPTIMIZE__} %{traditional} %{ftraditional:-traditional}\ 506*58997Selan %{traditional-cpp:-traditional} %{trigraphs}\ 507*58997Selan %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*}\ 508*58997Selan %i %{!M:%{!MM:%{!E:%{!pipe:%g.i}}}}%{E:%W{o*}}%{M:%W{o*}}%{MM:%W{o*}} |\n", 509*58997Selan "%{!M:%{!MM:%{!E:cc1plus %{!pipe:%g.i} %1 %2\ 510*58997Selan %{!Q:-quiet} -dumpbase %b.cc %{d*} %{m*} %{a}\ 511*58997Selan %{g*} %{O*} %{W*} %{w} %{pedantic*} %{ansi} %{traditional}\ 512*58997Selan %{v:-version} %{pg:-p} %{p} %{f*} %{+e*}\ 513*58997Selan %{aux-info*}\ 514*58997Selan %{pg:%{fomit-frame-pointer:%e-pg and -fomit-frame-pointer are incompatible}}\ 515*58997Selan %{S:%W{o*}%{!o*:-o %b.s}}%{!S:-o %{|!pipe:%g.s}} |\n\ 516*58997Selan %{!S:as %{R} %{j} %{J} %{h} %{d2} %a %Y\ 517*58997Selan %{c:%W{o*}%{!o*:-o %w%b.o}}%{!c:-o %d%w%u.o}\ 518*58997Selan %{!pipe:%g.s} %A\n }}}}"}, 519*58997Selan {".i", "@cpp-output"}, 520*58997Selan {"@cpp-output", 521*58997Selan "cc1 %i %1 %{!Q:-quiet} %{d*} %{m*} %{a}\ 522*58997Selan %{g*} %{O*} %{W*} %{w} %{pedantic*} %{ansi} %{traditional}\ 523*58997Selan %{v:-version} %{pg:-p} %{p} %{f*}\ 524*58997Selan %{aux-info*}\ 525*58997Selan %{pg:%{fomit-frame-pointer:%e-pg and -fomit-frame-pointer are incompatible}}\ 526*58997Selan %{S:%W{o*}%{!o*:-o %b.s}}%{!S:-o %{|!pipe:%g.s}} |\n\ 527*58997Selan %{!S:as %{R} %{j} %{J} %{h} %{d2} %a %Y\ 528*58997Selan %{c:%W{o*}%{!o*:-o %w%b.o}}%{!c:-o %d%w%u.o} %{!pipe:%g.s} %A\n }"}, 529*58997Selan {".ii", "@c++-cpp-output"}, 530*58997Selan {"@c++-cpp-output", 531*58997Selan "cc1plus %i %1 %2 %{!Q:-quiet} %{d*} %{m*} %{a}\ 532*58997Selan %{g*} %{O*} %{W*} %{w} %{pedantic*} %{ansi} %{traditional}\ 533*58997Selan %{v:-version} %{pg:-p} %{p} %{f*} %{+e*}\ 534*58997Selan %{aux-info*}\ 535*58997Selan %{pg:%{fomit-frame-pointer:%e-pg and -fomit-frame-pointer are incompatible}}\ 536*58997Selan %{S:%W{o*}%{!o*:-o %b.s}}%{!S:-o %{|!pipe:%g.s}} |\n\ 537*58997Selan %{!S:as %{R} %{j} %{J} %{h} %{d2} %a %Y\ 538*58997Selan %{c:%W{o*}%{!o*:-o %w%b.o}}%{!c:-o %d%w%u.o}\ 539*58997Selan %{!pipe:%g.s} %A\n }"}, 540*58997Selan {".s", "@assembler"}, 541*58997Selan {"@assembler", 542*58997Selan "%{!S:as %{R} %{j} %{J} %{h} %{d2} %a %Y\ 543*58997Selan %{c:%W{o*}%{!o*:-o %w%b.o}}%{!c:-o %d%w%u.o} %i %A\n }"}, 544*58997Selan {".S", "@assembler-with-cpp"}, 545*58997Selan {"@assembler-with-cpp", 546*58997Selan "cpp -lang-asm %{nostdinc*} %{C} %{v} %{A*} %{I*} %{P} %I\ 547*58997Selan %{C:%{!E:%eGNU C does not support -C without using -E}}\ 548*58997Selan %{M} %{MM} %{MD:-MD %b.d} %{MMD:-MMD %b.d} %{trigraphs} \ 549*58997Selan -undef -$ %{!undef:%p %P} -D__ASSEMBLER__ \ 550*58997Selan %c %{O*:-D__OPTIMIZE__} %{traditional} %{ftraditional:-traditional}\ 551*58997Selan %{traditional-cpp:-traditional}\ 552*58997Selan %{g*} %{W*} %{w} %{pedantic*} %{H} %{d*} %C %{D*} %{U*} %{i*}\ 553*58997Selan %i %{!M:%{!MM:%{!E:%{!pipe:%g.s}}}}%{E:%W{o*}}%{M:%W{o*}}%{MM:%W{o*}} |\n", 554*58997Selan "%{!M:%{!MM:%{!E:%{!S:as %{R} %{j} %{J} %{h} %{d2} %a %Y\ 555*58997Selan %{c:%W{o*}%{!o*:-o %w%b.o}}%{!c:-o %d%w%u.o}\ 556*58997Selan %{!pipe:%g.s} %A\n }}}}"}, 557*58997Selan /* Mark end of table */ 558*58997Selan {0, 0} 559*58997Selan }; 560*58997Selan 561*58997Selan /* Number of elements in default_compilers, not counting the terminator. */ 562*58997Selan 563*58997Selan static int n_default_compilers 564*58997Selan = (sizeof default_compilers / sizeof (struct compiler)) - 1; 565*58997Selan 566*58997Selan /* Here is the spec for running the linker, after compiling all files. */ 567*58997Selan 568*58997Selan /* -u* was put back because both BSD and SysV seem to support it. */ 569*58997Selan /* %{static:} simply prevents an error message if the target machine 570*58997Selan doesn't handle -static. */ 571*58997Selan #ifdef LINK_LIBGCC_SPECIAL_1 572*58997Selan /* Have gcc do the search for libgcc.a, but generate -L options as usual. */ 573*58997Selan static char *link_command_spec = "\ 574*58997Selan %{!c:%{!M:%{!MM:%{!E:%{!S:ld %l %X %{o*} %{A} %{d} %{e*} %{m} %{N} %{n} \ 575*58997Selan %{r} %{s} %{T*} %{t} %{u*} %{x} %{z}\ 576*58997Selan %{!A:%{!nostdlib:%S}} %{static:}\ 577*58997Selan %{L*} %D %o %{!nostdlib:libgcc.a%s %L libgcc.a%s %{!A:%E}}\n }}}}}"; 578*58997Selan #else 579*58997Selan #ifdef LINK_LIBGCC_SPECIAL 580*58997Selan /* Have gcc do the search for libgcc.a, and don't generate -L options. */ 581*58997Selan static char *link_command_spec = "\ 582*58997Selan %{!c:%{!M:%{!MM:%{!E:%{!S:ld %l %X %{o*} %{A} %{d} %{e*} %{m} %{N} %{n} \ 583*58997Selan %{r} %{s} %{T*} %{t} %{u*} %{x} %{z}\ 584*58997Selan %{!A:%{!nostdlib:%S}} %{static:}\ 585*58997Selan %{L*} %o %{!nostdlib:libgcc.a%s %L libgcc.a%s %{!A:%E}}\n }}}}}"; 586*58997Selan #else 587*58997Selan /* Use -L and have the linker do the search for -lgcc. */ 588*58997Selan static char *link_command_spec = "\ 589*58997Selan %{!c:%{!M:%{!MM:%{!E:%{!S:ld %l %X %{o*} %{A} %{d} %{e*} %{m} %{N} %{n} \ 590*58997Selan %{r} %{s} %{T*} %{t} %{u*} %{x} %{z}\ 591*58997Selan %{!A:%{!nostdlib:%S}} %{static:}\ 592*58997Selan %{L*} %D %o %{!nostdlib:-lgcc %L -lgcc %{!A:%E}}\n }}}}}"; 593*58997Selan #endif 594*58997Selan #endif 595*58997Selan 596*58997Selan /* A vector of options to give to the linker. 597*58997Selan These options are accumulated by -Xlinker and -Wl, 598*58997Selan and substituted into the linker command with %X. */ 599*58997Selan static int n_linker_options; 600*58997Selan static char **linker_options; 601*58997Selan 602*58997Selan /* A vector of options to give to the assembler. 603*58997Selan These options are accumulated by -Wa, 604*58997Selan and substituted into the assembler command with %X. */ 605*58997Selan static int n_assembler_options; 606*58997Selan static char **assembler_options; 607*58997Selan 608*58997Selan /* Read compilation specs from a file named FILENAME, 609*58997Selan replacing the default ones. 610*58997Selan 611*58997Selan A suffix which starts with `*' is a definition for 612*58997Selan one of the machine-specific sub-specs. The "suffix" should be 613*58997Selan *asm, *cc1, *cpp, *link, *startfile, *signed_char, etc. 614*58997Selan The corresponding spec is stored in asm_spec, etc., 615*58997Selan rather than in the `compilers' vector. 616*58997Selan 617*58997Selan Anything invalid in the file is a fatal error. */ 618*58997Selan 619*58997Selan static void 620*58997Selan read_specs (filename) 621*58997Selan char *filename; 622*58997Selan { 623*58997Selan int desc; 624*58997Selan struct stat statbuf; 625*58997Selan char *buffer; 626*58997Selan register char *p; 627*58997Selan 628*58997Selan if (verbose_flag) 629*58997Selan fprintf (stderr, "Reading specs from %s\n", filename); 630*58997Selan 631*58997Selan /* Open and stat the file. */ 632*58997Selan desc = open (filename, 0, 0); 633*58997Selan if (desc < 0) 634*58997Selan pfatal_with_name (filename); 635*58997Selan if (stat (filename, &statbuf) < 0) 636*58997Selan pfatal_with_name (filename); 637*58997Selan 638*58997Selan /* Read contents of file into BUFFER. */ 639*58997Selan buffer = xmalloc ((unsigned) statbuf.st_size + 1); 640*58997Selan read (desc, buffer, (unsigned) statbuf.st_size); 641*58997Selan buffer[statbuf.st_size] = 0; 642*58997Selan close (desc); 643*58997Selan 644*58997Selan /* Scan BUFFER for specs, putting them in the vector. */ 645*58997Selan p = buffer; 646*58997Selan while (1) 647*58997Selan { 648*58997Selan char *suffix; 649*58997Selan char *spec; 650*58997Selan char *in, *out, *p1, *p2; 651*58997Selan 652*58997Selan /* Advance P in BUFFER to the next nonblank nocomment line. */ 653*58997Selan p = skip_whitespace (p); 654*58997Selan if (*p == 0) 655*58997Selan break; 656*58997Selan 657*58997Selan /* Find the colon that should end the suffix. */ 658*58997Selan p1 = p; 659*58997Selan while (*p1 && *p1 != ':' && *p1 != '\n') p1++; 660*58997Selan /* The colon shouldn't be missing. */ 661*58997Selan if (*p1 != ':') 662*58997Selan fatal ("specs file malformed after %d characters", p1 - buffer); 663*58997Selan /* Skip back over trailing whitespace. */ 664*58997Selan p2 = p1; 665*58997Selan while (p2 > buffer && (p2[-1] == ' ' || p2[-1] == '\t')) p2--; 666*58997Selan /* Copy the suffix to a string. */ 667*58997Selan suffix = save_string (p, p2 - p); 668*58997Selan /* Find the next line. */ 669*58997Selan p = skip_whitespace (p1 + 1); 670*58997Selan if (p[1] == 0) 671*58997Selan fatal ("specs file malformed after %d characters", p - buffer); 672*58997Selan p1 = p; 673*58997Selan /* Find next blank line. */ 674*58997Selan while (*p1 && !(*p1 == '\n' && p1[1] == '\n')) p1++; 675*58997Selan /* Specs end at the blank line and do not include the newline. */ 676*58997Selan spec = save_string (p, p1 - p); 677*58997Selan p = p1; 678*58997Selan 679*58997Selan /* Delete backslash-newline sequences from the spec. */ 680*58997Selan in = spec; 681*58997Selan out = spec; 682*58997Selan while (*in != 0) 683*58997Selan { 684*58997Selan if (in[0] == '\\' && in[1] == '\n') 685*58997Selan in += 2; 686*58997Selan else if (in[0] == '#') 687*58997Selan { 688*58997Selan while (*in && *in != '\n') in++; 689*58997Selan } 690*58997Selan else 691*58997Selan *out++ = *in++; 692*58997Selan } 693*58997Selan *out = 0; 694*58997Selan 695*58997Selan if (suffix[0] == '*') 696*58997Selan { 697*58997Selan if (! strcmp (suffix, "*link_command")) 698*58997Selan link_command_spec = spec; 699*58997Selan else 700*58997Selan set_spec (suffix + 1, spec); 701*58997Selan } 702*58997Selan else 703*58997Selan { 704*58997Selan /* Add this pair to the vector. */ 705*58997Selan compilers 706*58997Selan = ((struct compiler *) 707*58997Selan xrealloc (compilers, (n_compilers + 2) * sizeof (struct compiler))); 708*58997Selan compilers[n_compilers].suffix = suffix; 709*58997Selan bzero (compilers[n_compilers].spec, 710*58997Selan sizeof compilers[n_compilers].spec); 711*58997Selan compilers[n_compilers].spec[0] = spec; 712*58997Selan n_compilers++; 713*58997Selan } 714*58997Selan 715*58997Selan if (*suffix == 0) 716*58997Selan link_command_spec = spec; 717*58997Selan } 718*58997Selan 719*58997Selan if (link_command_spec == 0) 720*58997Selan fatal ("spec file has no spec for linking"); 721*58997Selan } 722*58997Selan 723*58997Selan static char * 724*58997Selan skip_whitespace (p) 725*58997Selan char *p; 726*58997Selan { 727*58997Selan while (1) 728*58997Selan { 729*58997Selan /* A fully-blank line is a delimiter in the SPEC file and shouldn't 730*58997Selan be considered whitespace. */ 731*58997Selan if (p[0] == '\n' && p[1] == '\n' && p[2] == '\n') 732*58997Selan return p + 1; 733*58997Selan else if (*p == '\n' || *p == ' ' || *p == '\t') 734*58997Selan p++; 735*58997Selan else if (*p == '#') 736*58997Selan { 737*58997Selan while (*p != '\n') p++; 738*58997Selan p++; 739*58997Selan } 740*58997Selan else 741*58997Selan break; 742*58997Selan } 743*58997Selan 744*58997Selan return p; 745*58997Selan } 746*58997Selan 747*58997Selan /* Structure to keep track of the specs that have been defined so far. These 748*58997Selan are accessed using %(specname) or %[specname] in a compiler or link spec. */ 749*58997Selan 750*58997Selan struct spec_list 751*58997Selan { 752*58997Selan char *name; /* Name of the spec. */ 753*58997Selan char *spec; /* The spec itself. */ 754*58997Selan struct spec_list *next; /* Next spec in linked list. */ 755*58997Selan }; 756*58997Selan 757*58997Selan /* List of specs that have been defined so far. */ 758*58997Selan 759*58997Selan static struct spec_list *specs = (struct spec_list *) 0; 760*58997Selan 761*58997Selan /* Change the value of spec NAME to SPEC. If SPEC is empty, then the spec is 762*58997Selan removed; If the spec starts with a + then SPEC is added to the end of the 763*58997Selan current spec. */ 764*58997Selan 765*58997Selan static void 766*58997Selan set_spec (name, spec) 767*58997Selan char *name; 768*58997Selan char *spec; 769*58997Selan { 770*58997Selan struct spec_list *sl; 771*58997Selan char *old_spec; 772*58997Selan 773*58997Selan /* See if the spec already exists */ 774*58997Selan for (sl = specs; sl; sl = sl->next) 775*58997Selan if (strcmp (sl->name, name) == 0) 776*58997Selan break; 777*58997Selan 778*58997Selan if (!sl) 779*58997Selan { 780*58997Selan /* Not found - make it */ 781*58997Selan sl = (struct spec_list *) xmalloc (sizeof (struct spec_list)); 782*58997Selan sl->name = save_string (name, strlen (name)); 783*58997Selan sl->spec = save_string ("", 0); 784*58997Selan sl->next = specs; 785*58997Selan specs = sl; 786*58997Selan } 787*58997Selan 788*58997Selan old_spec = sl->spec; 789*58997Selan if (name && spec[0] == '+' && isspace (spec[1])) 790*58997Selan sl->spec = concat (old_spec, spec + 1, ""); 791*58997Selan else 792*58997Selan sl->spec = save_string (spec, strlen (spec)); 793*58997Selan 794*58997Selan if (! strcmp (name, "asm")) 795*58997Selan asm_spec = sl->spec; 796*58997Selan else if (! strcmp (name, "asm_final")) 797*58997Selan asm_final_spec = sl->spec; 798*58997Selan else if (! strcmp (name, "cc1")) 799*58997Selan cc1_spec = sl->spec; 800*58997Selan else if (! strcmp (name, "cc1plus")) 801*58997Selan cc1plus_spec = sl->spec; 802*58997Selan else if (! strcmp (name, "cpp")) 803*58997Selan cpp_spec = sl->spec; 804*58997Selan else if (! strcmp (name, "endfile")) 805*58997Selan endfile_spec = sl->spec; 806*58997Selan else if (! strcmp (name, "lib")) 807*58997Selan lib_spec = sl->spec; 808*58997Selan else if (! strcmp (name, "link")) 809*58997Selan link_spec = sl->spec; 810*58997Selan else if (! strcmp (name, "predefines")) 811*58997Selan cpp_predefines = sl->spec; 812*58997Selan else if (! strcmp (name, "signed_char")) 813*58997Selan signed_char_spec = sl->spec; 814*58997Selan else if (! strcmp (name, "startfile")) 815*58997Selan startfile_spec = sl->spec; 816*58997Selan else if (! strcmp (name, "switches_need_spaces")) 817*58997Selan switches_need_spaces = sl->spec; 818*58997Selan else if (! strcmp (name, "cross_compile")) 819*58997Selan cross_compile = atoi (sl->spec); 820*58997Selan /* Free the old spec */ 821*58997Selan if (old_spec) 822*58997Selan free (old_spec); 823*58997Selan } 824*58997Selan 825*58997Selan /* Accumulate a command (program name and args), and run it. */ 826*58997Selan 827*58997Selan /* Vector of pointers to arguments in the current line of specifications. */ 828*58997Selan 829*58997Selan static char **argbuf; 830*58997Selan 831*58997Selan /* Number of elements allocated in argbuf. */ 832*58997Selan 833*58997Selan static int argbuf_length; 834*58997Selan 835*58997Selan /* Number of elements in argbuf currently in use (containing args). */ 836*58997Selan 837*58997Selan static int argbuf_index; 838*58997Selan 839*58997Selan /* This is the list of suffixes and codes (%g/%u/%U) and the associated 840*58997Selan temp file. Used only if MKTEMP_EACH_FILE. */ 841*58997Selan 842*58997Selan static struct temp_name { 843*58997Selan char *suffix; /* suffix associated with the code. */ 844*58997Selan int length; /* strlen (suffix). */ 845*58997Selan int unique; /* Indicates whether %g or %u/%U was used. */ 846*58997Selan char *filename; /* associated filename. */ 847*58997Selan int filename_length; /* strlen (filename). */ 848*58997Selan struct temp_name *next; 849*58997Selan } *temp_names; 850*58997Selan 851*58997Selan /* Number of commands executed so far. */ 852*58997Selan 853*58997Selan static int execution_count; 854*58997Selan 855*58997Selan /* Number of commands that exited with a signal. */ 856*58997Selan 857*58997Selan static int signal_count; 858*58997Selan 859*58997Selan /* Name with which this program was invoked. */ 860*58997Selan 861*58997Selan static char *programname; 862*58997Selan 863*58997Selan /* Structures to keep track of prefixes to try when looking for files. */ 864*58997Selan 865*58997Selan struct prefix_list 866*58997Selan { 867*58997Selan char *prefix; /* String to prepend to the path. */ 868*58997Selan struct prefix_list *next; /* Next in linked list. */ 869*58997Selan int require_machine_suffix; /* Don't use without machine_suffix. */ 870*58997Selan /* 2 means try both machine_suffix and just_machine_suffix. */ 871*58997Selan int *used_flag_ptr; /* 1 if a file was found with this prefix. */ 872*58997Selan }; 873*58997Selan 874*58997Selan struct path_prefix 875*58997Selan { 876*58997Selan struct prefix_list *plist; /* List of prefixes to try */ 877*58997Selan int max_len; /* Max length of a prefix in PLIST */ 878*58997Selan char *name; /* Name of this list (used in config stuff) */ 879*58997Selan }; 880*58997Selan 881*58997Selan /* List of prefixes to try when looking for executables. */ 882*58997Selan 883*58997Selan static struct path_prefix exec_prefix = { 0, 0, "exec" }; 884*58997Selan 885*58997Selan /* List of prefixes to try when looking for startup (crt0) files. */ 886*58997Selan 887*58997Selan static struct path_prefix startfile_prefix = { 0, 0, "startfile" }; 888*58997Selan 889*58997Selan /* List of prefixes to try when looking for libraries. */ 890*58997Selan 891*58997Selan static struct path_prefix library_prefix = { 0, 0, "libraryfile" }; 892*58997Selan 893*58997Selan /* Suffix to attach to directories searched for commands. 894*58997Selan This looks like `MACHINE/VERSION/'. */ 895*58997Selan 896*58997Selan static char *machine_suffix = 0; 897*58997Selan 898*58997Selan /* Suffix to attach to directories searched for commands. 899*58997Selan This is just `MACHINE/'. */ 900*58997Selan 901*58997Selan static char *just_machine_suffix = 0; 902*58997Selan 903*58997Selan /* Adjusted value of GCC_EXEC_PREFIX envvar. */ 904*58997Selan 905*58997Selan static char *gcc_exec_prefix; 906*58997Selan 907*58997Selan /* Default prefixes to attach to command names. */ 908*58997Selan 909*58997Selan #ifdef CROSS_COMPILE /* Don't use these prefixes for a cross compiler. */ 910*58997Selan #undef MD_EXEC_PREFIX 911*58997Selan #undef MD_STARTFILE_PREFIX 912*58997Selan #undef MD_STARTFILE_PREFIX_1 913*58997Selan #endif 914*58997Selan 915*58997Selan #ifndef STANDARD_EXEC_PREFIX 916*58997Selan #define STANDARD_EXEC_PREFIX "/usr/local/lib/gcc-lib/" 917*58997Selan #endif /* !defined STANDARD_EXEC_PREFIX */ 918*58997Selan 919*58997Selan static char *standard_exec_prefix = STANDARD_EXEC_PREFIX; 920*58997Selan static char *standard_exec_prefix_1 = "/usr/lib/gcc/"; 921*58997Selan #ifdef MD_EXEC_PREFIX 922*58997Selan static char *md_exec_prefix = MD_EXEC_PREFIX; 923*58997Selan #endif 924*58997Selan 925*58997Selan #ifndef STANDARD_STARTFILE_PREFIX 926*58997Selan #define STANDARD_STARTFILE_PREFIX "/usr/local/lib/" 927*58997Selan #endif /* !defined STANDARD_STARTFILE_PREFIX */ 928*58997Selan 929*58997Selan #ifdef MD_STARTFILE_PREFIX 930*58997Selan static char *md_startfile_prefix = MD_STARTFILE_PREFIX; 931*58997Selan #endif 932*58997Selan #ifdef MD_STARTFILE_PREFIX_1 933*58997Selan static char *md_startfile_prefix_1 = MD_STARTFILE_PREFIX_1; 934*58997Selan #endif 935*58997Selan static char *standard_startfile_prefix = STANDARD_STARTFILE_PREFIX; 936*58997Selan static char *standard_startfile_prefix_1 = "/lib/"; 937*58997Selan static char *standard_startfile_prefix_2 = "/usr/lib/"; 938*58997Selan 939*58997Selan /* Clear out the vector of arguments (after a command is executed). */ 940*58997Selan 941*58997Selan static void 942*58997Selan clear_args () 943*58997Selan { 944*58997Selan argbuf_index = 0; 945*58997Selan } 946*58997Selan 947*58997Selan /* Add one argument to the vector at the end. 948*58997Selan This is done when a space is seen or at the end of the line. 949*58997Selan If DELETE_ALWAYS is nonzero, the arg is a filename 950*58997Selan and the file should be deleted eventually. 951*58997Selan If DELETE_FAILURE is nonzero, the arg is a filename 952*58997Selan and the file should be deleted if this compilation fails. */ 953*58997Selan 954*58997Selan static void 955*58997Selan store_arg (arg, delete_always, delete_failure) 956*58997Selan char *arg; 957*58997Selan int delete_always, delete_failure; 958*58997Selan { 959*58997Selan if (argbuf_index + 1 == argbuf_length) 960*58997Selan { 961*58997Selan argbuf = (char **) xrealloc (argbuf, (argbuf_length *= 2) * sizeof (char *)); 962*58997Selan } 963*58997Selan 964*58997Selan argbuf[argbuf_index++] = arg; 965*58997Selan argbuf[argbuf_index] = 0; 966*58997Selan 967*58997Selan if (delete_always || delete_failure) 968*58997Selan record_temp_file (arg, delete_always, delete_failure); 969*58997Selan } 970*58997Selan 971*58997Selan /* Record the names of temporary files we tell compilers to write, 972*58997Selan and delete them at the end of the run. */ 973*58997Selan 974*58997Selan /* This is the common prefix we use to make temp file names. 975*58997Selan It is chosen once for each run of this program. 976*58997Selan It is substituted into a spec by %g. 977*58997Selan Thus, all temp file names contain this prefix. 978*58997Selan In practice, all temp file names start with this prefix. 979*58997Selan 980*58997Selan This prefix comes from the envvar TMPDIR if it is defined; 981*58997Selan otherwise, from the P_tmpdir macro if that is defined; 982*58997Selan otherwise, in /usr/tmp or /tmp. */ 983*58997Selan 984*58997Selan static char *temp_filename; 985*58997Selan 986*58997Selan /* Length of the prefix. */ 987*58997Selan 988*58997Selan static int temp_filename_length; 989*58997Selan 990*58997Selan /* Define the list of temporary files to delete. */ 991*58997Selan 992*58997Selan struct temp_file 993*58997Selan { 994*58997Selan char *name; 995*58997Selan struct temp_file *next; 996*58997Selan }; 997*58997Selan 998*58997Selan /* Queue of files to delete on success or failure of compilation. */ 999*58997Selan static struct temp_file *always_delete_queue; 1000*58997Selan /* Queue of files to delete on failure of compilation. */ 1001*58997Selan static struct temp_file *failure_delete_queue; 1002*58997Selan 1003*58997Selan /* Record FILENAME as a file to be deleted automatically. 1004*58997Selan ALWAYS_DELETE nonzero means delete it if all compilation succeeds; 1005*58997Selan otherwise delete it in any case. 1006*58997Selan FAIL_DELETE nonzero means delete it if a compilation step fails; 1007*58997Selan otherwise delete it in any case. */ 1008*58997Selan 1009*58997Selan static void 1010*58997Selan record_temp_file (filename, always_delete, fail_delete) 1011*58997Selan char *filename; 1012*58997Selan int always_delete; 1013*58997Selan int fail_delete; 1014*58997Selan { 1015*58997Selan register char *name; 1016*58997Selan name = xmalloc (strlen (filename) + 1); 1017*58997Selan strcpy (name, filename); 1018*58997Selan 1019*58997Selan if (always_delete) 1020*58997Selan { 1021*58997Selan register struct temp_file *temp; 1022*58997Selan for (temp = always_delete_queue; temp; temp = temp->next) 1023*58997Selan if (! strcmp (name, temp->name)) 1024*58997Selan goto already1; 1025*58997Selan temp = (struct temp_file *) xmalloc (sizeof (struct temp_file)); 1026*58997Selan temp->next = always_delete_queue; 1027*58997Selan temp->name = name; 1028*58997Selan always_delete_queue = temp; 1029*58997Selan already1:; 1030*58997Selan } 1031*58997Selan 1032*58997Selan if (fail_delete) 1033*58997Selan { 1034*58997Selan register struct temp_file *temp; 1035*58997Selan for (temp = failure_delete_queue; temp; temp = temp->next) 1036*58997Selan if (! strcmp (name, temp->name)) 1037*58997Selan goto already2; 1038*58997Selan temp = (struct temp_file *) xmalloc (sizeof (struct temp_file)); 1039*58997Selan temp->next = failure_delete_queue; 1040*58997Selan temp->name = name; 1041*58997Selan failure_delete_queue = temp; 1042*58997Selan already2:; 1043*58997Selan } 1044*58997Selan } 1045*58997Selan 1046*58997Selan /* Delete all the temporary files whose names we previously recorded. */ 1047*58997Selan 1048*58997Selan static void 1049*58997Selan delete_temp_files () 1050*58997Selan { 1051*58997Selan register struct temp_file *temp; 1052*58997Selan 1053*58997Selan for (temp = always_delete_queue; temp; temp = temp->next) 1054*58997Selan { 1055*58997Selan #ifdef DEBUG 1056*58997Selan int i; 1057*58997Selan printf ("Delete %s? (y or n) ", temp->name); 1058*58997Selan fflush (stdout); 1059*58997Selan i = getchar (); 1060*58997Selan if (i != '\n') 1061*58997Selan while (getchar () != '\n') ; 1062*58997Selan if (i == 'y' || i == 'Y') 1063*58997Selan #endif /* DEBUG */ 1064*58997Selan { 1065*58997Selan struct stat st; 1066*58997Selan if (stat (temp->name, &st) >= 0) 1067*58997Selan { 1068*58997Selan /* Delete only ordinary files. */ 1069*58997Selan if (S_ISREG (st.st_mode)) 1070*58997Selan if (unlink (temp->name) < 0) 1071*58997Selan if (verbose_flag) 1072*58997Selan perror_with_name (temp->name); 1073*58997Selan } 1074*58997Selan } 1075*58997Selan } 1076*58997Selan 1077*58997Selan always_delete_queue = 0; 1078*58997Selan } 1079*58997Selan 1080*58997Selan /* Delete all the files to be deleted on error. */ 1081*58997Selan 1082*58997Selan static void 1083*58997Selan delete_failure_queue () 1084*58997Selan { 1085*58997Selan register struct temp_file *temp; 1086*58997Selan 1087*58997Selan for (temp = failure_delete_queue; temp; temp = temp->next) 1088*58997Selan { 1089*58997Selan #ifdef DEBUG 1090*58997Selan int i; 1091*58997Selan printf ("Delete %s? (y or n) ", temp->name); 1092*58997Selan fflush (stdout); 1093*58997Selan i = getchar (); 1094*58997Selan if (i != '\n') 1095*58997Selan while (getchar () != '\n') ; 1096*58997Selan if (i == 'y' || i == 'Y') 1097*58997Selan #endif /* DEBUG */ 1098*58997Selan { 1099*58997Selan if (unlink (temp->name) < 0) 1100*58997Selan if (verbose_flag) 1101*58997Selan perror_with_name (temp->name); 1102*58997Selan } 1103*58997Selan } 1104*58997Selan } 1105*58997Selan 1106*58997Selan static void 1107*58997Selan clear_failure_queue () 1108*58997Selan { 1109*58997Selan failure_delete_queue = 0; 1110*58997Selan } 1111*58997Selan 1112*58997Selan /* Compute a string to use as the base of all temporary file names. 1113*58997Selan It is substituted for %g. */ 1114*58997Selan 1115*58997Selan static void 1116*58997Selan choose_temp_base () 1117*58997Selan { 1118*58997Selan char *base = getenv ("TMPDIR"); 1119*58997Selan int len; 1120*58997Selan 1121*58997Selan if (base == (char *)0) 1122*58997Selan { 1123*58997Selan #ifdef P_tmpdir 1124*58997Selan if (access (P_tmpdir, R_OK | W_OK) == 0) 1125*58997Selan base = P_tmpdir; 1126*58997Selan #endif 1127*58997Selan if (base == (char *)0) 1128*58997Selan { 1129*58997Selan if (access ("/usr/tmp", R_OK | W_OK) == 0) 1130*58997Selan base = "/usr/tmp/"; 1131*58997Selan else 1132*58997Selan base = "/tmp/"; 1133*58997Selan } 1134*58997Selan } 1135*58997Selan 1136*58997Selan len = strlen (base); 1137*58997Selan temp_filename = xmalloc (len + sizeof("/ccXXXXXX")); 1138*58997Selan strcpy (temp_filename, base); 1139*58997Selan if (len > 0 && temp_filename[len-1] != '/') 1140*58997Selan temp_filename[len++] = '/'; 1141*58997Selan strcpy (temp_filename + len, "ccXXXXXX"); 1142*58997Selan 1143*58997Selan mktemp (temp_filename); 1144*58997Selan temp_filename_length = strlen (temp_filename); 1145*58997Selan if (temp_filename_length == 0) 1146*58997Selan abort (); 1147*58997Selan } 1148*58997Selan 1149*58997Selan 1150*58997Selan /* Routine to add variables to the environment. We do this to pass 1151*58997Selan the pathname of the gcc driver, and the directories search to the 1152*58997Selan collect2 program, which is being run as ld. This way, we can be 1153*58997Selan sure of executing the right compiler when collect2 wants to build 1154*58997Selan constructors and destructors. Since the environment variables we 1155*58997Selan use come from an obstack, we don't have to worry about allocating 1156*58997Selan space for them. */ 1157*58997Selan 1158*58997Selan #ifndef HAVE_PUTENV 1159*58997Selan 1160*58997Selan putenv (str) 1161*58997Selan char *str; 1162*58997Selan { 1163*58997Selan #ifndef VMS /* nor about VMS */ 1164*58997Selan 1165*58997Selan extern char **environ; 1166*58997Selan char **old_environ = environ; 1167*58997Selan char **envp; 1168*58997Selan int num_envs = 0; 1169*58997Selan int name_len = 1; 1170*58997Selan int str_len = strlen (str); 1171*58997Selan char *p = str; 1172*58997Selan int ch; 1173*58997Selan 1174*58997Selan while ((ch = *p++) != '\0' && ch != '=') 1175*58997Selan name_len++; 1176*58997Selan 1177*58997Selan if (!ch) 1178*58997Selan abort (); 1179*58997Selan 1180*58997Selan /* Search for replacing an existing environment variable, and 1181*58997Selan count the number of total environment variables. */ 1182*58997Selan for (envp = old_environ; *envp; envp++) 1183*58997Selan { 1184*58997Selan num_envs++; 1185*58997Selan if (!strncmp (str, *envp, name_len)) 1186*58997Selan { 1187*58997Selan *envp = str; 1188*58997Selan return; 1189*58997Selan } 1190*58997Selan } 1191*58997Selan 1192*58997Selan /* Add a new environment variable */ 1193*58997Selan environ = (char **) xmalloc (sizeof (char *) * (num_envs+2)); 1194*58997Selan *environ = str; 1195*58997Selan bcopy (old_environ, environ+1, sizeof (char *) * (num_envs+1)); 1196*58997Selan 1197*58997Selan #endif /* VMS */ 1198*58997Selan } 1199*58997Selan 1200*58997Selan #endif /* HAVE_PUTENV */ 1201*58997Selan 1202*58997Selan 1203*58997Selan /* Rebuild the COMPILER_PATH and LIBRARY_PATH environment variables for collect. */ 1204*58997Selan 1205*58997Selan static void 1206*58997Selan putenv_from_prefixes (paths, env_var) 1207*58997Selan struct path_prefix *paths; 1208*58997Selan char *env_var; 1209*58997Selan { 1210*58997Selan int suffix_len = (machine_suffix) ? strlen (machine_suffix) : 0; 1211*58997Selan int first_time = TRUE; 1212*58997Selan struct prefix_list *pprefix; 1213*58997Selan 1214*58997Selan obstack_grow (&collect_obstack, env_var, strlen (env_var)); 1215*58997Selan 1216*58997Selan for (pprefix = paths->plist; pprefix != 0; pprefix = pprefix->next) 1217*58997Selan { 1218*58997Selan int len = strlen (pprefix->prefix); 1219*58997Selan 1220*58997Selan if (machine_suffix) 1221*58997Selan { 1222*58997Selan if (!first_time) 1223*58997Selan obstack_grow (&collect_obstack, ":", 1); 1224*58997Selan 1225*58997Selan first_time = FALSE; 1226*58997Selan obstack_grow (&collect_obstack, pprefix->prefix, len); 1227*58997Selan obstack_grow (&collect_obstack, machine_suffix, suffix_len); 1228*58997Selan } 1229*58997Selan 1230*58997Selan if (just_machine_suffix && pprefix->require_machine_suffix == 2) 1231*58997Selan { 1232*58997Selan if (!first_time) 1233*58997Selan obstack_grow (&collect_obstack, ":", 1); 1234*58997Selan 1235*58997Selan first_time = FALSE; 1236*58997Selan obstack_grow (&collect_obstack, pprefix->prefix, len); 1237*58997Selan obstack_grow (&collect_obstack, machine_suffix, suffix_len); 1238*58997Selan } 1239*58997Selan 1240*58997Selan if (!pprefix->require_machine_suffix) 1241*58997Selan { 1242*58997Selan if (!first_time) 1243*58997Selan obstack_grow (&collect_obstack, ":", 1); 1244*58997Selan 1245*58997Selan first_time = FALSE; 1246*58997Selan obstack_grow (&collect_obstack, pprefix->prefix, len); 1247*58997Selan } 1248*58997Selan } 1249*58997Selan obstack_grow (&collect_obstack, "\0", 1); 1250*58997Selan putenv (obstack_finish (&collect_obstack)); 1251*58997Selan } 1252*58997Selan 1253*58997Selan 1254*58997Selan /* Search for NAME using the prefix list PREFIXES. MODE is passed to 1255*58997Selan access to check permissions. 1256*58997Selan Return 0 if not found, otherwise return its name, allocated with malloc. */ 1257*58997Selan 1258*58997Selan static char * 1259*58997Selan find_a_file (pprefix, name, mode) 1260*58997Selan struct path_prefix *pprefix; 1261*58997Selan char *name; 1262*58997Selan int mode; 1263*58997Selan { 1264*58997Selan char *temp; 1265*58997Selan char *file_suffix = ((mode & X_OK) != 0 ? EXECUTABLE_SUFFIX : ""); 1266*58997Selan struct prefix_list *pl; 1267*58997Selan int len = pprefix->max_len + strlen (name) + strlen (file_suffix) + 1; 1268*58997Selan 1269*58997Selan if (machine_suffix) 1270*58997Selan len += strlen (machine_suffix); 1271*58997Selan 1272*58997Selan temp = xmalloc (len); 1273*58997Selan 1274*58997Selan /* Determine the filename to execute (special case for absolute paths). */ 1275*58997Selan 1276*58997Selan if (*name == '/') 1277*58997Selan { 1278*58997Selan if (access (name, mode)) 1279*58997Selan { 1280*58997Selan strcpy (temp, name); 1281*58997Selan return temp; 1282*58997Selan } 1283*58997Selan } 1284*58997Selan else 1285*58997Selan for (pl = pprefix->plist; pl; pl = pl->next) 1286*58997Selan { 1287*58997Selan if (machine_suffix) 1288*58997Selan { 1289*58997Selan strcpy (temp, pl->prefix); 1290*58997Selan strcat (temp, machine_suffix); 1291*58997Selan strcat (temp, name); 1292*58997Selan if (access (temp, mode) == 0) 1293*58997Selan { 1294*58997Selan if (pl->used_flag_ptr != 0) 1295*58997Selan *pl->used_flag_ptr = 1; 1296*58997Selan return temp; 1297*58997Selan } 1298*58997Selan /* Some systems have a suffix for executable files. 1299*58997Selan So try appending that. */ 1300*58997Selan if (file_suffix[0] != 0) 1301*58997Selan { 1302*58997Selan strcat (temp, file_suffix); 1303*58997Selan if (access (temp, mode) == 0) 1304*58997Selan { 1305*58997Selan if (pl->used_flag_ptr != 0) 1306*58997Selan *pl->used_flag_ptr = 1; 1307*58997Selan return temp; 1308*58997Selan } 1309*58997Selan } 1310*58997Selan } 1311*58997Selan /* Certain prefixes are tried with just the machine type, 1312*58997Selan not the version. This is used for finding as, ld, etc. */ 1313*58997Selan if (just_machine_suffix && pl->require_machine_suffix == 2) 1314*58997Selan { 1315*58997Selan strcpy (temp, pl->prefix); 1316*58997Selan strcat (temp, just_machine_suffix); 1317*58997Selan strcat (temp, name); 1318*58997Selan if (access (temp, mode) == 0) 1319*58997Selan { 1320*58997Selan if (pl->used_flag_ptr != 0) 1321*58997Selan *pl->used_flag_ptr = 1; 1322*58997Selan return temp; 1323*58997Selan } 1324*58997Selan /* Some systems have a suffix for executable files. 1325*58997Selan So try appending that. */ 1326*58997Selan if (file_suffix[0] != 0) 1327*58997Selan { 1328*58997Selan strcat (temp, file_suffix); 1329*58997Selan if (access (temp, mode) == 0) 1330*58997Selan { 1331*58997Selan if (pl->used_flag_ptr != 0) 1332*58997Selan *pl->used_flag_ptr = 1; 1333*58997Selan return temp; 1334*58997Selan } 1335*58997Selan } 1336*58997Selan } 1337*58997Selan /* Certain prefixes can't be used without the machine suffix 1338*58997Selan when the machine or version is explicitly specified. */ 1339*58997Selan if (!pl->require_machine_suffix) 1340*58997Selan { 1341*58997Selan strcpy (temp, pl->prefix); 1342*58997Selan strcat (temp, name); 1343*58997Selan if (access (temp, mode) == 0) 1344*58997Selan { 1345*58997Selan if (pl->used_flag_ptr != 0) 1346*58997Selan *pl->used_flag_ptr = 1; 1347*58997Selan return temp; 1348*58997Selan } 1349*58997Selan /* Some systems have a suffix for executable files. 1350*58997Selan So try appending that. */ 1351*58997Selan if (file_suffix[0] != 0) 1352*58997Selan { 1353*58997Selan strcat (temp, file_suffix); 1354*58997Selan if (access (temp, mode) == 0) 1355*58997Selan { 1356*58997Selan if (pl->used_flag_ptr != 0) 1357*58997Selan *pl->used_flag_ptr = 1; 1358*58997Selan return temp; 1359*58997Selan } 1360*58997Selan } 1361*58997Selan } 1362*58997Selan } 1363*58997Selan 1364*58997Selan free (temp); 1365*58997Selan return 0; 1366*58997Selan } 1367*58997Selan 1368*58997Selan /* Add an entry for PREFIX in PLIST. If FIRST is set, it goes 1369*58997Selan at the start of the list, otherwise it goes at the end. 1370*58997Selan 1371*58997Selan If WARN is nonzero, we will warn if no file is found 1372*58997Selan through this prefix. WARN should point to an int 1373*58997Selan which will be set to 1 if this entry is used. 1374*58997Selan 1375*58997Selan REQUIRE_MACHINE_SUFFIX is 1 if this prefix can't be used without 1376*58997Selan the complete value of machine_suffix. 1377*58997Selan 2 means try both machine_suffix and just_machine_suffix. */ 1378*58997Selan 1379*58997Selan static void 1380*58997Selan add_prefix (pprefix, prefix, first, require_machine_suffix, warn) 1381*58997Selan struct path_prefix *pprefix; 1382*58997Selan char *prefix; 1383*58997Selan int first; 1384*58997Selan int require_machine_suffix; 1385*58997Selan int *warn; 1386*58997Selan { 1387*58997Selan struct prefix_list *pl, **prev; 1388*58997Selan int len; 1389*58997Selan 1390*58997Selan if (!first && pprefix->plist) 1391*58997Selan { 1392*58997Selan for (pl = pprefix->plist; pl->next; pl = pl->next) 1393*58997Selan ; 1394*58997Selan prev = &pl->next; 1395*58997Selan } 1396*58997Selan else 1397*58997Selan prev = &pprefix->plist; 1398*58997Selan 1399*58997Selan /* Keep track of the longest prefix */ 1400*58997Selan 1401*58997Selan len = strlen (prefix); 1402*58997Selan if (len > pprefix->max_len) 1403*58997Selan pprefix->max_len = len; 1404*58997Selan 1405*58997Selan pl = (struct prefix_list *) xmalloc (sizeof (struct prefix_list)); 1406*58997Selan pl->prefix = save_string (prefix, len); 1407*58997Selan pl->require_machine_suffix = require_machine_suffix; 1408*58997Selan pl->used_flag_ptr = warn; 1409*58997Selan if (warn) 1410*58997Selan *warn = 0; 1411*58997Selan 1412*58997Selan if (*prev) 1413*58997Selan pl->next = *prev; 1414*58997Selan else 1415*58997Selan pl->next = (struct prefix_list *) 0; 1416*58997Selan *prev = pl; 1417*58997Selan } 1418*58997Selan 1419*58997Selan /* Print warnings for any prefixes in the list PPREFIX that were not used. */ 1420*58997Selan 1421*58997Selan static void 1422*58997Selan unused_prefix_warnings (pprefix) 1423*58997Selan struct path_prefix *pprefix; 1424*58997Selan { 1425*58997Selan struct prefix_list *pl = pprefix->plist; 1426*58997Selan 1427*58997Selan while (pl) 1428*58997Selan { 1429*58997Selan if (pl->used_flag_ptr != 0 && !*pl->used_flag_ptr) 1430*58997Selan { 1431*58997Selan error ("file path prefix `%s' never used", 1432*58997Selan pl->prefix); 1433*58997Selan /* Prevent duplicate warnings. */ 1434*58997Selan *pl->used_flag_ptr = 1; 1435*58997Selan } 1436*58997Selan pl = pl->next; 1437*58997Selan } 1438*58997Selan } 1439*58997Selan 1440*58997Selan /* Get rid of all prefixes built up so far in *PLISTP. */ 1441*58997Selan 1442*58997Selan static void 1443*58997Selan free_path_prefix (pprefix) 1444*58997Selan struct path_prefix *pprefix; 1445*58997Selan { 1446*58997Selan struct prefix_list *pl = pprefix->plist; 1447*58997Selan struct prefix_list *temp; 1448*58997Selan 1449*58997Selan while (pl) 1450*58997Selan { 1451*58997Selan temp = pl; 1452*58997Selan pl = pl->next; 1453*58997Selan free (temp->prefix); 1454*58997Selan free ((char *) temp); 1455*58997Selan } 1456*58997Selan pprefix->plist = (struct prefix_list *) 0; 1457*58997Selan } 1458*58997Selan 1459*58997Selan /* stdin file number. */ 1460*58997Selan #define STDIN_FILE_NO 0 1461*58997Selan 1462*58997Selan /* stdout file number. */ 1463*58997Selan #define STDOUT_FILE_NO 1 1464*58997Selan 1465*58997Selan /* value of `pipe': port index for reading. */ 1466*58997Selan #define READ_PORT 0 1467*58997Selan 1468*58997Selan /* value of `pipe': port index for writing. */ 1469*58997Selan #define WRITE_PORT 1 1470*58997Selan 1471*58997Selan /* Pipe waiting from last process, to be used as input for the next one. 1472*58997Selan Value is STDIN_FILE_NO if no pipe is waiting 1473*58997Selan (i.e. the next command is the first of a group). */ 1474*58997Selan 1475*58997Selan static int last_pipe_input; 1476*58997Selan 1477*58997Selan /* Fork one piped subcommand. FUNC is the system call to use 1478*58997Selan (either execv or execvp). ARGV is the arg vector to use. 1479*58997Selan NOT_LAST is nonzero if this is not the last subcommand 1480*58997Selan (i.e. its output should be piped to the next one.) */ 1481*58997Selan 1482*58997Selan #ifndef OS2 1483*58997Selan #ifdef __MSDOS__ 1484*58997Selan 1485*58997Selan /* Declare these to avoid compilation error. They won't be called. */ 1486*58997Selan int execv(const char *a, const char **b){} 1487*58997Selan int execvp(const char *a, const char **b){} 1488*58997Selan 1489*58997Selan static int 1490*58997Selan pexecute (search_flag, program, argv, not_last) 1491*58997Selan int search_flag; 1492*58997Selan char *program; 1493*58997Selan char *argv[]; 1494*58997Selan int not_last; 1495*58997Selan { 1496*58997Selan char *scmd; 1497*58997Selan FILE *argfile; 1498*58997Selan int i; 1499*58997Selan 1500*58997Selan scmd = (char *)malloc (strlen (program) + strlen (temp_filename) + 6); 1501*58997Selan sprintf (scmd, "%s @%s.gp", program, temp_filename); 1502*58997Selan argfile = fopen (scmd+strlen (program) + 2, "w"); 1503*58997Selan if (argfile == 0) 1504*58997Selan pfatal_with_name (scmd + strlen (program) + 2); 1505*58997Selan 1506*58997Selan for (i=1; argv[i]; i++) 1507*58997Selan { 1508*58997Selan char *cp; 1509*58997Selan for (cp = argv[i]; *cp; cp++) 1510*58997Selan { 1511*58997Selan if (*cp == '"' || *cp == '\'' || *cp == '\\' || isspace (*cp)) 1512*58997Selan fputc ('\\', argfile); 1513*58997Selan fputc (*cp, argfile); 1514*58997Selan } 1515*58997Selan fputc ('\n', argfile); 1516*58997Selan } 1517*58997Selan fclose (argfile); 1518*58997Selan 1519*58997Selan i = system (scmd); 1520*58997Selan 1521*58997Selan remove (scmd + strlen (program) + 2); 1522*58997Selan return i << 8; 1523*58997Selan } 1524*58997Selan 1525*58997Selan #else /* not __MSDOS__ */ 1526*58997Selan 1527*58997Selan static int 1528*58997Selan pexecute (search_flag, program, argv, not_last) 1529*58997Selan int search_flag; 1530*58997Selan char *program; 1531*58997Selan char *argv[]; 1532*58997Selan int not_last; 1533*58997Selan { 1534*58997Selan int (*func)() = (search_flag ? execv : execvp); 1535*58997Selan int pid; 1536*58997Selan int pdes[2]; 1537*58997Selan int input_desc = last_pipe_input; 1538*58997Selan int output_desc = STDOUT_FILE_NO; 1539*58997Selan int retries, sleep_interval; 1540*58997Selan 1541*58997Selan /* If this isn't the last process, make a pipe for its output, 1542*58997Selan and record it as waiting to be the input to the next process. */ 1543*58997Selan 1544*58997Selan if (not_last) 1545*58997Selan { 1546*58997Selan if (pipe (pdes) < 0) 1547*58997Selan pfatal_with_name ("pipe"); 1548*58997Selan output_desc = pdes[WRITE_PORT]; 1549*58997Selan last_pipe_input = pdes[READ_PORT]; 1550*58997Selan } 1551*58997Selan else 1552*58997Selan last_pipe_input = STDIN_FILE_NO; 1553*58997Selan 1554*58997Selan /* Fork a subprocess; wait and retry if it fails. */ 1555*58997Selan sleep_interval = 1; 1556*58997Selan for (retries = 0; retries < 4; retries++) 1557*58997Selan { 1558*58997Selan pid = vfork (); 1559*58997Selan if (pid >= 0) 1560*58997Selan break; 1561*58997Selan sleep (sleep_interval); 1562*58997Selan sleep_interval *= 2; 1563*58997Selan } 1564*58997Selan 1565*58997Selan switch (pid) 1566*58997Selan { 1567*58997Selan case -1: 1568*58997Selan #ifdef vfork 1569*58997Selan pfatal_with_name ("fork"); 1570*58997Selan #else 1571*58997Selan pfatal_with_name ("vfork"); 1572*58997Selan #endif 1573*58997Selan /* NOTREACHED */ 1574*58997Selan return 0; 1575*58997Selan 1576*58997Selan case 0: /* child */ 1577*58997Selan /* Move the input and output pipes into place, if nec. */ 1578*58997Selan if (input_desc != STDIN_FILE_NO) 1579*58997Selan { 1580*58997Selan close (STDIN_FILE_NO); 1581*58997Selan dup (input_desc); 1582*58997Selan close (input_desc); 1583*58997Selan } 1584*58997Selan if (output_desc != STDOUT_FILE_NO) 1585*58997Selan { 1586*58997Selan close (STDOUT_FILE_NO); 1587*58997Selan dup (output_desc); 1588*58997Selan close (output_desc); 1589*58997Selan } 1590*58997Selan 1591*58997Selan /* Close the parent's descs that aren't wanted here. */ 1592*58997Selan if (last_pipe_input != STDIN_FILE_NO) 1593*58997Selan close (last_pipe_input); 1594*58997Selan 1595*58997Selan /* Exec the program. */ 1596*58997Selan (*func) (program, argv); 1597*58997Selan perror_exec (program); 1598*58997Selan exit (-1); 1599*58997Selan /* NOTREACHED */ 1600*58997Selan return 0; 1601*58997Selan 1602*58997Selan default: 1603*58997Selan /* In the parent, after forking. 1604*58997Selan Close the descriptors that we made for this child. */ 1605*58997Selan if (input_desc != STDIN_FILE_NO) 1606*58997Selan close (input_desc); 1607*58997Selan if (output_desc != STDOUT_FILE_NO) 1608*58997Selan close (output_desc); 1609*58997Selan 1610*58997Selan /* Return child's process number. */ 1611*58997Selan return pid; 1612*58997Selan } 1613*58997Selan } 1614*58997Selan 1615*58997Selan #endif /* not __MSDOS__ */ 1616*58997Selan #else /* not OS2 */ 1617*58997Selan 1618*58997Selan static int 1619*58997Selan pexecute (search_flag, program, argv, not_last) 1620*58997Selan int search_flag; 1621*58997Selan char *program; 1622*58997Selan char *argv[]; 1623*58997Selan int not_last; 1624*58997Selan { 1625*58997Selan return (search_flag ? spawnv : spawnvp) (1, program, argv); 1626*58997Selan } 1627*58997Selan #endif /* not OS2 */ 1628*58997Selan 1629*58997Selan /* Execute the command specified by the arguments on the current line of spec. 1630*58997Selan When using pipes, this includes several piped-together commands 1631*58997Selan with `|' between them. 1632*58997Selan 1633*58997Selan Return 0 if successful, -1 if failed. */ 1634*58997Selan 1635*58997Selan static int 1636*58997Selan execute () 1637*58997Selan { 1638*58997Selan int i; 1639*58997Selan int n_commands; /* # of command. */ 1640*58997Selan char *string; 1641*58997Selan struct command 1642*58997Selan { 1643*58997Selan char *prog; /* program name. */ 1644*58997Selan char **argv; /* vector of args. */ 1645*58997Selan int pid; /* pid of process for this command. */ 1646*58997Selan }; 1647*58997Selan 1648*58997Selan struct command *commands; /* each command buffer with above info. */ 1649*58997Selan 1650*58997Selan /* Count # of piped commands. */ 1651*58997Selan for (n_commands = 1, i = 0; i < argbuf_index; i++) 1652*58997Selan if (strcmp (argbuf[i], "|") == 0) 1653*58997Selan n_commands++; 1654*58997Selan 1655*58997Selan /* Get storage for each command. */ 1656*58997Selan commands 1657*58997Selan = (struct command *) alloca (n_commands * sizeof (struct command)); 1658*58997Selan 1659*58997Selan /* Split argbuf into its separate piped processes, 1660*58997Selan and record info about each one. 1661*58997Selan Also search for the programs that are to be run. */ 1662*58997Selan 1663*58997Selan commands[0].prog = argbuf[0]; /* first command. */ 1664*58997Selan commands[0].argv = &argbuf[0]; 1665*58997Selan string = find_a_file (&exec_prefix, commands[0].prog, X_OK); 1666*58997Selan if (string) 1667*58997Selan commands[0].argv[0] = string; 1668*58997Selan 1669*58997Selan for (n_commands = 1, i = 0; i < argbuf_index; i++) 1670*58997Selan if (strcmp (argbuf[i], "|") == 0) 1671*58997Selan { /* each command. */ 1672*58997Selan #ifdef __MSDOS__ 1673*58997Selan fatal ("-pipe not supported under MS-DOS"); 1674*58997Selan #endif 1675*58997Selan argbuf[i] = 0; /* termination of command args. */ 1676*58997Selan commands[n_commands].prog = argbuf[i + 1]; 1677*58997Selan commands[n_commands].argv = &argbuf[i + 1]; 1678*58997Selan string = find_a_file (&exec_prefix, commands[n_commands].prog, X_OK); 1679*58997Selan if (string) 1680*58997Selan commands[n_commands].argv[0] = string; 1681*58997Selan n_commands++; 1682*58997Selan } 1683*58997Selan 1684*58997Selan argbuf[argbuf_index] = 0; 1685*58997Selan 1686*58997Selan /* If -v, print what we are about to do, and maybe query. */ 1687*58997Selan 1688*58997Selan if (verbose_flag) 1689*58997Selan { 1690*58997Selan /* Print each piped command as a separate line. */ 1691*58997Selan for (i = 0; i < n_commands ; i++) 1692*58997Selan { 1693*58997Selan char **j; 1694*58997Selan 1695*58997Selan for (j = commands[i].argv; *j; j++) 1696*58997Selan fprintf (stderr, " %s", *j); 1697*58997Selan 1698*58997Selan /* Print a pipe symbol after all but the last command. */ 1699*58997Selan if (i + 1 != n_commands) 1700*58997Selan fprintf (stderr, " |"); 1701*58997Selan fprintf (stderr, "\n"); 1702*58997Selan } 1703*58997Selan fflush (stderr); 1704*58997Selan #ifdef DEBUG 1705*58997Selan fprintf (stderr, "\nGo ahead? (y or n) "); 1706*58997Selan fflush (stderr); 1707*58997Selan i = getchar (); 1708*58997Selan if (i != '\n') 1709*58997Selan while (getchar () != '\n') ; 1710*58997Selan if (i != 'y' && i != 'Y') 1711*58997Selan return 0; 1712*58997Selan #endif /* DEBUG */ 1713*58997Selan } 1714*58997Selan 1715*58997Selan /* Run each piped subprocess. */ 1716*58997Selan 1717*58997Selan last_pipe_input = STDIN_FILE_NO; 1718*58997Selan for (i = 0; i < n_commands; i++) 1719*58997Selan { 1720*58997Selan char *string = commands[i].argv[0]; 1721*58997Selan 1722*58997Selan commands[i].pid = pexecute (string != commands[i].prog, 1723*58997Selan string, commands[i].argv, 1724*58997Selan i + 1 < n_commands); 1725*58997Selan 1726*58997Selan if (string != commands[i].prog) 1727*58997Selan free (string); 1728*58997Selan } 1729*58997Selan 1730*58997Selan execution_count++; 1731*58997Selan 1732*58997Selan /* Wait for all the subprocesses to finish. 1733*58997Selan We don't care what order they finish in; 1734*58997Selan we know that N_COMMANDS waits will get them all. */ 1735*58997Selan 1736*58997Selan { 1737*58997Selan int ret_code = 0; 1738*58997Selan 1739*58997Selan for (i = 0; i < n_commands; i++) 1740*58997Selan { 1741*58997Selan int status; 1742*58997Selan int pid; 1743*58997Selan char *prog; 1744*58997Selan 1745*58997Selan #ifdef __MSDOS__ 1746*58997Selan status = pid = commands[i].pid; 1747*58997Selan #else 1748*58997Selan pid = wait (&status); 1749*58997Selan #endif 1750*58997Selan if (pid < 0) 1751*58997Selan abort (); 1752*58997Selan 1753*58997Selan if (status != 0) 1754*58997Selan { 1755*58997Selan int j; 1756*58997Selan for (j = 0; j < n_commands; j++) 1757*58997Selan if (commands[j].pid == pid) 1758*58997Selan prog = commands[j].prog; 1759*58997Selan 1760*58997Selan if ((status & 0x7F) != 0) 1761*58997Selan { 1762*58997Selan fatal ("Internal compiler error: program %s got fatal signal %d", 1763*58997Selan prog, (status & 0x7F)); 1764*58997Selan signal_count++; 1765*58997Selan } 1766*58997Selan if (((status & 0xFF00) >> 8) >= MIN_FATAL_STATUS) 1767*58997Selan ret_code = -1; 1768*58997Selan } 1769*58997Selan } 1770*58997Selan return ret_code; 1771*58997Selan } 1772*58997Selan } 1773*58997Selan 1774*58997Selan /* Find all the switches given to us 1775*58997Selan and make a vector describing them. 1776*58997Selan The elements of the vector are strings, one per switch given. 1777*58997Selan If a switch uses following arguments, then the `part1' field 1778*58997Selan is the switch itself and the `args' field 1779*58997Selan is a null-terminated vector containing the following arguments. 1780*58997Selan The `valid' field is nonzero if any spec has looked at this switch; 1781*58997Selan if it remains zero at the end of the run, it must be meaningless. */ 1782*58997Selan 1783*58997Selan struct switchstr 1784*58997Selan { 1785*58997Selan char *part1; 1786*58997Selan char **args; 1787*58997Selan int valid; 1788*58997Selan }; 1789*58997Selan 1790*58997Selan static struct switchstr *switches; 1791*58997Selan 1792*58997Selan static int n_switches; 1793*58997Selan 1794*58997Selan struct infile 1795*58997Selan { 1796*58997Selan char *name; 1797*58997Selan char *language; 1798*58997Selan }; 1799*58997Selan 1800*58997Selan /* Also a vector of input files specified. */ 1801*58997Selan 1802*58997Selan static struct infile *infiles; 1803*58997Selan 1804*58997Selan static int n_infiles; 1805*58997Selan 1806*58997Selan /* And a vector of corresponding output files is made up later. */ 1807*58997Selan 1808*58997Selan static char **outfiles; 1809*58997Selan 1810*58997Selan /* Create the vector `switches' and its contents. 1811*58997Selan Store its length in `n_switches'. */ 1812*58997Selan 1813*58997Selan static void 1814*58997Selan process_command (argc, argv) 1815*58997Selan int argc; 1816*58997Selan char **argv; 1817*58997Selan { 1818*58997Selan register int i; 1819*58997Selan char *temp; 1820*58997Selan char *spec_lang = 0; 1821*58997Selan int last_language_n_infiles; 1822*58997Selan 1823*58997Selan gcc_exec_prefix = getenv ("GCC_EXEC_PREFIX"); 1824*58997Selan 1825*58997Selan n_switches = 0; 1826*58997Selan n_infiles = 0; 1827*58997Selan 1828*58997Selan /* Default for -V is our version number, ending at first space. */ 1829*58997Selan spec_version = save_string (version_string, strlen (version_string)); 1830*58997Selan for (temp = spec_version; *temp && *temp != ' '; temp++); 1831*58997Selan if (*temp) *temp = '\0'; 1832*58997Selan 1833*58997Selan /* Set up the default search paths. */ 1834*58997Selan 1835*58997Selan if (gcc_exec_prefix) 1836*58997Selan { 1837*58997Selan add_prefix (&exec_prefix, gcc_exec_prefix, 0, 0, NULL_PTR); 1838*58997Selan add_prefix (&startfile_prefix, gcc_exec_prefix, 0, 0, NULL_PTR); 1839*58997Selan } 1840*58997Selan 1841*58997Selan /* COMPILER_PATH and LIBRARY_PATH have values 1842*58997Selan that are lists of directory names with colons. */ 1843*58997Selan 1844*58997Selan temp = getenv ("COMPILER_PATH"); 1845*58997Selan if (temp) 1846*58997Selan { 1847*58997Selan char *startp, *endp; 1848*58997Selan char *nstore = (char *) alloca (strlen (temp) + 3); 1849*58997Selan 1850*58997Selan startp = endp = temp; 1851*58997Selan while (1) 1852*58997Selan { 1853*58997Selan if (*endp == PATH_SEPARATOR || *endp == 0) 1854*58997Selan { 1855*58997Selan strncpy (nstore, startp, endp-startp); 1856*58997Selan if (endp == startp) 1857*58997Selan { 1858*58997Selan strcpy (nstore, "./"); 1859*58997Selan } 1860*58997Selan else if (endp[-1] != '/') 1861*58997Selan { 1862*58997Selan nstore[endp-startp] = '/'; 1863*58997Selan nstore[endp-startp+1] = 0; 1864*58997Selan } 1865*58997Selan else 1866*58997Selan nstore[endp-startp] = 0; 1867*58997Selan add_prefix (&exec_prefix, nstore, 0, 0, NULL_PTR); 1868*58997Selan if (*endp == 0) 1869*58997Selan break; 1870*58997Selan endp = startp = endp + 1; 1871*58997Selan } 1872*58997Selan else 1873*58997Selan endp++; 1874*58997Selan } 1875*58997Selan } 1876*58997Selan 1877*58997Selan temp = getenv ("LIBRARY_PATH"); 1878*58997Selan if (temp) 1879*58997Selan { 1880*58997Selan char *startp, *endp; 1881*58997Selan char *nstore = (char *) alloca (strlen (temp) + 3); 1882*58997Selan 1883*58997Selan startp = endp = temp; 1884*58997Selan while (1) 1885*58997Selan { 1886*58997Selan if (*endp == PATH_SEPARATOR || *endp == 0) 1887*58997Selan { 1888*58997Selan strncpy (nstore, startp, endp-startp); 1889*58997Selan if (endp == startp) 1890*58997Selan { 1891*58997Selan strcpy (nstore, "./"); 1892*58997Selan } 1893*58997Selan else if (endp[-1] != '/') 1894*58997Selan { 1895*58997Selan nstore[endp-startp] = '/'; 1896*58997Selan nstore[endp-startp+1] = 0; 1897*58997Selan } 1898*58997Selan else 1899*58997Selan nstore[endp-startp] = 0; 1900*58997Selan add_prefix (&startfile_prefix, nstore, 0, 0, NULL_PTR); 1901*58997Selan /* Make separate list of dirs that came from LIBRARY_PATH. */ 1902*58997Selan add_prefix (&library_prefix, nstore, 0, 0, NULL_PTR); 1903*58997Selan if (*endp == 0) 1904*58997Selan break; 1905*58997Selan endp = startp = endp + 1; 1906*58997Selan } 1907*58997Selan else 1908*58997Selan endp++; 1909*58997Selan } 1910*58997Selan } 1911*58997Selan 1912*58997Selan /* Use LPATH like LIBRARY_PATH (for the CMU build program). */ 1913*58997Selan temp = getenv ("LPATH"); 1914*58997Selan if (temp) 1915*58997Selan { 1916*58997Selan char *startp, *endp; 1917*58997Selan char *nstore = (char *) alloca (strlen (temp) + 3); 1918*58997Selan 1919*58997Selan startp = endp = temp; 1920*58997Selan while (1) 1921*58997Selan { 1922*58997Selan if (*endp == PATH_SEPARATOR || *endp == 0) 1923*58997Selan { 1924*58997Selan strncpy (nstore, startp, endp-startp); 1925*58997Selan if (endp == startp) 1926*58997Selan { 1927*58997Selan strcpy (nstore, "./"); 1928*58997Selan } 1929*58997Selan else if (endp[-1] != '/') 1930*58997Selan { 1931*58997Selan nstore[endp-startp] = '/'; 1932*58997Selan nstore[endp-startp+1] = 0; 1933*58997Selan } 1934*58997Selan else 1935*58997Selan nstore[endp-startp] = 0; 1936*58997Selan add_prefix (&startfile_prefix, nstore, 0, 0, NULL_PTR); 1937*58997Selan /* Make separate list of dirs that came from LIBRARY_PATH. */ 1938*58997Selan add_prefix (&library_prefix, nstore, 0, 0, NULL_PTR); 1939*58997Selan if (*endp == 0) 1940*58997Selan break; 1941*58997Selan endp = startp = endp + 1; 1942*58997Selan } 1943*58997Selan else 1944*58997Selan endp++; 1945*58997Selan } 1946*58997Selan } 1947*58997Selan 1948*58997Selan /* Scan argv twice. Here, the first time, just count how many switches 1949*58997Selan there will be in their vector, and how many input files in theirs. 1950*58997Selan Here we also parse the switches that cc itself uses (e.g. -v). */ 1951*58997Selan 1952*58997Selan for (i = 1; i < argc; i++) 1953*58997Selan { 1954*58997Selan if (! strcmp (argv[i], "-dumpspecs")) 1955*58997Selan { 1956*58997Selan printf ("*asm:\n%s\n\n", asm_spec); 1957*58997Selan printf ("*asm_final:\n%s\n\n", asm_final_spec); 1958*58997Selan printf ("*cpp:\n%s\n\n", cpp_spec); 1959*58997Selan printf ("*cc1:\n%s\n\n", cc1_spec); 1960*58997Selan printf ("*cc1plus:\n%s\n\n", cc1plus_spec); 1961*58997Selan printf ("*endfile:\n%s\n\n", endfile_spec); 1962*58997Selan printf ("*link:\n%s\n\n", link_spec); 1963*58997Selan printf ("*lib:\n%s\n\n", lib_spec); 1964*58997Selan printf ("*startfile:\n%s\n\n", startfile_spec); 1965*58997Selan printf ("*switches_need_spaces:\n%s\n\n", switches_need_spaces); 1966*58997Selan printf ("*signed_char:\n%s\n\n", signed_char_spec); 1967*58997Selan printf ("*predefines:\n%s\n\n", cpp_predefines); 1968*58997Selan printf ("*cross_compile:\n%d\n\n", cross_compile); 1969*58997Selan 1970*58997Selan exit (0); 1971*58997Selan } 1972*58997Selan else if (! strcmp (argv[i], "-dumpversion")) 1973*58997Selan { 1974*58997Selan printf ("%s\n", version_string); 1975*58997Selan exit (0); 1976*58997Selan } 1977*58997Selan else if (! strcmp (argv[i], "-print-libgcc-file-name")) 1978*58997Selan { 1979*58997Selan print_libgcc_file_name = 1; 1980*58997Selan } 1981*58997Selan else if (! strcmp (argv[i], "-Xlinker")) 1982*58997Selan { 1983*58997Selan /* Pass the argument of this option to the linker when we link. */ 1984*58997Selan 1985*58997Selan if (i + 1 == argc) 1986*58997Selan fatal ("argument to `-Xlinker' is missing"); 1987*58997Selan 1988*58997Selan n_linker_options++; 1989*58997Selan if (!linker_options) 1990*58997Selan linker_options 1991*58997Selan = (char **) xmalloc (n_linker_options * sizeof (char **)); 1992*58997Selan else 1993*58997Selan linker_options 1994*58997Selan = (char **) xrealloc (linker_options, 1995*58997Selan n_linker_options * sizeof (char **)); 1996*58997Selan 1997*58997Selan linker_options[n_linker_options - 1] = argv[++i]; 1998*58997Selan } 1999*58997Selan else if (! strncmp (argv[i], "-Wl,", 4)) 2000*58997Selan { 2001*58997Selan int prev, j; 2002*58997Selan /* Pass the rest of this option to the linker when we link. */ 2003*58997Selan 2004*58997Selan n_linker_options++; 2005*58997Selan if (!linker_options) 2006*58997Selan linker_options 2007*58997Selan = (char **) xmalloc (n_linker_options * sizeof (char **)); 2008*58997Selan else 2009*58997Selan linker_options 2010*58997Selan = (char **) xrealloc (linker_options, 2011*58997Selan n_linker_options * sizeof (char **)); 2012*58997Selan 2013*58997Selan /* Split the argument at commas. */ 2014*58997Selan prev = 4; 2015*58997Selan for (j = 4; argv[i][j]; j++) 2016*58997Selan if (argv[i][j] == ',') 2017*58997Selan { 2018*58997Selan linker_options[n_linker_options - 1] 2019*58997Selan = save_string (argv[i] + prev, j - prev); 2020*58997Selan n_linker_options++; 2021*58997Selan linker_options 2022*58997Selan = (char **) xrealloc (linker_options, 2023*58997Selan n_linker_options * sizeof (char **)); 2024*58997Selan prev = j + 1; 2025*58997Selan } 2026*58997Selan /* Record the part after the last comma. */ 2027*58997Selan linker_options[n_linker_options - 1] = argv[i] + prev; 2028*58997Selan } 2029*58997Selan else if (! strncmp (argv[i], "-Wa,", 4)) 2030*58997Selan { 2031*58997Selan int prev, j; 2032*58997Selan /* Pass the rest of this option to the assembler. */ 2033*58997Selan 2034*58997Selan n_assembler_options++; 2035*58997Selan if (!assembler_options) 2036*58997Selan assembler_options 2037*58997Selan = (char **) xmalloc (n_assembler_options * sizeof (char **)); 2038*58997Selan else 2039*58997Selan assembler_options 2040*58997Selan = (char **) xrealloc (assembler_options, 2041*58997Selan n_assembler_options * sizeof (char **)); 2042*58997Selan 2043*58997Selan /* Split the argument at commas. */ 2044*58997Selan prev = 4; 2045*58997Selan for (j = 4; argv[i][j]; j++) 2046*58997Selan if (argv[i][j] == ',') 2047*58997Selan { 2048*58997Selan assembler_options[n_assembler_options - 1] 2049*58997Selan = save_string (argv[i] + prev, j - prev); 2050*58997Selan n_assembler_options++; 2051*58997Selan assembler_options 2052*58997Selan = (char **) xrealloc (assembler_options, 2053*58997Selan n_assembler_options * sizeof (char **)); 2054*58997Selan prev = j + 1; 2055*58997Selan } 2056*58997Selan /* Record the part after the last comma. */ 2057*58997Selan assembler_options[n_assembler_options - 1] = argv[i] + prev; 2058*58997Selan } 2059*58997Selan else if (argv[i][0] == '+' && argv[i][1] == 'e') 2060*58997Selan /* Compensate for the +e options to the C++ front-end. */ 2061*58997Selan n_switches++; 2062*58997Selan else if (argv[i][0] == '-' && argv[i][1] != 0 && argv[i][1] != 'l') 2063*58997Selan { 2064*58997Selan register char *p = &argv[i][1]; 2065*58997Selan register int c = *p; 2066*58997Selan 2067*58997Selan switch (c) 2068*58997Selan { 2069*58997Selan case 'b': 2070*58997Selan if (p[1] == 0 && i + 1 == argc) 2071*58997Selan fatal ("argument to `-b' is missing"); 2072*58997Selan if (p[1] == 0) 2073*58997Selan spec_machine = argv[++i]; 2074*58997Selan else 2075*58997Selan spec_machine = p + 1; 2076*58997Selan break; 2077*58997Selan 2078*58997Selan case 'B': 2079*58997Selan { 2080*58997Selan int *temp = (int *) xmalloc (sizeof (int)); 2081*58997Selan char *value; 2082*58997Selan if (p[1] == 0 && i + 1 == argc) 2083*58997Selan fatal ("argument to `-B' is missing"); 2084*58997Selan if (p[1] == 0) 2085*58997Selan value = argv[++i]; 2086*58997Selan else 2087*58997Selan value = p + 1; 2088*58997Selan add_prefix (&exec_prefix, value, 1, 0, temp); 2089*58997Selan add_prefix (&startfile_prefix, value, 1, 0, temp); 2090*58997Selan } 2091*58997Selan break; 2092*58997Selan 2093*58997Selan case 'v': /* Print our subcommands and print versions. */ 2094*58997Selan n_switches++; 2095*58997Selan /* If they do anything other than exactly `-v', don't set 2096*58997Selan verbose_flag; rather, continue on to give the error. */ 2097*58997Selan if (p[1] != 0) 2098*58997Selan break; 2099*58997Selan verbose_flag++; 2100*58997Selan break; 2101*58997Selan 2102*58997Selan case 'V': 2103*58997Selan if (p[1] == 0 && i + 1 == argc) 2104*58997Selan fatal ("argument to `-V' is missing"); 2105*58997Selan if (p[1] == 0) 2106*58997Selan spec_version = argv[++i]; 2107*58997Selan else 2108*58997Selan spec_version = p + 1; 2109*58997Selan break; 2110*58997Selan 2111*58997Selan case 's': 2112*58997Selan if (!strcmp (p, "save-temps")) 2113*58997Selan { 2114*58997Selan save_temps_flag = 1; 2115*58997Selan n_switches++; 2116*58997Selan break; 2117*58997Selan } 2118*58997Selan default: 2119*58997Selan n_switches++; 2120*58997Selan 2121*58997Selan if (SWITCH_TAKES_ARG (c) > (p[1] != 0)) 2122*58997Selan i += SWITCH_TAKES_ARG (c) - (p[1] != 0); 2123*58997Selan else if (WORD_SWITCH_TAKES_ARG (p)) 2124*58997Selan i += WORD_SWITCH_TAKES_ARG (p); 2125*58997Selan } 2126*58997Selan } 2127*58997Selan else 2128*58997Selan n_infiles++; 2129*58997Selan } 2130*58997Selan 2131*58997Selan /* Set up the search paths before we go looking for config files. */ 2132*58997Selan 2133*58997Selan /* These come before the md prefixes so that we will find gcc's subcommands 2134*58997Selan (such as cpp) rather than those of the host system. */ 2135*58997Selan /* Use 2 as fourth arg meaning try just the machine as a suffix, 2136*58997Selan as well as trying the machine and the version. */ 2137*58997Selan add_prefix (&exec_prefix, standard_exec_prefix, 0, 2, NULL_PTR); 2138*58997Selan add_prefix (&exec_prefix, standard_exec_prefix_1, 0, 2, NULL_PTR); 2139*58997Selan 2140*58997Selan add_prefix (&startfile_prefix, standard_exec_prefix, 0, 1, NULL_PTR); 2141*58997Selan add_prefix (&startfile_prefix, standard_exec_prefix_1, 0, 1, NULL_PTR); 2142*58997Selan 2143*58997Selan /* More prefixes are enabled in main, after we read the specs file 2144*58997Selan and determine whether this is cross-compilation or not. */ 2145*58997Selan 2146*58997Selan 2147*58997Selan /* Then create the space for the vectors and scan again. */ 2148*58997Selan 2149*58997Selan switches = ((struct switchstr *) 2150*58997Selan xmalloc ((n_switches + 1) * sizeof (struct switchstr))); 2151*58997Selan infiles = (struct infile *) xmalloc ((n_infiles + 1) * sizeof (struct infile)); 2152*58997Selan n_switches = 0; 2153*58997Selan n_infiles = 0; 2154*58997Selan last_language_n_infiles = -1; 2155*58997Selan 2156*58997Selan /* This, time, copy the text of each switch and store a pointer 2157*58997Selan to the copy in the vector of switches. 2158*58997Selan Store all the infiles in their vector. */ 2159*58997Selan 2160*58997Selan for (i = 1; i < argc; i++) 2161*58997Selan { 2162*58997Selan /* Just skip the switches that were handled by the preceding loop. */ 2163*58997Selan if (!strcmp (argv[i], "-Xlinker")) 2164*58997Selan i++; 2165*58997Selan else if (! strncmp (argv[i], "-Wl,", 4)) 2166*58997Selan ; 2167*58997Selan else if (! strncmp (argv[i], "-Wa,", 4)) 2168*58997Selan ; 2169*58997Selan else if (! strcmp (argv[i], "-print-libgcc-file-name")) 2170*58997Selan ; 2171*58997Selan else if (argv[i][0] == '+' && argv[i][1] == 'e') 2172*58997Selan { 2173*58997Selan /* Compensate for the +e options to the C++ front-end; 2174*58997Selan they're there simply for cfront call-compatability. We do 2175*58997Selan some magic in default_compilers to pass them down properly. 2176*58997Selan Note we deliberately start at the `+' here, to avoid passing 2177*58997Selan -e0 or -e1 down into the linker. */ 2178*58997Selan switches[n_switches].part1 = &argv[i][0]; 2179*58997Selan switches[n_switches].args = 0; 2180*58997Selan switches[n_switches].valid = 0; 2181*58997Selan n_switches++; 2182*58997Selan } 2183*58997Selan else if (argv[i][0] == '-' && argv[i][1] != 0 && argv[i][1] != 'l') 2184*58997Selan { 2185*58997Selan register char *p = &argv[i][1]; 2186*58997Selan register int c = *p; 2187*58997Selan 2188*58997Selan if (c == 'B' || c == 'b' || c == 'V') 2189*58997Selan { 2190*58997Selan /* Skip a separate arg, if any. */ 2191*58997Selan if (p[1] == 0) 2192*58997Selan i++; 2193*58997Selan continue; 2194*58997Selan } 2195*58997Selan if (c == 'x') 2196*58997Selan { 2197*58997Selan if (p[1] == 0 && i + 1 == argc) 2198*58997Selan fatal ("argument to `-x' is missing"); 2199*58997Selan if (p[1] == 0) 2200*58997Selan spec_lang = argv[++i]; 2201*58997Selan else 2202*58997Selan spec_lang = p + 1; 2203*58997Selan if (! strcmp (spec_lang, "none")) 2204*58997Selan /* Suppress the warning if -xnone comes after the last input file, 2205*58997Selan because alternate command interfaces like g++ might find it 2206*58997Selan useful to place -xnone after each input file. */ 2207*58997Selan spec_lang = 0; 2208*58997Selan else 2209*58997Selan last_language_n_infiles = n_infiles; 2210*58997Selan continue; 2211*58997Selan } 2212*58997Selan switches[n_switches].part1 = p; 2213*58997Selan /* Deal with option arguments in separate argv elements. */ 2214*58997Selan if ((SWITCH_TAKES_ARG (c) > (p[1] != 0)) 2215*58997Selan || WORD_SWITCH_TAKES_ARG (p)) { 2216*58997Selan int j = 0; 2217*58997Selan int n_args = WORD_SWITCH_TAKES_ARG (p); 2218*58997Selan 2219*58997Selan if (n_args == 0) { 2220*58997Selan /* Count only the option arguments in separate argv elements. */ 2221*58997Selan n_args = SWITCH_TAKES_ARG (c) - (p[1] != 0); 2222*58997Selan } 2223*58997Selan if (i + n_args >= argc) 2224*58997Selan fatal ("argument to `-%s' is missing", p); 2225*58997Selan switches[n_switches].args 2226*58997Selan = (char **) xmalloc ((n_args + 1) * sizeof (char *)); 2227*58997Selan while (j < n_args) 2228*58997Selan switches[n_switches].args[j++] = argv[++i]; 2229*58997Selan /* Null-terminate the vector. */ 2230*58997Selan switches[n_switches].args[j] = 0; 2231*58997Selan } else if (*switches_need_spaces != 0 && (c == 'o' || c == 'L')) { 2232*58997Selan /* On some systems, ld cannot handle -o or -L without space. 2233*58997Selan So split the -o or -L from its argument. */ 2234*58997Selan switches[n_switches].part1 = (c == 'o' ? "o" : "L"); 2235*58997Selan switches[n_switches].args = (char **) xmalloc (2 * sizeof (char *)); 2236*58997Selan switches[n_switches].args[0] = xmalloc (strlen (p)); 2237*58997Selan strcpy (switches[n_switches].args[0], &p[1]); 2238*58997Selan switches[n_switches].args[1] = 0; 2239*58997Selan } else 2240*58997Selan switches[n_switches].args = 0; 2241*58997Selan switches[n_switches].valid = 0; 2242*58997Selan /* This is always valid, since gcc.c itself understands it. */ 2243*58997Selan if (!strcmp (p, "save-temps")) 2244*58997Selan switches[n_switches].valid = 1; 2245*58997Selan n_switches++; 2246*58997Selan } 2247*58997Selan else 2248*58997Selan { 2249*58997Selan infiles[n_infiles].language = spec_lang; 2250*58997Selan infiles[n_infiles++].name = argv[i]; 2251*58997Selan } 2252*58997Selan } 2253*58997Selan 2254*58997Selan if (n_infiles == last_language_n_infiles) 2255*58997Selan error ("Warning: `-x %s' after last input file has no effect", spec_lang); 2256*58997Selan 2257*58997Selan switches[n_switches].part1 = 0; 2258*58997Selan infiles[n_infiles].name = 0; 2259*58997Selan 2260*58997Selan /* If we have a GCC_EXEC_PREFIX envvar, modify it for cpp's sake. */ 2261*58997Selan if (gcc_exec_prefix) 2262*58997Selan { 2263*58997Selan temp = (char *) xmalloc (strlen (gcc_exec_prefix) + strlen (spec_version) 2264*58997Selan + strlen (spec_machine) + 3); 2265*58997Selan strcpy (temp, gcc_exec_prefix); 2266*58997Selan strcat (temp, spec_machine); 2267*58997Selan strcat (temp, "/"); 2268*58997Selan strcat (temp, spec_version); 2269*58997Selan strcat (temp, "/"); 2270*58997Selan gcc_exec_prefix = temp; 2271*58997Selan } 2272*58997Selan } 2273*58997Selan 2274*58997Selan /* Process a spec string, accumulating and running commands. */ 2275*58997Selan 2276*58997Selan /* These variables describe the input file name. 2277*58997Selan input_file_number is the index on outfiles of this file, 2278*58997Selan so that the output file name can be stored for later use by %o. 2279*58997Selan input_basename is the start of the part of the input file 2280*58997Selan sans all directory names, and basename_length is the number 2281*58997Selan of characters starting there excluding the suffix .c or whatever. */ 2282*58997Selan 2283*58997Selan static char *input_filename; 2284*58997Selan static int input_file_number; 2285*58997Selan static int input_filename_length; 2286*58997Selan static int basename_length; 2287*58997Selan static char *input_basename; 2288*58997Selan static char *input_suffix; 2289*58997Selan 2290*58997Selan /* These are variables used within do_spec and do_spec_1. */ 2291*58997Selan 2292*58997Selan /* Nonzero if an arg has been started and not yet terminated 2293*58997Selan (with space, tab or newline). */ 2294*58997Selan static int arg_going; 2295*58997Selan 2296*58997Selan /* Nonzero means %d or %g has been seen; the next arg to be terminated 2297*58997Selan is a temporary file name. */ 2298*58997Selan static int delete_this_arg; 2299*58997Selan 2300*58997Selan /* Nonzero means %w has been seen; the next arg to be terminated 2301*58997Selan is the output file name of this compilation. */ 2302*58997Selan static int this_is_output_file; 2303*58997Selan 2304*58997Selan /* Nonzero means %s has been seen; the next arg to be terminated 2305*58997Selan is the name of a library file and we should try the standard 2306*58997Selan search dirs for it. */ 2307*58997Selan static int this_is_library_file; 2308*58997Selan 2309*58997Selan /* Process the spec SPEC and run the commands specified therein. 2310*58997Selan Returns 0 if the spec is successfully processed; -1 if failed. */ 2311*58997Selan 2312*58997Selan static int 2313*58997Selan do_spec (spec) 2314*58997Selan char *spec; 2315*58997Selan { 2316*58997Selan int value; 2317*58997Selan 2318*58997Selan clear_args (); 2319*58997Selan arg_going = 0; 2320*58997Selan delete_this_arg = 0; 2321*58997Selan this_is_output_file = 0; 2322*58997Selan this_is_library_file = 0; 2323*58997Selan 2324*58997Selan value = do_spec_1 (spec, 0, NULL_PTR); 2325*58997Selan 2326*58997Selan /* Force out any unfinished command. 2327*58997Selan If -pipe, this forces out the last command if it ended in `|'. */ 2328*58997Selan if (value == 0) 2329*58997Selan { 2330*58997Selan if (argbuf_index > 0 && !strcmp (argbuf[argbuf_index - 1], "|")) 2331*58997Selan argbuf_index--; 2332*58997Selan 2333*58997Selan if (argbuf_index > 0) 2334*58997Selan value = execute (); 2335*58997Selan } 2336*58997Selan 2337*58997Selan return value; 2338*58997Selan } 2339*58997Selan 2340*58997Selan /* Process the sub-spec SPEC as a portion of a larger spec. 2341*58997Selan This is like processing a whole spec except that we do 2342*58997Selan not initialize at the beginning and we do not supply a 2343*58997Selan newline by default at the end. 2344*58997Selan INSWITCH nonzero means don't process %-sequences in SPEC; 2345*58997Selan in this case, % is treated as an ordinary character. 2346*58997Selan This is used while substituting switches. 2347*58997Selan INSWITCH nonzero also causes SPC not to terminate an argument. 2348*58997Selan 2349*58997Selan Value is zero unless a line was finished 2350*58997Selan and the command on that line reported an error. */ 2351*58997Selan 2352*58997Selan static int 2353*58997Selan do_spec_1 (spec, inswitch, soft_matched_part) 2354*58997Selan char *spec; 2355*58997Selan int inswitch; 2356*58997Selan char *soft_matched_part; 2357*58997Selan { 2358*58997Selan register char *p = spec; 2359*58997Selan register int c; 2360*58997Selan int i; 2361*58997Selan char *string; 2362*58997Selan 2363*58997Selan while (c = *p++) 2364*58997Selan /* If substituting a switch, treat all chars like letters. 2365*58997Selan Otherwise, NL, SPC, TAB and % are special. */ 2366*58997Selan switch (inswitch ? 'a' : c) 2367*58997Selan { 2368*58997Selan case '\n': 2369*58997Selan /* End of line: finish any pending argument, 2370*58997Selan then run the pending command if one has been started. */ 2371*58997Selan if (arg_going) 2372*58997Selan { 2373*58997Selan obstack_1grow (&obstack, 0); 2374*58997Selan string = obstack_finish (&obstack); 2375*58997Selan if (this_is_library_file) 2376*58997Selan string = find_file (string); 2377*58997Selan store_arg (string, delete_this_arg, this_is_output_file); 2378*58997Selan if (this_is_output_file) 2379*58997Selan outfiles[input_file_number] = string; 2380*58997Selan } 2381*58997Selan arg_going = 0; 2382*58997Selan 2383*58997Selan if (argbuf_index > 0 && !strcmp (argbuf[argbuf_index - 1], "|")) 2384*58997Selan { 2385*58997Selan int i; 2386*58997Selan for (i = 0; i < n_switches; i++) 2387*58997Selan if (!strcmp (switches[i].part1, "pipe")) 2388*58997Selan break; 2389*58997Selan 2390*58997Selan /* A `|' before the newline means use a pipe here, 2391*58997Selan but only if -pipe was specified. 2392*58997Selan Otherwise, execute now and don't pass the `|' as an arg. */ 2393*58997Selan if (i < n_switches) 2394*58997Selan { 2395*58997Selan switches[i].valid = 1; 2396*58997Selan break; 2397*58997Selan } 2398*58997Selan else 2399*58997Selan argbuf_index--; 2400*58997Selan } 2401*58997Selan 2402*58997Selan if (argbuf_index > 0) 2403*58997Selan { 2404*58997Selan int value = execute (); 2405*58997Selan if (value) 2406*58997Selan return value; 2407*58997Selan } 2408*58997Selan /* Reinitialize for a new command, and for a new argument. */ 2409*58997Selan clear_args (); 2410*58997Selan arg_going = 0; 2411*58997Selan delete_this_arg = 0; 2412*58997Selan this_is_output_file = 0; 2413*58997Selan this_is_library_file = 0; 2414*58997Selan break; 2415*58997Selan 2416*58997Selan case '|': 2417*58997Selan /* End any pending argument. */ 2418*58997Selan if (arg_going) 2419*58997Selan { 2420*58997Selan obstack_1grow (&obstack, 0); 2421*58997Selan string = obstack_finish (&obstack); 2422*58997Selan if (this_is_library_file) 2423*58997Selan string = find_file (string); 2424*58997Selan store_arg (string, delete_this_arg, this_is_output_file); 2425*58997Selan if (this_is_output_file) 2426*58997Selan outfiles[input_file_number] = string; 2427*58997Selan } 2428*58997Selan 2429*58997Selan /* Use pipe */ 2430*58997Selan obstack_1grow (&obstack, c); 2431*58997Selan arg_going = 1; 2432*58997Selan break; 2433*58997Selan 2434*58997Selan case '\t': 2435*58997Selan case ' ': 2436*58997Selan /* Space or tab ends an argument if one is pending. */ 2437*58997Selan if (arg_going) 2438*58997Selan { 2439*58997Selan obstack_1grow (&obstack, 0); 2440*58997Selan string = obstack_finish (&obstack); 2441*58997Selan if (this_is_library_file) 2442*58997Selan string = find_file (string); 2443*58997Selan store_arg (string, delete_this_arg, this_is_output_file); 2444*58997Selan if (this_is_output_file) 2445*58997Selan outfiles[input_file_number] = string; 2446*58997Selan } 2447*58997Selan /* Reinitialize for a new argument. */ 2448*58997Selan arg_going = 0; 2449*58997Selan delete_this_arg = 0; 2450*58997Selan this_is_output_file = 0; 2451*58997Selan this_is_library_file = 0; 2452*58997Selan break; 2453*58997Selan 2454*58997Selan case '%': 2455*58997Selan switch (c = *p++) 2456*58997Selan { 2457*58997Selan case 0: 2458*58997Selan fatal ("Invalid specification! Bug in cc."); 2459*58997Selan 2460*58997Selan case 'b': 2461*58997Selan obstack_grow (&obstack, input_basename, basename_length); 2462*58997Selan arg_going = 1; 2463*58997Selan break; 2464*58997Selan 2465*58997Selan case 'd': 2466*58997Selan delete_this_arg = 2; 2467*58997Selan break; 2468*58997Selan 2469*58997Selan /* Dump out the directories specified with LIBRARY_PATH, 2470*58997Selan followed by the absolute directories 2471*58997Selan that we search for startfiles. */ 2472*58997Selan case 'D': 2473*58997Selan for (i = 0; i < 2; i++) 2474*58997Selan { 2475*58997Selan struct prefix_list *pl 2476*58997Selan = (i == 0 ? library_prefix.plist : startfile_prefix.plist); 2477*58997Selan int bufsize = 100; 2478*58997Selan char *buffer = (char *) xmalloc (bufsize); 2479*58997Selan int idx; 2480*58997Selan 2481*58997Selan for (; pl; pl = pl->next) 2482*58997Selan { 2483*58997Selan #ifdef RELATIVE_PREFIX_NOT_LINKDIR 2484*58997Selan /* Used on systems which record the specified -L dirs 2485*58997Selan and use them to search for dynamic linking. */ 2486*58997Selan /* Relative directories always come from -B, 2487*58997Selan and it is better not to use them for searching 2488*58997Selan at run time. In particular, stage1 loses */ 2489*58997Selan if (pl->prefix[0] != '/') 2490*58997Selan continue; 2491*58997Selan #endif 2492*58997Selan if (machine_suffix) 2493*58997Selan { 2494*58997Selan if (is_linker_dir (pl->prefix, machine_suffix)) 2495*58997Selan { 2496*58997Selan do_spec_1 ("-L", 0, NULL_PTR); 2497*58997Selan #ifdef SPACE_AFTER_L_OPTION 2498*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2499*58997Selan #endif 2500*58997Selan do_spec_1 (pl->prefix, 1, NULL_PTR); 2501*58997Selan /* Remove slash from machine_suffix. */ 2502*58997Selan if (strlen (machine_suffix) >= bufsize) 2503*58997Selan bufsize = strlen (machine_suffix) * 2 + 1; 2504*58997Selan buffer = (char *) xrealloc (buffer, bufsize); 2505*58997Selan strcpy (buffer, machine_suffix); 2506*58997Selan idx = strlen (buffer); 2507*58997Selan if (buffer[idx - 1] == '/') 2508*58997Selan buffer[idx - 1] = 0; 2509*58997Selan do_spec_1 (buffer, 1, NULL_PTR); 2510*58997Selan /* Make this a separate argument. */ 2511*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2512*58997Selan } 2513*58997Selan } 2514*58997Selan if (!pl->require_machine_suffix) 2515*58997Selan { 2516*58997Selan if (is_linker_dir (pl->prefix, "")) 2517*58997Selan { 2518*58997Selan do_spec_1 ("-L", 0, NULL_PTR); 2519*58997Selan #ifdef SPACE_AFTER_L_OPTION 2520*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2521*58997Selan #endif 2522*58997Selan /* Remove slash from pl->prefix. */ 2523*58997Selan if (strlen (pl->prefix) >= bufsize) 2524*58997Selan bufsize = strlen (pl->prefix) * 2 + 1; 2525*58997Selan buffer = (char *) xrealloc (buffer, bufsize); 2526*58997Selan strcpy (buffer, pl->prefix); 2527*58997Selan idx = strlen (buffer); 2528*58997Selan if (buffer[idx - 1] == '/') 2529*58997Selan buffer[idx - 1] = 0; 2530*58997Selan do_spec_1 (buffer, 1, NULL_PTR); 2531*58997Selan /* Make this a separate argument. */ 2532*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2533*58997Selan } 2534*58997Selan } 2535*58997Selan } 2536*58997Selan free (buffer); 2537*58997Selan } 2538*58997Selan break; 2539*58997Selan 2540*58997Selan case 'e': 2541*58997Selan /* {...:%efoo} means report an error with `foo' as error message 2542*58997Selan and don't execute any more commands for this file. */ 2543*58997Selan { 2544*58997Selan char *q = p; 2545*58997Selan char *buf; 2546*58997Selan while (*p != 0 && *p != '\n') p++; 2547*58997Selan buf = (char *) alloca (p - q + 1); 2548*58997Selan strncpy (buf, q, p - q); 2549*58997Selan buf[p - q] = 0; 2550*58997Selan error ("%s", buf); 2551*58997Selan return -1; 2552*58997Selan } 2553*58997Selan break; 2554*58997Selan 2555*58997Selan case 'g': 2556*58997Selan case 'u': 2557*58997Selan case 'U': 2558*58997Selan if (save_temps_flag) 2559*58997Selan obstack_grow (&obstack, input_basename, basename_length); 2560*58997Selan else 2561*58997Selan { 2562*58997Selan #ifdef MKTEMP_EACH_FILE 2563*58997Selan /* ??? This has a problem: the total number of 2564*58997Selan values mktemp can return is limited. 2565*58997Selan That matters for the names of object files. 2566*58997Selan In 2.4, do something about that. */ 2567*58997Selan struct temp_name *t; 2568*58997Selan char *suffix = p; 2569*58997Selan while (*p == '.' || isalpha (*p)) 2570*58997Selan p++; 2571*58997Selan 2572*58997Selan /* See if we already have an association of %g/%u/%U and 2573*58997Selan suffix. */ 2574*58997Selan for (t = temp_names; t; t = t->next) 2575*58997Selan if (t->length == p - suffix 2576*58997Selan && strncmp (t->suffix, suffix, p - suffix) == 0 2577*58997Selan && t->unique == (c != 'g')) 2578*58997Selan break; 2579*58997Selan 2580*58997Selan /* Make a new association if needed. %u requires one. */ 2581*58997Selan if (t == 0 || c == 'u') 2582*58997Selan { 2583*58997Selan if (t == 0) 2584*58997Selan { 2585*58997Selan t = (struct temp_name *) xmalloc (sizeof (struct temp_name)); 2586*58997Selan t->next = temp_names; 2587*58997Selan temp_names = t; 2588*58997Selan } 2589*58997Selan t->length = p - suffix; 2590*58997Selan t->suffix = save_string (suffix, p - suffix); 2591*58997Selan t->unique = (c != 'g'); 2592*58997Selan choose_temp_base (); 2593*58997Selan t->filename = temp_filename; 2594*58997Selan t->filename_length = temp_filename_length; 2595*58997Selan } 2596*58997Selan 2597*58997Selan obstack_grow (&obstack, t->filename, t->filename_length); 2598*58997Selan delete_this_arg = 1; 2599*58997Selan #else 2600*58997Selan obstack_grow (&obstack, temp_filename, temp_filename_length); 2601*58997Selan if (c == 'u' || c == 'U') 2602*58997Selan { 2603*58997Selan static int unique; 2604*58997Selan char buff[9]; 2605*58997Selan if (c == 'u') 2606*58997Selan unique++; 2607*58997Selan sprintf (buff, "%d", unique); 2608*58997Selan obstack_grow (&obstack, buff, strlen (buff)); 2609*58997Selan } 2610*58997Selan #endif 2611*58997Selan delete_this_arg = 1; 2612*58997Selan } 2613*58997Selan arg_going = 1; 2614*58997Selan break; 2615*58997Selan 2616*58997Selan case 'i': 2617*58997Selan obstack_grow (&obstack, input_filename, input_filename_length); 2618*58997Selan arg_going = 1; 2619*58997Selan break; 2620*58997Selan 2621*58997Selan case 'I': 2622*58997Selan if (gcc_exec_prefix) 2623*58997Selan { 2624*58997Selan do_spec_1 ("-iprefix", 1, NULL_PTR); 2625*58997Selan /* Make this a separate argument. */ 2626*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2627*58997Selan do_spec_1 (gcc_exec_prefix, 1, NULL_PTR); 2628*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2629*58997Selan } 2630*58997Selan break; 2631*58997Selan 2632*58997Selan case 'o': 2633*58997Selan { 2634*58997Selan register int f; 2635*58997Selan for (f = 0; f < n_infiles; f++) 2636*58997Selan store_arg (outfiles[f], 0, 0); 2637*58997Selan } 2638*58997Selan break; 2639*58997Selan 2640*58997Selan case 's': 2641*58997Selan this_is_library_file = 1; 2642*58997Selan break; 2643*58997Selan 2644*58997Selan case 'w': 2645*58997Selan this_is_output_file = 1; 2646*58997Selan break; 2647*58997Selan 2648*58997Selan case 'W': 2649*58997Selan { 2650*58997Selan int index = argbuf_index; 2651*58997Selan /* Handle the {...} following the %W. */ 2652*58997Selan if (*p != '{') 2653*58997Selan abort (); 2654*58997Selan p = handle_braces (p + 1); 2655*58997Selan if (p == 0) 2656*58997Selan return -1; 2657*58997Selan /* If any args were output, mark the last one for deletion 2658*58997Selan on failure. */ 2659*58997Selan if (argbuf_index != index) 2660*58997Selan record_temp_file (argbuf[argbuf_index - 1], 0, 1); 2661*58997Selan break; 2662*58997Selan } 2663*58997Selan 2664*58997Selan /* %x{OPTION} records OPTION for %X to output. */ 2665*58997Selan case 'x': 2666*58997Selan { 2667*58997Selan char *p1 = p; 2668*58997Selan char *string; 2669*58997Selan 2670*58997Selan /* Skip past the option value and make a copy. */ 2671*58997Selan if (*p != '{') 2672*58997Selan abort (); 2673*58997Selan while (*p++ != '}') 2674*58997Selan ; 2675*58997Selan string = save_string (p1 + 1, p - p1 - 2); 2676*58997Selan 2677*58997Selan /* See if we already recorded this option. */ 2678*58997Selan for (i = 0; i < n_linker_options; i++) 2679*58997Selan if (! strcmp (string, linker_options[i])) 2680*58997Selan { 2681*58997Selan free (string); 2682*58997Selan return 0; 2683*58997Selan } 2684*58997Selan 2685*58997Selan /* This option is new; add it. */ 2686*58997Selan n_linker_options++; 2687*58997Selan if (!linker_options) 2688*58997Selan linker_options 2689*58997Selan = (char **) xmalloc (n_linker_options * sizeof (char **)); 2690*58997Selan else 2691*58997Selan linker_options 2692*58997Selan = (char **) xrealloc (linker_options, 2693*58997Selan n_linker_options * sizeof (char **)); 2694*58997Selan 2695*58997Selan linker_options[n_linker_options - 1] = string; 2696*58997Selan } 2697*58997Selan break; 2698*58997Selan 2699*58997Selan /* Dump out the options accumulated previously using %x, 2700*58997Selan -Xlinker and -Wl,. */ 2701*58997Selan case 'X': 2702*58997Selan for (i = 0; i < n_linker_options; i++) 2703*58997Selan { 2704*58997Selan do_spec_1 (linker_options[i], 1, NULL_PTR); 2705*58997Selan /* Make each accumulated option a separate argument. */ 2706*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2707*58997Selan } 2708*58997Selan break; 2709*58997Selan 2710*58997Selan /* Dump out the options accumulated previously using -Wa,. */ 2711*58997Selan case 'Y': 2712*58997Selan for (i = 0; i < n_assembler_options; i++) 2713*58997Selan { 2714*58997Selan do_spec_1 (assembler_options[i], 1, NULL_PTR); 2715*58997Selan /* Make each accumulated option a separate argument. */ 2716*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2717*58997Selan } 2718*58997Selan break; 2719*58997Selan 2720*58997Selan /* Here are digits and numbers that just process 2721*58997Selan a certain constant string as a spec. 2722*58997Selan /* Here are digits and numbers that just process 2723*58997Selan a certain constant string as a spec. */ 2724*58997Selan 2725*58997Selan case '1': 2726*58997Selan do_spec_1 (cc1_spec, 0, NULL_PTR); 2727*58997Selan break; 2728*58997Selan 2729*58997Selan case '2': 2730*58997Selan do_spec_1 (cc1plus_spec, 0, NULL_PTR); 2731*58997Selan break; 2732*58997Selan 2733*58997Selan case 'a': 2734*58997Selan do_spec_1 (asm_spec, 0, NULL_PTR); 2735*58997Selan break; 2736*58997Selan 2737*58997Selan case 'A': 2738*58997Selan do_spec_1 (asm_final_spec, 0, NULL_PTR); 2739*58997Selan break; 2740*58997Selan 2741*58997Selan case 'c': 2742*58997Selan do_spec_1 (signed_char_spec, 0, NULL_PTR); 2743*58997Selan break; 2744*58997Selan 2745*58997Selan case 'C': 2746*58997Selan do_spec_1 (cpp_spec, 0, NULL_PTR); 2747*58997Selan break; 2748*58997Selan 2749*58997Selan case 'E': 2750*58997Selan do_spec_1 (endfile_spec, 0, NULL_PTR); 2751*58997Selan break; 2752*58997Selan 2753*58997Selan case 'l': 2754*58997Selan do_spec_1 (link_spec, 0, NULL_PTR); 2755*58997Selan break; 2756*58997Selan 2757*58997Selan case 'L': 2758*58997Selan do_spec_1 (lib_spec, 0, NULL_PTR); 2759*58997Selan break; 2760*58997Selan 2761*58997Selan case 'p': 2762*58997Selan { 2763*58997Selan char *x = (char *) alloca (strlen (cpp_predefines) + 1); 2764*58997Selan char *buf = x; 2765*58997Selan char *y; 2766*58997Selan 2767*58997Selan /* Copy all of the -D options in CPP_PREDEFINES into BUF. */ 2768*58997Selan y = cpp_predefines; 2769*58997Selan while (*y != 0) 2770*58997Selan { 2771*58997Selan if (! strncmp (y, "-D", 2)) 2772*58997Selan /* Copy the whole option. */ 2773*58997Selan while (*y && *y != ' ' && *y != '\t') 2774*58997Selan *x++ = *y++; 2775*58997Selan else if (*y == ' ' || *y == '\t') 2776*58997Selan /* Copy whitespace to the result. */ 2777*58997Selan *x++ = *y++; 2778*58997Selan /* Don't copy other options. */ 2779*58997Selan else 2780*58997Selan y++; 2781*58997Selan } 2782*58997Selan 2783*58997Selan *x = 0; 2784*58997Selan 2785*58997Selan do_spec_1 (buf, 0, NULL_PTR); 2786*58997Selan } 2787*58997Selan break; 2788*58997Selan 2789*58997Selan case 'P': 2790*58997Selan { 2791*58997Selan char *x = (char *) alloca (strlen (cpp_predefines) * 4 + 1); 2792*58997Selan char *buf = x; 2793*58997Selan char *y; 2794*58997Selan 2795*58997Selan /* Copy all of CPP_PREDEFINES into BUF, 2796*58997Selan but put __ after every -D and at the end of each arg. */ 2797*58997Selan y = cpp_predefines; 2798*58997Selan while (*y != 0) 2799*58997Selan { 2800*58997Selan if (! strncmp (y, "-D", 2)) 2801*58997Selan { 2802*58997Selan int flag = 0; 2803*58997Selan 2804*58997Selan *x++ = *y++; 2805*58997Selan *x++ = *y++; 2806*58997Selan 2807*58997Selan if (strncmp (y, "__", 2)) 2808*58997Selan { 2809*58997Selan /* Stick __ at front of macro name. */ 2810*58997Selan *x++ = '_'; 2811*58997Selan *x++ = '_'; 2812*58997Selan /* Arrange to stick __ at the end as well. */ 2813*58997Selan flag = 1; 2814*58997Selan } 2815*58997Selan 2816*58997Selan /* Copy the macro name. */ 2817*58997Selan while (*y && *y != '=' && *y != ' ' && *y != '\t') 2818*58997Selan *x++ = *y++; 2819*58997Selan 2820*58997Selan if (flag) 2821*58997Selan { 2822*58997Selan *x++ = '_'; 2823*58997Selan *x++ = '_'; 2824*58997Selan } 2825*58997Selan 2826*58997Selan /* Copy the value given, if any. */ 2827*58997Selan while (*y && *y != ' ' && *y != '\t') 2828*58997Selan *x++ = *y++; 2829*58997Selan } 2830*58997Selan else if (*y == ' ' || *y == '\t') 2831*58997Selan /* Copy whitespace to the result. */ 2832*58997Selan *x++ = *y++; 2833*58997Selan /* Don't copy -A options */ 2834*58997Selan else 2835*58997Selan y++; 2836*58997Selan } 2837*58997Selan *x++ = ' '; 2838*58997Selan 2839*58997Selan /* Copy all of CPP_PREDEFINES into BUF, 2840*58997Selan but put __ after every -D. */ 2841*58997Selan y = cpp_predefines; 2842*58997Selan while (*y != 0) 2843*58997Selan { 2844*58997Selan if (! strncmp (y, "-D", 2)) 2845*58997Selan { 2846*58997Selan *x++ = *y++; 2847*58997Selan *x++ = *y++; 2848*58997Selan 2849*58997Selan if (strncmp (y, "__", 2)) 2850*58997Selan { 2851*58997Selan /* Stick __ at front of macro name. */ 2852*58997Selan *x++ = '_'; 2853*58997Selan *x++ = '_'; 2854*58997Selan } 2855*58997Selan 2856*58997Selan /* Copy the macro name. */ 2857*58997Selan while (*y && *y != '=' && *y != ' ' && *y != '\t') 2858*58997Selan *x++ = *y++; 2859*58997Selan 2860*58997Selan /* Copy the value given, if any. */ 2861*58997Selan while (*y && *y != ' ' && *y != '\t') 2862*58997Selan *x++ = *y++; 2863*58997Selan } 2864*58997Selan else if (*y == ' ' || *y == '\t') 2865*58997Selan /* Copy whitespace to the result. */ 2866*58997Selan *x++ = *y++; 2867*58997Selan /* Don't copy -A options */ 2868*58997Selan else 2869*58997Selan y++; 2870*58997Selan } 2871*58997Selan *x++ = ' '; 2872*58997Selan 2873*58997Selan /* Copy all of the -A options in CPP_PREDEFINES into BUF. */ 2874*58997Selan y = cpp_predefines; 2875*58997Selan while (*y != 0) 2876*58997Selan { 2877*58997Selan if (! strncmp (y, "-A", 2)) 2878*58997Selan /* Copy the whole option. */ 2879*58997Selan while (*y && *y != ' ' && *y != '\t') 2880*58997Selan *x++ = *y++; 2881*58997Selan else if (*y == ' ' || *y == '\t') 2882*58997Selan /* Copy whitespace to the result. */ 2883*58997Selan *x++ = *y++; 2884*58997Selan /* Don't copy other options. */ 2885*58997Selan else 2886*58997Selan y++; 2887*58997Selan } 2888*58997Selan 2889*58997Selan *x = 0; 2890*58997Selan 2891*58997Selan do_spec_1 (buf, 0, NULL_PTR); 2892*58997Selan } 2893*58997Selan break; 2894*58997Selan 2895*58997Selan case 'S': 2896*58997Selan do_spec_1 (startfile_spec, 0, NULL_PTR); 2897*58997Selan break; 2898*58997Selan 2899*58997Selan /* Here we define characters other than letters and digits. */ 2900*58997Selan 2901*58997Selan case '{': 2902*58997Selan p = handle_braces (p); 2903*58997Selan if (p == 0) 2904*58997Selan return -1; 2905*58997Selan break; 2906*58997Selan 2907*58997Selan case '%': 2908*58997Selan obstack_1grow (&obstack, '%'); 2909*58997Selan break; 2910*58997Selan 2911*58997Selan case '*': 2912*58997Selan do_spec_1 (soft_matched_part, 1, NULL_PTR); 2913*58997Selan do_spec_1 (" ", 0, NULL_PTR); 2914*58997Selan break; 2915*58997Selan 2916*58997Selan /* Process a string found as the value of a spec given by name. 2917*58997Selan This feature allows individual machine descriptions 2918*58997Selan to add and use their own specs. 2919*58997Selan %[...] modifies -D options the way %P does; 2920*58997Selan %(...) uses the spec unmodified. */ 2921*58997Selan case '(': 2922*58997Selan case '[': 2923*58997Selan { 2924*58997Selan char *name = p; 2925*58997Selan struct spec_list *sl; 2926*58997Selan int len; 2927*58997Selan 2928*58997Selan /* The string after the S/P is the name of a spec that is to be 2929*58997Selan processed. */ 2930*58997Selan while (*p && *p != ')' && *p != ']') 2931*58997Selan p++; 2932*58997Selan 2933*58997Selan /* See if it's in the list */ 2934*58997Selan for (len = p - name, sl = specs; sl; sl = sl->next) 2935*58997Selan if (strncmp (sl->name, name, len) == 0 && !sl->name[len]) 2936*58997Selan { 2937*58997Selan name = sl->spec; 2938*58997Selan break; 2939*58997Selan } 2940*58997Selan 2941*58997Selan if (sl) 2942*58997Selan { 2943*58997Selan if (c == '(') 2944*58997Selan do_spec_1 (name, 0, NULL_PTR); 2945*58997Selan else 2946*58997Selan { 2947*58997Selan char *x = (char *) alloca (strlen (name) * 2 + 1); 2948*58997Selan char *buf = x; 2949*58997Selan char *y = name; 2950*58997Selan 2951*58997Selan /* Copy all of NAME into BUF, but put __ after 2952*58997Selan every -D and at the end of each arg, */ 2953*58997Selan while (1) 2954*58997Selan { 2955*58997Selan if (! strncmp (y, "-D", 2)) 2956*58997Selan { 2957*58997Selan *x++ = '-'; 2958*58997Selan *x++ = 'D'; 2959*58997Selan *x++ = '_'; 2960*58997Selan *x++ = '_'; 2961*58997Selan y += 2; 2962*58997Selan } 2963*58997Selan else if (*y == ' ' || *y == 0) 2964*58997Selan { 2965*58997Selan *x++ = '_'; 2966*58997Selan *x++ = '_'; 2967*58997Selan if (*y == 0) 2968*58997Selan break; 2969*58997Selan else 2970*58997Selan *x++ = *y++; 2971*58997Selan } 2972*58997Selan else 2973*58997Selan *x++ = *y++; 2974*58997Selan } 2975*58997Selan *x = 0; 2976*58997Selan 2977*58997Selan do_spec_1 (buf, 0, NULL_PTR); 2978*58997Selan } 2979*58997Selan } 2980*58997Selan 2981*58997Selan /* Discard the closing paren or bracket. */ 2982*58997Selan if (*p) 2983*58997Selan p++; 2984*58997Selan } 2985*58997Selan break; 2986*58997Selan 2987*58997Selan default: 2988*58997Selan abort (); 2989*58997Selan } 2990*58997Selan break; 2991*58997Selan 2992*58997Selan case '\\': 2993*58997Selan /* Backslash: treat next character as ordinary. */ 2994*58997Selan c = *p++; 2995*58997Selan 2996*58997Selan /* fall through */ 2997*58997Selan default: 2998*58997Selan /* Ordinary character: put it into the current argument. */ 2999*58997Selan obstack_1grow (&obstack, c); 3000*58997Selan arg_going = 1; 3001*58997Selan } 3002*58997Selan 3003*58997Selan return 0; /* End of string */ 3004*58997Selan } 3005*58997Selan 3006*58997Selan /* Return 0 if we call do_spec_1 and that returns -1. */ 3007*58997Selan 3008*58997Selan static char * 3009*58997Selan handle_braces (p) 3010*58997Selan register char *p; 3011*58997Selan { 3012*58997Selan register char *q; 3013*58997Selan char *filter; 3014*58997Selan int pipe = 0; 3015*58997Selan int negate = 0; 3016*58997Selan int suffix = 0; 3017*58997Selan 3018*58997Selan if (*p == '|') 3019*58997Selan /* A `|' after the open-brace means, 3020*58997Selan if the test fails, output a single minus sign rather than nothing. 3021*58997Selan This is used in %{|!pipe:...}. */ 3022*58997Selan pipe = 1, ++p; 3023*58997Selan 3024*58997Selan if (*p == '!') 3025*58997Selan /* A `!' after the open-brace negates the condition: 3026*58997Selan succeed if the specified switch is not present. */ 3027*58997Selan negate = 1, ++p; 3028*58997Selan 3029*58997Selan if (*p == '.') 3030*58997Selan /* A `.' after the open-brace means test against the current suffix. */ 3031*58997Selan { 3032*58997Selan if (pipe) 3033*58997Selan abort (); 3034*58997Selan 3035*58997Selan suffix = 1; 3036*58997Selan ++p; 3037*58997Selan } 3038*58997Selan 3039*58997Selan filter = p; 3040*58997Selan while (*p != ':' && *p != '}') p++; 3041*58997Selan if (*p != '}') 3042*58997Selan { 3043*58997Selan register int count = 1; 3044*58997Selan q = p + 1; 3045*58997Selan while (count > 0) 3046*58997Selan { 3047*58997Selan if (*q == '{') 3048*58997Selan count++; 3049*58997Selan else if (*q == '}') 3050*58997Selan count--; 3051*58997Selan else if (*q == 0) 3052*58997Selan abort (); 3053*58997Selan q++; 3054*58997Selan } 3055*58997Selan } 3056*58997Selan else 3057*58997Selan q = p + 1; 3058*58997Selan 3059*58997Selan if (suffix) 3060*58997Selan { 3061*58997Selan int found = (input_suffix != 0 3062*58997Selan && strlen (input_suffix) == p - filter 3063*58997Selan && strncmp (input_suffix, filter, p - filter) == 0); 3064*58997Selan 3065*58997Selan if (p[0] == '}') 3066*58997Selan abort (); 3067*58997Selan 3068*58997Selan if (negate != found 3069*58997Selan && do_spec_1 (save_string (p + 1, q - p - 2), 0, NULL_PTR) < 0) 3070*58997Selan return 0; 3071*58997Selan 3072*58997Selan return q; 3073*58997Selan } 3074*58997Selan else if (p[-1] == '*' && p[0] == '}') 3075*58997Selan { 3076*58997Selan /* Substitute all matching switches as separate args. */ 3077*58997Selan register int i; 3078*58997Selan --p; 3079*58997Selan for (i = 0; i < n_switches; i++) 3080*58997Selan if (!strncmp (switches[i].part1, filter, p - filter)) 3081*58997Selan give_switch (i, 0); 3082*58997Selan } 3083*58997Selan else 3084*58997Selan { 3085*58997Selan /* Test for presence of the specified switch. */ 3086*58997Selan register int i; 3087*58997Selan int present = 0; 3088*58997Selan 3089*58997Selan /* If name specified ends in *, as in {x*:...}, 3090*58997Selan check for %* and handle that case. */ 3091*58997Selan if (p[-1] == '*' && !negate) 3092*58997Selan { 3093*58997Selan int substitution; 3094*58997Selan char *r = p; 3095*58997Selan 3096*58997Selan /* First see whether we have %*. */ 3097*58997Selan substitution = 0; 3098*58997Selan while (r < q) 3099*58997Selan { 3100*58997Selan if (*r == '%' && r[1] == '*') 3101*58997Selan substitution = 1; 3102*58997Selan r++; 3103*58997Selan } 3104*58997Selan /* If we do, handle that case. */ 3105*58997Selan if (substitution) 3106*58997Selan { 3107*58997Selan /* Substitute all matching switches as separate args. 3108*58997Selan But do this by substituting for %* 3109*58997Selan in the text that follows the colon. */ 3110*58997Selan 3111*58997Selan unsigned hard_match_len = p - filter - 1; 3112*58997Selan char *string = save_string (p + 1, q - p - 2); 3113*58997Selan 3114*58997Selan for (i = 0; i < n_switches; i++) 3115*58997Selan if (!strncmp (switches[i].part1, filter, hard_match_len)) 3116*58997Selan { 3117*58997Selan do_spec_1 (string, 0, &switches[i].part1[hard_match_len]); 3118*58997Selan /* Pass any arguments this switch has. */ 3119*58997Selan give_switch (i, 1); 3120*58997Selan } 3121*58997Selan 3122*58997Selan return q; 3123*58997Selan } 3124*58997Selan } 3125*58997Selan 3126*58997Selan /* If name specified ends in *, as in {x*:...}, 3127*58997Selan check for presence of any switch name starting with x. */ 3128*58997Selan if (p[-1] == '*') 3129*58997Selan { 3130*58997Selan for (i = 0; i < n_switches; i++) 3131*58997Selan { 3132*58997Selan unsigned hard_match_len = p - filter - 1; 3133*58997Selan 3134*58997Selan if (!strncmp (switches[i].part1, filter, hard_match_len)) 3135*58997Selan { 3136*58997Selan switches[i].valid = 1; 3137*58997Selan present = 1; 3138*58997Selan } 3139*58997Selan } 3140*58997Selan } 3141*58997Selan /* Otherwise, check for presence of exact name specified. */ 3142*58997Selan else 3143*58997Selan { 3144*58997Selan for (i = 0; i < n_switches; i++) 3145*58997Selan { 3146*58997Selan if (!strncmp (switches[i].part1, filter, p - filter) 3147*58997Selan && switches[i].part1[p - filter] == 0) 3148*58997Selan { 3149*58997Selan switches[i].valid = 1; 3150*58997Selan present = 1; 3151*58997Selan break; 3152*58997Selan } 3153*58997Selan } 3154*58997Selan } 3155*58997Selan 3156*58997Selan /* If it is as desired (present for %{s...}, absent for %{-s...}) 3157*58997Selan then substitute either the switch or the specified 3158*58997Selan conditional text. */ 3159*58997Selan if (present != negate) 3160*58997Selan { 3161*58997Selan if (*p == '}') 3162*58997Selan { 3163*58997Selan give_switch (i, 0); 3164*58997Selan } 3165*58997Selan else 3166*58997Selan { 3167*58997Selan if (do_spec_1 (save_string (p + 1, q - p - 2), 0, NULL_PTR) < 0) 3168*58997Selan return 0; 3169*58997Selan } 3170*58997Selan } 3171*58997Selan else if (pipe) 3172*58997Selan { 3173*58997Selan /* Here if a %{|...} conditional fails: output a minus sign, 3174*58997Selan which means "standard output" or "standard input". */ 3175*58997Selan do_spec_1 ("-", 0, NULL_PTR); 3176*58997Selan } 3177*58997Selan } 3178*58997Selan 3179*58997Selan return q; 3180*58997Selan } 3181*58997Selan 3182*58997Selan /* Pass a switch to the current accumulating command 3183*58997Selan in the same form that we received it. 3184*58997Selan SWITCHNUM identifies the switch; it is an index into 3185*58997Selan the vector of switches gcc received, which is `switches'. 3186*58997Selan This cannot fail since it never finishes a command line. 3187*58997Selan 3188*58997Selan If OMIT_FIRST_WORD is nonzero, then we omit .part1 of the argument. */ 3189*58997Selan 3190*58997Selan static void 3191*58997Selan give_switch (switchnum, omit_first_word) 3192*58997Selan int switchnum; 3193*58997Selan int omit_first_word; 3194*58997Selan { 3195*58997Selan if (!omit_first_word) 3196*58997Selan { 3197*58997Selan do_spec_1 ("-", 0, NULL_PTR); 3198*58997Selan do_spec_1 (switches[switchnum].part1, 1, NULL_PTR); 3199*58997Selan } 3200*58997Selan do_spec_1 (" ", 0, NULL_PTR); 3201*58997Selan if (switches[switchnum].args != 0) 3202*58997Selan { 3203*58997Selan char **p; 3204*58997Selan for (p = switches[switchnum].args; *p; p++) 3205*58997Selan { 3206*58997Selan do_spec_1 (*p, 1, NULL_PTR); 3207*58997Selan do_spec_1 (" ", 0, NULL_PTR); 3208*58997Selan } 3209*58997Selan } 3210*58997Selan switches[switchnum].valid = 1; 3211*58997Selan } 3212*58997Selan 3213*58997Selan /* Search for a file named NAME trying various prefixes including the 3214*58997Selan user's -B prefix and some standard ones. 3215*58997Selan Return the absolute file name found. If nothing is found, return NAME. */ 3216*58997Selan 3217*58997Selan static char * 3218*58997Selan find_file (name) 3219*58997Selan char *name; 3220*58997Selan { 3221*58997Selan char *newname; 3222*58997Selan 3223*58997Selan newname = find_a_file (&startfile_prefix, name, R_OK); 3224*58997Selan return newname ? newname : name; 3225*58997Selan } 3226*58997Selan 3227*58997Selan /* Determine whether a -L option is relevant. Not required for certain 3228*58997Selan fixed names and for directories that don't exist. */ 3229*58997Selan 3230*58997Selan static int 3231*58997Selan is_linker_dir (path1, path2) 3232*58997Selan char *path1; 3233*58997Selan char *path2; 3234*58997Selan { 3235*58997Selan int len1 = strlen (path1); 3236*58997Selan int len2 = strlen (path2); 3237*58997Selan char *path = (char *) alloca (3 + len1 + len2); 3238*58997Selan char *cp; 3239*58997Selan struct stat st; 3240*58997Selan 3241*58997Selan /* Construct the path from the two parts. Ensure the string ends with "/.". 3242*58997Selan The resulting path will be a directory even if the given path is a 3243*58997Selan symbolic link. */ 3244*58997Selan bcopy (path1, path, len1); 3245*58997Selan bcopy (path2, path + len1, len2); 3246*58997Selan cp = path + len1 + len2; 3247*58997Selan if (cp[-1] != '/') 3248*58997Selan *cp++ = '/'; 3249*58997Selan *cp++ = '.'; 3250*58997Selan *cp = '\0'; 3251*58997Selan 3252*58997Selan /* Exclude directories that the linker is known to search. */ 3253*58997Selan if ((cp - path == 6 && strcmp (path, "/lib/.") == 0) 3254*58997Selan || (cp - path == 10 && strcmp (path, "/usr/lib/.") == 0)) 3255*58997Selan return 0; 3256*58997Selan 3257*58997Selan return (stat (path, &st) >= 0 && S_ISDIR (st.st_mode)); 3258*58997Selan } 3259*58997Selan 3260*58997Selan /* On fatal signals, delete all the temporary files. */ 3261*58997Selan 3262*58997Selan static void 3263*58997Selan fatal_error (signum) 3264*58997Selan int signum; 3265*58997Selan { 3266*58997Selan signal (signum, SIG_DFL); 3267*58997Selan delete_failure_queue (); 3268*58997Selan delete_temp_files (); 3269*58997Selan /* Get the same signal again, this time not handled, 3270*58997Selan so its normal effect occurs. */ 3271*58997Selan kill (getpid (), signum); 3272*58997Selan } 3273*58997Selan 3274*58997Selan int 3275*58997Selan main (argc, argv) 3276*58997Selan int argc; 3277*58997Selan char **argv; 3278*58997Selan { 3279*58997Selan register int i; 3280*58997Selan int j; 3281*58997Selan int value; 3282*58997Selan int error_count = 0; 3283*58997Selan int linker_was_run = 0; 3284*58997Selan char *explicit_link_files; 3285*58997Selan char *specs_file; 3286*58997Selan 3287*58997Selan programname = argv[0]; 3288*58997Selan 3289*58997Selan if (signal (SIGINT, SIG_IGN) != SIG_IGN) 3290*58997Selan signal (SIGINT, fatal_error); 3291*58997Selan if (signal (SIGHUP, SIG_IGN) != SIG_IGN) 3292*58997Selan signal (SIGHUP, fatal_error); 3293*58997Selan if (signal (SIGTERM, SIG_IGN) != SIG_IGN) 3294*58997Selan signal (SIGTERM, fatal_error); 3295*58997Selan #ifdef SIGPIPE 3296*58997Selan if (signal (SIGPIPE, SIG_IGN) != SIG_IGN) 3297*58997Selan signal (SIGPIPE, fatal_error); 3298*58997Selan #endif 3299*58997Selan 3300*58997Selan argbuf_length = 10; 3301*58997Selan argbuf = (char **) xmalloc (argbuf_length * sizeof (char *)); 3302*58997Selan 3303*58997Selan obstack_init (&obstack); 3304*58997Selan 3305*58997Selan /* Set up to remember the pathname of gcc and any options 3306*58997Selan needed for collect. */ 3307*58997Selan obstack_init (&collect_obstack); 3308*58997Selan obstack_grow (&collect_obstack, "COLLECT_GCC=", sizeof ("COLLECT_GCC=")-1); 3309*58997Selan obstack_grow (&collect_obstack, programname, strlen (programname)+1); 3310*58997Selan putenv (obstack_finish (&collect_obstack)); 3311*58997Selan 3312*58997Selan /* Choose directory for temp files. */ 3313*58997Selan 3314*58997Selan choose_temp_base (); 3315*58997Selan 3316*58997Selan /* Make a table of what switches there are (switches, n_switches). 3317*58997Selan Make a table of specified input files (infiles, n_infiles). 3318*58997Selan Decode switches that are handled locally. */ 3319*58997Selan 3320*58997Selan process_command (argc, argv); 3321*58997Selan 3322*58997Selan /* Initialize the vector of specs to just the default. 3323*58997Selan This means one element containing 0s, as a terminator. */ 3324*58997Selan 3325*58997Selan compilers = (struct compiler *) xmalloc (sizeof default_compilers); 3326*58997Selan bcopy (default_compilers, compilers, sizeof default_compilers); 3327*58997Selan n_compilers = n_default_compilers; 3328*58997Selan 3329*58997Selan /* Read specs from a file if there is one. */ 3330*58997Selan 3331*58997Selan machine_suffix = concat (spec_machine, "/", concat (spec_version, "/", "")); 3332*58997Selan just_machine_suffix = concat (spec_machine, "/", ""); 3333*58997Selan 3334*58997Selan specs_file = find_a_file (&startfile_prefix, "specs", R_OK); 3335*58997Selan /* Read the specs file unless it is a default one. */ 3336*58997Selan if (specs_file != 0 && strcmp (specs_file, "specs")) 3337*58997Selan read_specs (specs_file); 3338*58997Selan 3339*58997Selan /* If not cross-compiling, look for startfiles in the standard places. */ 3340*58997Selan /* The fact that these are done here, after reading the specs file, 3341*58997Selan means that it cannot be found in these directories. 3342*58997Selan But that's okay. It should never be there anyway. */ 3343*58997Selan if (!cross_compile) 3344*58997Selan { 3345*58997Selan #ifdef MD_EXEC_PREFIX 3346*58997Selan add_prefix (&exec_prefix, md_exec_prefix, 0, 0, NULL_PTR); 3347*58997Selan add_prefix (&startfile_prefix, md_exec_prefix, 0, 0, NULL_PTR); 3348*58997Selan #endif 3349*58997Selan 3350*58997Selan #ifdef MD_STARTFILE_PREFIX 3351*58997Selan add_prefix (&startfile_prefix, md_startfile_prefix, 0, 0, NULL_PTR); 3352*58997Selan #endif 3353*58997Selan 3354*58997Selan #ifdef MD_STARTFILE_PREFIX_1 3355*58997Selan add_prefix (&startfile_prefix, md_startfile_prefix_1, 0, 0, NULL_PTR); 3356*58997Selan #endif 3357*58997Selan 3358*58997Selan add_prefix (&startfile_prefix, standard_startfile_prefix, 0, 0, 3359*58997Selan NULL_PTR); 3360*58997Selan add_prefix (&startfile_prefix, standard_startfile_prefix_1, 0, 0, 3361*58997Selan NULL_PTR); 3362*58997Selan add_prefix (&startfile_prefix, standard_startfile_prefix_2, 0, 0, 3363*58997Selan NULL_PTR); 3364*58997Selan #if 0 /* Can cause surprises, and one can use -B./ instead. */ 3365*58997Selan add_prefix (&startfile_prefix, "./", 0, 1, NULL_PTR); 3366*58997Selan #endif 3367*58997Selan } 3368*58997Selan 3369*58997Selan /* Now we have the specs. 3370*58997Selan Set the `valid' bits for switches that match anything in any spec. */ 3371*58997Selan 3372*58997Selan validate_all_switches (); 3373*58997Selan 3374*58997Selan /* Warn about any switches that no pass was interested in. */ 3375*58997Selan 3376*58997Selan for (i = 0; i < n_switches; i++) 3377*58997Selan if (! switches[i].valid) 3378*58997Selan error ("unrecognized option `-%s'", switches[i].part1); 3379*58997Selan 3380*58997Selan if (print_libgcc_file_name) 3381*58997Selan { 3382*58997Selan printf ("%s\n", find_file ("libgcc.a")); 3383*58997Selan exit (0); 3384*58997Selan } 3385*58997Selan 3386*58997Selan /* Obey some of the options. */ 3387*58997Selan 3388*58997Selan if (verbose_flag) 3389*58997Selan { 3390*58997Selan fprintf (stderr, "gcc version %s\n", version_string); 3391*58997Selan if (n_infiles == 0) 3392*58997Selan exit (0); 3393*58997Selan } 3394*58997Selan 3395*58997Selan if (n_infiles == 0) 3396*58997Selan fatal ("No input files specified."); 3397*58997Selan 3398*58997Selan /* Make a place to record the compiler output file names 3399*58997Selan that correspond to the input files. */ 3400*58997Selan 3401*58997Selan outfiles = (char **) xmalloc (n_infiles * sizeof (char *)); 3402*58997Selan bzero (outfiles, n_infiles * sizeof (char *)); 3403*58997Selan 3404*58997Selan /* Record which files were specified explicitly as link input. */ 3405*58997Selan 3406*58997Selan explicit_link_files = xmalloc (n_infiles); 3407*58997Selan bzero (explicit_link_files, n_infiles); 3408*58997Selan 3409*58997Selan for (i = 0; i < n_infiles; i++) 3410*58997Selan { 3411*58997Selan register struct compiler *cp = 0; 3412*58997Selan int this_file_error = 0; 3413*58997Selan 3414*58997Selan /* Tell do_spec what to substitute for %i. */ 3415*58997Selan 3416*58997Selan input_filename = infiles[i].name; 3417*58997Selan input_filename_length = strlen (input_filename); 3418*58997Selan input_file_number = i; 3419*58997Selan 3420*58997Selan /* Use the same thing in %o, unless cp->spec says otherwise. */ 3421*58997Selan 3422*58997Selan outfiles[i] = input_filename; 3423*58997Selan 3424*58997Selan /* Figure out which compiler from the file's suffix. */ 3425*58997Selan 3426*58997Selan cp = lookup_compiler (infiles[i].name, input_filename_length, 3427*58997Selan infiles[i].language); 3428*58997Selan 3429*58997Selan if (cp) 3430*58997Selan { 3431*58997Selan /* Ok, we found an applicable compiler. Run its spec. */ 3432*58997Selan /* First say how much of input_filename to substitute for %b */ 3433*58997Selan register char *p; 3434*58997Selan int len; 3435*58997Selan 3436*58997Selan input_basename = input_filename; 3437*58997Selan for (p = input_filename; *p; p++) 3438*58997Selan if (*p == '/') 3439*58997Selan input_basename = p + 1; 3440*58997Selan 3441*58997Selan /* Find a suffix starting with the last period, 3442*58997Selan and set basename_length to exclude that suffix. */ 3443*58997Selan basename_length = strlen (input_basename); 3444*58997Selan p = input_basename + basename_length; 3445*58997Selan while (p != input_basename && *p != '.') --p; 3446*58997Selan if (*p == '.' && p != input_basename) 3447*58997Selan { 3448*58997Selan basename_length = p - input_basename; 3449*58997Selan input_suffix = p + 1; 3450*58997Selan } 3451*58997Selan else 3452*58997Selan input_suffix = ""; 3453*58997Selan 3454*58997Selan len = 0; 3455*58997Selan for (j = 0; j < sizeof cp->spec / sizeof cp->spec[0]; j++) 3456*58997Selan if (cp->spec[j]) 3457*58997Selan len += strlen (cp->spec[j]); 3458*58997Selan 3459*58997Selan p = (char *) xmalloc (len + 1); 3460*58997Selan 3461*58997Selan len = 0; 3462*58997Selan for (j = 0; j < sizeof cp->spec / sizeof cp->spec[0]; j++) 3463*58997Selan if (cp->spec[j]) 3464*58997Selan { 3465*58997Selan strcpy (p + len, cp->spec[j]); 3466*58997Selan len += strlen (cp->spec[j]); 3467*58997Selan } 3468*58997Selan 3469*58997Selan value = do_spec (p); 3470*58997Selan free (p); 3471*58997Selan if (value < 0) 3472*58997Selan this_file_error = 1; 3473*58997Selan } 3474*58997Selan 3475*58997Selan /* If this file's name does not contain a recognized suffix, 3476*58997Selan record it as explicit linker input. */ 3477*58997Selan 3478*58997Selan else 3479*58997Selan explicit_link_files[i] = 1; 3480*58997Selan 3481*58997Selan /* Clear the delete-on-failure queue, deleting the files in it 3482*58997Selan if this compilation failed. */ 3483*58997Selan 3484*58997Selan if (this_file_error) 3485*58997Selan { 3486*58997Selan delete_failure_queue (); 3487*58997Selan error_count++; 3488*58997Selan } 3489*58997Selan /* If this compilation succeeded, don't delete those files later. */ 3490*58997Selan clear_failure_queue (); 3491*58997Selan } 3492*58997Selan 3493*58997Selan /* Run ld to link all the compiler output files. */ 3494*58997Selan 3495*58997Selan if (error_count == 0) 3496*58997Selan { 3497*58997Selan int tmp = execution_count; 3498*58997Selan int i; 3499*58997Selan int first_time; 3500*58997Selan 3501*58997Selan /* Rebuild the COMPILER_PATH and LIBRARY_PATH environment variables 3502*58997Selan for collect. */ 3503*58997Selan putenv_from_prefixes (&exec_prefix, "COMPILER_PATH="); 3504*58997Selan putenv_from_prefixes (&startfile_prefix, "LIBRARY_PATH="); 3505*58997Selan 3506*58997Selan /* Build COLLECT_GCC_OPTIONS to have all of the options specified to 3507*58997Selan the compiler. */ 3508*58997Selan obstack_grow (&collect_obstack, "COLLECT_GCC_OPTIONS=", 3509*58997Selan sizeof ("COLLECT_GCC_OPTIONS=")-1); 3510*58997Selan 3511*58997Selan first_time = TRUE; 3512*58997Selan for (i = 0; i < n_switches; i++) 3513*58997Selan { 3514*58997Selan char **args; 3515*58997Selan if (!first_time) 3516*58997Selan obstack_grow (&collect_obstack, " ", 1); 3517*58997Selan 3518*58997Selan first_time = FALSE; 3519*58997Selan obstack_grow (&collect_obstack, "-", 1); 3520*58997Selan obstack_grow (&collect_obstack, switches[i].part1, 3521*58997Selan strlen (switches[i].part1)); 3522*58997Selan 3523*58997Selan for (args = switches[i].args; args && *args; args++) 3524*58997Selan { 3525*58997Selan obstack_grow (&collect_obstack, " ", 1); 3526*58997Selan obstack_grow (&collect_obstack, *args, strlen (*args)); 3527*58997Selan } 3528*58997Selan } 3529*58997Selan obstack_grow (&collect_obstack, "\0", 1); 3530*58997Selan putenv (obstack_finish (&collect_obstack)); 3531*58997Selan 3532*58997Selan value = do_spec (link_command_spec); 3533*58997Selan if (value < 0) 3534*58997Selan error_count = 1; 3535*58997Selan linker_was_run = (tmp != execution_count); 3536*58997Selan } 3537*58997Selan 3538*58997Selan /* Warn if a -B option was specified but the prefix was never used. */ 3539*58997Selan unused_prefix_warnings (&exec_prefix); 3540*58997Selan unused_prefix_warnings (&startfile_prefix); 3541*58997Selan 3542*58997Selan /* If options said don't run linker, 3543*58997Selan complain about input files to be given to the linker. */ 3544*58997Selan 3545*58997Selan if (! linker_was_run && error_count == 0) 3546*58997Selan for (i = 0; i < n_infiles; i++) 3547*58997Selan if (explicit_link_files[i]) 3548*58997Selan error ("%s: linker input file unused since linking not done", 3549*58997Selan outfiles[i]); 3550*58997Selan 3551*58997Selan /* Delete some or all of the temporary files we made. */ 3552*58997Selan 3553*58997Selan if (error_count) 3554*58997Selan delete_failure_queue (); 3555*58997Selan delete_temp_files (); 3556*58997Selan 3557*58997Selan exit (error_count > 0 ? (signal_count ? 2 : 1) : 0); 3558*58997Selan /* NOTREACHED */ 3559*58997Selan return 0; 3560*58997Selan } 3561*58997Selan 3562*58997Selan /* Find the proper compilation spec for the file name NAME, 3563*58997Selan whose length is LENGTH. LANGUAGE is the specified language, 3564*58997Selan or 0 if none specified. */ 3565*58997Selan 3566*58997Selan static struct compiler * 3567*58997Selan lookup_compiler (name, length, language) 3568*58997Selan char *name; 3569*58997Selan int length; 3570*58997Selan char *language; 3571*58997Selan { 3572*58997Selan struct compiler *cp; 3573*58997Selan 3574*58997Selan /* Look for the language, if one is spec'd. */ 3575*58997Selan if (language != 0) 3576*58997Selan { 3577*58997Selan for (cp = compilers + n_compilers - 1; cp >= compilers; cp--) 3578*58997Selan { 3579*58997Selan if (language != 0) 3580*58997Selan { 3581*58997Selan if (cp->suffix[0] == '@' 3582*58997Selan && !strcmp (cp->suffix + 1, language)) 3583*58997Selan return cp; 3584*58997Selan } 3585*58997Selan } 3586*58997Selan error ("language %s not recognized", language); 3587*58997Selan } 3588*58997Selan 3589*58997Selan /* Look for a suffix. */ 3590*58997Selan for (cp = compilers + n_compilers - 1; cp >= compilers; cp--) 3591*58997Selan { 3592*58997Selan if (strlen (cp->suffix) < length 3593*58997Selan /* See if the suffix matches the end of NAME. */ 3594*58997Selan && !strcmp (cp->suffix, 3595*58997Selan name + length - strlen (cp->suffix)) 3596*58997Selan /* The suffix `-' matches only the file name `-'. */ 3597*58997Selan && !(!strcmp (cp->suffix, "-") && length != 1)) 3598*58997Selan { 3599*58997Selan if (cp->spec[0][0] == '@') 3600*58997Selan { 3601*58997Selan struct compiler *new; 3602*58997Selan /* An alias entry maps a suffix to a language. 3603*58997Selan Search for the language; pass 0 for NAME and LENGTH 3604*58997Selan to avoid infinite recursion if language not found. 3605*58997Selan Construct the new compiler spec. */ 3606*58997Selan language = cp->spec[0] + 1; 3607*58997Selan new = (struct compiler *) xmalloc (sizeof (struct compiler)); 3608*58997Selan new->suffix = cp->suffix; 3609*58997Selan bcopy (lookup_compiler (NULL_PTR, 0, language)->spec, 3610*58997Selan new->spec, sizeof new->spec); 3611*58997Selan return new; 3612*58997Selan } 3613*58997Selan /* A non-alias entry: return it. */ 3614*58997Selan return cp; 3615*58997Selan } 3616*58997Selan } 3617*58997Selan 3618*58997Selan return 0; 3619*58997Selan } 3620*58997Selan 3621*58997Selan char * 3622*58997Selan xmalloc (size) 3623*58997Selan unsigned size; 3624*58997Selan { 3625*58997Selan register char *value = (char *) malloc (size); 3626*58997Selan if (value == 0) 3627*58997Selan fatal ("virtual memory exhausted"); 3628*58997Selan return value; 3629*58997Selan } 3630*58997Selan 3631*58997Selan char * 3632*58997Selan xrealloc (ptr, size) 3633*58997Selan char *ptr; 3634*58997Selan unsigned size; 3635*58997Selan { 3636*58997Selan register char *value = (char *) realloc (ptr, size); 3637*58997Selan if (value == 0) 3638*58997Selan fatal ("virtual memory exhausted"); 3639*58997Selan return value; 3640*58997Selan } 3641*58997Selan 3642*58997Selan /* Return a newly-allocated string whose contents concatenate those of s1, s2, s3. */ 3643*58997Selan 3644*58997Selan static char * 3645*58997Selan concat (s1, s2, s3) 3646*58997Selan char *s1, *s2, *s3; 3647*58997Selan { 3648*58997Selan int len1 = strlen (s1), len2 = strlen (s2), len3 = strlen (s3); 3649*58997Selan char *result = xmalloc (len1 + len2 + len3 + 1); 3650*58997Selan 3651*58997Selan strcpy (result, s1); 3652*58997Selan strcpy (result + len1, s2); 3653*58997Selan strcpy (result + len1 + len2, s3); 3654*58997Selan *(result + len1 + len2 + len3) = 0; 3655*58997Selan 3656*58997Selan return result; 3657*58997Selan } 3658*58997Selan 3659*58997Selan static char * 3660*58997Selan save_string (s, len) 3661*58997Selan char *s; 3662*58997Selan int len; 3663*58997Selan { 3664*58997Selan register char *result = xmalloc (len + 1); 3665*58997Selan 3666*58997Selan bcopy (s, result, len); 3667*58997Selan result[len] = 0; 3668*58997Selan return result; 3669*58997Selan } 3670*58997Selan 3671*58997Selan static void 3672*58997Selan pfatal_with_name (name) 3673*58997Selan char *name; 3674*58997Selan { 3675*58997Selan char *s; 3676*58997Selan 3677*58997Selan if (errno < sys_nerr) 3678*58997Selan s = concat ("%s: ", sys_errlist[errno], ""); 3679*58997Selan else 3680*58997Selan s = "cannot open %s"; 3681*58997Selan fatal (s, name); 3682*58997Selan } 3683*58997Selan 3684*58997Selan static void 3685*58997Selan perror_with_name (name) 3686*58997Selan char *name; 3687*58997Selan { 3688*58997Selan char *s; 3689*58997Selan 3690*58997Selan if (errno < sys_nerr) 3691*58997Selan s = concat ("%s: ", sys_errlist[errno], ""); 3692*58997Selan else 3693*58997Selan s = "cannot open %s"; 3694*58997Selan error (s, name); 3695*58997Selan } 3696*58997Selan 3697*58997Selan static void 3698*58997Selan perror_exec (name) 3699*58997Selan char *name; 3700*58997Selan { 3701*58997Selan char *s; 3702*58997Selan 3703*58997Selan if (errno < sys_nerr) 3704*58997Selan s = concat ("installation problem, cannot exec %s: ", 3705*58997Selan sys_errlist[errno], ""); 3706*58997Selan else 3707*58997Selan s = "installation problem, cannot exec %s"; 3708*58997Selan error (s, name); 3709*58997Selan } 3710*58997Selan 3711*58997Selan /* More 'friendly' abort that prints the line and file. 3712*58997Selan config.h can #define abort fancy_abort if you like that sort of thing. */ 3713*58997Selan 3714*58997Selan void 3715*58997Selan fancy_abort () 3716*58997Selan { 3717*58997Selan fatal ("Internal gcc abort."); 3718*58997Selan } 3719*58997Selan 3720*58997Selan #ifdef HAVE_VPRINTF 3721*58997Selan 3722*58997Selan /* Output an error message and exit */ 3723*58997Selan 3724*58997Selan static void 3725*58997Selan fatal (va_alist) 3726*58997Selan va_dcl 3727*58997Selan { 3728*58997Selan va_list ap; 3729*58997Selan char *format; 3730*58997Selan 3731*58997Selan va_start (ap); 3732*58997Selan format = va_arg (ap, char *); 3733*58997Selan fprintf (stderr, "%s: ", programname); 3734*58997Selan vfprintf (stderr, format, ap); 3735*58997Selan va_end (ap); 3736*58997Selan fprintf (stderr, "\n"); 3737*58997Selan delete_temp_files (); 3738*58997Selan exit (1); 3739*58997Selan } 3740*58997Selan 3741*58997Selan static void 3742*58997Selan error (va_alist) 3743*58997Selan va_dcl 3744*58997Selan { 3745*58997Selan va_list ap; 3746*58997Selan char *format; 3747*58997Selan 3748*58997Selan va_start (ap); 3749*58997Selan format = va_arg (ap, char *); 3750*58997Selan fprintf (stderr, "%s: ", programname); 3751*58997Selan vfprintf (stderr, format, ap); 3752*58997Selan va_end (ap); 3753*58997Selan 3754*58997Selan fprintf (stderr, "\n"); 3755*58997Selan } 3756*58997Selan 3757*58997Selan #else /* not HAVE_VPRINTF */ 3758*58997Selan 3759*58997Selan static void 3760*58997Selan fatal (msg, arg1, arg2) 3761*58997Selan char *msg, *arg1, *arg2; 3762*58997Selan { 3763*58997Selan error (msg, arg1, arg2); 3764*58997Selan delete_temp_files (); 3765*58997Selan exit (1); 3766*58997Selan } 3767*58997Selan 3768*58997Selan static void 3769*58997Selan error (msg, arg1, arg2) 3770*58997Selan char *msg, *arg1, *arg2; 3771*58997Selan { 3772*58997Selan fprintf (stderr, "%s: ", programname); 3773*58997Selan fprintf (stderr, msg, arg1, arg2); 3774*58997Selan fprintf (stderr, "\n"); 3775*58997Selan } 3776*58997Selan 3777*58997Selan #endif /* not HAVE_VPRINTF */ 3778*58997Selan 3779*58997Selan 3780*58997Selan static void 3781*58997Selan validate_all_switches () 3782*58997Selan { 3783*58997Selan struct compiler *comp; 3784*58997Selan register char *p; 3785*58997Selan register char c; 3786*58997Selan struct spec_list *spec; 3787*58997Selan 3788*58997Selan for (comp = compilers; comp->spec[0]; comp++) 3789*58997Selan { 3790*58997Selan int i; 3791*58997Selan for (i = 0; i < sizeof comp->spec / sizeof comp->spec[0] && comp->spec[i]; i++) 3792*58997Selan { 3793*58997Selan p = comp->spec[i]; 3794*58997Selan while (c = *p++) 3795*58997Selan if (c == '%' && *p == '{') 3796*58997Selan /* We have a switch spec. */ 3797*58997Selan validate_switches (p + 1); 3798*58997Selan } 3799*58997Selan } 3800*58997Selan 3801*58997Selan /* look through the linked list of extra specs read from the specs file */ 3802*58997Selan for (spec = specs; spec ; spec = spec->next) 3803*58997Selan { 3804*58997Selan p = spec->spec; 3805*58997Selan while (c = *p++) 3806*58997Selan if (c == '%' && *p == '{') 3807*58997Selan /* We have a switch spec. */ 3808*58997Selan validate_switches (p + 1); 3809*58997Selan } 3810*58997Selan 3811*58997Selan p = link_command_spec; 3812*58997Selan while (c = *p++) 3813*58997Selan if (c == '%' && *p == '{') 3814*58997Selan /* We have a switch spec. */ 3815*58997Selan validate_switches (p + 1); 3816*58997Selan 3817*58997Selan /* Now notice switches mentioned in the machine-specific specs. */ 3818*58997Selan 3819*58997Selan p = asm_spec; 3820*58997Selan while (c = *p++) 3821*58997Selan if (c == '%' && *p == '{') 3822*58997Selan /* We have a switch spec. */ 3823*58997Selan validate_switches (p + 1); 3824*58997Selan 3825*58997Selan p = asm_final_spec; 3826*58997Selan while (c = *p++) 3827*58997Selan if (c == '%' && *p == '{') 3828*58997Selan /* We have a switch spec. */ 3829*58997Selan validate_switches (p + 1); 3830*58997Selan 3831*58997Selan p = cpp_spec; 3832*58997Selan while (c = *p++) 3833*58997Selan if (c == '%' && *p == '{') 3834*58997Selan /* We have a switch spec. */ 3835*58997Selan validate_switches (p + 1); 3836*58997Selan 3837*58997Selan p = signed_char_spec; 3838*58997Selan while (c = *p++) 3839*58997Selan if (c == '%' && *p == '{') 3840*58997Selan /* We have a switch spec. */ 3841*58997Selan validate_switches (p + 1); 3842*58997Selan 3843*58997Selan p = cc1_spec; 3844*58997Selan while (c = *p++) 3845*58997Selan if (c == '%' && *p == '{') 3846*58997Selan /* We have a switch spec. */ 3847*58997Selan validate_switches (p + 1); 3848*58997Selan 3849*58997Selan p = cc1plus_spec; 3850*58997Selan while (c = *p++) 3851*58997Selan if (c == '%' && *p == '{') 3852*58997Selan /* We have a switch spec. */ 3853*58997Selan validate_switches (p + 1); 3854*58997Selan 3855*58997Selan p = link_spec; 3856*58997Selan while (c = *p++) 3857*58997Selan if (c == '%' && *p == '{') 3858*58997Selan /* We have a switch spec. */ 3859*58997Selan validate_switches (p + 1); 3860*58997Selan 3861*58997Selan p = lib_spec; 3862*58997Selan while (c = *p++) 3863*58997Selan if (c == '%' && *p == '{') 3864*58997Selan /* We have a switch spec. */ 3865*58997Selan validate_switches (p + 1); 3866*58997Selan 3867*58997Selan p = startfile_spec; 3868*58997Selan while (c = *p++) 3869*58997Selan if (c == '%' && *p == '{') 3870*58997Selan /* We have a switch spec. */ 3871*58997Selan validate_switches (p + 1); 3872*58997Selan } 3873*58997Selan 3874*58997Selan /* Look at the switch-name that comes after START 3875*58997Selan and mark as valid all supplied switches that match it. */ 3876*58997Selan 3877*58997Selan static void 3878*58997Selan validate_switches (start) 3879*58997Selan char *start; 3880*58997Selan { 3881*58997Selan register char *p = start; 3882*58997Selan char *filter; 3883*58997Selan register int i; 3884*58997Selan int suffix = 0; 3885*58997Selan 3886*58997Selan if (*p == '|') 3887*58997Selan ++p; 3888*58997Selan 3889*58997Selan if (*p == '!') 3890*58997Selan ++p; 3891*58997Selan 3892*58997Selan if (*p == '.') 3893*58997Selan suffix = 1, ++p; 3894*58997Selan 3895*58997Selan filter = p; 3896*58997Selan while (*p != ':' && *p != '}') p++; 3897*58997Selan 3898*58997Selan if (suffix) 3899*58997Selan ; 3900*58997Selan else if (p[-1] == '*') 3901*58997Selan { 3902*58997Selan /* Mark all matching switches as valid. */ 3903*58997Selan --p; 3904*58997Selan for (i = 0; i < n_switches; i++) 3905*58997Selan if (!strncmp (switches[i].part1, filter, p - filter)) 3906*58997Selan switches[i].valid = 1; 3907*58997Selan } 3908*58997Selan else 3909*58997Selan { 3910*58997Selan /* Mark an exact matching switch as valid. */ 3911*58997Selan for (i = 0; i < n_switches; i++) 3912*58997Selan { 3913*58997Selan if (!strncmp (switches[i].part1, filter, p - filter) 3914*58997Selan && switches[i].part1[p - filter] == 0) 3915*58997Selan switches[i].valid = 1; 3916*58997Selan } 3917*58997Selan } 3918*58997Selan } 3919