zcov: / lib/Driver/ToolChains.cpp


Files: 1 Branches Taken: 50.5% 198 / 392
Generated: 2010-02-10 01:31 Branches Executed: 72.7% 285 / 392
Line Coverage: 75.1% 335 / 446


Programs: 2 Runs 3018


       1                 : //===--- ToolChains.cpp - ToolChain Implementations ---------------------*-===//
       2                 : //
       3                 : //                     The LLVM Compiler Infrastructure
       4                 : //
       5                 : // This file is distributed under the University of Illinois Open Source
       6                 : // License. See LICENSE.TXT for details.
       7                 : //
       8                 : //===----------------------------------------------------------------------===//
       9                 : 
      10                 : #include "ToolChains.h"
      11                 : 
      12                 : #include "clang/Driver/Arg.h"
      13                 : #include "clang/Driver/ArgList.h"
      14                 : #include "clang/Driver/Driver.h"
      15                 : #include "clang/Driver/DriverDiagnostic.h"
      16                 : #include "clang/Driver/HostInfo.h"
      17                 : #include "clang/Driver/OptTable.h"
      18                 : #include "clang/Driver/Option.h"
      19                 : #include "clang/Driver/Options.h"
      20                 : 
      21                 : #include "llvm/ADT/StringExtras.h"
      22                 : #include "llvm/Support/ErrorHandling.h"
      23                 : #include "llvm/Support/raw_ostream.h"
      24                 : #include "llvm/System/Path.h"
      25                 : 
      26                 : #include <cstdlib> // ::getenv
      27                 : 
      28                 : using namespace clang::driver;
      29                 : using namespace clang::driver::toolchains;
      30                 : 
      31                 : /// Darwin - Darwin tool chain for i386 and x86_64.
      32                 : 
      33                 : Darwin::Darwin(const HostInfo &Host, const llvm::Triple& Triple,
      34               58:                const unsigned (&_DarwinVersion)[3])
      35               58:   : ToolChain(Host, Triple), TargetInitialized(false)
      36                 : {
      37                 :   llvm::raw_string_ostream(MacosxVersionMin)
      38                 :     << "10." << std::max(0, (int)_DarwinVersion[0] - 4) << '.'
      39               58:     << _DarwinVersion[1];
      40               58: }
      41                 : 
      42                 : // FIXME: Can we tablegen this?
      43               12: static const char *GetArmArchForMArch(llvm::StringRef Value) {
                        6: branch 2 taken
                        6: branch 3 taken
      44               12:   if (Value == "armv6k")
      45                6:     return "armv6";
      46                 : 
                        0: branch 2 not taken
                        6: branch 3 taken
      47                6:   if (Value == "armv5tej")
      48                0:     return "armv5";
      49                 : 
                        0: branch 2 not taken
                        6: branch 3 taken
      50                6:   if (Value == "xscale")
      51                0:     return "xscale";
      52                 : 
                        0: branch 2 not taken
                        6: branch 3 taken
      53                6:   if (Value == "armv4t")
      54                0:     return "armv4t";
      55                 : 
                        6: branch 2 taken
                        0: branch 3 not taken
                        6: branch 6 taken
                        0: branch 7 not taken
                        6: branch 10 taken
                        0: branch 11 not taken
                        6: branch 14 taken
                        0: branch 15 not taken
                        0: branch 18 not taken
                        6: branch 19 taken
                        0: branch 22 not taken
                        0: branch 23 not taken
                        0: branch 26 not taken
                        0: branch 27 not taken
                        6: branch 28 taken
                        0: branch 29 not taken
      56                6:   if (Value == "armv7" || Value == "armv7-a" || Value == "armv7-r" ||
      57                 :       Value == "armv7-m" || Value == "armv7a" || Value == "armv7r" ||
      58                 :       Value == "armv7m")
      59                6:     return "armv7";
      60                 : 
      61                0:   return 0;
      62                 : }
      63                 : 
      64                 : // FIXME: Can we tablegen this?
      65                0: static const char *GetArmArchForMCpu(llvm::StringRef Value) {
                        0: branch 2 not taken
                        0: branch 3 not taken
                        0: branch 6 not taken
                        0: branch 7 not taken
                        0: branch 10 not taken
                        0: branch 11 not taken
                        0: branch 14 not taken
                        0: branch 15 not taken
                        0: branch 18 not taken
                        0: branch 19 not taken
                        0: branch 22 not taken
                        0: branch 23 not taken
                        0: branch 26 not taken
                        0: branch 27 not taken
                        0: branch 30 not taken
                        0: branch 31 not taken
                        0: branch 34 not taken
                        0: branch 35 not taken
                        0: branch 38 not taken
                        0: branch 39 not taken
                        0: branch 42 not taken
                        0: branch 43 not taken
                        0: branch 44 not taken
                        0: branch 45 not taken
      66                0:   if (Value == "arm10tdmi" || Value == "arm1020t" || Value == "arm9e" ||
      67                 :       Value == "arm946e-s" || Value == "arm966e-s" ||
      68                 :       Value == "arm968e-s" || Value == "arm10e" ||
      69                 :       Value == "arm1020e" || Value == "arm1022e" || Value == "arm926ej-s" ||
      70                 :       Value == "arm1026ej-s")
      71                0:     return "armv5";
      72                 : 
                        0: branch 2 not taken
                        0: branch 3 not taken
      73                0:   if (Value == "xscale")
      74                0:     return "xscale";
      75                 : 
                        0: branch 2 not taken
                        0: branch 3 not taken
                        0: branch 6 not taken
                        0: branch 7 not taken
                        0: branch 10 not taken
                        0: branch 11 not taken
                        0: branch 14 not taken
                        0: branch 15 not taken
                        0: branch 16 not taken
                        0: branch 17 not taken
      76                0:   if (Value == "arm1136j-s" || Value == "arm1136jf-s" ||
      77                 :       Value == "arm1176jz-s" || Value == "arm1176jzf-s")
      78                0:     return "armv6";
      79                 : 
                        0: branch 2 not taken
                        0: branch 3 not taken
                        0: branch 6 not taken
                        0: branch 7 not taken
                        0: branch 10 not taken
                        0: branch 11 not taken
                        0: branch 12 not taken
                        0: branch 13 not taken
      80                0:   if (Value == "cortex-a8" || Value == "cortex-r4" || Value == "cortex-m3")
      81                0:     return "armv7";
      82                 : 
      83                0:   return 0;
      84                 : }
      85                 : 
      86               32: llvm::StringRef Darwin::getDarwinArchName(const ArgList &Args) const {
                       20: branch 2 taken
                       12: branch 3 taken
      87               32:   switch (getTriple().getArch()) {
      88                 :   default:
      89               20:     return getArchName();
      90                 : 
      91                 :   case llvm::Triple::arm: {
                       12: branch 2 taken
                        0: branch 3 not taken
      92               12:     if (const Arg *A = Args.getLastArg(options::OPT_march_EQ))
                       12: branch 3 taken
                        0: branch 4 not taken
      93               12:       if (const char *Arch = GetArmArchForMArch(A->getValue(Args)))
      94               12:         return Arch;
      95                 : 
                        0: branch 2 not taken
                        0: branch 3 not taken
      96                0:     if (const Arg *A = Args.getLastArg(options::OPT_mcpu_EQ))
                        0: branch 3 not taken
                        0: branch 4 not taken
      97                0:       if (const char *Arch = GetArmArchForMCpu(A->getValue(Args)))
      98                0:         return Arch;
      99                 : 
     100                0:     return "arm";
     101                 :   }
     102                 :   }
     103                 : }
     104                 : 
     105                 : DarwinGCC::DarwinGCC(const HostInfo &Host, const llvm::Triple& Triple,
     106                 :                      const unsigned (&DarwinVersion)[3],
     107               44:                      const unsigned (&_GCCVersion)[3])
     108               44:   : Darwin(Host, Triple, DarwinVersion)
     109                 : {
     110               44:   GCCVersion[0] = _GCCVersion[0];
     111               44:   GCCVersion[1] = _GCCVersion[1];
     112               44:   GCCVersion[2] = _GCCVersion[2];
     113                 : 
     114                 :   // Set up the tool chain paths to match gcc.
     115               44:   ToolChainDir = "i686-apple-darwin";
     116               44:   ToolChainDir += llvm::utostr(DarwinVersion[0]);
     117               44:   ToolChainDir += "/";
     118               44:   ToolChainDir += llvm::utostr(GCCVersion[0]);
     119               44:   ToolChainDir += '.';
     120               44:   ToolChainDir += llvm::utostr(GCCVersion[1]);
     121               44:   ToolChainDir += '.';
     122               44:   ToolChainDir += llvm::utostr(GCCVersion[2]);
     123                 : 
     124                 :   // Try the next major version if that tool chain dir is invalid.
     125               44:   std::string Tmp = "/usr/lib/gcc/" + ToolChainDir;
                       44: branch 4 taken
                        0: branch 5 not taken
                        0: branch 10 not taken
                        0: branch 11 not taken
     126               44:   if (!llvm::sys::Path(Tmp).exists()) {
     127               44:     std::string Next = "i686-apple-darwin";
     128               44:     Next += llvm::utostr(DarwinVersion[0] + 1);
     129               44:     Next += "/";
     130               44:     Next += llvm::utostr(GCCVersion[0]);
     131               44:     Next += '.';
     132               44:     Next += llvm::utostr(GCCVersion[1]);
     133               44:     Next += '.';
     134               44:     Next += llvm::utostr(GCCVersion[2]);
     135                 : 
     136                 :     // Use that if it exists, otherwise hope the user isn't linking.
     137                 :     //
     138                 :     // FIXME: Drop dependency on gcc's tool chain.
     139               44:     Tmp = "/usr/lib/gcc/" + Next;
                        0: branch 4 not taken
                       44: branch 5 taken
                        0: branch 10 not taken
                        0: branch 11 not taken
     140               44:     if (llvm::sys::Path(Tmp).exists())
     141                0:       ToolChainDir = Next;
     142                 :   }
     143                 : 
     144               44:   std::string Path;
                        8: branch 3 taken
                       36: branch 4 taken
                        0: branch 8 not taken
                        0: branch 9 not taken
     145               44:   if (getArchName() == "x86_64") {
     146                8:     Path = getDriver().Dir;
     147                8:     Path += "/../lib/gcc/";
     148                8:     Path += ToolChainDir;
     149                8:     Path += "/x86_64";
     150                8:     getFilePaths().push_back(Path);
     151                 : 
     152                8:     Path = "/usr/lib/gcc/";
     153                8:     Path += ToolChainDir;
     154                8:     Path += "/x86_64";
     155                8:     getFilePaths().push_back(Path);
     156                 :   }
     157                 : 
     158               44:   Path = getDriver().Dir;
     159               44:   Path += "/../lib/gcc/";
     160               44:   Path += ToolChainDir;
     161               44:   getFilePaths().push_back(Path);
     162                 : 
     163               44:   Path = "/usr/lib/gcc/";
     164               44:   Path += ToolChainDir;
     165               44:   getFilePaths().push_back(Path);
     166                 : 
     167               44:   Path = getDriver().Dir;
     168               44:   Path += "/../libexec/gcc/";
     169               44:   Path += ToolChainDir;
     170               44:   getProgramPaths().push_back(Path);
     171                 : 
     172               44:   Path = "/usr/libexec/gcc/";
     173               44:   Path += ToolChainDir;
     174               44:   getProgramPaths().push_back(Path);
     175                 : 
     176               44:   getProgramPaths().push_back(getDriver().Dir);
     177               44: }
     178                 : 
     179               58: Darwin::~Darwin() {
     180                 :   // Free tool implementations.
                        0: branch 3 not taken
                        0: branch 4 not taken
                        0: branch 8 not taken
                        0: branch 9 not taken
                       68: branch 13 taken
                       58: branch 14 taken
     181              126:   for (llvm::DenseMap<unsigned, Tool*>::iterator
     182               58:          it = Tools.begin(), ie = Tools.end(); it != ie; ++it)
                        0: branch 1 not taken
                        0: branch 2 not taken
                        0: branch 5 not taken
                        0: branch 6 not taken
                       68: branch 9 taken
                        0: branch 10 not taken
     183               68:     delete it->second;
                        0: branch 3 not taken
                        0: branch 4 not taken
                        0: branch 9 not taken
                        0: branch 10 not taken
                        0: branch 15 not taken
                       58: branch 16 taken
     184               58: }
     185                 : 
     186               68: Tool &Darwin::SelectTool(const Compilation &C, const JobAction &JA) const {
     187                 :   Action::ActionClass Key;
                       34: branch 3 taken
                       34: branch 4 taken
     188               68:   if (getDriver().ShouldUseClangCompiler(C, JA, getTriple()))
     189               34:     Key = Action::AnalyzeJobClass;
     190                 :   else
     191               34:     Key = JA.getKind();
     192                 : 
     193               68:   Tool *&T = Tools[Key];
                       68: branch 0 taken
                        0: branch 1 not taken
     194               68:   if (!T) {
                        0: branch 0 not taken
                        1: branch 1 taken
                       35: branch 2 taken
                        2: branch 3 taken
                        9: branch 4 taken
                       19: branch 5 taken
                        2: branch 6 taken
                        0: branch 7 not taken
     195               68:     switch (Key) {
     196                 :     case Action::InputClass:
     197                 :     case Action::BindArchClass:
     198                0:       assert(0 && "Invalid tool kind.");
     199                 :     case Action::PreprocessJobClass:
     200                1:       T = new tools::darwin::Preprocess(*this); break;
     201                 :     case Action::AnalyzeJobClass:
     202               35:       T = new tools::Clang(*this); break;
     203                 :     case Action::PrecompileJobClass:
     204                 :     case Action::CompileJobClass:
     205                2:       T = new tools::darwin::Compile(*this); break;
     206                 :     case Action::AssembleJobClass:
     207                9:       T = new tools::darwin::Assemble(*this); break;
     208                 :     case Action::LinkJobClass:
     209               19:       T = new tools::darwin::Link(*this); break;
     210                 :     case Action::LipoJobClass:
     211                2:       T = new tools::darwin::Lipo(*this); break;
     212                 :     }
     213                 :   }
     214                 : 
     215               68:   return *T;
     216                 : }
     217                 : 
     218                 : void DarwinGCC::AddLinkSearchPathArgs(const ArgList &Args,
     219               12:                                       ArgStringList &CmdArgs) const {
     220                 :   // FIXME: Derive these correctly.
                        2: branch 3 taken
                       10: branch 4 taken
     221               12:   if (getArchName() == "x86_64") {
     222                 :     CmdArgs.push_back(Args.MakeArgString("-L/usr/lib/gcc/" + ToolChainDir +
     223                2:                                          "/x86_64"));
     224                 :     // Intentionally duplicated for (temporary) gcc bug compatibility.
     225                 :     CmdArgs.push_back(Args.MakeArgString("-L/usr/lib/gcc/" + ToolChainDir +
     226                2:                                          "/x86_64"));
     227                 :   }
     228               12:   CmdArgs.push_back(Args.MakeArgString("-L/usr/lib/" + ToolChainDir));
     229               12:   CmdArgs.push_back(Args.MakeArgString("-L/usr/lib/gcc/" + ToolChainDir));
     230                 :   // Intentionally duplicated for (temporary) gcc bug compatibility.
     231               12:   CmdArgs.push_back(Args.MakeArgString("-L/usr/lib/gcc/" + ToolChainDir));
     232                 :   CmdArgs.push_back(Args.MakeArgString("-L/usr/lib/gcc/" + ToolChainDir +
     233               12:                                        "/../../../" + ToolChainDir));
     234                 :   CmdArgs.push_back(Args.MakeArgString("-L/usr/lib/gcc/" + ToolChainDir +
     235               12:                                        "/../../.."));
     236               12: }
     237                 : 
     238                 : void DarwinGCC::AddLinkRuntimeLibArgs(const ArgList &Args,
     239               11:                                       ArgStringList &CmdArgs) const {
     240                 :   // Note that this routine is only used for targetting OS X.
     241                 : 
     242                 :   // Derived from libgcc and lib specs but refactored.
                        1: branch 2 taken
                       10: branch 3 taken
     243               11:   if (Args.hasArg(options::OPT_static)) {
     244                1:     CmdArgs.push_back("-lgcc_static");
     245                 :   } else {
                        0: branch 2 not taken
                       10: branch 3 taken
     246               10:     if (Args.hasArg(options::OPT_static_libgcc)) {
     247                0:       CmdArgs.push_back("-lgcc_eh");
                        0: branch 2 not taken
                       10: branch 3 taken
     248               10:     } else if (Args.hasArg(options::OPT_miphoneos_version_min_EQ)) {
     249                 :       // Derived from darwin_iphoneos_libgcc spec.
                        0: branch 1 not taken
                        0: branch 2 not taken
     250                0:       if (isTargetIPhoneOS()) {
     251                0:         CmdArgs.push_back("-lgcc_s.1");
     252                 :       } else {
     253                0:         CmdArgs.push_back("-lgcc_s.10.5");
     254                 :       }
                       10: branch 2 taken
                        0: branch 3 not taken
                        0: branch 7 not taken
                       10: branch 8 taken
                        0: branch 11 not taken
                        0: branch 12 not taken
                       10: branch 13 taken
                        0: branch 14 not taken
     255               10:     } else if (Args.hasArg(options::OPT_shared_libgcc) ||
     256                 :                Args.hasFlag(options::OPT_fexceptions,
     257                 :                             options::OPT_fno_exceptions) ||
     258                 :                Args.hasArg(options::OPT_fgnu_runtime)) {
     259                 :       // FIXME: This is probably broken on 10.3?
                        2: branch 1 taken
                        8: branch 2 taken
     260               10:       if (isMacosxVersionLT(10, 5))
     261                2:         CmdArgs.push_back("-lgcc_s.10.4");
                        7: branch 1 taken
                        1: branch 2 taken
     262                8:       else if (isMacosxVersionLT(10, 6))
     263                7:         CmdArgs.push_back("-lgcc_s.10.5");
     264                 :     } else {
                        0: branch 1 not taken
                        0: branch 2 not taken
     265                0:       if (isMacosxVersionLT(10, 3, 9))
     266                 :         ; // Do nothing.
                        0: branch 1 not taken
                        0: branch 2 not taken
     267                0:       else if (isMacosxVersionLT(10, 5))
     268                0:         CmdArgs.push_back("-lgcc_s.10.4");
                        0: branch 1 not taken
                        0: branch 2 not taken
     269                0:       else if (isMacosxVersionLT(10, 6))
     270                0:         CmdArgs.push_back("-lgcc_s.10.5");
     271                 :     }
     272                 : 
                       10: branch 1 taken
                        0: branch 2 not taken
                        9: branch 4 taken
                        1: branch 5 taken
                        9: branch 6 taken
                        1: branch 7 taken
     273               10:     if (isTargetIPhoneOS() || isMacosxVersionLT(10, 6)) {
     274                9:       CmdArgs.push_back("-lgcc");
     275                9:       CmdArgs.push_back("-lSystem");
     276                 :     } else {
     277                1:       CmdArgs.push_back("-lSystem");
     278                1:       CmdArgs.push_back("-lgcc");
     279                 :     }
     280                 :   }
     281               11: }
     282                 : 
     283                 : DarwinClang::DarwinClang(const HostInfo &Host, const llvm::Triple& Triple,
     284               14:                          const unsigned (&DarwinVersion)[3])
     285               14:   : Darwin(Host, Triple, DarwinVersion)
     286                 : {
     287                 :   // We expect 'as', 'ld', etc. to be adjacent to our install dir.
     288               14:   getProgramPaths().push_back(getDriver().Dir);
     289               14: }
     290                 : 
     291                 : void DarwinClang::AddLinkSearchPathArgs(const ArgList &Args,
     292                6:                                        ArgStringList &CmdArgs) const {
     293                 :   // The Clang toolchain uses explicit paths for internal libraries.
     294                6: }
     295                 : 
     296                 : void DarwinClang::AddLinkRuntimeLibArgs(const ArgList &Args,
     297                6:                                         ArgStringList &CmdArgs) const {
     298                 :   // Darwin doesn't support real static executables, don't link any runtime
     299                 :   // libraries with -static.
                        0: branch 2 not taken
                        6: branch 3 taken
     300                6:   if (Args.hasArg(options::OPT_static))
     301                0:     return;
     302                 : 
     303                 :   // Reject -static-libgcc for now, we can deal with this when and if someone
     304                 :   // cares. This is useful in situations where someone wants to statically link
     305                 :   // something like libstdc++, and needs its runtime support routines.
                        0: branch 2 not taken
                        6: branch 3 taken
     306                6:   if (const Arg *A = Args.getLastArg(options::OPT_static_libgcc)) {
     307                 :     getDriver().Diag(clang::diag::err_drv_unsupported_opt)
     308                0:       << A->getAsString(Args);
     309                0:     return;
     310                 :   }
     311                 : 
     312                 :   // Otherwise link libSystem, then the dynamic runtime library, and finally any
     313                 :   // target specific static runtime library.
     314                6:   CmdArgs.push_back("-lSystem");
     315                 : 
     316                 :   // Select the dynamic runtime library and the target specific static library.
     317                6:   const char *DarwinStaticLib = 0;
                        6: branch 1 taken
                        0: branch 2 not taken
     318                6:   if (isTargetIPhoneOS()) {
     319                6:     CmdArgs.push_back("-lgcc_s.1");
     320                 : 
     321                 :     // We may need some static functions for armv6/thumb which are required to
     322                 :     // be in the same linkage unit as their caller.
                        3: branch 3 taken
                        3: branch 4 taken
     323                6:     if (getDarwinArchName(Args) == "armv6")
     324                3:       DarwinStaticLib = "libclang_rt.armv6.a";
     325                 :   } else {
     326                 :     // The dynamic runtime library was merged with libSystem for 10.6 and
     327                 :     // beyond; only 10.4 and 10.5 need an additional runtime library.
                        0: branch 1 not taken
                        0: branch 2 not taken
     328                0:     if (isMacosxVersionLT(10, 5))
     329                0:       CmdArgs.push_back("-lgcc_s.10.4");
                        0: branch 1 not taken
                        0: branch 2 not taken
     330                0:     else if (isMacosxVersionLT(10, 6))
     331                0:       CmdArgs.push_back("-lgcc_s.10.5");
     332                 : 
     333                 :     // For OS X, we only need a static runtime library when targetting 10.4, to
     334                 :     // provide versions of the static functions which were omitted from
     335                 :     // 10.4.dylib.
                        0: branch 1 not taken
                        0: branch 2 not taken
     336                0:     if (isMacosxVersionLT(10, 5))
     337                0:       DarwinStaticLib = "libclang_rt.10.4.a";
     338                 :   }
     339                 : 
     340                 :   /// Add the target specific static library, if needed.
                        3: branch 0 taken
                        3: branch 1 taken
     341                6:   if (DarwinStaticLib) {
     342                3:     llvm::sys::Path P(getDriver().ResourceDir);
     343                3:     P.appendComponent("lib");
     344                3:     P.appendComponent("darwin");
     345                3:     P.appendComponent(DarwinStaticLib);
     346                 : 
     347                 :     // For now, allow missing resource libraries to support developers who may
     348                 :     // not have compiler-rt checked out or integrated into their build.
                        3: branch 1 taken
                        0: branch 2 not taken
     349                3:     if (!P.exists())
     350                 :       getDriver().Diag(clang::diag::warn_drv_missing_resource_library)
     351                3:         << P.str();
     352                 :     else
     353                0:       CmdArgs.push_back(Args.MakeArgString(P.str()));
     354                 :   }
     355                 : }
     356                 : 
     357                 : DerivedArgList *Darwin::TranslateArgs(InputArgList &Args,
     358               52:                                       const char *BoundArch) const {
     359               52:   DerivedArgList *DAL = new DerivedArgList(Args, false);
     360               52:   const OptTable &Opts = getDriver().getOpts();
     361                 : 
     362                 :   // FIXME: We really want to get out of the tool chain level argument
     363                 :   // translation business, as it makes the driver functionality much
     364                 :   // more opaque. For now, we follow gcc closely solely for the
     365                 :   // purpose of easily achieving feature parity & testability. Once we
     366                 :   // have something that works, we should reevaluate each translation
     367                 :   // and try to push it down into tool specific logic.
     368                 : 
     369               52:   Arg *OSXVersion = Args.getLastArg(options::OPT_mmacosx_version_min_EQ);
     370               52:   Arg *iPhoneVersion = Args.getLastArg(options::OPT_miphoneos_version_min_EQ);
                        5: branch 0 taken
                       47: branch 1 taken
                        1: branch 2 taken
                        4: branch 3 taken
     371               53:   if (OSXVersion && iPhoneVersion) {
     372                 :     getDriver().Diag(clang::diag::err_drv_argument_not_allowed_with)
     373                 :           << OSXVersion->getAsString(Args)
     374                1:           << iPhoneVersion->getAsString(Args);
     375                1:     iPhoneVersion = 0;
                       47: branch 0 taken
                        4: branch 1 taken
                       39: branch 2 taken
                        8: branch 3 taken
     376               51:   } else if (!OSXVersion && !iPhoneVersion) {
     377                 :     // If neither OS X nor iPhoneOS targets were specified, check for
     378                 :     // environment defines.
     379               39:     const char *OSXTarget = ::getenv("MACOSX_DEPLOYMENT_TARGET");
     380               39:     const char *iPhoneOSTarget = ::getenv("IPHONEOS_DEPLOYMENT_TARGET");
     381                 : 
     382                 :     // Ignore empty strings.
                        2: branch 0 taken
                       37: branch 1 taken
                        0: branch 2 not taken
                        2: branch 3 taken
     383               39:     if (OSXTarget && OSXTarget[0] == '\0')
     384                0:       OSXTarget = 0;
                        2: branch 0 taken
                       37: branch 1 taken
                        0: branch 2 not taken
                        2: branch 3 taken
     385               39:     if (iPhoneOSTarget && iPhoneOSTarget[0] == '\0')
     386                0:       iPhoneOSTarget = 0;
     387                 : 
     388                 :     // Diagnose conflicting deployment targets, and choose default platform
     389                 :     // based on the tool chain.
     390                 :     //
     391                 :     // FIXME: Don't hardcode default here.
                        2: branch 0 taken
                       37: branch 1 taken
                        0: branch 2 not taken
                        2: branch 3 taken
     392               39:     if (OSXTarget && iPhoneOSTarget) {
     393                 :       // FIXME: We should see if we can get away with warning or erroring on
     394                 :       // this. Perhaps put under -pedantic?
                        0: branch 2 not taken
                        0: branch 3 not taken
                        0: branch 6 not taken
                        0: branch 7 not taken
                        0: branch 8 not taken
                        0: branch 9 not taken
     395                0:       if (getTriple().getArch() == llvm::Triple::arm ||
     396                 :           getTriple().getArch() == llvm::Triple::thumb)
     397                0:         OSXVersion = 0;
     398                 :       else
     399                0:         iPhoneVersion = 0;
     400                 :     }
     401                 : 
                        2: branch 0 taken
                       37: branch 1 taken
     402               39:     if (OSXTarget) {
     403                2:       const Option *O = Opts.getOption(options::OPT_mmacosx_version_min_EQ);
     404                2:       OSXVersion = DAL->MakeJoinedArg(0, O, OSXTarget);
     405                2:       DAL->append(OSXVersion);
                        2: branch 0 taken
                       35: branch 1 taken
     406               37:     } else if (iPhoneOSTarget) {
     407                2:       const Option *O = Opts.getOption(options::OPT_miphoneos_version_min_EQ);
     408                2:       iPhoneVersion = DAL->MakeJoinedArg(0, O, iPhoneOSTarget);
     409                2:       DAL->append(iPhoneVersion);
     410                 :     } else {
     411                 :       // Otherwise, choose a default platform based on the tool chain.
     412                 :       //
     413                 :       // FIXME: Don't hardcode default here.
                       29: branch 2 taken
                        6: branch 3 taken
                        0: branch 6 not taken
                       29: branch 7 taken
                        6: branch 8 taken
                       29: branch 9 taken
     414               35:       if (getTriple().getArch() == llvm::Triple::arm ||
     415                 :           getTriple().getArch() == llvm::Triple::thumb) {
     416                6:         const Option *O = Opts.getOption(options::OPT_miphoneos_version_min_EQ);
     417                6:         iPhoneVersion = DAL->MakeJoinedArg(0, O, "3.0");
     418                6:         DAL->append(iPhoneVersion);
     419                 :       } else {
     420               29:         const Option *O = Opts.getOption(options::OPT_mmacosx_version_min_EQ);
     421               29:         OSXVersion = DAL->MakeJoinedArg(0, O, MacosxVersionMin);
     422               29:         DAL->append(OSXVersion);
     423                 :       }
     424                 :     }
     425                 :   }
     426                 : 
     427                 :   // Set the tool chain target information.
     428                 :   unsigned Major, Minor, Micro;
     429                 :   bool HadExtra;
                       36: branch 0 taken
                       16: branch 1 taken
     430               52:   if (OSXVersion) {
                        0: branch 0 not taken
                       36: branch 1 taken
     431               36:     assert(!iPhoneVersion && "Unknown target platform!");
                       36: branch 2 taken
                        0: branch 3 not taken
                       36: branch 4 taken
                        0: branch 5 not taken
                       36: branch 6 taken
                        0: branch 7 not taken
                       36: branch 8 taken
                        0: branch 9 not taken
                        0: branch 10 not taken
                       36: branch 11 taken
                        0: branch 12 not taken
                       36: branch 13 taken
     432               36:     if (!Driver::GetReleaseVersion(OSXVersion->getValue(Args), Major, Minor,
     433                 :                                    Micro, HadExtra) || HadExtra ||
     434                 :         Major != 10 || Minor >= 10 || Micro >= 10)
     435                 :       getDriver().Diag(clang::diag::err_drv_invalid_version_number)
     436                0:         << OSXVersion->getAsString(Args);
     437                 :   } else {
                        0: branch 0 not taken
                       16: branch 1 taken
     438               16:     assert(iPhoneVersion && "Unknown target platform!");
                       16: branch 2 taken
                        0: branch 3 not taken
                       16: branch 4 taken
                        0: branch 5 not taken
                       16: branch 6 taken
                        0: branch 7 not taken
                       16: branch 8 taken
                        0: branch 9 not taken
                        0: branch 10 not taken
                       16: branch 11 taken
                        0: branch 12 not taken
                       16: branch 13 taken
     439               16:     if (!Driver::GetReleaseVersion(iPhoneVersion->getValue(Args), Major, Minor,
     440                 :                                    Micro, HadExtra) || HadExtra ||
     441                 :         Major >= 10 || Minor >= 100 || Micro >= 100)
     442                 :       getDriver().Diag(clang::diag::err_drv_invalid_version_number)
     443                0:         << iPhoneVersion->getAsString(Args);
     444                 :   }
     445               52:   setTarget(iPhoneVersion, Major, Minor, Micro);
     446                 : 
                      414: branch 2 taken
                       52: branch 3 taken
     447              466:   for (ArgList::iterator it = Args.begin(), ie = Args.end(); it != ie; ++it) {
     448              414:     Arg *A = *it;
     449                 : 
                        5: branch 3 taken
                      409: branch 4 taken
     450              414:     if (A->getOption().matches(options::OPT_Xarch__)) {
     451                 :       // FIXME: Canonicalize name.
                        1: branch 4 taken
                        4: branch 5 taken
     452                5:       if (getArchName() != A->getValue(Args, 0))
     453                1:         continue;
     454                 : 
     455                 :       // FIXME: The arg is leaked here, and we should have a nicer
     456                 :       // interface for this.
     457                4:       unsigned Prev, Index = Prev = A->getIndex() + 1;
     458                4:       Arg *XarchArg = Opts.ParseOneArg(Args, Index);
     459                 : 
     460                 :       // If the argument parsing failed or more than one argument was
     461                 :       // consumed, the -Xarch_ argument's parameter tried to consume
     462                 :       // extra arguments. Emit an error and ignore.
     463                 :       //
     464                 :       // We also want to disallow any options which would alter the
     465                 :       // driver behavior; that isn't going to work in our model. We
     466                 :       // use isDriverOption() as an approximation, although things
     467                 :       // like -O4 are going to slip through.
                        3: branch 0 taken
                        1: branch 1 taken
                        2: branch 2 taken
                        1: branch 3 taken
                        1: branch 6 taken
                        1: branch 7 taken
                        3: branch 8 taken
                        1: branch 9 taken
     468                4:       if (!XarchArg || Index > Prev + 1 ||
     469                 :           XarchArg->getOption().isDriverOption()) {
     470                 :        getDriver().Diag(clang::diag::err_drv_invalid_Xarch_argument)
     471                3:           << A->getAsString(Args);
     472                3:         continue;
     473                 :       }
     474                 : 
     475                1:       XarchArg->setBaseArg(A);
     476                1:       A = XarchArg;
     477                 :     }
     478                 : 
     479                 :     // Sob. These is strictly gcc compatible for the time being. Apple
     480                 :     // gcc translates options twice, which means that self-expanding
     481                 :     // options add duplicates.
                      408: branch 2 taken
                        1: branch 3 taken
                        0: branch 4 not taken
                        1: branch 5 taken
                        0: branch 6 not taken
                        0: branch 7 not taken
                        0: branch 8 not taken
                        0: branch 9 not taken
                        0: branch 10 not taken
                        0: branch 11 not taken
                        0: branch 12 not taken
                        0: branch 13 not taken
                        0: branch 14 not taken
     482              410:     switch ((options::ID) A->getOption().getID()) {
     483                 :     default:
     484              408:       DAL->append(A);
     485              408:       break;
     486                 : 
     487                 :     case options::OPT_mkernel:
     488                 :     case options::OPT_fapple_kext:
     489                1:       DAL->append(A);
     490                1:       DAL->append(DAL->MakeFlagArg(A, Opts.getOption(options::OPT_static)));
     491                1:       DAL->append(DAL->MakeFlagArg(A, Opts.getOption(options::OPT_static)));
     492                1:       break;
     493                 : 
     494                 :     case options::OPT_dependency_file:
     495                 :       DAL->append(DAL->MakeSeparateArg(A, Opts.getOption(options::OPT_MF),
     496                0:                                        A->getValue(Args)));
     497                0:       break;
     498                 : 
     499                 :     case options::OPT_gfull:
     500                1:       DAL->append(DAL->MakeFlagArg(A, Opts.getOption(options::OPT_g_Flag)));
     501                 :       DAL->append(DAL->MakeFlagArg(A,
     502                1:              Opts.getOption(options::OPT_fno_eliminate_unused_debug_symbols)));
     503                1:       break;
     504                 : 
     505                 :     case options::OPT_gused:
     506                0:       DAL->append(DAL->MakeFlagArg(A, Opts.getOption(options::OPT_g_Flag)));
     507                 :       DAL->append(DAL->MakeFlagArg(A,
     508                0:              Opts.getOption(options::OPT_feliminate_unused_debug_symbols)));
     509                0:       break;
     510                 : 
     511                 :     case options::OPT_fterminated_vtables:
     512                 :     case options::OPT_findirect_virtual_calls:
     513                 :       DAL->append(DAL->MakeFlagArg(A,
     514                0:                                    Opts.getOption(options::OPT_fapple_kext)));
     515                0:       DAL->append(DAL->MakeFlagArg(A, Opts.getOption(options::OPT_static)));
     516                0:       break;
     517                 : 
     518                 :     case options::OPT_shared:
     519                0:       DAL->append(DAL->MakeFlagArg(A, Opts.getOption(options::OPT_dynamiclib)));
     520                0:       break;
     521                 : 
     522                 :     case options::OPT_fconstant_cfstrings:
     523                 :       DAL->append(DAL->MakeFlagArg(A,
     524                0:                              Opts.getOption(options::OPT_mconstant_cfstrings)));
     525                0:       break;
     526                 : 
     527                 :     case options::OPT_fno_constant_cfstrings:
     528                 :       DAL->append(DAL->MakeFlagArg(A,
     529                0:                           Opts.getOption(options::OPT_mno_constant_cfstrings)));
     530                0:       break;
     531                 : 
     532                 :     case options::OPT_Wnonportable_cfstrings:
     533                 :       DAL->append(DAL->MakeFlagArg(A,
     534                0:                      Opts.getOption(options::OPT_mwarn_nonportable_cfstrings)));
     535                0:       break;
     536                 : 
     537                 :     case options::OPT_Wno_nonportable_cfstrings:
     538                 :       DAL->append(DAL->MakeFlagArg(A,
     539                0:                   Opts.getOption(options::OPT_mno_warn_nonportable_cfstrings)));
     540                0:       break;
     541                 : 
     542                 :     case options::OPT_fpascal_strings:
     543                 :       DAL->append(DAL->MakeFlagArg(A,
     544                0:                                  Opts.getOption(options::OPT_mpascal_strings)));
     545                0:       break;
     546                 : 
     547                 :     case options::OPT_fno_pascal_strings:
     548                 :       DAL->append(DAL->MakeFlagArg(A,
     549                0:                               Opts.getOption(options::OPT_mno_pascal_strings)));
     550                 :       break;
     551                 :     }
     552                 :   }
     553                 : 
                       22: branch 2 taken
                       30: branch 3 taken
                        8: branch 6 taken
                       14: branch 7 taken
                       38: branch 8 taken
                       14: branch 9 taken
     554               52:   if (getTriple().getArch() == llvm::Triple::x86 ||
     555                 :       getTriple().getArch() == llvm::Triple::x86_64)
                       38: branch 2 taken
                        0: branch 3 not taken
     556               38:     if (!Args.hasArgNoClaim(options::OPT_mtune_EQ))
     557                 :       DAL->append(DAL->MakeJoinedArg(0, Opts.getOption(options::OPT_mtune_EQ),
     558               38:                                      "core2"));
     559                 : 
     560                 :   // Add the arch options based on the particular spelling of -arch, to match
     561                 :   // how the driver driver works.
                       15: branch 0 taken
                       37: branch 1 taken
     562               52:   if (BoundArch) {
     563               15:     llvm::StringRef Name = BoundArch;
     564               15:     const Option *MCpu = Opts.getOption(options::OPT_mcpu_EQ);
     565               15:     const Option *MArch = Opts.getOption(options::OPT_march_EQ);
     566                 : 
     567                 :     // This code must be kept in sync with LLVM's getArchTypeForDarwinArch,
     568                 :     // which defines the list of which architectures we accept.
                       15: branch 2 taken
                        0: branch 3 not taken
     569               15:     if (Name == "ppc")
     570                 :       ;
                        0: branch 2 not taken
                       15: branch 3 taken
     571               15:     else if (Name == "ppc601")
     572                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "601"));
                        0: branch 2 not taken
                       15: branch 3 taken
     573               15:     else if (Name == "ppc603")
     574                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "603"));
                        0: branch 2 not taken
                       15: branch 3 taken
     575               15:     else if (Name == "ppc604")
     576                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "604"));
                        0: branch 2 not taken
                       15: branch 3 taken
     577               15:     else if (Name == "ppc604e")
     578                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "604e"));
                        0: branch 2 not taken
                       15: branch 3 taken
     579               15:     else if (Name == "ppc750")
     580                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "750"));
                        0: branch 2 not taken
                       15: branch 3 taken
     581               15:     else if (Name == "ppc7400")
     582                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "7400"));
                        0: branch 2 not taken
                       15: branch 3 taken
     583               15:     else if (Name == "ppc7450")
     584                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "7450"));
                        0: branch 2 not taken
                       15: branch 3 taken
     585               15:     else if (Name == "ppc970")
     586                0:       DAL->append(DAL->MakeJoinedArg(0, MCpu, "970"));
     587                 : 
                        0: branch 2 not taken
                       15: branch 3 taken
     588               15:     else if (Name == "ppc64")
     589                0:       DAL->append(DAL->MakeFlagArg(0, Opts.getOption(options::OPT_m64)));
     590                 : 
                       13: branch 2 taken
                        2: branch 3 taken
     591               15:     else if (Name == "i386")
     592                 :       ;
                        0: branch 2 not taken
                       13: branch 3 taken
     593               13:     else if (Name == "i486")
     594                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "i486"));
                        0: branch 2 not taken
                       13: branch 3 taken
     595               13:     else if (Name == "i586")
     596                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "i586"));
                        0: branch 2 not taken
                       13: branch 3 taken
     597               13:     else if (Name == "i686")
     598                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "i686"));
                        0: branch 2 not taken
                       13: branch 3 taken
     599               13:     else if (Name == "pentium")
     600                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "pentium"));
                        0: branch 2 not taken
                       13: branch 3 taken
     601               13:     else if (Name == "pentium2")
     602                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "pentium2"));
                        0: branch 2 not taken
                       13: branch 3 taken
     603               13:     else if (Name == "pentpro")
     604                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "pentiumpro"));
                        0: branch 2 not taken
                       13: branch 3 taken
     605               13:     else if (Name == "pentIIm3")
     606                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "pentium2"));
     607                 : 
                        2: branch 2 taken
                       11: branch 3 taken
     608               13:     else if (Name == "x86_64")
     609                2:       DAL->append(DAL->MakeFlagArg(0, Opts.getOption(options::OPT_m64)));
     610                 : 
                        1: branch 2 taken
                       10: branch 3 taken
     611               11:     else if (Name == "arm")
     612                1:       DAL->append(DAL->MakeJoinedArg(0, MArch, "armv4t"));
                        0: branch 2 not taken
                       10: branch 3 taken
     613               10:     else if (Name == "armv4t")
     614                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "armv4t"));
                        0: branch 2 not taken
                       10: branch 3 taken
     615               10:     else if (Name == "armv5")
     616                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "armv5tej"));
                        0: branch 2 not taken
                       10: branch 3 taken
     617               10:     else if (Name == "xscale")
     618                0:       DAL->append(DAL->MakeJoinedArg(0, MArch, "xscale"));
                        3: branch 2 taken
                        7: branch 3 taken
     619               10:     else if (Name == "armv6")
     620                3:       DAL->append(DAL->MakeJoinedArg(0, MArch, "armv6k"));
                        7: branch 2 taken
                        0: branch 3 not taken
     621                7:     else if (Name == "armv7")
     622                7:       DAL->append(DAL->MakeJoinedArg(0, MArch, "armv7a"));
     623                 : 
     624                 :     else
     625                0:       llvm_unreachable("invalid Darwin arch");
     626                 :   }
     627                 : 
     628               52:   return DAL;
     629                 : }
     630                 : 
     631               34: bool Darwin::IsUnwindTablesDefault() const {
     632                 :   // FIXME: Gross; we should probably have some separate target
     633                 :   // definition, possibly even reusing the one in clang.
     634               34:   return getArchName() == "x86_64";
     635                 : }
     636                 : 
     637               34: bool Darwin::UseDwarfDebugFlags() const {
                        1: branch 1 taken
                       33: branch 2 taken
     638               34:   if (const char *S = ::getenv("RC_DEBUG_OPTIONS"))
     639                1:     return S[0] != '\0';
     640               33:   return false;
     641                 : }
     642                 : 
     643               29: const char *Darwin::GetDefaultRelocationModel() const {
     644               29:   return "pic";
     645                 : }
     646                 : 
     647               34: const char *Darwin::GetForcedPicModel() const {
                        5: branch 3 taken
                       29: branch 4 taken
     648               34:   if (getArchName() == "x86_64")
     649                5:     return "pic";
     650               29:   return 0;
     651                 : }
     652                 : 
     653                 : /// Generic_GCC - A tool chain using the 'gcc' command to perform
     654                 : /// all subcommands; this relies on gcc translating the majority of
     655                 : /// command line options.
     656                 : 
     657              192: Generic_GCC::Generic_GCC(const HostInfo &Host, const llvm::Triple& Triple)
     658              192:   : ToolChain(Host, Triple) {
     659              192:   getProgramPaths().push_back(getDriver().Dir);
     660              192: }
     661                 : 
     662              192: Generic_GCC::~Generic_GCC() {
     663                 :   // Free tool implementations.
                       37: branch 3 taken
                       33: branch 4 taken
                        0: branch 8 not taken
                        0: branch 9 not taken
                      155: branch 13 taken
                      159: branch 14 taken
     664              384:   for (llvm::DenseMap<unsigned, Tool*>::iterator
     665              192:          it = Tools.begin(), ie = Tools.end(); it != ie; ++it)
                       37: branch 1 taken
                        0: branch 2 not taken
                        0: branch 5 not taken
                        0: branch 6 not taken
                      155: branch 9 taken
                        0: branch 10 not taken
     666              192:     delete it->second;
                       33: branch 2 taken
                        0: branch 3 not taken
                        0: branch 7 not taken
                        0: branch 8 not taken
                        0: branch 12 not taken
                      159: branch 13 taken
     667              192: }
     668                 : 
     669                 : Tool &Generic_GCC::SelectTool(const Compilation &C,
     670              189:                               const JobAction &JA) const {
     671                 :   Action::ActionClass Key;
                      160: branch 3 taken
                       29: branch 4 taken
     672              189:   if (getDriver().ShouldUseClangCompiler(C, JA, getTriple()))
     673              160:     Key = Action::AnalyzeJobClass;
     674                 :   else
     675               29:     Key = JA.getKind();
     676                 : 
     677              189:   Tool *&T = Tools[Key];
                      186: branch 0 taken
                        3: branch 1 taken
     678              189:   if (!T) {
                        0: branch 0 not taken
                        3: branch 1 taken
                        1: branch 2 taken
                      157: branch 3 taken
                        7: branch 4 taken
                       10: branch 5 taken
                        8: branch 6 taken
                        0: branch 7 not taken
                        0: branch 8 not taken
     679              186:     switch (Key) {
     680                 :     case Action::InputClass:
     681                 :     case Action::BindArchClass:
     682                0:       assert(0 && "Invalid tool kind.");
     683                 :     case Action::PreprocessJobClass:
     684                3:       T = new tools::gcc::Preprocess(*this); break;
     685                 :     case Action::PrecompileJobClass:
     686                1:       T = new tools::gcc::Precompile(*this); break;
     687                 :     case Action::AnalyzeJobClass:
     688              157:       T = new tools::Clang(*this); break;
     689                 :     case Action::CompileJobClass:
     690                7:       T = new tools::gcc::Compile(*this); break;
     691                 :     case Action::AssembleJobClass:
     692               10:       T = new tools::gcc::Assemble(*this); break;
     693                 :     case Action::LinkJobClass:
     694                8:       T = new tools::gcc::Link(*this); break;
     695                 : 
     696                 :       // This is a bit ungeneric, but the only platform using a driver
     697                 :       // driver is Darwin.
     698                 :     case Action::LipoJobClass:
     699                0:       T = new tools::darwin::Lipo(*this); break;
     700                 :     }
     701                 :   }
     702                 : 
     703              189:   return *T;
     704                 : }
     705                 : 
     706              154: bool Generic_GCC::IsUnwindTablesDefault() const {
     707                 :   // FIXME: Gross; we should probably have some separate target
     708                 :   // definition, possibly even reusing the one in clang.
     709              154:   return getArchName() == "x86_64";
     710                 : }
     711                 : 
     712              151: const char *Generic_GCC::GetDefaultRelocationModel() const {
     713              151:   return "static";
     714                 : }
     715                 : 
     716              154: const char *Generic_GCC::GetForcedPicModel() const {
     717              154:   return 0;
     718                 : }
     719                 : 
     720                 : DerivedArgList *Generic_GCC::TranslateArgs(InputArgList &Args,
     721              155:                                            const char *BoundArch) const {
     722              155:   return new DerivedArgList(Args, true);
     723                 : }
     724                 : 
     725                 : /// OpenBSD - OpenBSD tool chain which can call as(1) and ld(1) directly.
     726                 : 
     727                1: OpenBSD::OpenBSD(const HostInfo &Host, const llvm::Triple& Triple)
     728                1:   : Generic_GCC(Host, Triple) {
     729                1:   getFilePaths().push_back(getDriver().Dir + "/../lib");
     730                1:   getFilePaths().push_back("/usr/lib");
     731                1: }
     732                 : 
     733                3: Tool &OpenBSD::SelectTool(const Compilation &C, const JobAction &JA) const {
     734                 :   Action::ActionClass Key;
                        1: branch 3 taken
                        2: branch 4 taken
     735                3:   if (getDriver().ShouldUseClangCompiler(C, JA, getTriple()))
     736                1:     Key = Action::AnalyzeJobClass;
     737                 :   else
     738                2:     Key = JA.getKind();
     739                 : 
     740                3:   Tool *&T = Tools[Key];
                        3: branch 0 taken
                        0: branch 1 not taken
     741                3:   if (!T) {
                        1: branch 0 taken
                        1: branch 1 taken
                        1: branch 2 taken
     742                3:     switch (Key) {
     743                 :     case Action::AssembleJobClass:
     744                1:       T = new tools::openbsd::Assemble(*this); break;
     745                 :     case Action::LinkJobClass:
     746                1:       T = new tools::openbsd::Link(*this); break;
     747                 :     default:
     748                1:       T = &Generic_GCC::SelectTool(C, JA);
     749                 :     }
     750                 :   }
     751                 : 
     752                3:   return *T;
     753                 : }
     754                 : 
     755                 : /// FreeBSD - FreeBSD tool chain which can call as(1) and ld(1) directly.
     756                 : 
     757                1: FreeBSD::FreeBSD(const HostInfo &Host, const llvm::Triple& Triple, bool Lib32)
     758                1:   : Generic_GCC(Host, Triple) {
                        0: branch 0 not taken
                        1: branch 1 taken
                        1: branch 2 taken
                        1: branch 3 taken
     759                1:   if (Lib32) {
     760                0:     getFilePaths().push_back(getDriver().Dir + "/../lib32");
     761                0:     getFilePaths().push_back("/usr/lib32");
     762                 :   } else {
     763                1:     getFilePaths().push_back(getDriver().Dir + "/../lib");
     764                1:     getFilePaths().push_back("/usr/lib");
     765                 :   }
     766                1: }
     767                 : 
     768                3: Tool &FreeBSD::SelectTool(const Compilation &C, const JobAction &JA) const {
     769                 :   Action::ActionClass Key;
                        1: branch 3 taken
                        2: branch 4 taken
     770                3:   if (getDriver().ShouldUseClangCompiler(C, JA, getTriple()))
     771                1:     Key = Action::AnalyzeJobClass;
     772                 :   else
     773                2:     Key = JA.getKind();
     774                 : 
     775                3:   Tool *&T = Tools[Key];
                        3: branch 0 taken
                        0: branch 1 not taken
     776                3:   if (!T) {
                        1: branch 0 taken
                        1: branch 1 taken
                        1: branch 2 taken
     777                3:     switch (Key) {
     778                 :     case Action::AssembleJobClass:
     779                1:       T = new tools::freebsd::Assemble(*this); break;
     780                 :     case Action::LinkJobClass:
     781                1:       T = new tools::freebsd::Link(*this); break;
     782                 :     default:
     783                1:       T = &Generic_GCC::SelectTool(C, JA);
     784                 :     }
     785                 :   }
     786                 : 
     787                3:   return *T;
     788                 : }
     789                 : 
     790                 : /// AuroraUX - AuroraUX tool chain which can call as(1) and ld(1) directly.
     791                 : 
     792                0: AuroraUX::AuroraUX(const HostInfo &Host, const llvm::Triple& Triple)
     793                0:   : Generic_GCC(Host, Triple) {
     794                 : 
     795                0:   getProgramPaths().push_back(getDriver().Dir);
     796                 : 
     797                0:   getFilePaths().push_back(getDriver().Dir + "/../lib");
     798                0:   getFilePaths().push_back("/usr/lib");
     799                0:   getFilePaths().push_back("/usr/sfw/lib");
     800                0:   getFilePaths().push_back("/opt/gcc4/lib");
     801                0:   getFilePaths().push_back("/opt/gcc4/lib/gcc/i386-pc-solaris2.11/4.2.4");
     802                 : 
     803                0: }
     804                 : 
     805                0: Tool &AuroraUX::SelectTool(const Compilation &C, const JobAction &JA) const {
     806                 :   Action::ActionClass Key;
                        0: branch 3 not taken
                        0: branch 4 not taken
     807                0:   if (getDriver().ShouldUseClangCompiler(C, JA, getTriple()))
     808                0:     Key = Action::AnalyzeJobClass;
     809                 :   else
     810                0:     Key = JA.getKind();
     811                 : 
     812                0:   Tool *&T = Tools[Key];
                        0: branch 0 not taken
                        0: branch 1 not taken
     813                0:   if (!T) {
                        0: branch 0 not taken
                        0: branch 1 not taken
                        0: branch 2 not taken
     814                0:     switch (Key) {
     815                 :     case Action::AssembleJobClass:
     816                0:       T = new tools::auroraux::Assemble(*this); break;
     817                 :     case Action::LinkJobClass:
     818                0:       T = new tools::auroraux::Link(*this); break;
     819                 :     default:
     820                0:       T = &Generic_GCC::SelectTool(C, JA);
     821                 :     }
     822                 :   }
     823                 : 
     824                0:   return *T;
     825                 : }
     826                 : 
     827                 : 
     828                 : /// Linux toolchain (very bare-bones at the moment).
     829                 : 
     830              152: Linux::Linux(const HostInfo &Host, const llvm::Triple& Triple)
     831              152:   : Generic_GCC(Host, Triple) {
     832              152:   getFilePaths().push_back(getDriver().Dir + "/../lib/clang/1.0/");
     833              152:   getFilePaths().push_back("/lib/");
     834              152:   getFilePaths().push_back("/usr/lib/");
     835                 : 
     836                 :   // Depending on the Linux distribution, any combination of lib{,32,64} is
     837                 :   // possible. E.g. Debian uses lib and lib32 for mixed i386/x86-64 systems,
     838                 :   // openSUSE uses lib and lib64 for the same purpose.
     839              152:   getFilePaths().push_back("/lib32/");
     840              152:   getFilePaths().push_back("/usr/lib32/");
     841              152:   getFilePaths().push_back("/lib64/");
     842              152:   getFilePaths().push_back("/usr/lib64/");
     843                 : 
     844                 :   // FIXME: Figure out some way to get gcc's libdir
     845                 :   // (e.g. /usr/lib/gcc/i486-linux-gnu/4.3/ for Ubuntu 32-bit); we need
     846                 :   // crtbegin.o/crtend.o/etc., and want static versions of various
     847                 :   // libraries. If we had our own crtbegin.o/crtend.o/etc, we could probably
     848                 :   // get away with using shared versions in /usr/lib, though.
     849                 :   // We could fall back to the approach we used for includes (a massive
     850                 :   // list), but that's messy at best.
     851              152: }
     852                 : 
     853                 : /// DragonFly - DragonFly tool chain which can call as(1) and ld(1) directly.
     854                 : 
     855                1: DragonFly::DragonFly(const HostInfo &Host, const llvm::Triple& Triple)
     856                1:   : Generic_GCC(Host, Triple) {
     857                 : 
     858                 :   // Path mangling to find libexec
     859                1:   getProgramPaths().push_back(getDriver().Dir);
     860                 : 
     861                1:   getFilePaths().push_back(getDriver().Dir + "/../lib");
     862                1:   getFilePaths().push_back("/usr/lib");
     863                1:   getFilePaths().push_back("/usr/lib/gcc41");
     864                1: }
     865                 : 
     866                3: Tool &DragonFly::SelectTool(const Compilation &C, const JobAction &JA) const {
     867                 :   Action::ActionClass Key;
                        1: branch 3 taken
                        2: branch 4 taken
     868                3:   if (getDriver().ShouldUseClangCompiler(C, JA, getTriple()))
     869                1:     Key = Action::AnalyzeJobClass;
     870                 :   else
     871                2:     Key = JA.getKind();
     872                 : 
     873                3:   Tool *&T = Tools[Key];
                        3: branch 0 taken
                        0: branch 1 not taken
     874                3:   if (!T) {
                        1: branch 0 taken
                        1: branch 1 taken
                        1: branch 2 taken
     875                3:     switch (Key) {
     876                 :     case Action::AssembleJobClass:
     877                1:       T = new tools::dragonfly::Assemble(*this); break;
     878                 :     case Action::LinkJobClass:
     879                1:       T = new tools::dragonfly::Link(*this); break;
     880                 :     default:
     881                1:       T = &Generic_GCC::SelectTool(C, JA);
     882                 :     }
     883                 :   }
     884                 : 
     885                3:   return *T;
     886                 : }

Generated: 2010-02-10 01:31 by zcov