]> git.ipfire.org Git - thirdparty/gcc.git/blob - gcc/go/gospec.c
Update copyright years.
[thirdparty/gcc.git] / gcc / go / gospec.c
1 /* gospec.c -- Specific flags and argument handling of the gcc Go front end.
2 Copyright (C) 2009-2019 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 "opts.h"
25
26 /* This bit is set if we saw a `-xfoo' language specification. */
27 #define LANGSPEC (1<<1)
28 /* This bit is set if they did `-lm' or `-lmath'. */
29 #define MATHLIB (1<<2)
30 /* This bit is set if they did `-lpthread'. */
31 #define THREADLIB (1<<3)
32 /* This bit is set if they did `-lc'. */
33 #define WITHLIBC (1<<4)
34 /* Skip this option. */
35 #define SKIPOPT (1<<5)
36
37 #ifndef MATH_LIBRARY
38 #define MATH_LIBRARY "m"
39 #endif
40 #ifndef MATH_LIBRARY_PROFILE
41 #define MATH_LIBRARY_PROFILE MATH_LIBRARY
42 #endif
43
44 #define THREAD_LIBRARY "pthread"
45 #define THREAD_LIBRARY_PROFILE THREAD_LIBRARY
46
47 #define LIBGO "go"
48 #define LIBGO_PROFILE LIBGO
49 #define LIBGOBEGIN "gobegin"
50
51 void
52 lang_specific_driver (struct cl_decoded_option **in_decoded_options,
53 unsigned int *in_decoded_options_count,
54 int *in_added_libraries)
55 {
56 unsigned int i, j;
57
58 /* If true, the user gave us the `-p' or `-pg' flag. */
59 bool saw_profile_flag = false;
60
61 /* This is a tristate:
62 -1 means we should not link in libgo
63 0 means we should link in libgo if it is needed
64 1 means libgo is needed and should be linked in.
65 2 means libgo is needed and should be linked statically. */
66 int library = 0;
67
68 /* The new argument list will be contained in this. */
69 struct cl_decoded_option *new_decoded_options;
70
71 /* "-lm" or "-lmath" if it appears on the command line. */
72 const struct cl_decoded_option *saw_math = 0;
73
74 /* "-lpthread" if it appears on the command line. */
75 const struct cl_decoded_option *saw_thread = 0;
76
77 /* "-lc" if it appears on the command line. */
78 const struct cl_decoded_option *saw_libc = 0;
79
80 /* An array used to flag each argument that needs a bit set for
81 LANGSPEC, MATHLIB, or WITHLIBC. */
82 int *args;
83
84 /* Whether we need the thread library. */
85 int need_thread = 0;
86
87 /* By default, we throw on the math library if we have one. */
88 int need_math = (MATH_LIBRARY[0] != '\0');
89
90 /* True if we saw -static. */
91 int static_link = 0;
92
93 /* True if we should add -shared-libgcc to the command-line. */
94 int shared_libgcc = 1;
95
96 /* The total number of arguments with the new stuff. */
97 unsigned int argc;
98
99 /* The argument list. */
100 struct cl_decoded_option *decoded_options;
101
102 /* The number of libraries added in. */
103 int added_libraries;
104
105 /* The total number of arguments with the new stuff. */
106 int num_args = 1;
107
108 /* Supports split stack */
109 int supports_split_stack = 0;
110
111 /* Whether the -o option was used. */
112 bool saw_opt_o = false;
113
114 /* Whether the -c option was used. Also used for -E, -fsyntax-only,
115 in general anything which implies only compilation and not
116 linking. */
117 bool saw_opt_c = false;
118
119 /* Whether the -S option was used. */
120 bool saw_opt_S = false;
121
122 #ifdef TARGET_CAN_SPLIT_STACK_64BIT
123 /* Whether the -m64 option is in force. */
124 bool is_m64 = TARGET_CAN_SPLIT_STACK_64BIT;
125 #endif
126
127 /* The first input file with an extension of .go. */
128 const char *first_go_file = NULL;
129
130 argc = *in_decoded_options_count;
131 decoded_options = *in_decoded_options;
132 added_libraries = *in_added_libraries;
133
134 args = XCNEWVEC (int, argc);
135
136 for (i = 1; i < argc; i++)
137 {
138 const char *arg = decoded_options[i].arg;
139
140 switch (decoded_options[i].opt_index)
141 {
142 case OPT_r:
143 case OPT_nostdlib:
144 case OPT_nodefaultlibs:
145 library = -1;
146 break;
147
148 case OPT_l:
149 if (strcmp (arg, MATH_LIBRARY) == 0)
150 {
151 args[i] |= MATHLIB;
152 need_math = 0;
153 }
154 else if (strcmp (arg, THREAD_LIBRARY) == 0)
155 args[i] |= THREADLIB;
156 else if (strcmp (arg, "c") == 0)
157 args[i] |= WITHLIBC;
158 else
159 /* Unrecognized libraries (e.g. -lfoo) may require libgo. */
160 library = (library == 0) ? 1 : library;
161 break;
162
163 #ifdef TARGET_CAN_SPLIT_STACK_64BIT
164 case OPT_m32:
165 is_m64 = false;
166 break;
167
168 case OPT_m64:
169 is_m64 = true;
170 break;
171 #endif
172
173 case OPT_pg:
174 case OPT_p:
175 saw_profile_flag = true;
176 break;
177
178 case OPT_x:
179 if (library == 0 && strcmp (arg, "go") == 0)
180 library = 1;
181 break;
182
183 case OPT_Xlinker:
184 case OPT_Wl_:
185 /* Arguments that go directly to the linker might be .o files,
186 or something, and so might cause libgo to be needed. */
187 if (library == 0)
188 library = 1;
189 break;
190
191 case OPT_c:
192 case OPT_E:
193 case OPT_M:
194 case OPT_MM:
195 case OPT_fsyntax_only:
196 /* Don't specify libraries if we won't link, since that would
197 cause a warning. */
198 saw_opt_c = true;
199 library = -1;
200 break;
201
202 case OPT_S:
203 saw_opt_S = true;
204 library = -1;
205 break;
206
207 case OPT_o:
208 saw_opt_o = true;
209 break;
210
211 case OPT_static:
212 static_link = 1;
213 break;
214
215 case OPT_static_libgcc:
216 shared_libgcc = 0;
217 break;
218
219 case OPT_static_libgo:
220 library = library >= 0 ? 2 : library;
221 args[i] |= SKIPOPT;
222 break;
223
224 case OPT_SPECIAL_input_file:
225 if (library == 0)
226 library = 1;
227
228 if (first_go_file == NULL)
229 {
230 int len;
231
232 len = strlen (arg);
233 if (len > 3 && strcmp (arg + len - 3, ".go") == 0)
234 first_go_file = arg;
235 }
236
237 break;
238 }
239 }
240
241 /* There's no point adding -shared-libgcc if we don't have a shared
242 libgcc. */
243 #ifndef ENABLE_SHARED_LIBGCC
244 shared_libgcc = 0;
245 #endif
246
247 /* Make sure to have room for the trailing NULL argument. */
248 num_args = argc + need_math + shared_libgcc + (library > 0) * 5 + 10;
249 new_decoded_options = XNEWVEC (struct cl_decoded_option, num_args);
250
251 i = 0;
252 j = 0;
253
254 /* Copy the 0th argument, i.e., the name of the program itself. */
255 new_decoded_options[j++] = decoded_options[i++];
256
257 #ifdef TARGET_CAN_SPLIT_STACK
258 supports_split_stack = 1;
259 #endif
260
261 #ifdef TARGET_CAN_SPLIT_STACK_64BIT
262 if (is_m64)
263 supports_split_stack = 1;
264 #endif
265
266 /* If we are linking, pass -fsplit-stack if it is supported. */
267 if ((library >= 0) && supports_split_stack)
268 {
269 generate_option (OPT_fsplit_stack, NULL, 1, CL_DRIVER,
270 &new_decoded_options[j]);
271 j++;
272 }
273
274 /* NOTE: We start at 1 now, not 0. */
275 while (i < argc)
276 {
277 new_decoded_options[j] = decoded_options[i];
278
279 /* Make sure -lgo is before the math library, since libgo itself
280 uses those math routines. */
281 if (!saw_math && (args[i] & MATHLIB) && library > 0)
282 {
283 --j;
284 saw_math = &decoded_options[i];
285 }
286
287 if (!saw_thread && (args[i] & THREADLIB) && library > 0)
288 {
289 --j;
290 saw_thread = &decoded_options[i];
291 }
292
293 if (!saw_libc && (args[i] & WITHLIBC) && library > 0)
294 {
295 --j;
296 saw_libc = &decoded_options[i];
297 }
298
299 if ((args[i] & SKIPOPT) != 0)
300 --j;
301
302 i++;
303 j++;
304 }
305
306 /* If we didn't see a -o option, add one. This is because we need
307 the driver to pass all .go files to go1. Without a -o option the
308 driver will invoke go1 separately for each input file. FIXME:
309 This should probably use some other interface to force the driver
310 to set combine_inputs. */
311 if (first_go_file != NULL && !saw_opt_o)
312 {
313 if (saw_opt_c || saw_opt_S)
314 {
315 const char *base;
316 int baselen;
317 int alen;
318 char *out;
319
320 base = lbasename (first_go_file);
321 baselen = strlen (base) - 3;
322 alen = baselen + 3;
323 out = XNEWVEC (char, alen);
324 memcpy (out, base, baselen);
325 /* The driver will convert .o to some other suffix (e.g.,
326 .obj) if appropriate. */
327 out[baselen] = '.';
328 if (saw_opt_S)
329 out[baselen + 1] = 's';
330 else
331 out[baselen + 1] = 'o';
332 out[baselen + 2] = '\0';
333 generate_option (OPT_o, out, 1, CL_DRIVER,
334 &new_decoded_options[j]);
335 }
336 else
337 generate_option (OPT_o, "a.out", 1, CL_DRIVER,
338 &new_decoded_options[j]);
339 j++;
340 }
341
342 /* Add `-lgo' if we haven't already done so. */
343 if (library > 0)
344 {
345 generate_option (OPT_l, LIBGOBEGIN, 1, CL_DRIVER,
346 &new_decoded_options[j]);
347 added_libraries++;
348 j++;
349
350 #ifdef HAVE_LD_STATIC_DYNAMIC
351 if (library > 1 && !static_link)
352 {
353 generate_option (OPT_Wl_, LD_STATIC_OPTION, 1, CL_DRIVER,
354 &new_decoded_options[j]);
355 j++;
356 }
357 #endif
358
359 generate_option (OPT_l, saw_profile_flag ? LIBGO_PROFILE : LIBGO, 1,
360 CL_DRIVER, &new_decoded_options[j]);
361 added_libraries++;
362 j++;
363
364 #ifdef HAVE_LD_STATIC_DYNAMIC
365 if (library > 1 && !static_link)
366 {
367 generate_option (OPT_Wl_, LD_DYNAMIC_OPTION, 1, CL_DRIVER,
368 &new_decoded_options[j]);
369 j++;
370 }
371 #endif
372
373 /* When linking libgo statically we also need to link with the
374 pthread library. */
375 if (library > 1 || static_link)
376 need_thread = 1;
377 }
378
379 if (saw_thread)
380 new_decoded_options[j++] = *saw_thread;
381 else if (library > 0 && need_thread)
382 {
383 generate_option (OPT_l,
384 (saw_profile_flag
385 ? THREAD_LIBRARY_PROFILE
386 : THREAD_LIBRARY),
387 1, CL_DRIVER, &new_decoded_options[j]);
388 added_libraries++;
389 j++;
390 }
391
392 if (saw_math)
393 new_decoded_options[j++] = *saw_math;
394 else if (library > 0 && need_math)
395 {
396 generate_option (OPT_l,
397 saw_profile_flag ? MATH_LIBRARY_PROFILE : MATH_LIBRARY,
398 1, CL_DRIVER, &new_decoded_options[j]);
399 added_libraries++;
400 j++;
401 }
402
403 if (saw_libc)
404 new_decoded_options[j++] = *saw_libc;
405 if (shared_libgcc && !static_link)
406 generate_option (OPT_shared_libgcc, NULL, 1, CL_DRIVER,
407 &new_decoded_options[j++]);
408
409 /* libgcc wraps pthread_create to support split stack, however, due to
410 relative ordering of -lpthread and -lgcc, we can't just mark
411 __real_pthread_create in libgcc as non-weak. But we need to link in
412 pthread_create from pthread if we are statically linking, so we work-
413 around by passing -u pthread_create to the linker. */
414 if (static_link && supports_split_stack)
415 {
416 generate_option (OPT_Wl_, "-u,pthread_create", 1, CL_DRIVER,
417 &new_decoded_options[j]);
418 j++;
419 }
420
421 #if defined(TARGET_SOLARIS) && !defined(USE_GLD)
422 /* We use a common symbol for go$zerovalue. On Solaris, when not
423 using the GNU linker, the Solaris linker needs an option to not
424 warn about this. Everything works without this option, but you
425 get unsightly warnings at link time. */
426 generate_option (OPT_Wl_, "-t", 1, CL_DRIVER, &new_decoded_options[j]);
427 j++;
428 #endif
429
430 *in_decoded_options_count = j;
431 *in_decoded_options = new_decoded_options;
432 *in_added_libraries = added_libraries;
433 }
434
435 /* Called before linking. Returns 0 on success and -1 on failure. */
436 int lang_specific_pre_link (void) /* Not used for Go. */
437 {
438 return 0;
439 }
440
441 /* Number of extra output files that lang_specific_pre_link may generate. */
442 int lang_specific_extra_outfiles = 0; /* Not used for Go. */