LCOV - code coverage report
Current view: top level - gcc/m2 - gm2spec.cc (source / functions) Coverage Total Hit
Test: gcc.info Lines: 77.3 % 374 289
Test Date: 2024-04-13 14:00:49 Functions: 92.3 % 13 12
Legend: Lines: hit not hit | Branches: + taken - not taken # not executed Branches: - 0 0

             Branch data     Line data    Source code
       1                 :             : /* gm2spec.cc specific flags and argument handling within GNU Modula-2.
       2                 :             : 
       3                 :             : Copyright (C) 2007-2024 Free Software Foundation, Inc.
       4                 :             : Contributed by Gaius Mulley <gaius@glam.ac.uk>.
       5                 :             : 
       6                 :             : This file is part of GNU Modula-2.
       7                 :             : 
       8                 :             : GNU Modula-2 is free software; you can redistribute it and/or modify
       9                 :             : it under the terms of the GNU General Public License as published by
      10                 :             : the Free Software Foundation; either version 3, or (at your option)
      11                 :             : any later version.
      12                 :             : 
      13                 :             : GNU Modula-2 is distributed in the hope that it will be useful, but
      14                 :             : WITHOUT ANY WARRANTY; without even the implied warranty of
      15                 :             : MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
      16                 :             : General Public License for more details.
      17                 :             : 
      18                 :             : You should have received a copy of the GNU General Public License
      19                 :             : along with GNU Modula-2; see the file COPYING3.  If not see
      20                 :             : <http://www.gnu.org/licenses/>.  */
      21                 :             : 
      22                 :             : #include "config.h"
      23                 :             : #include "system.h"
      24                 :             : #include "coretypes.h"
      25                 :             : #include "tm.h"
      26                 :             : #include "xregex.h"
      27                 :             : #include "obstack.h"
      28                 :             : #include "intl.h"
      29                 :             : #include "prefix.h"
      30                 :             : #include "opt-suggestions.h"
      31                 :             : #include "gcc.h"
      32                 :             : #include "opts.h"
      33                 :             : #include "vec.h"
      34                 :             : #include <vector>
      35                 :             : #include <string>
      36                 :             : 
      37                 :             : #include "m2/gm2config.h"
      38                 :             : 
      39                 :             : #ifdef HAVE_DIRENT_H
      40                 :             : #include <dirent.h>
      41                 :             : #else
      42                 :             : #ifdef HAVE_SYS_NDIR_H
      43                 :             : #include <sys/ndir.h>
      44                 :             : #endif
      45                 :             : #ifdef HAVE_SYS_DIR_H
      46                 :             : #include <sys/dir.h>
      47                 :             : #endif
      48                 :             : #ifdef HAVE_NDIR_H
      49                 :             : #include <ndir.h>
      50                 :             : #endif
      51                 :             : #endif
      52                 :             : 
      53                 :             : /* This bit is set if the arguments is a M2 source file.  */
      54                 :             : #define M2SOURCE        (1<<1)
      55                 :             : /* This bit is set if we saw a `-xfoo' language specification.  */
      56                 :             : #define LANGSPEC        (1<<2)
      57                 :             : /* This bit is set if they did `-lm' or `-lmath'.  */
      58                 :             : #define MATHLIB         (1<<3)
      59                 :             : /* This bit is set if they did `-lc'.  */
      60                 :             : #define WITHLIBC        (1<<4)
      61                 :             : /* Skip this option.  */
      62                 :             : #define SKIPOPT         (1<<5)
      63                 :             : 
      64                 :             : #ifndef MATH_LIBRARY
      65                 :             : #define MATH_LIBRARY "m"
      66                 :             : #endif
      67                 :             : #ifndef MATH_LIBRARY_PROFILE
      68                 :             : #define MATH_LIBRARY_PROFILE MATH_LIBRARY
      69                 :             : #endif
      70                 :             : 
      71                 :             : #ifndef LIBSTDCXX
      72                 :             : #define LIBSTDCXX "stdc++"
      73                 :             : #endif
      74                 :             : #ifndef LIBSTDCXX_PROFILE
      75                 :             : #define LIBSTDCXX_PROFILE LIBSTDCXX
      76                 :             : #endif
      77                 :             : #ifndef LIBSTDCXX_STATIC
      78                 :             : #define LIBSTDCXX_STATIC NULL
      79                 :             : #endif
      80                 :             : 
      81                 :             : #ifndef LIBCXX
      82                 :             : #define LIBCXX "c++"
      83                 :             : #endif
      84                 :             : #ifndef LIBCXX_PROFILE
      85                 :             : #define LIBCXX_PROFILE LIBCXX
      86                 :             : #endif
      87                 :             : #ifndef LIBCXX_STATIC
      88                 :             : #define LIBCXX_STATIC NULL
      89                 :             : #endif
      90                 :             : 
      91                 :             : #ifndef LIBCXXABI
      92                 :             : #define LIBCXXABI "c++abi"
      93                 :             : #endif
      94                 :             : #ifndef LIBCXXABI_PROFILE
      95                 :             : #define LIBCXXABI_PROFILE LIBCXXABI
      96                 :             : #endif
      97                 :             : #ifndef LIBCXXABI_STATIC
      98                 :             : #define LIBCXXABI_STATIC NULL
      99                 :             : #endif
     100                 :             : 
     101                 :             : /* The values used here must match those of the stdlib_kind enumeration
     102                 :             :    in c.opt.  */
     103                 :             : enum stdcxxlib_kind
     104                 :             : {
     105                 :             :   USE_LIBSTDCXX = 1,
     106                 :             :   USE_LIBCXX = 2
     107                 :             : };
     108                 :             : 
     109                 :             : #define DEFAULT_DIALECT "pim"
     110                 :             : 
     111                 :             : #undef DEBUG_ARG
     112                 :             : 
     113                 :             : typedef enum { iso, pim, min, logitech, pimcoroutine, maxlib } libs;
     114                 :             : 
     115                 :             : /* These are the library names which are installed as part of gm2 and reflect
     116                 :             :    -flibs=name.  The -flibs= option provides the user with a short cut to add
     117                 :             :    libraries without having to know the include and link path.  */
     118                 :             : 
     119                 :             : static const char *library_name[maxlib]
     120                 :             :     = { "m2iso", "m2pim", "m2min", "m2log", "m2cor" };
     121                 :             : 
     122                 :             : /* They match the installed archive name for example libm2iso.a,
     123                 :             :    libm2pim.a, libm2min.a, libm2log.a and libm2cor.a.  They also match a
     124                 :             :    subdirectory name where the definition modules are kept.  The driver
     125                 :             :    checks the argument to -flibs= for an entry in library_name or
     126                 :             :    alternatively the existance of the subdirectory (to allow for third
     127                 :             :    party libraries to coexist).  */
     128                 :             : 
     129                 :             : static const char *library_abbrev[maxlib]
     130                 :             :     = { "iso", "pim", "min", "log", "cor" };
     131                 :             : 
     132                 :             : /* Users may specifiy -flibs=pim,iso etc which are mapped onto
     133                 :             :    -flibs=m2pim,m2iso respectively.  This provides a match between
     134                 :             :    the dialect of Modula-2 and the library set.  */
     135                 :             : 
     136                 :             : static bool seen_scaffold_static = false;
     137                 :             : static bool seen_scaffold_dynamic = false;
     138                 :             : static bool seen_scaffold_main = false;
     139                 :             : static bool scaffold_static = false;
     140                 :             : static bool scaffold_dynamic = true; // Default uses -fscaffold-dynamic.
     141                 :             : static bool scaffold_main = false;
     142                 :             : static bool seen_gen_module_list = false;
     143                 :             : static bool seen_uselist = false;
     144                 :             : static bool uselist = false;
     145                 :             : static bool gen_module_list = true;  // Default uses -fgen-module-list=-.
     146                 :             : static const char *gen_module_filename = "-";
     147                 :             : /* The original argument list and related info is copied here.  */
     148                 :             : static unsigned int gm2_xargc;
     149                 :             : static const struct cl_decoded_option *gm2_x_decoded_options;
     150                 :             : static void append_arg (const struct cl_decoded_option *);
     151                 :             : 
     152                 :             : /* The new argument list will be built here.  */
     153                 :             : static unsigned int gm2_newargc;
     154                 :             : static struct cl_decoded_option *gm2_new_decoded_options;
     155                 :             : static const char *libraries = NULL;  /* Abbreviated libraries.  */
     156                 :             : static const char *m2_path_name = "";
     157                 :             : 
     158                 :      237456 : typedef struct named_path_s {
     159                 :             :   std::vector<const char*>path;
     160                 :             :   const char *name;
     161                 :             : } named_path;
     162                 :             : 
     163                 :             : static std::vector<named_path>Ipaths;
     164                 :             : 
     165                 :             : 
     166                 :             : static void
     167                 :      106926 : push_back_Ipath (const char *arg)
     168                 :             : {
     169                 :      106926 :   if (Ipaths.empty ())
     170                 :             :     {
     171                 :       16690 :       named_path np;
     172                 :       16690 :       np.path.push_back (arg);
     173                 :       16690 :       np.name = m2_path_name;
     174                 :       16690 :       Ipaths.push_back (np);
     175                 :       16690 :     }
     176                 :             :   else
     177                 :             :     {
     178                 :       90236 :       if (strcmp (Ipaths.back ().name,
     179                 :             :                   m2_path_name) == 0)
     180                 :       32158 :         Ipaths.back ().path.push_back (arg);
     181                 :             :       else
     182                 :             :         {
     183                 :       58078 :           named_path np;
     184                 :       58078 :           np.path.push_back (arg);
     185                 :       58078 :           np.name = m2_path_name;
     186                 :       58078 :           Ipaths.push_back (np);
     187                 :       58078 :         }
     188                 :             :     }
     189                 :      106926 : }
     190                 :             : 
     191                 :             : /* Return whether strings S1 and S2 are both NULL or both the same
     192                 :             :    string.  */
     193                 :             : 
     194                 :             : static bool
     195                 :      356790 : strings_same (const char *s1, const char *s2)
     196                 :             : {
     197                 :      356790 :   return s1 == s2 || (s1 != NULL && s2 != NULL && strcmp (s1, s2) == 0);
     198                 :             : }
     199                 :             : 
     200                 :             : bool
     201                 :       74484 : options_same (const struct cl_decoded_option *opt1,
     202                 :             :               const struct cl_decoded_option *opt2)
     203                 :             : {
     204                 :       74484 :   return (opt1->opt_index == opt2->opt_index
     205                 :       59465 :           && strings_same (opt1->arg, opt2->arg)
     206                 :       59465 :           && strings_same (opt1->orig_option_with_args_text,
     207                 :       59465 :                            opt2->orig_option_with_args_text)
     208                 :       59465 :           && strings_same (opt1->canonical_option[0],
     209                 :       59465 :                            opt2->canonical_option[0])
     210                 :       59465 :           && strings_same (opt1->canonical_option[1],
     211                 :       59465 :                            opt2->canonical_option[1])
     212                 :       59465 :           && strings_same (opt1->canonical_option[2],
     213                 :       59465 :                            opt2->canonical_option[2])
     214                 :       59465 :           && strings_same (opt1->canonical_option[3],
     215                 :       59465 :                            opt2->canonical_option[3])
     216                 :       59465 :           && (opt1->canonical_option_num_elements
     217                 :       59465 :               == opt2->canonical_option_num_elements)
     218                 :       59465 :           && opt1->value == opt2->value
     219                 :      133949 :           && opt1->errors == opt2->errors);
     220                 :             : }
     221                 :             : 
     222                 :             : /* Append another argument to the list being built.  */
     223                 :             : 
     224                 :             : static void
     225                 :      542089 : append_arg (const struct cl_decoded_option *arg)
     226                 :             : {
     227                 :      542089 :   static unsigned int newargsize;
     228                 :             : 
     229                 :      542089 :   if (gm2_new_decoded_options == gm2_x_decoded_options
     230                 :       76155 :       && gm2_newargc < gm2_xargc
     231                 :      616573 :       && options_same (arg, &gm2_x_decoded_options[gm2_newargc]))
     232                 :             :     {
     233                 :       59465 :       ++gm2_newargc;
     234                 :       59465 :       return;                   /* Nothing new here.  */
     235                 :             :     }
     236                 :             : 
     237                 :      482624 :   if (gm2_new_decoded_options == gm2_x_decoded_options)
     238                 :             :     {                           /* Make new arglist.  */
     239                 :       16690 :       unsigned int i;
     240                 :             : 
     241                 :       16690 :       newargsize = (gm2_xargc << 2) + 20; /* This should handle all.  */
     242                 :       16690 :       gm2_new_decoded_options = XNEWVEC (struct cl_decoded_option, newargsize);
     243                 :             : 
     244                 :             :       /* Copy what has been done so far.  */
     245                 :       76155 :       for (i = 0; i < gm2_newargc; ++i)
     246                 :       59465 :         gm2_new_decoded_options[i] = gm2_x_decoded_options[i];
     247                 :             :     }
     248                 :             : 
     249                 :      482624 :   if (gm2_newargc == newargsize)
     250                 :           0 :     fatal_error (input_location, "overflowed output argument list for %qs",
     251                 :           0 :                  arg->orig_option_with_args_text);
     252                 :             : 
     253                 :      482624 :   gm2_new_decoded_options[gm2_newargc++] = *arg;
     254                 :             : }
     255                 :             : 
     256                 :             : /* Append an option described by OPT_INDEX, ARG and VALUE to the list
     257                 :             :    being built.  */
     258                 :             : 
     259                 :             : static void
     260                 :      286741 : append_option (size_t opt_index, const char *arg, int value)
     261                 :             : {
     262                 :      286741 :   struct cl_decoded_option decoded;
     263                 :             : 
     264                 :      286741 :   generate_option (opt_index, arg, value, CL_DRIVER, &decoded);
     265                 :      286741 :   append_arg (&decoded);
     266                 :      286741 : }
     267                 :             : 
     268                 :             : /* safe_strdup safely duplicates a string.  */
     269                 :             : 
     270                 :             : static char *
     271                 :      188354 : safe_strdup (const char *s)
     272                 :             : {
     273                 :           0 :   if (s != NULL)
     274                 :      106926 :     return xstrdup (s);
     275                 :             :   return NULL;
     276                 :             : }
     277                 :             : 
     278                 :             : /* add_default_libs adds the -l option which is derived from the
     279                 :             :    libraries.  */
     280                 :             : 
     281                 :             : static int
     282                 :        1665 : add_default_libs (const char *libraries)
     283                 :             : {
     284                 :        1665 :   const char *l = libraries;
     285                 :        1665 :   const char *e;
     286                 :        1665 :   char *libname;
     287                 :        1665 :   unsigned int libcount = 0;
     288                 :             : 
     289                 :        6660 :   while ((l != NULL) && (l[0] != (char)0))
     290                 :             :     {
     291                 :        6660 :       e = index (l, ',');
     292                 :        6660 :       if (e == NULL)
     293                 :             :         {
     294                 :        1665 :           libname = xstrdup (l);
     295                 :        1665 :           l = NULL;
     296                 :        1665 :           append_option (OPT_l, safe_strdup (libname), 1);
     297                 :        1665 :           libcount++;
     298                 :        1665 :           free (libname);
     299                 :             :         }
     300                 :             :       else
     301                 :             :         {
     302                 :        4995 :           libname = xstrndup (l, e - l);
     303                 :        4995 :           l = e + 1;
     304                 :        4995 :           append_option (OPT_l, safe_strdup (libname), 1);
     305                 :        4995 :           libcount++;
     306                 :        4995 :           free (libname);
     307                 :             :         }
     308                 :             :     }
     309                 :        1665 :   return libcount;
     310                 :             : }
     311                 :             : 
     312                 :             : /* add_word returns a new string which has the contents of lib
     313                 :             :    appended to list.  If list is NULL then lib is duplicated and
     314                 :             :    returned otherwise the list is appended by "," and the contents of
     315                 :             :    lib.  */
     316                 :             : 
     317                 :             : static const char *
     318                 :        9124 : add_word (const char *list, const char *lib)
     319                 :             : {
     320                 :        9124 :   char *copy;
     321                 :        9124 :   if (list == NULL)
     322                 :        2281 :     return xstrdup (lib);
     323                 :        6843 :   copy = (char *) xmalloc (strlen (list) + strlen (lib) + 1 + 1);
     324                 :        6843 :   strcpy (copy, list);
     325                 :        6843 :   strcat (copy, ",");
     326                 :        6843 :   strcat (copy, lib);
     327                 :        6843 :   return copy;
     328                 :             : }
     329                 :             : 
     330                 :             : /* convert_abbreviation checks abbreviation against known library
     331                 :             :    abbreviations.  If an abbreviation is found it converts the element
     332                 :             :    to the full library name, otherwise the user supplied name is added
     333                 :             :    to the full_libraries list.  A new string is returned.  */
     334                 :             : 
     335                 :             : static const char *
     336                 :        9124 : convert_abbreviation (const char *full_libraries, const char *abbreviation)
     337                 :             : {
     338                 :       54744 :   for (int i = 0; i < maxlib; i++)
     339                 :       45620 :     if (strcmp (abbreviation, library_abbrev[i]) == 0)
     340                 :           0 :       return add_word (full_libraries, library_name[i]);
     341                 :             :   /* Perhaps the user typed in the whole lib name rather than an abbrev.  */
     342                 :       27372 :   for (int i = 0; i < maxlib; i++)
     343                 :       27372 :     if (strcmp (abbreviation, library_name[i]) == 0)
     344                 :        9124 :       return add_word (full_libraries, abbreviation);
     345                 :             :   /* Not found, probably a user typo.  */
     346                 :           0 :   error ("%qs is not a valid Modula-2 system library name or abbreviation",
     347                 :             :          abbreviation);
     348                 :           0 :   return full_libraries;
     349                 :             : }
     350                 :             : 
     351                 :             : /* convert_abbreviations checks each element in the library list to
     352                 :             :    see if an a known library abbreviation was used.  If found it
     353                 :             :    converts the element to the full library name, otherwise the
     354                 :             :    element is copied into the list.  A new string is returned.  */
     355                 :             : 
     356                 :             : static const char *
     357                 :        2281 : convert_abbreviations (const char *libraries)
     358                 :             : {
     359                 :        2281 :   const char *start = libraries;
     360                 :        2281 :   const char *end;
     361                 :        2281 :   const char *full_libraries = NULL;
     362                 :             : 
     363                 :        9124 :   do
     364                 :             :     {
     365                 :        9124 :       end = index (start, ',');
     366                 :        9124 :       if (end == NULL)
     367                 :             :         {
     368                 :        2281 :           full_libraries = convert_abbreviation (full_libraries, start);
     369                 :        2281 :           start = NULL;
     370                 :             :         }
     371                 :             :       else
     372                 :             :         {
     373                 :        6843 :           full_libraries = convert_abbreviation (full_libraries,
     374                 :        6843 :                                                  xstrndup (start, end - start));
     375                 :        6843 :           start = end + 1;
     376                 :             :         }
     377                 :             :     }
     378                 :        9124 :   while ((start != NULL) && (start[0] != (char)0));
     379                 :        2281 :   return full_libraries;
     380                 :             : }
     381                 :             : 
     382                 :             : /* add_m2_I_path appends -fm2-pathname and -fm2-pathnameI options to
     383                 :             :    the command line which are contructed in the saved Ipaths.  */
     384                 :             : 
     385                 :             : static void
     386                 :       16690 : add_m2_I_path (void)
     387                 :             : {
     388                 :       91458 :   for (auto np : Ipaths)
     389                 :             :     {
     390                 :       74768 :       if (strcmp (np.name, "") == 0)
     391                 :        1693 :         append_option (OPT_fm2_pathname_, safe_strdup ("-"), 1);
     392                 :             :       else
     393                 :       73075 :         append_option (OPT_fm2_pathname_, safe_strdup (np.name), 1);
     394                 :      181694 :       for (auto *s : np.path)
     395                 :      213852 :         append_option (OPT_fm2_pathnameI, safe_strdup (s), 1);
     396                 :       74768 :     }
     397                 :       16690 :   Ipaths.clear();
     398                 :       16690 : }
     399                 :             : 
     400                 :             : 
     401                 :             : void
     402                 :       16690 : lang_specific_driver (struct cl_decoded_option **in_decoded_options,
     403                 :             :                       unsigned int *in_decoded_options_count,
     404                 :             :                       int *in_added_libraries)
     405                 :             : {
     406                 :       16690 :   unsigned int argc = *in_decoded_options_count;
     407                 :       16690 :   struct cl_decoded_option *decoded_options = *in_decoded_options;
     408                 :       16690 :   unsigned int i;
     409                 :             : 
     410                 :             :   /* True if we saw a `-xfoo' language specification on the command
     411                 :             :      line.  This function will add a -xmodula-2 if the user has not
     412                 :             :      already placed one onto the command line.  */
     413                 :       16690 :   bool seen_x_flag = false;
     414                 :       16690 :   const char *language = NULL;
     415                 :             : 
     416                 :             :   /* If nonzero, the user gave us the `-p' or `-pg' flag.  */
     417                 :       16690 :   int saw_profile_flag = 0;
     418                 :             : 
     419                 :             :   /* What action to take for the c++ runtime library:
     420                 :             :     -1  means we should not link it in.
     421                 :             :      0  means we should link it if it is needed.
     422                 :             :      1  means it is needed and should be linked in.
     423                 :             :      2  means it is needed but should be linked statically.  */
     424                 :       16690 :   int library = 0;
     425                 :             : 
     426                 :             :   /* Which c++ runtime library to link.  */
     427                 :       16690 :   stdcxxlib_kind which_library = USE_LIBSTDCXX;
     428                 :             : 
     429                 :       16690 :   const char *dialect = DEFAULT_DIALECT;
     430                 :             : 
     431                 :             :   /* An array used to flag each argument that needs a bit set for
     432                 :             :      LANGSPEC, MATHLIB, or WITHLIBC.  */
     433                 :       16690 :   int *args;
     434                 :             : 
     435                 :             :   /* Have we seen -fmod=?  */
     436                 :       16690 :   char *module_extension = NULL;
     437                 :             : 
     438                 :             :   /* Should the driver perform a link?  */
     439                 :       16690 :   bool linking = true;
     440                 :             : 
     441                 :             :   /* Should the driver link the shared gm2 libs?  */
     442                 :       16690 :   bool shared_libgm2 = true;
     443                 :             : 
     444                 :             :   /* "-lm" or "-lmath" if it appears on the command line.  */
     445                 :       16690 :   const struct cl_decoded_option *saw_math = NULL;
     446                 :             : 
     447                 :             :   /* "-lc" if it appears on the command line.  */
     448                 :       16690 :   const struct cl_decoded_option *saw_libc = NULL;
     449                 :             : 
     450                 :             :   /* By default, we throw on the math library if we have one.  */
     451                 :       16690 :   int need_math = (MATH_LIBRARY[0] != '\0');
     452                 :             : 
     453                 :             :   /* 1 if we should add -lpthread to the command-line.
     454                 :             :      FIXME: the default should be a configuration choice.  */
     455                 :       16690 :   int need_pthread = 1;
     456                 :             : 
     457                 :             :   /* True if we saw -static.  */
     458                 :       16690 :   int static_link = 0;
     459                 :             : 
     460                 :             :   /* True if we should add -shared-libgcc to the command-line.  */
     461                 :       16690 :   int shared_libgcc = 1;
     462                 :             : 
     463                 :             :   /* Have we seen the -v flag?  */
     464                 :       16690 :   bool verbose = false;
     465                 :             : 
     466                 :             :   /* Have we seen the -fm2-pathname flag?  */
     467                 :       16690 :   bool seen_pathname = false;
     468                 :             : 
     469                 :             :   /* The number of libraries added in.  */
     470                 :       16690 :   int added_libraries;
     471                 :             : 
     472                 :             :   /* True if we should add -fplugin=m2rte to the command-line.  */
     473                 :       16690 :   bool need_plugin = false;
     474                 :             : 
     475                 :             :   /* True if we should set up include paths and library paths.  */
     476                 :       16690 :   bool allow_libraries = true;
     477                 :             : 
     478                 :             : #if defined(DEBUG_ARG)
     479                 :             :   printf ("argc = %d\n", argc);
     480                 :             :   fprintf (stderr, "Incoming:");
     481                 :             :   for (i = 0; i < argc; i++)
     482                 :             :     fprintf (stderr, " %s", decoded_options[i].orig_option_with_args_text);
     483                 :             :   fprintf (stderr, "\n");
     484                 :             : #endif
     485                 :             : 
     486                 :             :   // add_spec_function ("m2I", add_m2_I_path);
     487                 :       16690 :   gm2_xargc = argc;
     488                 :       16690 :   gm2_x_decoded_options = decoded_options;
     489                 :       16690 :   gm2_newargc = 0;
     490                 :       16690 :   gm2_new_decoded_options = decoded_options;
     491                 :       16690 :   added_libraries = *in_added_libraries;
     492                 :       16690 :   args = XCNEWVEC (int, argc);
     493                 :             : 
     494                 :             :   /* First pass through arglist.
     495                 :             : 
     496                 :             :      If -nostdlib or a "turn-off-linking" option is anywhere in the
     497                 :             :      command line, don't do any library-option processing (except
     498                 :             :      relating to -x).  */
     499                 :             : 
     500                 :      466990 :   for (i = 1; i < argc; i++)
     501                 :             :     {
     502                 :      450300 :       const char *arg = decoded_options[i].arg;
     503                 :      450300 :       args[i] = 0;
     504                 :             : #if defined(DEBUG_ARG)
     505                 :             :       printf ("1st pass: %s\n",
     506                 :             :               decoded_options[i].orig_option_with_args_text);
     507                 :             : #endif
     508                 :      450300 :       switch (decoded_options[i].opt_index)
     509                 :             :         {
     510                 :             :         case OPT_fiso:
     511                 :      450300 :           dialect = "iso";
     512                 :             :           break;
     513                 :         146 :         case OPT_fpim2:
     514                 :         146 :           dialect = "pim2";
     515                 :         146 :           break;
     516                 :          27 :         case OPT_fpim3:
     517                 :          27 :           dialect = "pim3";
     518                 :          27 :           break;
     519                 :          96 :         case OPT_fpim4:
     520                 :          96 :           dialect = "pim4";
     521                 :          96 :           break;
     522                 :       10688 :         case OPT_fpim:
     523                 :       10688 :           dialect = "pim";
     524                 :       10688 :           break;
     525                 :       16792 :         case OPT_flibs_:
     526                 :       16792 :           libraries = xstrdup (arg);
     527                 :       16792 :           allow_libraries = decoded_options[i].value;
     528                 :       16792 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     529                 :       16792 :           break;
     530                 :           6 :         case OPT_fmod_:
     531                 :           6 :           module_extension = xstrdup (arg);
     532                 :             : #if defined(DEBUG_ARG)
     533                 :             :           printf ("seen -fmod=%s\n", module_extension);
     534                 :             : #endif
     535                 :           6 :           break;
     536                 :           0 :         case OPT_fpthread:
     537                 :           0 :           need_pthread = decoded_options[i].value;
     538                 :           0 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     539                 :           0 :           break;
     540                 :         465 :         case OPT_fm2_plugin:
     541                 :         465 :           need_plugin = decoded_options[i].value;
     542                 :             : #ifndef ENABLE_PLUGIN
     543                 :             :           if (need_plugin)
     544                 :             :             error ("plugin support is disabled; configure with "
     545                 :             :                    "%<--enable-plugin%>");
     546                 :             : #endif
     547                 :         465 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     548                 :         465 :           break;
     549                 :          57 :         case OPT_fscaffold_dynamic:
     550                 :          57 :           seen_scaffold_dynamic = true;
     551                 :          57 :           scaffold_dynamic = decoded_options[i].value;
     552                 :          57 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     553                 :          57 :           break;
     554                 :          22 :         case OPT_fscaffold_static:
     555                 :          22 :           seen_scaffold_static = true;
     556                 :          22 :           scaffold_static = decoded_options[i].value;
     557                 :          22 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     558                 :          22 :           break;
     559                 :          78 :         case OPT_fscaffold_main:
     560                 :          78 :           seen_scaffold_main = true;
     561                 :          78 :           scaffold_main = decoded_options[i].value;
     562                 :          78 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     563                 :          78 :           break;
     564                 :           0 :         case OPT_fgen_module_list_:
     565                 :           0 :           seen_gen_module_list = true;
     566                 :           0 :           gen_module_list = decoded_options[i].value;
     567                 :           0 :           if (gen_module_list)
     568                 :           0 :             gen_module_filename = decoded_options[i].arg;
     569                 :             :           break;
     570                 :           0 :         case OPT_fuse_list_:
     571                 :           0 :           seen_uselist = true;
     572                 :           0 :           uselist = decoded_options[i].value;
     573                 :           0 :           break;
     574                 :       88995 :         case OPT_fm2_pathname_:
     575                 :       88995 :           seen_pathname = true;
     576                 :       88995 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     577                 :       88995 :           m2_path_name = decoded_options[i].arg;
     578                 :       88995 :           break;
     579                 :      105233 :         case OPT_I:
     580                 :      105233 :           args[i] |= SKIPOPT; /* We will add the option if it is needed.  */
     581                 :      105233 :           push_back_Ipath (decoded_options[i].arg);
     582                 :      105233 :           break;
     583                 :           0 :         case OPT_nostdlib:
     584                 :           0 :         case OPT_nostdlib__:
     585                 :           0 :         case OPT_nodefaultlibs:
     586                 :           0 :           library = -1;
     587                 :           0 :           break;
     588                 :             : 
     589                 :        2384 :         case OPT_l:
     590                 :        2384 :           if (strcmp (arg, MATH_LIBRARY) == 0)
     591                 :             :             {
     592                 :        2384 :               args[i] |= MATHLIB;
     593                 :        2384 :               need_math = 0;
     594                 :             :             }
     595                 :           0 :           else if (strcmp (arg, "c") == 0)
     596                 :           0 :             args[i] |= WITHLIBC;
     597                 :             :           else
     598                 :             :             /* Unrecognized libraries (e.g. -lfoo) may require libstdc++.  */
     599                 :           0 :             library = (library == 0) ? 1 : library;
     600                 :             :           break;
     601                 :             : 
     602                 :           0 :         case OPT_pg:
     603                 :           0 :         case OPT_p:
     604                 :           0 :           saw_profile_flag++;
     605                 :           0 :           break;
     606                 :             : 
     607                 :           0 :         case OPT_x:
     608                 :           0 :           seen_x_flag = true;
     609                 :           0 :           language = arg;
     610                 :           0 :           break;
     611                 :             : 
     612                 :           0 :         case OPT_v:
     613                 :           0 :           verbose = true;
     614                 :           0 :           break;
     615                 :             : 
     616                 :           0 :         case OPT_Xlinker:
     617                 :           0 :         case OPT_Wl_:
     618                 :             :           /* Arguments that go directly to the linker might be .o files,
     619                 :             :              or something, and so might cause libstdc++ to be needed.  */
     620                 :           0 :           if (library == 0)
     621                 :      450300 :             library = 1;
     622                 :             :           break;
     623                 :             : 
     624                 :       11006 :         case OPT_c:
     625                 :       11006 :         case OPT_r:
     626                 :       11006 :         case OPT_S:
     627                 :       11006 :         case OPT_E:
     628                 :       11006 :         case OPT_M:
     629                 :       11006 :         case OPT_MM:
     630                 :       11006 :         case OPT_fsyntax_only:
     631                 :             :           /* Don't specify libraries if we won't link, since that would
     632                 :             :              cause a warning.  */
     633                 :       11006 :           linking = false;
     634                 :       11006 :           library = -1;
     635                 :       11006 :           break;
     636                 :             : 
     637                 :             :         /* PCH makes no sense here, we do not catch -output-pch on purpose,
     638                 :             :            that should flag an error.  */
     639                 :           0 :         case OPT_fpch_deps:
     640                 :           0 :         case OPT_fpch_preprocess:
     641                 :           0 :         case OPT_Winvalid_pch:
     642                 :           0 :           args[i] |= SKIPOPT;
     643                 :           0 :           break;
     644                 :             : 
     645                 :           0 :         case OPT_static:
     646                 :           0 :           static_link = 1;
     647                 :           0 :           break;
     648                 :             : 
     649                 :           0 :         case OPT_static_libgcc:
     650                 :           0 :           shared_libgcc = 0;
     651                 :           0 :           break;
     652                 :             : 
     653                 :           0 :         case OPT_static_libstdc__:
     654                 :           0 :           library = library >= 0 ? 2 : library;
     655                 :             : #ifdef HAVE_LD_STATIC_DYNAMIC
     656                 :             :           /* Remove -static-libstdc++ from the command only if target supports
     657                 :             :              LD_STATIC_DYNAMIC.  When not supported, it is left in so that a
     658                 :             :              back-end target can use outfile substitution.  */
     659                 :           0 :           args[i] |= SKIPOPT;
     660                 :             : #endif
     661                 :           0 :           break;
     662                 :             : 
     663                 :           0 :         case OPT_static_libgm2:
     664                 :           0 :           shared_libgm2 = false;
     665                 :             : #ifdef HAVE_LD_STATIC_DYNAMIC
     666                 :             :           /* Remove -static-libgm2 from the command only if target supports
     667                 :             :              LD_STATIC_DYNAMIC.  When not supported, it is left in so that a
     668                 :             :              back-end target can use outfile substitution.  */
     669                 :           0 :           args[i] |= SKIPOPT;
     670                 :             : #endif
     671                 :           0 :           break;
     672                 :             : 
     673                 :           0 :         case OPT_stdlib_:
     674                 :           0 :           which_library = (stdcxxlib_kind) decoded_options[i].value;
     675                 :           0 :           break;
     676                 :             : 
     677                 :       23340 :         case OPT_SPECIAL_input_file:
     678                 :       23340 :           {
     679                 :       23340 :             const char *source_file = decoded_options[i].orig_option_with_args_text;
     680                 :             : #if defined(DEBUG_ARG)
     681                 :             :             printf ("seen OPT_SPECIAL_input_file: %s\n", source_file);
     682                 :             : #endif
     683                 :       23340 :             if (source_file != NULL)
     684                 :             :               {
     685                 :             :                 /* Record that this is a Modula-2 source file.  */
     686                 :       23340 :                 const char *suffix = strrchr (source_file, '.');
     687                 :             : #if defined(DEBUG_ARG)
     688                 :             :                 printf ("ext = %s\n", suffix);
     689                 :             : #endif
     690                 :       23340 :                 if ((suffix != NULL)
     691                 :       23337 :                     && ((strcmp (suffix, ".mod") == 0)
     692                 :        9954 :                         || ((module_extension != NULL)
     693                 :           6 :                             && (strcmp (suffix, module_extension) == 0))))
     694                 :             :                   {
     695                 :             : #if defined(DEBUG_ARG)
     696                 :             :                     printf ("modula-2 source file detected: %s\n", source_file);
     697                 :             : #endif
     698                 :       13389 :                     args[i] |= M2SOURCE;
     699                 :             :                   }
     700                 :             :               }
     701                 :             :           }
     702                 :             :           break;
     703                 :             : 
     704                 :             :         default:
     705                 :             :           break;
     706                 :             :         }
     707                 :             :     }
     708                 :       16690 :   if (language != NULL && (strcmp (language, "modula-2") != 0))
     709                 :             :     return;
     710                 :             : 
     711                 :       16690 :   if (! seen_pathname)
     712                 :             :     /* Not seen -fm2-pathname therefore make current working directory
     713                 :             :        the first place to look for modules.  */
     714                 :        1693 :     push_back_Ipath (".");
     715                 :             : 
     716                 :             :   /* Override the default when the user specifies it.  */
     717                 :       16690 :   if (seen_scaffold_static && scaffold_static && !seen_scaffold_dynamic)
     718                 :           0 :     scaffold_dynamic = false;
     719                 :             : 
     720                 :             :   /* If both options have been seen and both are true, that means the user
     721                 :             :      tried to set both.  */
     722                 :       16690 :   if (seen_scaffold_dynamic && scaffold_dynamic
     723                 :           0 :      && seen_scaffold_static && scaffold_static)
     724                 :           0 :     error ("%qs and %qs cannot both be enabled",
     725                 :             :            "-fscaffold-dynamic", "-fscaffold-static");
     726                 :             : 
     727                 :       16690 :   if (uselist && gen_module_list)
     728                 :             :     {
     729                 :           0 :       if (! seen_gen_module_list)
     730                 :           0 :         gen_module_list = false;
     731                 :           0 :       if (uselist && gen_module_list)
     732                 :           0 :         error ("%qs and %qs cannot both be enabled",
     733                 :             :                "-fgen-module-list=", "-fuse-list=");
     734                 :             :     }
     735                 :             : 
     736                 :             : 
     737                 :             :   /* There's no point adding -shared-libgcc if we don't have a shared
     738                 :             :      libgcc.  */
     739                 :             : #ifndef ENABLE_SHARED_LIBGCC
     740                 :             :   shared_libgcc = 0;
     741                 :             : #endif
     742                 :             : 
     743                 :             :   /* Second pass through arglist, transforming arguments as appropriate.  */
     744                 :             : 
     745                 :       16690 :   append_arg (&decoded_options[0]); /* Start with command name, of course.  */
     746                 :      483680 :   for (i = 1; i < argc; ++i)
     747                 :             :     {
     748                 :             : #if defined(DEBUG_ARG)
     749                 :             :       printf ("2nd pass: %s",
     750                 :             :               decoded_options[i].orig_option_with_args_text);
     751                 :             :       if ((args[i] & SKIPOPT) != 0)
     752                 :             :         printf (" skipped");
     753                 :             :       if ((args[i] & M2SOURCE) != 0)
     754                 :             :         printf (" m2 source");
     755                 :             :       printf ("\n");
     756                 :             : #endif
     757                 :      450300 :       if ((args[i] & SKIPOPT) == 0)
     758                 :             :         {
     759                 :      238658 :           if ((args[i] & M2SOURCE) == 0)
     760                 :             :             {
     761                 :      225269 :               append_arg (&decoded_options[i]);
     762                 :             :               /* Make sure -lstdc++ is before the math library, since libstdc++
     763                 :             :                  itself uses those math routines.  */
     764                 :      225269 :               if (!saw_math && (args[i] & MATHLIB) && library > 0)
     765                 :             :                 saw_math = &decoded_options[i];
     766                 :             : 
     767                 :      225269 :               if (!saw_libc && (args[i] & WITHLIBC) && library > 0)
     768                 :             :                 saw_libc = &decoded_options[i];
     769                 :             :             }
     770                 :             :           else
     771                 :             :             {
     772                 :       13389 :               if ((! seen_x_flag) && module_extension)
     773                 :             :                 {
     774                 :             : #if defined(DEBUG_ARG)
     775                 :             :                   printf (" adding: -x modula-2 ");
     776                 :             : #endif
     777                 :           6 :                   append_option (OPT_x, "modula-2", 1);
     778                 :             :                 }
     779                 :       13389 :               append_arg (&decoded_options[i]);
     780                 :             : #if defined(DEBUG_ARG)
     781                 :             :               printf (" adding: %s\n",
     782                 :             :                       decoded_options[i].orig_option_with_args_text);
     783                 :             : #endif
     784                 :       13389 :               if ((! seen_x_flag) && module_extension)
     785                 :             :                 {
     786                 :             : #if defined(DEBUG_ARG)
     787                 :             :                   printf (" adding: -x none ");
     788                 :             : #endif
     789                 :           6 :                   append_option (OPT_x, "none", 1);
     790                 :             :                 }
     791                 :             :             }
     792                 :             :         }
     793                 :             : #if defined(DEBUG_ARG)
     794                 :             :       else
     795                 :             :         printf ("skipping: %s\n",
     796                 :             :                 decoded_options[i].orig_option_with_args_text);
     797                 :             : #endif
     798                 :             :     }
     799                 :             : 
     800                 :       16690 :   add_m2_I_path ();
     801                 :             :   /* We now add in extra arguments to facilitate a successful link.
     802                 :             :      Note that the libraries are added to the end of the link here
     803                 :             :      and also placed earlier into the link by lang-specs.h.  Possibly
     804                 :             :      this is needed because the m2pim,m2iso libraries are cross linked
     805                 :             :      (--fixme-- combine all the m2 libraries into a single archive).
     806                 :             : 
     807                 :             :      We also add default scaffold linking options.  */
     808                 :             : 
     809                 :             :   /* If we have not seen either uselist or gen_module_list and we need
     810                 :             :      to link or compile a module list then we turn on -fgen_module_list=-
     811                 :             :      as the default.  */
     812                 :       16690 :   if (!seen_uselist && !seen_gen_module_list
     813                 :       16690 :       && (linking || scaffold_main))
     814                 :        5696 :     append_option (OPT_fgen_module_list_, "-", 1);
     815                 :             : 
     816                 :             :   /* We checked that they were not both enabled above, if there was a set
     817                 :             :      value (even iff that is 'off'), pass that to the FE.  */
     818                 :       16690 :   if (seen_scaffold_dynamic || scaffold_dynamic)
     819                 :       16690 :     append_option (OPT_fscaffold_dynamic, NULL, scaffold_dynamic);
     820                 :       16690 :   if (seen_scaffold_static)
     821                 :          22 :     append_option (OPT_fscaffold_static, NULL, scaffold_static);
     822                 :             : 
     823                 :             :   /* If the user has set fscaffold-main specifically, use that.  Otherwise, if
     824                 :             :      we are linking then set it so that we generate the relevant code for the
     825                 :             :      main module.  */
     826                 :       16690 :   if (seen_scaffold_main)
     827                 :          78 :     append_option (OPT_fscaffold_main, NULL, scaffold_main);
     828                 :       16612 :   else if (linking)
     829                 :        5648 :     append_option (OPT_fscaffold_main, NULL, true);
     830                 :             : 
     831                 :       16690 :   if (allow_libraries)
     832                 :             :     {
     833                 :             :       /* If the libraries have not been specified by the user, select the
     834                 :             :          appropriate libraries for the active dialect.  */
     835                 :        2281 :       if (libraries == NULL)
     836                 :             :         {
     837                 :        2281 :           if (strcmp (dialect, "iso") == 0)
     838                 :         306 :             libraries = xstrdup ("m2iso,m2cor,m2pim,m2log");
     839                 :             :           else
     840                 :             :             /* Default to pim libraries otherwise.  */
     841                 :        1975 :             libraries = xstrdup ("m2cor,m2log,m2pim,m2iso");
     842                 :             :         }
     843                 :        2281 :       libraries = convert_abbreviations (libraries);
     844                 :        2281 :       append_option (OPT_flibs_, xstrdup (libraries), 1);
     845                 :             :     }
     846                 :             :   else
     847                 :       14409 :     append_option (OPT_flibs_, xstrdup ("-"), 0); /* no system libs.  */
     848                 :             : 
     849                 :       16690 :   if (need_plugin)
     850                 :         181 :     append_option (OPT_fplugin_, "m2rte", 1);
     851                 :             : 
     852                 :       16690 :   if (linking)
     853                 :             :     {
     854                 :        5684 :       if (allow_libraries)
     855                 :             :         {
     856                 :             : #ifdef HAVE_LD_STATIC_DYNAMIC
     857                 :        1665 :           if (!shared_libgm2)
     858                 :           0 :             append_option (OPT_Wl_, LD_STATIC_OPTION, 1);
     859                 :             : #endif
     860                 :        1665 :           added_libraries += add_default_libs (libraries);
     861                 :             : #ifdef HAVE_LD_STATIC_DYNAMIC
     862                 :        1665 :           if (!shared_libgm2)
     863                 :           0 :             append_option (OPT_Wl_, LD_DYNAMIC_OPTION, 1);
     864                 :             : #endif
     865                 :             :         }
     866                 :             : 
     867                 :             :       /* Add `-lstdc++' if we haven't already done so.  */
     868                 :             : #ifdef HAVE_LD_STATIC_DYNAMIC
     869                 :        5684 :       if (library > 1 && !static_link)
     870                 :           0 :         append_option (OPT_Wl_, LD_STATIC_OPTION, 1);
     871                 :             : #endif
     872                 :        5684 :       if (which_library == USE_LIBCXX)
     873                 :             :         {
     874                 :           0 :           append_option (OPT_l, saw_profile_flag ? LIBCXX_PROFILE : LIBCXX, 1);
     875                 :           0 :           added_libraries++;
     876                 :           0 :           if (LIBCXXABI != NULL)
     877                 :             :             {
     878                 :           0 :               append_option (OPT_l, saw_profile_flag ? LIBCXXABI_PROFILE
     879                 :             :                              : LIBCXXABI, 1);
     880                 :           0 :               added_libraries++;
     881                 :             :             }
     882                 :             :         }
     883                 :             :       else
     884                 :             :         {
     885                 :        5684 :           append_option (OPT_l, saw_profile_flag ? LIBSTDCXX_PROFILE
     886                 :             :                          : LIBSTDCXX, 1);
     887                 :        5684 :           added_libraries++;
     888                 :             :         }
     889                 :             :       /* Add target-dependent static library, if necessary.  */
     890                 :        5684 :       if ((static_link || library > 1) && LIBSTDCXX_STATIC != NULL)
     891                 :             :         {
     892                 :             :           append_option (OPT_l, LIBSTDCXX_STATIC, 1);
     893                 :             :           added_libraries++;
     894                 :             :         }
     895                 :             : #ifdef HAVE_LD_STATIC_DYNAMIC
     896                 :        5684 :       if (library > 1 && !static_link)
     897                 :           0 :         append_option (OPT_Wl_, LD_DYNAMIC_OPTION, 1);
     898                 :             : #endif
     899                 :             :     }
     900                 :       16690 :   if (need_math)
     901                 :             :     {
     902                 :       14306 :       append_option (OPT_l, saw_profile_flag ? MATH_LIBRARY_PROFILE :
     903                 :             :                      MATH_LIBRARY, 1);
     904                 :       14306 :       added_libraries++;
     905                 :             :     }
     906                 :       16690 :   if (need_pthread)
     907                 :             :     {
     908                 :       16690 :       append_option (OPT_l, "pthread", 1);
     909                 :       16690 :       added_libraries++;
     910                 :             :     }
     911                 :       16690 :   if (shared_libgcc && !static_link)
     912                 :       16690 :     append_option (OPT_shared_libgcc, NULL, 1);
     913                 :             : 
     914                 :       16690 :   if (verbose && gm2_new_decoded_options != gm2_x_decoded_options)
     915                 :             :     {
     916                 :           0 :       fprintf (stderr, _("Driving:"));
     917                 :           0 :       for (i = 0; i < gm2_newargc; i++)
     918                 :           0 :         fprintf (stderr, " %s",
     919                 :           0 :                  gm2_new_decoded_options[i].orig_option_with_args_text);
     920                 :           0 :       fprintf (stderr, "\n");
     921                 :           0 :       fprintf (stderr, "new argc = %d, added_libraries = %d\n",
     922                 :             :                gm2_newargc, added_libraries);
     923                 :             :     }
     924                 :             : 
     925                 :       16690 :   *in_decoded_options_count = gm2_newargc;
     926                 :       16690 :   *in_decoded_options = gm2_new_decoded_options;
     927                 :       16690 :   *in_added_libraries = added_libraries;
     928                 :             : }
     929                 :             : 
     930                 :             : 
     931                 :             : /* Called before linking.  Returns 0 on success and -1 on failure.  */
     932                 :             : int
     933                 :       11995 : lang_specific_pre_link (void)  /* Not used for M2.  */
     934                 :             : {
     935                 :       11995 :   return 0;
     936                 :             : }
     937                 :             : 
     938                 :             : /* Number of extra output files that lang_specific_pre_link may generate.  */
     939                 :             : int lang_specific_extra_outfiles = 0;
        

Generated by: LCOV version 2.1-beta

LCOV profile is generated on x86_64 machine using following configure options: configure --disable-bootstrap --enable-coverage=opt --enable-languages=c,c++,fortran,go,jit,lto,rust,m2 --enable-host-shared. GCC test suite is run with the built compiler.