OSDN Git Service

* gospec.c (lang_specific_driver): If we see -S without -o, add -o
[pf3gnuchains/gcc-fork.git] / gcc / go / gospec.c
1 /* gospec.c -- Specific flags and argument handling of the gcc Go front end.
2    Copyright (C) 2009, 2010, 2011, 2012 Free Software Foundation, Inc.
3
4 This file is part of GCC.
5
6 GCC is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 3, or (at your option) any later
9 version.
10
11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
14 for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GCC; see the file COPYING3.  If not see
18 <http://www.gnu.org/licenses/>.  */
19
20 #include "config.h"
21 #include "system.h"
22 #include "coretypes.h"
23 #include "tm.h"
24 #include "gcc.h"
25 #include "opts.h"
26
27 /* This bit is set if we saw a `-xfoo' language specification.  */
28 #define LANGSPEC        (1<<1)
29 /* This bit is set if they did `-lm' or `-lmath'.  */
30 #define MATHLIB         (1<<2)
31 /* This bit is set if they did `-lpthread'.  */
32 #define THREADLIB       (1<<3)
33 /* This bit is set if they did `-lc'.  */
34 #define WITHLIBC        (1<<4)
35 /* Skip this option.  */
36 #define SKIPOPT         (1<<5)
37
38 #ifndef MATH_LIBRARY
39 #define MATH_LIBRARY "m"
40 #endif
41 #ifndef MATH_LIBRARY_PROFILE
42 #define MATH_LIBRARY_PROFILE MATH_LIBRARY
43 #endif
44
45 #define THREAD_LIBRARY "pthread"
46 #define THREAD_LIBRARY_PROFILE THREAD_LIBRARY
47
48 #define LIBGO "go"
49 #define LIBGO_PROFILE LIBGO
50 #define LIBGOBEGIN "gobegin"
51
52 void
53 lang_specific_driver (struct cl_decoded_option **in_decoded_options,
54                       unsigned int *in_decoded_options_count,
55                       int *in_added_libraries)
56 {
57   unsigned int i, j;
58
59   /* If true, the user gave us the `-p' or `-pg' flag.  */
60   bool saw_profile_flag = false;
61
62   /* This is a tristate:
63      -1 means we should not link in libgo
64      0  means we should link in libgo if it is needed
65      1  means libgo is needed and should be linked in.
66      2  means libgo is needed and should be linked statically.  */
67   int library = 0;
68
69   /* The new argument list will be contained in this.  */
70   struct cl_decoded_option *new_decoded_options;
71
72   /* "-lm" or "-lmath" if it appears on the command line.  */
73   const struct cl_decoded_option *saw_math = 0;
74
75   /* "-lpthread" if it appears on the command line.  */
76   const struct cl_decoded_option *saw_thread = 0;
77
78   /* "-lc" if it appears on the command line.  */
79   const struct cl_decoded_option *saw_libc = 0;
80
81   /* An array used to flag each argument that needs a bit set for
82      LANGSPEC, MATHLIB, or WITHLIBC.  */
83   int *args;
84
85   /* Whether we need the thread library.  */
86   int need_thread = 0;
87
88   /* By default, we throw on the math library if we have one.  */
89   int need_math = (MATH_LIBRARY[0] != '\0');
90
91   /* True if we saw -static.  */
92   int static_link = 0;
93
94   /* True if we should add -shared-libgcc to the command-line.  */
95   int shared_libgcc = 1;
96
97   /* The total number of arguments with the new stuff.  */
98   unsigned int argc;
99
100   /* The argument list.  */
101   struct cl_decoded_option *decoded_options;
102
103   /* The number of libraries added in.  */
104   int added_libraries;
105
106   /* The total number of arguments with the new stuff.  */
107   int num_args = 1;
108
109   /* Whether the -o option was used.  */
110   bool saw_opt_o = false;
111
112   /* Whether the -S option was used.  */
113   bool saw_opt_S = false;
114
115   /* The first input file with an extension of .go.  */
116   const char *first_go_file = NULL;  
117
118   argc = *in_decoded_options_count;
119   decoded_options = *in_decoded_options;
120   added_libraries = *in_added_libraries;
121
122   args = XCNEWVEC (int, argc);
123
124   for (i = 1; i < argc; i++)
125     {
126       const char *arg = decoded_options[i].arg;
127
128       switch (decoded_options[i].opt_index)
129         {
130         case OPT_nostdlib:
131         case OPT_nodefaultlibs:
132           library = -1;
133           break;
134
135         case OPT_l:
136           if (strcmp (arg, MATH_LIBRARY) == 0)
137             {
138               args[i] |= MATHLIB;
139               need_math = 0;
140             }
141           else if (strcmp (arg, THREAD_LIBRARY) == 0)
142             args[i] |= THREADLIB;
143           else if (strcmp (arg, "c") == 0)
144             args[i] |= WITHLIBC;
145           else
146             /* Unrecognized libraries (e.g. -lfoo) may require libgo.  */
147             library = (library == 0) ? 1 : library;
148           break;
149
150         case OPT_pg:
151         case OPT_p:
152           saw_profile_flag = true;
153           break;
154
155         case OPT_x:
156           if (library == 0 && strcmp (arg, "go") == 0)
157             library = 1;
158           break;
159
160         case OPT_Xlinker:
161         case OPT_Wl_:
162           /* Arguments that go directly to the linker might be .o files,
163              or something, and so might cause libgo to be needed.  */
164           if (library == 0)
165             library = 1;
166           break;
167
168         case OPT_c:
169         case OPT_E:
170         case OPT_M:
171         case OPT_MM:
172         case OPT_fsyntax_only:
173           /* Don't specify libraries if we won't link, since that would
174              cause a warning.  */
175           library = -1;
176           break;
177
178         case OPT_S:
179           saw_opt_S = true;
180           library = -1;
181           break;
182
183         case OPT_o:
184           saw_opt_o = true;
185           break;
186
187         case OPT_static:
188           static_link = 1;
189           break;
190
191         case OPT_static_libgcc:
192           shared_libgcc = 0;
193           break;
194
195         case OPT_static_libgo:
196           library = library >= 0 ? 2 : library;
197           args[i] |= SKIPOPT;
198           break;
199
200         case OPT_SPECIAL_input_file:
201           if (library == 0)
202             library = 1;
203
204           if (first_go_file == NULL)
205             {
206               int len;
207
208               len = strlen (arg);
209               if (len > 3 && strcmp (arg + len - 3, ".go") == 0)
210                 first_go_file = arg;
211             }
212
213           break;
214         }
215     }
216
217   /* There's no point adding -shared-libgcc if we don't have a shared
218      libgcc.  */
219 #ifndef ENABLE_SHARED_LIBGCC
220   shared_libgcc = 0;
221 #endif
222
223   /* Make sure to have room for the trailing NULL argument.  */
224   num_args = argc + need_math + shared_libgcc + (library > 0) * 5 + 5;
225   new_decoded_options = XNEWVEC (struct cl_decoded_option, num_args);
226
227   i = 0;
228   j = 0;
229
230   /* Copy the 0th argument, i.e., the name of the program itself.  */
231   new_decoded_options[j++] = decoded_options[i++];
232
233   /* If we are linking, pass -fsplit-stack if it is supported.  */
234 #ifdef TARGET_CAN_SPLIT_STACK
235   if (library >= 0)
236     {
237       generate_option (OPT_fsplit_stack, NULL, 1, CL_DRIVER,
238                        &new_decoded_options[j]);
239       j++;
240     }
241 #endif
242
243   /* NOTE: We start at 1 now, not 0.  */
244   while (i < argc)
245     {
246       new_decoded_options[j] = decoded_options[i];
247
248       /* Make sure -lgo is before the math library, since libgo itself
249          uses those math routines.  */
250       if (!saw_math && (args[i] & MATHLIB) && library > 0)
251         {
252           --j;
253           saw_math = &decoded_options[i];
254         }
255
256       if (!saw_thread && (args[i] & THREADLIB) && library > 0)
257         {
258           --j;
259           saw_thread = &decoded_options[i];
260         }
261
262       if (!saw_libc && (args[i] & WITHLIBC) && library > 0)
263         {
264           --j;
265           saw_libc = &decoded_options[i];
266         }
267
268       if ((args[i] & SKIPOPT) != 0)
269         --j;
270
271       i++;
272       j++;
273     }
274
275   /* If we are not linking, add a -o option.  This is because we need
276      the driver to pass all .go files to go1.  Without a -o option the
277      driver will invoke go1 separately for each input file.  */
278   if (library < 0 && first_go_file != NULL && !saw_opt_o)
279     {
280       const char *base;
281       int baselen;
282       int alen;
283       char *out;
284
285       base = lbasename (first_go_file);
286       baselen = strlen (base) - 3;
287       alen = baselen + 3;
288       out = XNEWVEC (char, alen);
289       memcpy (out, base, baselen);
290       /* The driver will convert .o to some other suffix (e.g., .obj)
291          if appropriate.  */
292       out[baselen] = '.';
293       if (saw_opt_S)
294         out[baselen + 1] = 's';
295       else
296         out[baselen + 1] = 'o';
297       out[baselen + 2] = '\0';
298       generate_option (OPT_o, out, 1, CL_DRIVER,
299                        &new_decoded_options[j]);
300       j++;
301     }
302
303   /* Add `-lgo' if we haven't already done so.  */
304   if (library > 0)
305     {
306       generate_option (OPT_l, LIBGOBEGIN, 1, CL_DRIVER,
307                        &new_decoded_options[j]);
308       added_libraries++;
309       j++;
310
311 #ifdef HAVE_LD_STATIC_DYNAMIC
312       if (library > 1 && !static_link)
313         {
314           generate_option (OPT_Wl_, LD_STATIC_OPTION, 1, CL_DRIVER,
315                            &new_decoded_options[j]);
316           j++;
317         }
318 #endif
319
320       generate_option (OPT_l, saw_profile_flag ? LIBGO_PROFILE : LIBGO, 1,
321                        CL_DRIVER, &new_decoded_options[j]);
322       added_libraries++;
323       j++;
324
325 #ifdef HAVE_LD_STATIC_DYNAMIC
326       if (library > 1 && !static_link)
327         {
328           generate_option (OPT_Wl_, LD_DYNAMIC_OPTION, 1, CL_DRIVER,
329                            &new_decoded_options[j]);
330           j++;
331         }
332 #endif
333
334       /* When linking libgo statically we also need to link with the
335          pthread library.  */
336       if (library > 1 || static_link)
337         need_thread = 1;
338     }
339
340   if (saw_thread)
341     new_decoded_options[j++] = *saw_thread;
342   else if (library > 0 && need_thread)
343     {
344       generate_option (OPT_l,
345                        (saw_profile_flag
346                         ? THREAD_LIBRARY_PROFILE
347                         : THREAD_LIBRARY),
348                        1, CL_DRIVER, &new_decoded_options[j]);
349       added_libraries++;
350       j++;
351     }
352
353   if (saw_math)
354     new_decoded_options[j++] = *saw_math;
355   else if (library > 0 && need_math)
356     {
357       generate_option (OPT_l,
358                        saw_profile_flag ? MATH_LIBRARY_PROFILE : MATH_LIBRARY,
359                        1, CL_DRIVER, &new_decoded_options[j]);
360       added_libraries++;
361       j++;
362     }
363
364   if (saw_libc)
365     new_decoded_options[j++] = *saw_libc;
366   if (shared_libgcc && !static_link)
367     generate_option (OPT_shared_libgcc, NULL, 1, CL_DRIVER,
368                      &new_decoded_options[j++]);
369
370   *in_decoded_options_count = j;
371   *in_decoded_options = new_decoded_options;
372   *in_added_libraries = added_libraries;
373 }
374
375 /* Called before linking.  Returns 0 on success and -1 on failure.  */
376 int lang_specific_pre_link (void)  /* Not used for Go.  */
377 {
378   return 0;
379 }
380
381 /* Number of extra output files that lang_specific_pre_link may generate.  */
382 int lang_specific_extra_outfiles = 0;  /* Not used for Go.  */