<div dir="ltr"><div class="gmail_quote"><div dir="ltr">On Sat, Jan 9, 2016 at 1:18 AM Mike Aizatsky via llvm-commits <<a href="mailto:llvm-commits@lists.llvm.org">llvm-commits@lists.llvm.org</a>> wrote:<br></div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">Author: aizatsky<br>
Date: Fri Jan  8 18:14:35 2016<br>
New Revision: 257236<br>
<br>
URL: <a href="http://llvm.org/viewvc/llvm-project?rev=257236&view=rev" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project?rev=257236&view=rev</a><br>
Log:<br>
[llvm-symbolizer] -print-source-context-lines option to print source code around the line.<br>
<br>
Differential Revision: <a href="http://reviews.llvm.org/D15909" rel="noreferrer" target="_blank">http://reviews.llvm.org/D15909</a><br>
<br>
Added:<br>
    llvm/trunk/test/tools/llvm-symbolizer/print_context.c<br>
Modified:<br>
    llvm/trunk/include/llvm/DebugInfo/Symbolize/DIPrinter.h<br>
    llvm/trunk/lib/DebugInfo/Symbolize/DIPrinter.cpp<br>
    llvm/trunk/test/lit.cfg<br>
    llvm/trunk/tools/llvm-symbolizer/llvm-symbolizer.cpp<br>
<br>
Modified: llvm/trunk/include/llvm/DebugInfo/Symbolize/DIPrinter.h<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/DebugInfo/Symbolize/DIPrinter.h?rev=257236&r1=257235&r2=257236&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/include/llvm/DebugInfo/Symbolize/DIPrinter.h?rev=257236&r1=257235&r2=257236&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/include/llvm/DebugInfo/Symbolize/DIPrinter.h (original)<br>
+++ llvm/trunk/include/llvm/DebugInfo/Symbolize/DIPrinter.h Fri Jan  8 18:14:35 2016<br>
@@ -28,13 +28,16 @@ class DIPrinter {<br>
   raw_ostream &OS;<br>
   bool PrintFunctionNames;<br>
   bool PrintPretty;<br>
-  void printName(const DILineInfo &Info, bool Inlined);<br>
+  int PrintSourceContext;<br>
+<br>
+  void print(const DILineInfo &Info, bool Inlined);<br>
+  void printContext(std::string FileName, int64_t Line);<br>
<br>
 public:<br>
   DIPrinter(raw_ostream &OS, bool PrintFunctionNames = true,<br>
-            bool PrintPretty = false)<br>
+            bool PrintPretty = false, int PrintSourceContext = 0)<br>
       : OS(OS), PrintFunctionNames(PrintFunctionNames),<br>
-        PrintPretty(PrintPretty) {}<br>
+        PrintPretty(PrintPretty), PrintSourceContext(PrintSourceContext) {}<br>
<br>
   DIPrinter &operator<<(const DILineInfo &Info);<br>
   DIPrinter &operator<<(const DIInliningInfo &Info);<br>
<br>
Modified: llvm/trunk/lib/DebugInfo/Symbolize/DIPrinter.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/DebugInfo/Symbolize/DIPrinter.cpp?rev=257236&r1=257235&r2=257236&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/DebugInfo/Symbolize/DIPrinter.cpp?rev=257236&r1=257235&r2=257236&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/lib/DebugInfo/Symbolize/DIPrinter.cpp (original)<br>
+++ llvm/trunk/lib/DebugInfo/Symbolize/DIPrinter.cpp Fri Jan  8 18:14:35 2016<br>
@@ -15,6 +15,7 @@<br>
 #include "llvm/DebugInfo/Symbolize/DIPrinter.h"<br>
<br>
 #include "llvm/DebugInfo/DIContext.h"<br>
+#include "llvm/Support/LineIterator.h"<br>
<br>
 namespace llvm {<br>
 namespace symbolize {<br>
@@ -24,7 +25,36 @@ namespace symbolize {<br>
 static const char kDILineInfoBadString[] = "<invalid>";<br>
 static const char kBadString[] = "??";<br>
<br>
-void DIPrinter::printName(const DILineInfo &Info, bool Inlined) {<br>
+// Prints source code around in the FileName the Line.<br>
+void DIPrinter::printContext(std::string FileName, int64_t Line) {<br>
+  if (PrintSourceContext <= 0)<br>
+    return;<br>
+<br>
+  ErrorOr<std::unique_ptr<MemoryBuffer>> BufOrErr =<br>
+      MemoryBuffer::getFile(FileName);<br>
+  if (!BufOrErr)<br>
+    return;<br>
+<br>
+  std::unique_ptr<MemoryBuffer> Buf = std::move(BufOrErr.get());<br>
+  int64_t FirstLine = std::max(1l, Line - PrintSourceContext / 2);<br>
+  int64_t LastLine = FirstLine + PrintSourceContext;<br>
+  size_t MaxLineNumberWidth = std::ceil(std::log10(LastLine));<br>
+<br>
+  for (line_iterator I = line_iterator(*Buf, false);<br>
+       !I.is_at_eof() && I.line_number() <= LastLine; ++I) {<br>
+    int64_t L = I.line_number();<br>
+    if (L >= FirstLine && L <= LastLine) {<br>
+      OS << format_decimal(L, MaxLineNumberWidth);<br>
+      if (L == Line)<br>
+        OS << " >: ";<br>
+      else<br>
+        OS << "  : ";<br>
+      OS << *I << "\n";<br>
+    }<br>
+  }<br>
+}<br>
+<br>
+void DIPrinter::print(const DILineInfo &Info, bool Inlined) {<br>
   if (PrintFunctionNames) {<br>
     std::string FunctionName = Info.FunctionName;<br>
     if (FunctionName == kDILineInfoBadString)<br>
@@ -38,21 +68,22 @@ void DIPrinter::printName(const DILineIn<br>
   if (Filename == kDILineInfoBadString)<br>
     Filename = kBadString;<br>
   OS << Filename << ":" << Info.Line << ":" << Info.Column << "\n";<br>
+  printContext(Filename, Info.Line);<br>
 }<br>
<br>
 DIPrinter &DIPrinter::operator<<(const DILineInfo &Info) {<br>
-  printName(Info, false);<br>
+  print(Info, false);<br>
   return *this;<br>
 }<br>
<br>
 DIPrinter &DIPrinter::operator<<(const DIInliningInfo &Info) {<br>
   uint32_t FramesNum = Info.getNumberOfFrames();<br>
   if (FramesNum == 0) {<br>
-    printName(DILineInfo(), false);<br>
+    print(DILineInfo(), false);<br>
     return *this;<br>
   }<br>
   for (uint32_t i = 0; i < FramesNum; i++)<br>
-    printName(Info.getFrame(i), i > 0);<br>
+    print(Info.getFrame(i), i > 0);<br>
   return *this;<br>
 }<br>
<br>
<br>
Modified: llvm/trunk/test/lit.cfg<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/lit.cfg?rev=257236&r1=257235&r2=257236&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/lit.cfg?rev=257236&r1=257235&r2=257236&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/test/lit.cfg (original)<br>
+++ llvm/trunk/test/lit.cfg Fri Jan  8 18:14:35 2016<br>
@@ -194,6 +194,7 @@ config.substitutions.append( ('%llvmshli<br>
 config.substitutions.append( ('%shlibext', config.llvm_shlib_ext) )<br>
 config.substitutions.append( ('%exeext', config.llvm_exe_ext) )<br>
 config.substitutions.append( ('%python', config.python_executable) )<br>
+config.substitutions.append( ('%host_cc', config.host_cc) )<br>
<br>
 # OCaml substitutions.<br>
 # Support tests for both native and bytecode builds.<br>
@@ -276,6 +277,7 @@ for pattern in [r"\bbugpoint\b(?!-)",<br>
                 r"\bllvm-split\b",<br>
                 r"\bllvm-tblgen\b",<br>
                 r"\bllvm-c-test\b",<br>
+                NOJUNK + r"\bllvm-symbolizer\b",<br>
                 NOJUNK + r"\bopt\b",<br>
                 r"\bFileCheck\b",<br>
                 r"\bobj2yaml\b",<br>
<br>
Added: llvm/trunk/test/tools/llvm-symbolizer/print_context.c<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-symbolizer/print_context.c?rev=257236&view=auto" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/test/tools/llvm-symbolizer/print_context.c?rev=257236&view=auto</a><br>
==============================================================================<br>
--- llvm/trunk/test/tools/llvm-symbolizer/print_context.c (added)<br>
+++ llvm/trunk/test/tools/llvm-symbolizer/print_context.c Fri Jan  8 18:14:35 2016<br>
@@ -0,0 +1,22 @@<br>
+// REQUIRES: x86_64-linux<br>
+// RUN: %host_cc -O0 -g %s -o %t 2>&1<br></blockquote><div><br></div><div>It seems brittle to have tests depend on the host compiler.</div><div><br></div><div>Benjamin apparently has ideas for alternatives.</div><div> </div><blockquote class="gmail_quote" style="margin:0 0 0 .8ex;border-left:1px #ccc solid;padding-left:1ex">
+// RUN: %t 2>&1 | llvm-symbolizer -print-source-context-lines=5 -obj=%t | FileCheck %s --check-prefix=CHECK<br>
+<br>
+#include <stdio.h><br>
+<br>
+int inc(int a) {<br>
+  return a + 1;<br>
+}<br>
+<br>
+int main() {<br>
+  printf("%p\n", inc);<br>
+  return 0;<br>
+}<br>
+<br>
+// CHECK: inc<br>
+// CHECK: print_context.c:7<br>
+// CHECK: 5  : #include<br>
+// CHECK: 6  :<br>
+// CHECK: 7 >: int inc<br>
+// CHECK: 8  :   return<br>
+// CHECK: 9  : }<br>
<br>
Modified: llvm/trunk/tools/llvm-symbolizer/llvm-symbolizer.cpp<br>
URL: <a href="http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-symbolizer/llvm-symbolizer.cpp?rev=257236&r1=257235&r2=257236&view=diff" rel="noreferrer" target="_blank">http://llvm.org/viewvc/llvm-project/llvm/trunk/tools/llvm-symbolizer/llvm-symbolizer.cpp?rev=257236&r1=257235&r2=257236&view=diff</a><br>
==============================================================================<br>
--- llvm/trunk/tools/llvm-symbolizer/llvm-symbolizer.cpp (original)<br>
+++ llvm/trunk/tools/llvm-symbolizer/llvm-symbolizer.cpp Fri Jan  8 18:14:35 2016<br>
@@ -82,6 +82,10 @@ static cl::opt<bool><br>
     ClPrettyPrint("pretty-print", cl::init(false),<br>
                   cl::desc("Make the output more human friendly"));<br>
<br>
+static cl::opt<int> ClPrintSourceContextLines(<br>
+    "print-source-context-lines", cl::init(0),<br>
+    cl::desc("Print N number of source file context"));<br>
+<br>
 static bool error(std::error_code ec) {<br>
   if (!ec)<br>
     return false;<br>
@@ -155,7 +159,7 @@ int main(int argc, char **argv) {<br>
   LLVMSymbolizer Symbolizer(Opts);<br>
<br>
   DIPrinter Printer(outs(), ClPrintFunctions != FunctionNameKind::None,<br>
-                    ClPrettyPrint);<br>
+                    ClPrettyPrint, ClPrintSourceContextLines);<br>
<br>
   const int kMaxInputStringLength = 1024;<br>
   char InputString[kMaxInputStringLength];<br>
<br>
<br>
_______________________________________________<br>
llvm-commits mailing list<br>
<a href="mailto:llvm-commits@lists.llvm.org" target="_blank">llvm-commits@lists.llvm.org</a><br>
<a href="http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits" rel="noreferrer" target="_blank">http://lists.llvm.org/cgi-bin/mailman/listinfo/llvm-commits</a><br>
</blockquote></div></div>