Re: [PATCH] D12200: Add framework for iterative compilation to clang

2015-09-25 Thread Zoran Jovanovic via cfe-commits
zoran.jovanovic updated this revision to Diff 35727.
zoran.jovanovic added a comment.

Updated to follow new revision of patch for iterative compilation in llvm:
http://reviews.llvm.org/D12199


http://reviews.llvm.org/D12200

Files:
  include/clang/Driver/Compilation.h
  include/clang/Driver/Driver.h
  include/clang/Driver/Options.td
  lib/CodeGen/BackendUtil.cpp
  lib/Driver/Driver.cpp
  lib/Driver/Tools.cpp
  tools/driver/driver.cpp

Index: tools/driver/driver.cpp
===
--- tools/driver/driver.cpp
+++ tools/driver/driver.cpp
@@ -50,6 +50,12 @@
 #include "llvm/Support/raw_ostream.h"
 #include 
 #include 
+#include "llvm/Analysis/IterativeCompilation.h"
+#include "llvm/Support/Program.h"
+#include 
+#include 
+#include 
+#include 
 using namespace clang;
 using namespace clang::driver;
 using namespace llvm::opt;
@@ -386,6 +392,80 @@
   return 1;
 }
 
+void initControlFiles(llvm::ModuleDecisionTrees &MDT, int CurrentIteration)
+{
+  std::string ICResultsFile;
+  std::string ICResultsFile2;
+
+  // assign control files
+  llvm::ICResultsFile results1("ic-results", CurrentIteration);
+  llvm::ICResultsFile results2("ic-results2", CurrentIteration);
+  MDT.getICResultsFile() = results1;
+  MDT.getICResultsFile2() = results2;
+
+  llvm::ICInputFile input1("ic-input", CurrentIteration);
+  llvm::ICInputFile input2("ic-input2", CurrentIteration);
+  MDT.getICInputFile() = input1;
+  MDT.getICInputFile2() = input2;
+}
+
+void writeInputFiles(llvm::ModuleDecisionTrees &MDT)
+{
+  // inits and declarations
+  llvm::ICPathsMap paths;
+  llvm::ICPathsMap pathBeforeCodegen;
+  llvm::ICPathsMap pathAfterCodegen;
+
+  // split paths
+  MDT.getPaths(paths);
+  MDT.splitPaths(paths, pathBeforeCodegen, pathAfterCodegen);
+
+  // convert paths to strings and write them to files
+  llvm::ICInputFile input1 = MDT.getICInputFile();
+  llvm::ICInputFile input2 = MDT.getICInputFile2();
+
+  input1.setPaths(pathBeforeCodegen);
+  input2.setPaths(pathAfterCodegen);
+
+  input1.write();
+  input2.write();
+}
+
+void removeControlFiles(llvm::ModuleDecisionTrees &MDT) {
+  MDT.getICResultsFile().remove();
+  MDT.getICResultsFile2().remove();
+}
+
+int loadResultFiles(llvm::ModuleDecisionTrees &MDT,
+std::vector &merged) {
+  llvm::ICResultsFile results1 = MDT.getICResultsFile();
+  llvm::ICResultsFile results2 = MDT.getICResultsFile2();
+
+  int r1 = results1.read();
+  int r2 = results2.read();
+
+  if(r1 || r2)
+return 1;
+
+  llvm::MdtResults::mergeMdtResults(merged,
+  results1.getResults(), results2.getResults());
+
+  return 0;
+}
+
+llvm::MdtResults* getModuleResults(std::vector &merged,
+   std::string name)
+{
+  llvm::MdtResults *moduleResults = NULL;
+
+  for(auto res : merged) {
+if (res.FunctionNameAndPhase.getName() == name)
+  moduleResults = new llvm::MdtResults(res);
+  }
+
+  return moduleResults;
+}
+
 int main(int argc_, const char **argv_) {
   llvm::sys::PrintStackTraceOnErrorSignal();
   llvm::PrettyStackTraceProgram X(argc_, argv_);
@@ -506,6 +586,31 @@
 Diags.takeClient(), std::move(SerializedConsumer)));
   }
 
+  // Get number of iterations for iterative compilation.
+  // declare files and number of iterations
+  int ICNumberOfIterations = 0;
+
+  // extract number of iterations from cli args
+  std::unique_ptr CCopts(createDriverOptTable());
+  unsigned MissingArgIndex, MissingArgCount;
+  ArrayRef argv_ref(argv);
+  InputArgList Args = CCopts->ParseArgs(argv_ref.slice(1),
+MissingArgIndex, MissingArgCount);
+  if (Args.getLastArg(options::OPT_fiterative_comp_EQ)) {
+std::string Val = Args.getLastArgValue(options::OPT_fiterative_comp_EQ, "1");
+std::stringstream Convert(Val);
+Convert >> ICNumberOfIterations;
+   }
+  if (!ICNumberOfIterations)
+ICNumberOfIterations = 1; // Default value is 1.
+
+  llvm::ModuleDecisionTrees moduleDecisionTrees;
+  int CurrentIteration = 0;
+  int Res = 0;
+
+  llvm::FnNameAndPhase::ICPhase CurrICPhase = llvm::FnNameAndPhase::ModulePhase;
+
+  for (; CurrentIteration < ICNumberOfIterations; CurrentIteration++) {
   ProcessWarningOptions(Diags, *DiagOpts, /*ReportDiags=*/false);
 
   Driver TheDriver(Path, llvm::sys::getDefaultTargetTriple(), Diags);
@@ -516,12 +621,54 @@
 
   SetBackdoorDriverOutputsFromEnvVars(TheDriver);
 
+  if (ICNumberOfIterations > 1) {
+TheDriver.setModuleDecisionTrees(&moduleDecisionTrees);
+
+initControlFiles(moduleDecisionTrees, CurrentIteration);
+writeInputFiles(moduleDecisionTrees);
+
+moduleDecisionTrees.startNewIteration();
+  }
+
   std::unique_ptr C(TheDriver.BuildCompilation(argv));
   int Res = 0;
   SmallVector, 4> FailingCommands;
   if (C.get())
 Res = TheDriver.ExecuteCompilation(*C, FailingCommands);
 
+  if (ICNumberOfIterations > 1) {
+std::vector MergerdResults;
+if(loadResultFiles(moduleDecisionTrees, MergerdR

[PATCH] D12200: Add framework for iterative compilation to clang

2015-08-20 Thread Zoran Jovanovic via cfe-commits
zoran.jovanovic created this revision.
zoran.jovanovic added reviewers: hfinkel, atrick, chandlerc.
zoran.jovanovic added subscribers: cfe-commits, yaron.keren, petarj, 
Atlantic777, Radovan.Obradovic.

This patch adds command line option for iterative compilation, as well
as the code that invokes clang iteratively.
Communication between multiple runs is done over temporary files.

http://reviews.llvm.org/D12200

Files:
  include/clang/Driver/Compilation.h
  include/clang/Driver/Driver.h
  include/clang/Driver/Options.td
  lib/CodeGen/BackendUtil.cpp
  lib/Driver/Driver.cpp
  lib/Driver/Tools.cpp
  tools/driver/driver.cpp

Index: tools/driver/driver.cpp
===
--- tools/driver/driver.cpp
+++ tools/driver/driver.cpp
@@ -50,6 +50,10 @@
 #include "llvm/Support/raw_ostream.h"
 #include 
 #include 
+#include "llvm/Analysis/IterativeCompilation.h"
+#include "llvm/Support/Program.h"
+#include 
+#include 
 using namespace clang;
 using namespace clang::driver;
 using namespace llvm::opt;
@@ -386,6 +390,80 @@
   return 1;
 }
 
+void initControlFiles(llvm::ModuleDecisionTrees &MDT, int CurrentIteration)
+{
+  std::string ICResultsFile;
+  std::string ICResultsFile2;
+
+  // assign control files
+  llvm::ICResultsFile results1("ic-results", CurrentIteration);
+  llvm::ICResultsFile results2("ic-results2", CurrentIteration);
+  MDT.getICResultsFile() = results1;
+  MDT.getICResultsFile2() = results2;
+
+  llvm::ICInputFile input1("ic-input", CurrentIteration);
+  llvm::ICInputFile input2("ic-input2", CurrentIteration);
+  MDT.getICInputFile() = input1;
+  MDT.getICInputFile2() = input2;
+}
+
+void writeInputFiles(llvm::ModuleDecisionTrees &MDT)
+{
+  // inits and declarations
+  llvm::ICPathsMap paths;
+  llvm::ICPathsMap pathBeforeCodegen;
+  llvm::ICPathsMap pathAfterCodegen;
+
+  // split paths
+  MDT.getPaths(paths);
+  MDT.splitPaths(paths, pathBeforeCodegen, pathAfterCodegen);
+
+  // convert paths to strings and write them to files
+  llvm::ICInputFile input1 = MDT.getICInputFile();
+  llvm::ICInputFile input2 = MDT.getICInputFile2();
+
+  input1.setPaths(pathBeforeCodegen);
+  input2.setPaths(pathAfterCodegen);
+
+  input1.write();
+  input2.write();
+}
+
+void removeControlFiles(llvm::ModuleDecisionTrees &MDT) {
+  MDT.getICResultsFile().remove();
+  MDT.getICResultsFile2().remove();
+}
+
+int loadResultFiles(llvm::ModuleDecisionTrees &MDT,
+std::vector &merged) {
+  llvm::ICResultsFile results1 = MDT.getICResultsFile();
+  llvm::ICResultsFile results2 = MDT.getICResultsFile2();
+
+  int r1 = results1.read();
+  int r2 = results2.read();
+
+  if(r1 || r2)
+return 1;
+
+  llvm::MdtResults::mergeMdtResults(merged,
+  results1.getResults(), results2.getResults());
+
+  return 0;
+}
+
+llvm::MdtResults* getModuleResults(std::vector &merged,
+   std::string name)
+{
+  llvm::MdtResults *moduleResults = NULL;
+
+  for(auto res : merged) {
+if (res.FunctionNameAndPhase.getName() == name)
+  moduleResults = new llvm::MdtResults(res);
+  }
+
+  return moduleResults;
+}
+
 int main(int argc_, const char **argv_) {
   llvm::sys::PrintStackTraceOnErrorSignal();
   llvm::PrettyStackTraceProgram X(argc_, argv_);
@@ -506,6 +584,31 @@
 Diags.takeClient(), std::move(SerializedConsumer)));
   }
 
+  // Get number of iterations for iterative compilation.
+  // declare files and number of iterations
+  int ICNumberOfIterations = 0;
+
+  // extract number of iterations from cli args
+  std::unique_ptr CCopts(createDriverOptTable());
+  unsigned MissingArgIndex, MissingArgCount;
+  ArrayRef argv_ref(argv);
+  InputArgList Args = CCopts->ParseArgs(argv_ref.slice(1),
+MissingArgIndex, MissingArgCount);
+  if (Args.getLastArg(options::OPT_fiterative_comp_EQ)) {
+std::string Val = Args.getLastArgValue(options::OPT_fiterative_comp_EQ, "1");
+std::stringstream Convert(Val);
+Convert >> ICNumberOfIterations;
+   }
+  if (!ICNumberOfIterations)
+ICNumberOfIterations = 1; // Default value is 1.
+
+  llvm::ModuleDecisionTrees moduleDecisionTrees;
+  int CurrentIteration = 0;
+  int Res = 0;
+
+  llvm::FnNameAndPhase::ICPhase CurrICPhase = llvm::FnNameAndPhase::ModulePhase;
+
+  for (; CurrentIteration < ICNumberOfIterations; CurrentIteration++) {
   ProcessWarningOptions(Diags, *DiagOpts, /*ReportDiags=*/false);
 
   Driver TheDriver(Path, llvm::sys::getDefaultTargetTriple(), Diags);
@@ -516,12 +619,51 @@
 
   SetBackdoorDriverOutputsFromEnvVars(TheDriver);
 
+  if (ICNumberOfIterations > 1) {
+TheDriver.setModuleDecisionTrees(&moduleDecisionTrees);
+
+initControlFiles(moduleDecisionTrees, CurrentIteration);
+writeInputFiles(moduleDecisionTrees);
+
+moduleDecisionTrees.startNewIteration();
+  }
+
   std::unique_ptr C(TheDriver.BuildCompilation(argv));
   int Res = 0;
   SmallVector, 4> FailingCommands;
   if (C.get())
 Res = TheDri

Re: [PATCH] D12200: Add framework for iterative compilation to clang

2015-08-20 Thread Zoran Jovanovic via cfe-commits
zoran.jovanovic added a comment.

This patch needs to be applied along with the patch for llvm.
See http://reviews.llvm.org/D12199 for more details.

As suggested new revision created for this patch,
previous patch versions can be found here:
http://reviews.llvm.org/D4724


http://reviews.llvm.org/D12200



___
cfe-commits mailing list
cfe-commits@lists.llvm.org
http://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits


Re: [PATCH] D12200: Add framework for iterative compilation to clang

2016-04-22 Thread Zoran Jovanovic via cfe-commits
zoran.jovanovic updated this revision to Diff 54640.
zoran.jovanovic added a comment.

New patch version rebased to r256194.
Any comments to this work?


http://reviews.llvm.org/D12200

Files:
  include/clang/Driver/Compilation.h
  include/clang/Driver/Driver.h
  include/clang/Driver/Options.td
  lib/CodeGen/BackendUtil.cpp
  lib/Driver/Driver.cpp
  lib/Driver/Tools.cpp
  tools/driver/driver.cpp

Index: tools/driver/driver.cpp
===
--- tools/driver/driver.cpp
+++ tools/driver/driver.cpp
@@ -50,6 +50,11 @@
 #include "llvm/Support/raw_ostream.h"
 #include 
 #include 
+#include "llvm/Analysis/IterativeCompilation.h"
+#include "llvm/Support/Program.h"
+#include 
+#include 
+#include 
 using namespace clang;
 using namespace clang::driver;
 using namespace llvm::opt;
@@ -307,6 +312,80 @@
   return 1;
 }
 
+void initControlFiles(llvm::ModuleDecisionTrees &MDT, int CurrentIteration)
+{
+  std::string ICResultsFile;
+  std::string ICResultsFile2;
+
+  // assign control files
+  llvm::ICResultsFile results1("ic-results", CurrentIteration);
+  llvm::ICResultsFile results2("ic-results2", CurrentIteration);
+  MDT.getICResultsFile() = results1;
+  MDT.getICResultsFile2() = results2;
+
+  llvm::ICInputFile input1("ic-input", CurrentIteration);
+  llvm::ICInputFile input2("ic-input2", CurrentIteration);
+  MDT.getICInputFile() = input1;
+  MDT.getICInputFile2() = input2;
+}
+
+void writeInputFiles(llvm::ModuleDecisionTrees &MDT)
+{
+  // inits and declarations
+  llvm::ICPathsMap paths;
+  llvm::ICPathsMap pathBeforeCodegen;
+  llvm::ICPathsMap pathAfterCodegen;
+
+  // split paths
+  MDT.getPaths(paths);
+  MDT.splitPaths(paths, pathBeforeCodegen, pathAfterCodegen);
+
+  // convert paths to strings and write them to files
+  llvm::ICInputFile input1 = MDT.getICInputFile();
+  llvm::ICInputFile input2 = MDT.getICInputFile2();
+
+  input1.setPaths(pathBeforeCodegen);
+  input2.setPaths(pathAfterCodegen);
+
+  input1.write();
+  input2.write();
+}
+
+void removeControlFiles(llvm::ModuleDecisionTrees &MDT) {
+  MDT.getICResultsFile().remove();
+  MDT.getICResultsFile2().remove();
+}
+
+int loadResultFiles(llvm::ModuleDecisionTrees &MDT,
+std::vector &merged) {
+  llvm::ICResultsFile results1 = MDT.getICResultsFile();
+  llvm::ICResultsFile results2 = MDT.getICResultsFile2();
+
+  int r1 = results1.read();
+  int r2 = results2.read();
+
+  if(r1 || r2)
+return 1;
+
+  llvm::MdtResults::mergeMdtResults(merged,
+  results1.getResults(), results2.getResults());
+
+  return 0;
+}
+
+llvm::MdtResults* getModuleResults(std::vector &merged,
+   std::string name)
+{
+  llvm::MdtResults *moduleResults = NULL;
+
+  for(auto res : merged) {
+if (res.FunctionNameAndPhase.getName() == name)
+  moduleResults = new llvm::MdtResults(res);
+  }
+
+  return moduleResults;
+}
+
 int main(int argc_, const char **argv_) {
   llvm::sys::PrintStackTraceOnErrorSignal();
   llvm::PrettyStackTraceProgram X(argc_, argv_);
@@ -437,6 +516,34 @@
 Diags.takeClient(), std::move(SerializedConsumer)));
   }
 
+  // Get number of iterations for iterative compilation.
+  // declare files and number of iterations
+  int ICNumberOfIterations = 0;
+
+  // extract number of iterations from cli args
+  std::unique_ptr CCopts(createDriverOptTable());
+  unsigned MissingArgIndex, MissingArgCount;
+  ArrayRef argv_ref(argv);
+  InputArgList Args = CCopts->ParseArgs(argv_ref.slice(1),
+MissingArgIndex, MissingArgCount);
+  if (Args.getLastArg(options::OPT_fiterative_comp_EQ)) {
+std::string Val = Args.getLastArgValue(options::OPT_fiterative_comp_EQ, "1");
+std::stringstream Convert(Val);
+Convert >> ICNumberOfIterations;
+   }
+  if (!ICNumberOfIterations)
+ICNumberOfIterations = 1; // Default value is 1.
+
+  std::string moduleName = llvm::getModuleName(argc_, argv_);
+
+  llvm::ModuleDecisionTrees moduleDecisionTrees(ICNumberOfIterations, true, moduleName);
+  int CurrentIteration = 0;
+  int Res = 0;
+
+  llvm::FnNameAndPhase::ICPhase CurrICPhase = llvm::FnNameAndPhase::ModulePhase;
+
+  // start of iterative compilation loop
+  for (; CurrentIteration < ICNumberOfIterations; CurrentIteration++) {
   ProcessWarningOptions(Diags, *DiagOpts, /*ReportDiags=*/false);
 
   Driver TheDriver(Path, llvm::sys::getDefaultTargetTriple(), Diags);
@@ -447,12 +554,34 @@
 
   SetBackdoorDriverOutputsFromEnvVars(TheDriver);
 
+  if (ICNumberOfIterations > 1) {
+TheDriver.setModuleDecisionTrees(&moduleDecisionTrees);
+
+initControlFiles(moduleDecisionTrees, CurrentIteration);
+writeInputFiles(moduleDecisionTrees);
+
+moduleDecisionTrees.startNewIteration();
+  }
+
   std::unique_ptr C(TheDriver.BuildCompilation(argv));
   int Res = 0;
   SmallVector, 4> FailingCommands;
   if (C.get())
 Res = TheDriver.ExecuteCompilation(*C, FailingCommands);
 
+  if (ICNumberOfIteration

Re: [PATCH] D12200: Add framework for iterative compilation to clang

2015-12-30 Thread Zoran Jovanovic via cfe-commits
zoran.jovanovic updated this revision to Diff 43793.
zoran.jovanovic added a comment.

New patch version that corresponds to latest version of: 
http://reviews.llvm.org/D12199


http://reviews.llvm.org/D12200

Files:
  include/clang/Driver/Compilation.h
  include/clang/Driver/Driver.h
  include/clang/Driver/Options.td
  lib/CodeGen/BackendUtil.cpp
  lib/Driver/Driver.cpp
  lib/Driver/Tools.cpp
  tools/driver/driver.cpp

Index: tools/driver/driver.cpp
===
--- tools/driver/driver.cpp
+++ tools/driver/driver.cpp
@@ -50,6 +50,11 @@
 #include "llvm/Support/raw_ostream.h"
 #include 
 #include 
+#include "llvm/Analysis/IterativeCompilation.h"
+#include "llvm/Support/Program.h"
+#include 
+#include 
+#include 
 using namespace clang;
 using namespace clang::driver;
 using namespace llvm::opt;
@@ -307,6 +312,80 @@
   return 1;
 }
 
+void initControlFiles(llvm::ModuleDecisionTrees &MDT, int CurrentIteration)
+{
+  std::string ICResultsFile;
+  std::string ICResultsFile2;
+
+  // assign control files
+  llvm::ICResultsFile results1("ic-results", CurrentIteration);
+  llvm::ICResultsFile results2("ic-results2", CurrentIteration);
+  MDT.getICResultsFile() = results1;
+  MDT.getICResultsFile2() = results2;
+
+  llvm::ICInputFile input1("ic-input", CurrentIteration);
+  llvm::ICInputFile input2("ic-input2", CurrentIteration);
+  MDT.getICInputFile() = input1;
+  MDT.getICInputFile2() = input2;
+}
+
+void writeInputFiles(llvm::ModuleDecisionTrees &MDT)
+{
+  // inits and declarations
+  llvm::ICPathsMap paths;
+  llvm::ICPathsMap pathBeforeCodegen;
+  llvm::ICPathsMap pathAfterCodegen;
+
+  // split paths
+  MDT.getPaths(paths);
+  MDT.splitPaths(paths, pathBeforeCodegen, pathAfterCodegen);
+
+  // convert paths to strings and write them to files
+  llvm::ICInputFile input1 = MDT.getICInputFile();
+  llvm::ICInputFile input2 = MDT.getICInputFile2();
+
+  input1.setPaths(pathBeforeCodegen);
+  input2.setPaths(pathAfterCodegen);
+
+  input1.write();
+  input2.write();
+}
+
+void removeControlFiles(llvm::ModuleDecisionTrees &MDT) {
+  MDT.getICResultsFile().remove();
+  MDT.getICResultsFile2().remove();
+}
+
+int loadResultFiles(llvm::ModuleDecisionTrees &MDT,
+std::vector &merged) {
+  llvm::ICResultsFile results1 = MDT.getICResultsFile();
+  llvm::ICResultsFile results2 = MDT.getICResultsFile2();
+
+  int r1 = results1.read();
+  int r2 = results2.read();
+
+  if(r1 || r2)
+return 1;
+
+  llvm::MdtResults::mergeMdtResults(merged,
+  results1.getResults(), results2.getResults());
+
+  return 0;
+}
+
+llvm::MdtResults* getModuleResults(std::vector &merged,
+   std::string name)
+{
+  llvm::MdtResults *moduleResults = NULL;
+
+  for(auto res : merged) {
+if (res.FunctionNameAndPhase.getName() == name)
+  moduleResults = new llvm::MdtResults(res);
+  }
+
+  return moduleResults;
+}
+
 int main(int argc_, const char **argv_) {
   llvm::sys::PrintStackTraceOnErrorSignal();
   llvm::PrettyStackTraceProgram X(argc_, argv_);
@@ -429,6 +508,34 @@
 Diags.takeClient(), std::move(SerializedConsumer)));
   }
 
+  // Get number of iterations for iterative compilation.
+  // declare files and number of iterations
+  int ICNumberOfIterations = 0;
+
+  // extract number of iterations from cli args
+  std::unique_ptr CCopts(createDriverOptTable());
+  unsigned MissingArgIndex, MissingArgCount;
+  ArrayRef argv_ref(argv);
+  InputArgList Args = CCopts->ParseArgs(argv_ref.slice(1),
+MissingArgIndex, MissingArgCount);
+  if (Args.getLastArg(options::OPT_fiterative_comp_EQ)) {
+std::string Val = Args.getLastArgValue(options::OPT_fiterative_comp_EQ, "1");
+std::stringstream Convert(Val);
+Convert >> ICNumberOfIterations;
+   }
+  if (!ICNumberOfIterations)
+ICNumberOfIterations = 1; // Default value is 1.
+
+  std::string moduleName = llvm::getModuleName(argc_, argv_);
+
+  llvm::ModuleDecisionTrees moduleDecisionTrees(ICNumberOfIterations, true, moduleName);
+  int CurrentIteration = 0;
+  int Res = 0;
+
+  llvm::FnNameAndPhase::ICPhase CurrICPhase = llvm::FnNameAndPhase::ModulePhase;
+
+  // start of iterative compilation loop
+  for (; CurrentIteration < ICNumberOfIterations; CurrentIteration++) {
   ProcessWarningOptions(Diags, *DiagOpts, /*ReportDiags=*/false);
 
   Driver TheDriver(Path, llvm::sys::getDefaultTargetTriple(), Diags);
@@ -439,12 +546,34 @@
 
   SetBackdoorDriverOutputsFromEnvVars(TheDriver);
 
+  if (ICNumberOfIterations > 1) {
+TheDriver.setModuleDecisionTrees(&moduleDecisionTrees);
+
+initControlFiles(moduleDecisionTrees, CurrentIteration);
+writeInputFiles(moduleDecisionTrees);
+
+moduleDecisionTrees.startNewIteration();
+  }
+
   std::unique_ptr C(TheDriver.BuildCompilation(argv));
   int Res = 0;
   SmallVector, 4> FailingCommands;
   if (C.get())
 Res = TheDriver.ExecuteCompilation(*C, FailingCommands);
 
+