[llvm] 2b70beb - [MachineFunctionPass] Support -print-changed={,c}diff{,-quiet}

Fangrui Song via llvm-commits llvm-commits at lists.llvm.org
Mon Aug 1 12:56:26 PDT 2022


Author: Fangrui Song
Date: 2022-08-01T12:56:15-07:00
New Revision: 2b70bebc6d7b9d452a032ca48a59a2e72a4934f8

URL: https://github.com/llvm/llvm-project/commit/2b70bebc6d7b9d452a032ca48a59a2e72a4934f8
DIFF: https://github.com/llvm/llvm-project/commit/2b70bebc6d7b9d452a032ca48a59a2e72a4934f8.diff

LOG: [MachineFunctionPass] Support -print-changed={,c}diff{,-quiet}

Follow-up to D130434.
Move doSystemDiff to PrintPasses.cpp and call it in MachineFunctionPass.cpp.

Reviewed By: aeubanks

Differential Revision: https://reviews.llvm.org/D130833

Added: 
    llvm/test/Other/ChangePrinters/print-changed-diff-machine.ll

Modified: 
    llvm/include/llvm/IR/PrintPasses.h
    llvm/lib/CodeGen/MachineFunctionPass.cpp
    llvm/lib/IR/PrintPasses.cpp
    llvm/lib/Passes/StandardInstrumentations.cpp
    llvm/test/Other/print-changed-machine.ll

Removed: 
    


################################################################################
diff  --git a/llvm/include/llvm/IR/PrintPasses.h b/llvm/include/llvm/IR/PrintPasses.h
index e721db9993412..599820a1e3ef4 100644
--- a/llvm/include/llvm/IR/PrintPasses.h
+++ b/llvm/include/llvm/IR/PrintPasses.h
@@ -54,6 +54,14 @@ bool forcePrintModuleIR();
 // Returns true if we should print the function.
 bool isFunctionInPrintList(StringRef FunctionName);
 
+// Perform a system based 
diff  between \p Before and \p After, using \p
+// OldLineFormat, \p NewLineFormat, and \p UnchangedLineFormat to control the
+// formatting of the output. Return an error message for any failures instead
+// of the 
diff .
+std::string doSystemDiff(StringRef Before, StringRef After,
+                         StringRef OldLineFormat, StringRef NewLineFormat,
+                         StringRef UnchangedLineFormat);
+
 } // namespace llvm
 
 #endif // LLVM_IR_PRINTPASSES_H

diff  --git a/llvm/lib/CodeGen/MachineFunctionPass.cpp b/llvm/lib/CodeGen/MachineFunctionPass.cpp
index 477310f591122..c6f7393338e8e 100644
--- a/llvm/lib/CodeGen/MachineFunctionPass.cpp
+++ b/llvm/lib/CodeGen/MachineFunctionPass.cpp
@@ -120,8 +120,34 @@ bool MachineFunctionPass::runOnFunction(Function &F) {
       if (const PassInfo *PI = Pass::lookupPassInfo(getPassID()))
         Arg = PI->getPassArgument();
       errs() << ("*** IR Dump After " + getPassName() + " (" + Arg + ") on " +
-                 MF.getName() + " ***\n" + AfterStr);
-    } else if (PrintChanged == ChangePrinter::Verbose) {
+                 MF.getName() + " ***\n");
+      switch (PrintChanged) {
+      case ChangePrinter::None:
+        llvm_unreachable("");
+      case ChangePrinter::Quiet:
+      case ChangePrinter::Verbose:
+      case ChangePrinter::DotCfgQuiet:   // unimplemented
+      case ChangePrinter::DotCfgVerbose: // unimplemented
+        errs() << AfterStr;
+        break;
+      case ChangePrinter::DiffQuiet:
+      case ChangePrinter::DiffVerbose:
+      case ChangePrinter::ColourDiffQuiet:
+      case ChangePrinter::ColourDiffVerbose: {
+        bool Color = llvm::is_contained(
+            {ChangePrinter::ColourDiffQuiet, ChangePrinter::ColourDiffVerbose},
+            PrintChanged.getValue());
+        StringRef Removed = Color ? "\033[31m-%l\033[0m\n" : "-%l\n";
+        StringRef Added = Color ? "\033[32m+%l\033[0m\n" : "+%l\n";
+        StringRef NoChange = " %l\n";
+        errs() << doSystemDiff(BeforeStr, AfterStr, Removed, Added, NoChange);
+        break;
+      }
+      }
+    } else if (llvm::is_contained({ChangePrinter::Verbose,
+                                   ChangePrinter::DiffVerbose,
+                                   ChangePrinter::ColourDiffVerbose},
+                                  PrintChanged.getValue())) {
       errs() << ("*** IR Dump After " + getPassName() + " on " + MF.getName() +
                  " omitted because no change ***\n");
     }

diff  --git a/llvm/lib/IR/PrintPasses.cpp b/llvm/lib/IR/PrintPasses.cpp
index fe2da5ca114f2..e7ecd7e3972fd 100644
--- a/llvm/lib/IR/PrintPasses.cpp
+++ b/llvm/lib/IR/PrintPasses.cpp
@@ -8,6 +8,9 @@
 
 #include "llvm/IR/PrintPasses.h"
 #include "llvm/Support/CommandLine.h"
+#include "llvm/Support/FileSystem.h"
+#include "llvm/Support/MemoryBuffer.h"
+#include "llvm/Support/Program.h"
 #include <unordered_set>
 
 using namespace llvm;
@@ -73,6 +76,11 @@ cl::opt<ChangePrinter> llvm::PrintChanged(
         // Sentinel value for unspecified option.
         clEnumValN(ChangePrinter::Verbose, "", "")));
 
+// An option for specifying the 
diff  used by print-changed=[
diff  | 
diff -quiet]
+static cl::opt<std::string>
+    DiffBinary("print-changed-
diff -path", cl::Hidden, cl::init("
diff "),
+               cl::desc("system 
diff  used by change reporters"));
+
 static cl::opt<bool>
     PrintModuleScope("print-module-scope",
                      cl::desc("When printing IR for print-[before|after]{-all} "
@@ -130,3 +138,66 @@ bool llvm::isFunctionInPrintList(StringRef FunctionName) {
   return PrintFuncNames.empty() ||
          PrintFuncNames.count(std::string(FunctionName));
 }
+
+std::string llvm::doSystemDiff(StringRef Before, StringRef After,
+                               StringRef OldLineFormat, StringRef NewLineFormat,
+                               StringRef UnchangedLineFormat) {
+  StringRef SR[2]{Before, After};
+  // Store the 2 bodies into temporary files and call 
diff  on them
+  // to get the body of the node.
+  const unsigned NumFiles = 3;
+  static std::string FileName[NumFiles];
+  static int FD[NumFiles]{-1, -1, -1};
+  for (unsigned I = 0; I < NumFiles; ++I) {
+    if (FD[I] == -1) {
+      SmallVector<char, 200> SV;
+      std::error_code EC =
+          sys::fs::createTemporaryFile("tmp
diff ", "txt", FD[I], SV);
+      if (EC)
+        return "Unable to create temporary file.";
+      FileName[I] = Twine(SV).str();
+    }
+    // The third file is used as the result of the 
diff .
+    if (I == NumFiles - 1)
+      break;
+
+    std::error_code EC = sys::fs::openFileForWrite(FileName[I], FD[I]);
+    if (EC)
+      return "Unable to open temporary file for writing.";
+
+    raw_fd_ostream OutStream(FD[I], /*shouldClose=*/true);
+    if (FD[I] == -1)
+      return "Error opening file for writing.";
+    OutStream << SR[I];
+  }
+
+  static ErrorOr<std::string> DiffExe = sys::findProgramByName(DiffBinary);
+  if (!DiffExe)
+    return "Unable to find 
diff  executable.";
+
+  SmallString<128> OLF, NLF, ULF;
+  ("--old-line-format=" + OldLineFormat).toVector(OLF);
+  ("--new-line-format=" + NewLineFormat).toVector(NLF);
+  ("--unchanged-line-format=" + UnchangedLineFormat).toVector(ULF);
+
+  StringRef Args[] = {DiffBinary, "-w", "-d",        OLF,
+                      NLF,        ULF,  FileName[0], FileName[1]};
+  Optional<StringRef> Redirects[] = {None, StringRef(FileName[2]), None};
+  int Result = sys::ExecuteAndWait(*DiffExe, Args, None, Redirects);
+  if (Result < 0)
+    return "Error executing system 
diff .";
+  std::string Diff;
+  auto B = MemoryBuffer::getFile(FileName[2]);
+  if (B && *B)
+    Diff = (*B)->getBuffer().str();
+  else
+    return "Unable to read result.";
+
+  // Clean up.
+  for (const std::string &I : FileName) {
+    std::error_code EC = sys::fs::remove(I);
+    if (EC)
+      return "Unable to remove temporary file.";
+  }
+  return Diff;
+}

diff  --git a/llvm/lib/Passes/StandardInstrumentations.cpp b/llvm/lib/Passes/StandardInstrumentations.cpp
index a0c63fb33369e..e6dab5f09a452 100644
--- a/llvm/lib/Passes/StandardInstrumentations.cpp
+++ b/llvm/lib/Passes/StandardInstrumentations.cpp
@@ -69,11 +69,6 @@ static cl::opt<bool>
                        cl::desc("Print before passes that change them"),
                        cl::init(false), cl::Hidden);
 
-// An option for specifying the 
diff  used by print-changed=[
diff  | 
diff -quiet]
-static cl::opt<std::string>
-    DiffBinary("print-changed-
diff -path", cl::Hidden, cl::init("
diff "),
-               cl::desc("system 
diff  used by change reporters"));
-
 // An option for specifying the dot used by
 // print-changed=[dot-cfg | dot-cfg-quiet]
 static cl::opt<std::string>
@@ -116,73 +111,6 @@ static cl::opt<bool>
 
 namespace {
 
-// Perform a system based 
diff  between \p Before and \p After, using
-// \p OldLineFormat, \p NewLineFormat, and \p UnchangedLineFormat
-// to control the formatting of the output.  Return an error message
-// for any failures instead of the 
diff .
-std::string doSystemDiff(StringRef Before, StringRef After,
-                         StringRef OldLineFormat, StringRef NewLineFormat,
-                         StringRef UnchangedLineFormat) {
-  StringRef SR[2]{Before, After};
-  // Store the 2 bodies into temporary files and call 
diff  on them
-  // to get the body of the node.
-  const unsigned NumFiles = 3;
-  static std::string FileName[NumFiles];
-  static int FD[NumFiles]{-1, -1, -1};
-  for (unsigned I = 0; I < NumFiles; ++I) {
-    if (FD[I] == -1) {
-      SmallVector<char, 200> SV;
-      std::error_code EC =
-          sys::fs::createTemporaryFile("tmp
diff ", "txt", FD[I], SV);
-      if (EC)
-        return "Unable to create temporary file.";
-      FileName[I] = Twine(SV).str();
-    }
-    // The third file is used as the result of the 
diff .
-    if (I == NumFiles - 1)
-      break;
-
-    std::error_code EC = sys::fs::openFileForWrite(FileName[I], FD[I]);
-    if (EC)
-      return "Unable to open temporary file for writing.";
-
-    raw_fd_ostream OutStream(FD[I], /*shouldClose=*/true);
-    if (FD[I] == -1)
-      return "Error opening file for writing.";
-    OutStream << SR[I];
-  }
-
-  static ErrorOr<std::string> DiffExe = sys::findProgramByName(DiffBinary);
-  if (!DiffExe)
-    return "Unable to find 
diff  executable.";
-
-  SmallString<128> OLF = formatv("--old-line-format={0}", OldLineFormat);
-  SmallString<128> NLF = formatv("--new-line-format={0}", NewLineFormat);
-  SmallString<128> ULF =
-      formatv("--unchanged-line-format={0}", UnchangedLineFormat);
-
-  StringRef Args[] = {DiffBinary, "-w", "-d",        OLF,
-                      NLF,        ULF,  FileName[0], FileName[1]};
-  Optional<StringRef> Redirects[] = {None, StringRef(FileName[2]), None};
-  int Result = sys::ExecuteAndWait(*DiffExe, Args, None, Redirects);
-  if (Result < 0)
-    return "Error executing system 
diff .";
-  std::string Diff;
-  auto B = MemoryBuffer::getFile(FileName[2]);
-  if (B && *B)
-    Diff = (*B)->getBuffer().str();
-  else
-    return "Unable to read result.";
-
-  // Clean up.
-  for (const std::string &I : FileName) {
-    std::error_code EC = sys::fs::remove(I);
-    if (EC)
-      return "Unable to remove temporary file.";
-  }
-  return Diff;
-}
-
 /// Extract Module out of \p IR unit. May return nullptr if \p IR does not match
 /// certain global filters. Will never return nullptr if \p Force is true.
 const Module *unwrapModule(Any IR, bool Force = false) {

diff  --git a/llvm/test/Other/ChangePrinters/print-changed-
diff -machine.ll b/llvm/test/Other/ChangePrinters/print-changed-
diff -machine.ll
new file mode 100644
index 0000000000000..3a4e3ef7ba9b5
--- /dev/null
+++ b/llvm/test/Other/ChangePrinters/print-changed-
diff -machine.ll
@@ -0,0 +1,33 @@
+; REQUIRES: aarch64-registered-target
+; RUN: llc -filetype=null -mtriple=aarch64 -O0 -print-changed=
diff  %s 2>&1 | FileCheck %s --check-prefixes=DIFF,VERBOSE
+; RUN: llc -filetype=null -mtriple=aarch64 -O0 -print-changed=
diff -quiet %s 2>&1 | FileCheck %s --check-prefixes=DIFF,QUIET
+; RUN: llc -filetype=null -mtriple=aarch64 -O0 -print-changed=c
diff  %s 2>&1 | FileCheck %s --check-prefixes=CDIFF,VERBOSE
+; RUN: llc -filetype=null -mtriple=aarch64 -O0 -print-changed=c
diff -quiet %s 2>&1 | FileCheck %s --check-prefixes=CDIFF,QUIET
+
+; VERBOSE:    *** IR Dump After AArch64O0PreLegalizerCombiner on foo omitted because no change ***
+; QUIET-NOT:  *** {{.*}} omitted because no change ***
+
+; DIFF:      *** IR Dump After Legalizer (legalizer) on foo ***
+; DIFF-NEXT: -# Machine code for function foo: IsSSA, TracksLiveness
+; DIFF-NEXT: +# Machine code for function foo: IsSSA, TracksLiveness, Legalized
+; DIFF-NEXT:  Function Live Ins: $w0
+
+; CDIFF:      *** IR Dump After Legalizer (legalizer) on foo ***
+; CDIFF-NEXT: {{.\[31m-}}# Machine code for function foo: IsSSA, TracksLiveness{{.\[0m}}
+; CDIFF-NEXT: {{.\[32m\+}}# Machine code for function foo: IsSSA, TracksLiveness, Legalized{{.\[0m}}
+
+ at var = global i32 0
+
+define void @foo(i32 %a) {
+entry:
+  %b = add i32 %a, 1
+  store i32 %b, ptr @var
+  ret void
+}
+
+define void @bar(i32 %a) {
+entry:
+  %b = add i32 %a, 2
+  store i32 %b, ptr @var
+  ret void
+}

diff  --git a/llvm/test/Other/print-changed-machine.ll b/llvm/test/Other/print-changed-machine.ll
index cb6a8b397dfa9..bd6f334696ff6 100644
--- a/llvm/test/Other/print-changed-machine.ll
+++ b/llvm/test/Other/print-changed-machine.ll
@@ -24,8 +24,8 @@
 ; QUIET-NOT:     ***
 ; QUIET:         *** IR Dump After Legalizer (legalizer) on foo ***
 
-;; Other modes are unimplemented. Currently they behave like 'quiet'.
-; RUN: llc -filetype=null -mtriple=aarch64 -O0 -print-changed=
diff  %s 2>&1 | FileCheck %s --check-prefix=QUIET
+;; dot-cfg/dot-cfg-quiet are unimplemented. Currently they behave like 'quiet'.
+; RUN: llc -filetype=null -mtriple=aarch64 -O0 -print-changed=dot-cfg %s 2>&1 | FileCheck %s --check-prefix=QUIET
 
 @var = global i32 0
 


        


More information about the llvm-commits mailing list