r174349 - Driver and option support for -gsplit-dwarf. This is a part of

David Blaikie dblaikie at gmail.com
Tue Feb 5 10:21:33 PST 2013


On Mon, Feb 4, 2013 at 11:29 PM, Eric Christopher <echristo at gmail.com> wrote:
> Author: echristo
> Date: Tue Feb  5 01:29:57 2013
> New Revision: 174349
>
> URL: http://llvm.org/viewvc/llvm-project?rev=174349&view=rev
> Log:
> Driver and option support for -gsplit-dwarf. This is a part of
> the DWARF5 split dwarf proposal.
>
> Added:
>     cfe/trunk/test/Driver/split-debug.c
> Modified:
>     cfe/trunk/include/clang/Driver/Action.h
>     cfe/trunk/include/clang/Driver/CC1Options.td
>     cfe/trunk/include/clang/Driver/Options.td
>     cfe/trunk/lib/Driver/Action.cpp
>     cfe/trunk/lib/Driver/Driver.cpp
>     cfe/trunk/lib/Driver/ToolChains.cpp
>     cfe/trunk/lib/Driver/Tools.cpp
>     cfe/trunk/lib/Driver/Tools.h
>     cfe/trunk/lib/Driver/WindowsToolChain.cpp
>
> Modified: cfe/trunk/include/clang/Driver/Action.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Driver/Action.h?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Driver/Action.h (original)
> +++ cfe/trunk/include/clang/Driver/Action.h Tue Feb  5 01:29:57 2013
> @@ -46,9 +46,10 @@ public:
>      LipoJobClass,
>      DsymutilJobClass,
>      VerifyJobClass,
> +    SplitDebugJobClass,
>
>      JobClassFirst=PreprocessJobClass,
> -    JobClassLast=VerifyJobClass
> +    JobClassLast=SplitDebugJobClass
>    };
>
>    static const char *getClassName(ActionClass AC);
> @@ -233,6 +234,15 @@ public:
>    }
>  };
>
> +class SplitDebugJobAction : public JobAction {
> +  virtual void anchor();
> +public:
> +  SplitDebugJobAction(ActionList &Inputs, types::ID Type);
> +  static bool classof(const Action *A) {
> +    return A->getKind() == SplitDebugJobClass;
> +  }
> +};
> +
>  } // end namespace driver
>  } // end namespace clang
>
>
> Modified: cfe/trunk/include/clang/Driver/CC1Options.td
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Driver/CC1Options.td?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Driver/CC1Options.td (original)
> +++ cfe/trunk/include/clang/Driver/CC1Options.td Tue Feb  5 01:29:57 2013
> @@ -134,6 +134,8 @@ def dwarf_debug_flags : Separate<["-"],
>    HelpText<"The string to embed in the Dwarf debug flags record.">;
>  def dwarf_column_info : Flag<["-"], "dwarf-column-info">,
>    HelpText<"Turn on column location information.">;
> +def split_dwarf : Flag<["-"], "split-dwarf">,
> +  HelpText<"Split out the dwarf .dwo sections">;
>  def fforbid_guard_variables : Flag<["-"], "fforbid-guard-variables">,
>    HelpText<"Emit an error if a C++ static local initializer would need a guard variable">;
>  def no_implicit_float : Flag<["-"], "no-implicit-float">,
>
> Modified: cfe/trunk/include/clang/Driver/Options.td
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Driver/Options.td?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/include/clang/Driver/Options.td (original)
> +++ cfe/trunk/include/clang/Driver/Options.td Tue Feb  5 01:29:57 2013
> @@ -760,6 +760,7 @@ def gno_record_gcc_switches : Flag<["-"]
>  def gstrict_dwarf : Flag<["-"], "gstrict-dwarf">, Group<g_flags_Group>;
>  def gno_strict_dwarf : Flag<["-"], "gno-strict-dwarf">, Group<g_flags_Group>;
>  def gcolumn_info : Flag<["-"], "gcolumn-info">, Group<g_flags_Group>;
> +def gsplit_dwarf : Flag<["-"], "gsplit-dwarf">, Group<g_flags_Group>;
>  def headerpad__max__install__names : Joined<["-"], "headerpad_max_install_names">;
>  def help : Flag<["-", "--"], "help">, Flags<[CC1Option]>,
>    HelpText<"Display available options">;
>
> Modified: cfe/trunk/lib/Driver/Action.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Driver/Action.cpp?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Driver/Action.cpp (original)
> +++ cfe/trunk/lib/Driver/Action.cpp Tue Feb  5 01:29:57 2013
> @@ -33,6 +33,7 @@ const char *Action::getClassName(ActionC
>    case LipoJobClass: return "lipo";
>    case DsymutilJobClass: return "dsymutil";
>    case VerifyJobClass: return "verify";
> +  case SplitDebugJobClass: return "split-debug";
>    }
>
>    llvm_unreachable("invalid class");
> @@ -119,3 +120,9 @@ void VerifyJobAction::anchor() {}
>  VerifyJobAction::VerifyJobAction(ActionList &Inputs, types::ID Type)
>    : JobAction(VerifyJobClass, Inputs, Type) {
>  }
> +
> +void SplitDebugJobAction::anchor() {}
> +
> +SplitDebugJobAction::SplitDebugJobAction(ActionList &Inputs, types::ID Type)
> +  : JobAction(SplitDebugJobClass, Inputs, Type) {
> +}
>
> Modified: cfe/trunk/lib/Driver/Driver.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Driver/Driver.cpp?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Driver/Driver.cpp (original)
> +++ cfe/trunk/lib/Driver/Driver.cpp Tue Feb  5 01:29:57 2013
> @@ -25,6 +25,7 @@
>  #include "llvm/ADT/ArrayRef.h"
>  #include "llvm/ADT/OwningPtr.h"
>  #include "llvm/ADT/StringSet.h"
> +#include "llvm/Support/Debug.h"
>  #include "llvm/Support/ErrorHandling.h"
>  #include "llvm/Support/FileSystem.h"
>  #include "llvm/Support/Path.h"
> @@ -1036,6 +1037,7 @@ void Driver::BuildActions(const ToolChai
>
>    // Construct the actions to perform.
>    ActionList LinkerInputs;
> +  ActionList SplitInputs;
>    unsigned NumSteps = 0;
>    for (unsigned i = 0, e = Inputs.size(); i != e; ++i) {
>      types::ID InputType = Inputs[i].first;
> @@ -1105,6 +1107,12 @@ void Driver::BuildActions(const ToolChai
>        Current.reset(ConstructPhaseAction(Args, Phase, Current.take()));
>        if (Current->getType() == types::TY_Nothing)
>          break;
> +      else if (Current->getType() == types::TY_Object &&
> +               Args.hasArg(options::OPT_gsplit_dwarf)) {
> +        ActionList Input;
> +        Input.push_back(Current.take());
> +        Current.reset(new SplitDebugJobAction(Input, types::TY_Object));
> +      }
>      }
>
>      // If we ended with something, add to the output list.
> @@ -1112,6 +1120,16 @@ void Driver::BuildActions(const ToolChai
>        Actions.push_back(Current.take());
>    }
>
> +  if (!SplitInputs.empty()) {
> +    for (ActionList::iterator i = SplitInputs.begin(), e = SplitInputs.end();
> +         i != e; ++i) {
> +      Action *Act = *i;
> +      ActionList Inputs;
> +      Inputs.push_back(Act);
> +      Actions.push_back(new SplitDebugJobAction(Inputs, types::TY_Object));
> +    }
> +  }
> +
>    // Add a link action if necessary.
>    if (!LinkerInputs.empty())
>      Actions.push_back(new LinkJobAction(LinkerInputs, types::TY_Image));
> @@ -1396,12 +1414,13 @@ void Driver::BuildJobsForAction(Compilat
>      BaseInput = InputInfos[0].getFilename();
>
>    // Determine the place to write output to, if any.
> -  if (JA->getType() == types::TY_Nothing) {
> +  if (JA->getType() == types::TY_Nothing)
>      Result = InputInfo(A->getType(), BaseInput);
> -  } else {
> +  else if (isa<SplitDebugJobAction>(A))
> +    Result = InputInfos[0];
> +  else
>      Result = InputInfo(GetNamedOutputPath(C, *JA, BaseInput, AtTopLevel),
>                         A->getType(), BaseInput);
> -  }
>
>    if (CCCPrintBindings && !CCGenDiagnostics) {
>      llvm::errs() << "# \"" << T.getToolChain().getTripleString() << '"'
>
> Modified: cfe/trunk/lib/Driver/ToolChains.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Driver/ToolChains.cpp?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Driver/ToolChains.cpp (original)
> +++ cfe/trunk/lib/Driver/ToolChains.cpp Tue Feb  5 01:29:57 2013
> @@ -189,6 +189,7 @@ Tool &Darwin::SelectTool(const Compilati
>    Tool *&T = Tools[Key];
>    if (!T) {
>      switch (Key) {
> +    case Action::SplitDebugJobClass:
>      case Action::InputClass:
>      case Action::BindArchClass:
>        llvm_unreachable("Invalid tool kind.");
> @@ -1388,6 +1389,7 @@ Tool &Generic_GCC::SelectTool(const Comp
>    Tool *&T = Tools[Key];
>    if (!T) {
>      switch (Key) {
> +    case Action::SplitDebugJobClass:
>      case Action::InputClass:
>      case Action::BindArchClass:
>        llvm_unreachable("Invalid tool kind.");
> @@ -2450,6 +2452,8 @@ Tool &Linux::SelectTool(const Compilatio
>        break;
>      case Action::LinkJobClass:
>        T = new tools::linuxtools::Link(*this); break;
> +    case Action::SplitDebugJobClass:
> +      T = new tools::linuxtools::SplitDebug(*this); break;
>      default:
>        T = &Generic_GCC::SelectTool(C, JA, Inputs);
>      }
>
> Modified: cfe/trunk/lib/Driver/Tools.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Driver/Tools.cpp?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Driver/Tools.cpp (original)
> +++ cfe/trunk/lib/Driver/Tools.cpp Tue Feb  5 01:29:57 2013
> @@ -2250,16 +2250,15 @@ void Clang::ConstructJob(Compilation &C,
>                        D.CCLogDiagnosticsFilename : "-");
>    }
>
> -  // Use the last option from "-g" group. "-gline-tables-only" is
> -  // preserved, all other debug options are substituted with "-g".
> +  // Use the last option from "-g" group. "-gline-tables-only"
> +  // is preserved, all other debug options are substituted with "-g".
>    Args.ClaimAllArgs(options::OPT_g_Group);
>    if (Arg *A = Args.getLastArg(options::OPT_g_Group)) {
> -    if (A->getOption().matches(options::OPT_gline_tables_only)) {
> +    if (A->getOption().matches(options::OPT_gline_tables_only))
>        CmdArgs.push_back("-gline-tables-only");
> -    } else if (!A->getOption().matches(options::OPT_g0) &&
> -               !A->getOption().matches(options::OPT_ggdb0)) {
> +    else if (!A->getOption().matches(options::OPT_g0) &&
> +             !A->getOption().matches(options::OPT_ggdb0))
>        CmdArgs.push_back("-g");
> -    }
>    }
>
>    // We ignore flags -gstrict-dwarf and -grecord-gcc-switches for now.
> @@ -2267,6 +2266,14 @@ void Clang::ConstructJob(Compilation &C,
>    if (Args.hasArg(options::OPT_gcolumn_info))
>      CmdArgs.push_back("-dwarf-column-info");
>
> +  // -gsplit-dwarf should turn on -g and enable the backend dwarf
> +  // splitting and extraction.
> +  if (Args.hasArg(options::OPT_gsplit_dwarf)) {
> +    CmdArgs.push_back("-g");
> +    CmdArgs.push_back("-backend-option");
> +    CmdArgs.push_back("-split-dwarf=Enable");
> +  }
> +
>    Args.AddAllArgs(CmdArgs, options::OPT_ffunction_sections);
>    Args.AddAllArgs(CmdArgs, options::OPT_fdata_sections);
>
> @@ -5829,6 +5836,42 @@ void linuxtools::Link::ConstructJob(Comp
>    C.addCommand(new Command(JA, *this, ToolChain.Linker.c_str(), CmdArgs));
>  }
>
> +void linuxtools::SplitDebug::ConstructJob(Compilation &C, const JobAction &JA,
> +                                          const InputInfo &Output,
> +                                          const InputInfoList &Inputs,
> +                                          const ArgList &Args,
> +                                          const char *LinkingOutput) const {
> +  // Assert some invariants.
> +  assert(Inputs.size() == 1 && "Unable to handle multiple inputs.");
> +  const InputInfo &Input = Inputs[0];
> +  assert(Input.isFilename() && "Unexpected verify input");
> +
> +  ArgStringList ExtractArgs;
> +  ExtractArgs.push_back("--extract-dwo");
> +
> +  ArgStringList StripArgs;
> +  StripArgs.push_back("--strip-dwo");

So objcopy itself (this isn't an LLVM tool but a system tool, right)
is dwo-aware? I assume this is a recent development alongside the
DWARFv5 proposal? Are the test cases going to work on most systems
that might not have such a bleeding edge objcopy? What's the behavior
like for users if their objcopy doesn't have this functionality?

> +
> +  // Grabbing the output of the earlier compile step.
> +  StripArgs.push_back(Input.getFilename());
> +  ExtractArgs.push_back(Input.getFilename());
> +
> +  // Add an output for the extract.
> +  SmallString<128> T(Inputs[0].getBaseInput());
> +  llvm::sys::path::replace_extension(T, "dwo");
> +  const char *OutFile = Args.MakeArgString(T);
> +  ExtractArgs.push_back(OutFile);
> +
> +  const char *Exec =
> +    Args.MakeArgString(getToolChain().GetProgramPath("objcopy"));
> +
> +  // First extract the dwo sections.
> +  C.addCommand(new Command(JA, *this, Exec, ExtractArgs));
> +
> +  // Then remove them from the original .o file.
> +  C.addCommand(new Command(JA, *this, Exec, StripArgs));
> +}
> +
>  void minix::Assemble::ConstructJob(Compilation &C, const JobAction &JA,
>                                     const InputInfo &Output,
>                                     const InputInfoList &Inputs,
>
> Modified: cfe/trunk/lib/Driver/Tools.h
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Driver/Tools.h?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Driver/Tools.h (original)
> +++ cfe/trunk/lib/Driver/Tools.h Tue Feb  5 01:29:57 2013
> @@ -454,6 +454,20 @@ namespace linuxtools {
>                                const ArgList &TCArgs,
>                                const char *LinkingOutput) const;
>    };
> +
> +  class LLVM_LIBRARY_VISIBILITY SplitDebug : public Tool  {
> +  public:
> +    SplitDebug(const ToolChain &TC) : Tool("linuxtools::SplitDebug",
> +                                           "objcopy", TC) {}
> +
> +    virtual bool hasIntegratedCPP() const { return false; }
> +
> +    virtual void ConstructJob(Compilation &C, const JobAction &JA,
> +                              const InputInfo &Output,
> +                              const InputInfoList &Inputs,
> +                              const ArgList &TCArgs,
> +                              const char *LinkingOutput) const;
> +  };
>  }
>    /// minix -- Directly call GNU Binutils assembler and linker
>  namespace minix {
>
> Modified: cfe/trunk/lib/Driver/WindowsToolChain.cpp
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Driver/WindowsToolChain.cpp?rev=174349&r1=174348&r2=174349&view=diff
> ==============================================================================
> --- cfe/trunk/lib/Driver/WindowsToolChain.cpp (original)
> +++ cfe/trunk/lib/Driver/WindowsToolChain.cpp Tue Feb  5 01:29:57 2013
> @@ -54,6 +54,7 @@ Tool &Windows::SelectTool(const Compilat
>      case Action::LipoJobClass:
>      case Action::DsymutilJobClass:
>      case Action::VerifyJobClass:
> +    case Action::SplitDebugJobClass:
>        llvm_unreachable("Invalid tool kind.");
>      case Action::PreprocessJobClass:
>      case Action::PrecompileJobClass:
>
> Added: cfe/trunk/test/Driver/split-debug.c
> URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Driver/split-debug.c?rev=174349&view=auto
> ==============================================================================
> --- cfe/trunk/test/Driver/split-debug.c (added)
> +++ cfe/trunk/test/Driver/split-debug.c Tue Feb  5 01:29:57 2013
> @@ -0,0 +1,19 @@
> +// Check that we split debug output properly
> +//
> +// REQUIRES: asserts
> +// RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-phases \
> +// RUN:   -gsplit-dwarf -arch x86_64 %s 2> %t
> +// RUN: FileCheck -check-prefix=CHECK-ACTIONS < %t %s

I'm not sure I've seen test cases written this way (with the file
argument to FileCheck after the stdin specification) I assume it's
more common to write it as "%s < %t" at the end? 'spose it doesn't
matter though.

> +//
> +// CHECK-ACTIONS: 0: input, "{{.*}}split-debug.c", c
> +// CHECK-ACTIONS: 4: split-debug, {3}, object
> +
> +// Check output name derivation.
> +//
> +// RUN: %clang -target x86_64-unknown-linux-gnu -ccc-print-bindings \
> +// RUN:   -gsplit-dwarf -arch x86_64 -c %s 2> %t
> +// RUN: FileCheck -check-prefix=CHECK-OUTPUT-NAME < %t %s
> +//
> +// CHECK-OUTPUT-NAME:# "x86_64-unknown-linux-gnu" - "clang", inputs: ["{{.*}}split-debug.c"], output: "{{.*}}split-debug{{.*}}.o"
> +// CHECK-OUTPUT-NAME:# "x86_64-unknown-linux-gnu" - "linuxtools::SplitDebug", inputs: ["{{.*}}split-debug{{.*}}.o"], output: "{{.*}}split-debug{{.*}}.o"

I don't see any mention of '.dwo' in this test case - does it verify
that the dwo file is a product in any way?

- David

> +
>
>
> _______________________________________________
> cfe-commits mailing list
> cfe-commits at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits



More information about the cfe-commits mailing list