Branch data Line data Source code
1 : : /* Specific flags and argument handling of the C++ front end.
2 : : Copyright (C) 1996-2025 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
7 : : it under the terms of the GNU General Public License as published by
8 : : the Free Software Foundation; either version 3, or (at your option)
9 : : any later version.
10 : :
11 : : GCC is distributed in the hope that it will be useful,
12 : : but WITHOUT ANY WARRANTY; without even the implied warranty of
13 : : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 : : GNU General Public License 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 `-lc'. */
31 : : #define WITHLIBC (1<<3)
32 : : /* Skip this option. */
33 : : #define SKIPOPT (1<<4)
34 : : /* Add -lstdc++exp for experimental features that need library support. */
35 : : #define EXPERIMENTAL (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 : : #ifndef LIBSTDCXX
45 : : #define LIBSTDCXX "stdc++"
46 : : #endif
47 : : #ifndef LIBSTDCXX_PROFILE
48 : : #define LIBSTDCXX_PROFILE LIBSTDCXX
49 : : #endif
50 : : #ifndef LIBSTDCXX_STATIC
51 : : #define LIBSTDCXX_STATIC NULL
52 : : #endif
53 : :
54 : : #ifndef LIBCXX
55 : : #define LIBCXX "c++"
56 : : #endif
57 : : #ifndef LIBCXX_PROFILE
58 : : #define LIBCXX_PROFILE LIBCXX
59 : : #endif
60 : : #ifndef LIBCXX_STATIC
61 : : #define LIBCXX_STATIC NULL
62 : : #endif
63 : :
64 : : #ifndef LIBCXXABI
65 : : #define LIBCXXABI "c++abi"
66 : : #endif
67 : : #ifndef LIBCXXABI_PROFILE
68 : : #define LIBCXXABI_PROFILE LIBCXXABI
69 : : #endif
70 : : #ifndef LIBCXXABI_STATIC
71 : : #define LIBCXXABI_STATIC NULL
72 : : #endif
73 : :
74 : : /* The values used here must match those of the stdlib_kind enumeration
75 : : in c.opt. */
76 : : enum stdcxxlib_kind
77 : : {
78 : : USE_LIBSTDCXX = 1,
79 : : USE_LIBCXX = 2
80 : : };
81 : :
82 : : void
83 : 101686 : lang_specific_driver (struct cl_decoded_option **in_decoded_options,
84 : : unsigned int *in_decoded_options_count,
85 : : int *in_added_libraries)
86 : : {
87 : 101686 : unsigned int i, j;
88 : :
89 : : /* If nonzero, the user gave us the `-p' or `-pg' flag. */
90 : 101686 : int saw_profile_flag = 0;
91 : :
92 : : /* What action to take for the c++ runtime library:
93 : : -1 means we should not link it in.
94 : : 0 means we should link it if it is needed.
95 : : 1 means it is needed and should be linked in.
96 : : 2 means it is needed but should be linked statically. */
97 : 101686 : int library = 0;
98 : :
99 : : /* Which c++ runtime library to link. */
100 : 101686 : stdcxxlib_kind which_library = USE_LIBSTDCXX;
101 : :
102 : : /* The number of arguments being added to what's in argv, other than
103 : : libraries. We use this to track the number of times we've inserted
104 : : -xc++/-xnone. */
105 : 101686 : int added = 0;
106 : :
107 : : /* The new argument list will be contained in this. */
108 : 101686 : struct cl_decoded_option *new_decoded_options;
109 : :
110 : : /* Nonzero if we saw a `-xfoo' language specification on the
111 : : command line. Used to avoid adding our own -xc++ if the user
112 : : already gave a language for the file. */
113 : 101686 : int saw_speclang = 0;
114 : :
115 : : /* "-lm" or "-lmath" if it appears on the command line. */
116 : 101686 : const struct cl_decoded_option *saw_math = NULL;
117 : :
118 : : /* "-lrt" or eqivalent if it appears on the command line. */
119 : 101686 : const struct cl_decoded_option *saw_time = NULL;
120 : :
121 : : /* "-lc" if it appears on the command line. */
122 : 101686 : const struct cl_decoded_option *saw_libc = NULL;
123 : :
124 : : /* An array used to flag each argument that needs a bit set for
125 : : LANGSPEC, MATHLIB, or WITHLIBC. */
126 : 101686 : int *args;
127 : :
128 : : /* By default, we throw on the math library if we have one. */
129 : 101686 : int need_math = (MATH_LIBRARY[0] != '\0');
130 : :
131 : : /* By default, we don't add -lstdc++exp. */
132 : 101686 : bool need_experimental = false;
133 : :
134 : : /* Whether to also compile module std. */
135 : 101686 : bool std_module = false;
136 : :
137 : : /* True if we saw -static. */
138 : 101686 : int static_link = 0;
139 : :
140 : : /* True if we should add -shared-libgcc to the command-line. */
141 : 101686 : int shared_libgcc = 1;
142 : :
143 : : /* The total number of arguments with the new stuff. */
144 : 101686 : unsigned int argc;
145 : :
146 : : /* The argument list. */
147 : 101686 : struct cl_decoded_option *decoded_options;
148 : :
149 : : /* The number of libraries added in. */
150 : 101686 : int added_libraries;
151 : :
152 : : /* The total number of arguments with the new stuff. */
153 : 101686 : unsigned int num_args = 1;
154 : :
155 : 101686 : argc = *in_decoded_options_count;
156 : 101686 : decoded_options = *in_decoded_options;
157 : 101686 : added_libraries = *in_added_libraries;
158 : :
159 : 101686 : args = XCNEWVEC (int, argc);
160 : :
161 : 2699216 : for (i = 1; i < argc; i++)
162 : : {
163 : 2597530 : const char *arg = decoded_options[i].arg;
164 : 2597530 : if (decoded_options[i].errors & CL_ERR_MISSING_ARG)
165 : 0 : continue; /* Avoid examining arguments of options missing them. */
166 : :
167 : 2597530 : switch (decoded_options[i].opt_index)
168 : : {
169 : : case OPT_fcontracts:
170 : 2597530 : need_experimental = true;
171 : : break;
172 : :
173 : 3 : case OPT_nostdlib__:
174 : 3 : args[i] |= SKIPOPT;
175 : : /* FALLTHRU */
176 : : case OPT_nostdlib:
177 : : case OPT_nodefaultlibs:
178 : : library = -1;
179 : : break;
180 : :
181 : 21349 : case OPT_l:
182 : 21349 : if (strcmp (arg, MATH_LIBRARY) == 0)
183 : : {
184 : 21144 : args[i] |= MATHLIB;
185 : 21144 : need_math = 0;
186 : : }
187 : 205 : else if (strcmp (arg, "c") == 0)
188 : 0 : args[i] |= WITHLIBC;
189 : : else
190 : : /* Unrecognized libraries (e.g. -lfoo) may require libstdc++. */
191 : 205 : library = (library == 0) ? 1 : library;
192 : : break;
193 : :
194 : 87 : case OPT_pg:
195 : 87 : case OPT_p:
196 : 87 : saw_profile_flag++;
197 : 87 : break;
198 : :
199 : 2880 : case OPT_x:
200 : 2880 : if (library == 0
201 : 2824 : && (strcmp (arg, "c++") == 0
202 : 2824 : || strcmp (arg, "c++-cpp-output") == 0
203 : 2824 : || strcmp (arg, "objective-c++") == 0
204 : 2824 : || strcmp (arg, "objective-c++-cpp-output") == 0))
205 : 0 : library = 1;
206 : :
207 : : saw_speclang = 1;
208 : : break;
209 : :
210 : 6773 : case OPT_Xlinker:
211 : 6773 : case OPT_Wl_:
212 : : /* Arguments that go directly to the linker might be .o files,
213 : : or something, and so might cause libstdc++ to be needed. */
214 : 6773 : if (library == 0)
215 : 2597530 : library = 1;
216 : : break;
217 : :
218 : 77251 : case OPT_c:
219 : 77251 : case OPT_r:
220 : 77251 : case OPT_S:
221 : 77251 : case OPT_E:
222 : 77251 : case OPT_M:
223 : 77251 : case OPT_MM:
224 : 77251 : case OPT_fsyntax_only:
225 : : /* Don't specify libraries if we won't link, since that would
226 : : cause a warning. */
227 : 77251 : library = -1;
228 : 77251 : break;
229 : :
230 : 30 : case OPT_static:
231 : 30 : static_link = 1;
232 : 30 : break;
233 : :
234 : 1 : case OPT_static_libgcc:
235 : 1 : shared_libgcc = 0;
236 : 1 : break;
237 : :
238 : 10 : case OPT_static_libstdc__:
239 : 10 : library = library >= 0 ? 2 : library;
240 : : #ifdef HAVE_LD_STATIC_DYNAMIC
241 : : /* Remove -static-libstdc++ from the command only if target supports
242 : : LD_STATIC_DYNAMIC. When not supported, it is left in so that a
243 : : back-end target can use outfile substitution. */
244 : 10 : args[i] |= SKIPOPT;
245 : : #endif
246 : 10 : break;
247 : :
248 : 0 : case OPT_stdlib_:
249 : 0 : which_library = (stdcxxlib_kind) decoded_options[i].value;
250 : 0 : break;
251 : :
252 : 1 : case OPT__compile_std_module:
253 : 1 : std_module = true;
254 : 1 : break;
255 : :
256 : 106449 : case OPT_SPECIAL_input_file:
257 : 106449 : {
258 : 106449 : int len;
259 : :
260 : : /* We don't do this anymore, since we don't get them with minus
261 : : signs on them. */
262 : 106449 : if (arg[0] == '\0' || arg[1] == '\0')
263 : 0 : continue;
264 : :
265 : 106449 : if (saw_speclang)
266 : : {
267 : 2871 : saw_speclang = 0;
268 : 2871 : continue;
269 : : }
270 : :
271 : : /* If the filename ends in .[chi], put options around it.
272 : : But not if a specified -x option is currently active. */
273 : 103578 : len = strlen (arg);
274 : 103578 : if (len > 2
275 : 103578 : && (arg[len - 1] == 'c'
276 : 77228 : || arg[len - 1] == 'i'
277 : 77228 : || arg[len - 1] == 'h')
278 : 26350 : && arg[len - 2] == '.')
279 : : {
280 : 13037 : args[i] |= LANGSPEC;
281 : 13037 : added += 2;
282 : : }
283 : :
284 : : /* If we don't know that this is a header file, we might
285 : : need to be linking in the libraries. */
286 : 103578 : if (library == 0)
287 : : {
288 : 85675 : if ((len <= 2 || strcmp (arg + (len - 2), ".H") != 0)
289 : 85675 : && (len <= 2 || strcmp (arg + (len - 2), ".h") != 0)
290 : 84705 : && (len <= 4 || strcmp (arg + (len - 4), ".hpp") != 0)
291 : 84705 : && (len <= 3 || strcmp (arg + (len - 3), ".hp") != 0)
292 : 84705 : && (len <= 4 || strcmp (arg + (len - 4), ".hxx") != 0)
293 : 84705 : && (len <= 4 || strcmp (arg + (len - 4), ".h++") != 0)
294 : 84705 : && (len <= 4 || strcmp (arg + (len - 4), ".HPP") != 0)
295 : 84705 : && (len <= 4 || strcmp (arg + (len - 4), ".tcc") != 0)
296 : 84705 : && (len <= 3 || strcmp (arg + (len - 3), ".hh") != 0))
297 : 2597530 : library = 1;
298 : : }
299 : : }
300 : : break;
301 : : }
302 : : }
303 : :
304 : : /* There's no point adding -shared-libgcc if we don't have a shared
305 : : libgcc. */
306 : : #ifndef ENABLE_SHARED_LIBGCC
307 : : shared_libgcc = 0;
308 : : #endif
309 : :
310 : : /* Add one for shared_libgcc or extra static library. */
311 : 203372 : num_args = (argc + added + need_math + need_experimental
312 : 101686 : + (std_module * 5)
313 : 101686 : + (library > 0) * 4 + 1);
314 : : /* For libc++, on most platforms, the ABI library (usually called libc++abi)
315 : : is provided as a separate DSO, which we must also append.
316 : : However, a platform might have the ability to forward the ABI library
317 : : from libc++, or combine it in some other way; in that case, LIBCXXABI
318 : : should be set to NULL to signal that it need not be appended. */
319 : 101686 : if (which_library == USE_LIBCXX && LIBCXXABI != NULL)
320 : 0 : num_args += 4;
321 : 101686 : new_decoded_options = XNEWVEC (struct cl_decoded_option, num_args);
322 : :
323 : 101686 : i = 0;
324 : 101686 : j = 0;
325 : :
326 : : /* Copy the 0th argument, i.e., the name of the program itself. */
327 : 101686 : new_decoded_options[j++] = decoded_options[i++];
328 : :
329 : : /* NOTE: We start at 1 now, not 0. */
330 : 2699216 : while (i < argc)
331 : : {
332 : 2597530 : new_decoded_options[j] = decoded_options[i];
333 : :
334 : : /* Make sure -lstdc++ is before the math library, since libstdc++
335 : : itself uses those math routines. */
336 : 2597530 : if (!saw_math && (args[i] & MATHLIB) && library > 0)
337 : : {
338 : 21136 : --j;
339 : 21136 : saw_math = &decoded_options[i];
340 : : }
341 : :
342 : 2597530 : if (!saw_libc && (args[i] & WITHLIBC) && library > 0)
343 : : {
344 : 0 : --j;
345 : 0 : saw_libc = &decoded_options[i];
346 : : }
347 : :
348 : : /* Insert --compile-std-module options before any -x or source files. */
349 : 2597530 : size_t opt = decoded_options[i].opt_index;
350 : 2597530 : if (std_module
351 : 4 : && (opt == OPT__compile_std_module
352 : 4 : || opt == OPT_SPECIAL_input_file
353 : 3 : || opt == OPT_x))
354 : : {
355 : 1 : generate_option (OPT_x, "c++-system-header", 1, CL_DRIVER,
356 : 1 : &new_decoded_options[j++]);
357 : 1 : generate_option_input_file ("bits/stdc++.h",
358 : 1 : &new_decoded_options[j]);
359 : : /* Tell process_command that this file was added by the driver. */
360 : 1 : new_decoded_options[j++].mask = CL_DRIVER;
361 : 1 : generate_option (OPT_x, "c++-system-module", 1, CL_DRIVER,
362 : 1 : &new_decoded_options[j++]);
363 : 1 : generate_option_input_file ("bits/std.cc",
364 : 1 : &new_decoded_options[j]);
365 : 1 : new_decoded_options[j++].mask = CL_DRIVER;
366 : 1 : generate_option_input_file ("bits/std.compat.cc",
367 : 1 : &new_decoded_options[j]);
368 : 1 : new_decoded_options[j++].mask = CL_DRIVER;
369 : 1 : generate_option (OPT_x, "none", 1, CL_DRIVER,
370 : 1 : &new_decoded_options[j++]);
371 : 1 : new_decoded_options[j] = decoded_options[i];
372 : 1 : std_module = false;
373 : : }
374 : 2597530 : if (opt == OPT__compile_std_module)
375 : 1 : --j;
376 : :
377 : : /* Wrap foo.[chi] files in a language specification to
378 : : force the gcc compiler driver to run cc1plus on them. */
379 : 2597530 : if (args[i] & LANGSPEC)
380 : : {
381 : 13037 : const char *arg = decoded_options[i].arg;
382 : 13037 : int len = strlen (arg);
383 : 13037 : switch (arg[len - 1])
384 : : {
385 : 13037 : case 'c':
386 : 13037 : generate_option (OPT_x, "c++", 1, CL_DRIVER,
387 : 13037 : &new_decoded_options[j++]);
388 : 13037 : break;
389 : 0 : case 'i':
390 : 0 : generate_option (OPT_x, "c++-cpp-output", 1, CL_DRIVER,
391 : 0 : &new_decoded_options[j++]);
392 : 0 : break;
393 : 0 : case 'h':
394 : 0 : generate_option (OPT_x, "c++-header", 1, CL_DRIVER,
395 : 0 : &new_decoded_options[j++]);
396 : 0 : break;
397 : 0 : default:
398 : 0 : gcc_unreachable ();
399 : : }
400 : 13037 : new_decoded_options[j++] = decoded_options[i];
401 : 13037 : generate_option (OPT_x, "none", 1, CL_DRIVER,
402 : 13037 : &new_decoded_options[j]);
403 : : }
404 : :
405 : 2597530 : if ((args[i] & SKIPOPT) != 0)
406 : 13 : --j;
407 : :
408 : 2597530 : i++;
409 : 2597530 : j++;
410 : : }
411 : :
412 : : /* Add `-lstdc++' if we haven't already done so. */
413 : 101686 : if (library > 0)
414 : : {
415 : 21546 : if (need_experimental && which_library == USE_LIBSTDCXX)
416 : : {
417 : 58 : generate_option (OPT_l, "stdc++exp", 1, CL_DRIVER,
418 : 58 : &new_decoded_options[j++]);
419 : 58 : ++added_libraries;
420 : : }
421 : : #ifdef HAVE_LD_STATIC_DYNAMIC
422 : 21546 : if (library > 1 && !static_link)
423 : : {
424 : 10 : generate_option (OPT_Wl_, LD_STATIC_OPTION, 1, CL_DRIVER,
425 : 10 : &new_decoded_options[j]);
426 : 10 : j++;
427 : : }
428 : : #endif
429 : 21546 : if (which_library == USE_LIBCXX)
430 : : {
431 : 0 : generate_option (OPT_l,
432 : : saw_profile_flag ? LIBCXX_PROFILE : LIBCXX, 1,
433 : 0 : CL_DRIVER, &new_decoded_options[j]);
434 : 0 : if (LIBCXXABI != NULL)
435 : : {
436 : 0 : j++;
437 : 0 : added_libraries++;
438 : 0 : generate_option (OPT_l,
439 : : saw_profile_flag ? LIBCXXABI_PROFILE
440 : : : LIBCXXABI, 1,
441 : 0 : CL_DRIVER, &new_decoded_options[j]);
442 : : }
443 : : }
444 : : else
445 : 21546 : generate_option (OPT_l,
446 : : saw_profile_flag ? LIBSTDCXX_PROFILE : LIBSTDCXX, 1,
447 : 21546 : CL_DRIVER, &new_decoded_options[j]);
448 : 21546 : added_libraries++;
449 : 21546 : j++;
450 : : /* Add target-dependent static library, if necessary. */
451 : 21546 : if ((static_link || library > 1) && LIBSTDCXX_STATIC != NULL)
452 : : {
453 : : generate_option (OPT_l, LIBSTDCXX_STATIC, 1,
454 : : CL_DRIVER, &new_decoded_options[j]);
455 : : added_libraries++;
456 : : j++;
457 : : }
458 : : #ifdef HAVE_LD_STATIC_DYNAMIC
459 : 21546 : if (library > 1 && !static_link)
460 : : {
461 : 10 : generate_option (OPT_Wl_, LD_DYNAMIC_OPTION, 1, CL_DRIVER,
462 : 10 : &new_decoded_options[j]);
463 : 10 : j++;
464 : : }
465 : : #endif
466 : : }
467 : 101686 : if (saw_math)
468 : 21136 : new_decoded_options[j++] = *saw_math;
469 : 80550 : else if (library > 0 && need_math)
470 : : {
471 : 410 : generate_option (OPT_l,
472 : : saw_profile_flag ? MATH_LIBRARY_PROFILE : MATH_LIBRARY,
473 : 410 : 1, CL_DRIVER, &new_decoded_options[j]);
474 : 410 : added_libraries++;
475 : 410 : j++;
476 : : }
477 : 101686 : if (saw_time)
478 : : new_decoded_options[j++] = *saw_time;
479 : 101686 : if (saw_libc)
480 : 0 : new_decoded_options[j++] = *saw_libc;
481 : 101686 : if (shared_libgcc && !static_link)
482 : 101655 : generate_option (OPT_shared_libgcc, NULL, 1, CL_DRIVER,
483 : 101655 : &new_decoded_options[j++]);
484 : :
485 : 101686 : *in_decoded_options_count = j;
486 : 101686 : *in_decoded_options = new_decoded_options;
487 : 101686 : *in_added_libraries = added_libraries;
488 : 101686 : }
489 : :
490 : : /* Called before linking. Returns 0 on success and -1 on failure. */
491 : 79051 : int lang_specific_pre_link (void) /* Not used for C++. */
492 : : {
493 : 79051 : return 0;
494 : : }
495 : :
496 : : /* Number of extra output files that lang_specific_pre_link may generate. */
497 : : int lang_specific_extra_outfiles = 0; /* Not used for C++. */
|