[PATCH] D62371: [llvm-symbolizer] Flush output on bad input

James Henderson via Phabricator via llvm-commits llvm-commits at lists.llvm.org
Tue Jun 4 07:31:45 PDT 2019


jhenderson updated this revision to Diff 202937.
jhenderson added a comment.

Switch to using os._exit() instead of sys.exit(). This terminates the process even from the subthread. There's no need to do any cleanup etc, so this should be sufficient for our test.

(I originally was going to put a try/except block around the stdin/stdout reading/writing blocks, but on second thoughts, I don't think that's necessary).


Repository:
  rL LLVM

CHANGES SINCE LAST ACTION
  https://reviews.llvm.org/D62371/new/

https://reviews.llvm.org/D62371

Files:
  test/tools/llvm-symbolizer/Inputs/flush-output.py
  test/tools/llvm-symbolizer/flush-output.s
  tools/llvm-symbolizer/llvm-symbolizer.cpp


Index: tools/llvm-symbolizer/llvm-symbolizer.cpp
===================================================================
--- tools/llvm-symbolizer/llvm-symbolizer.cpp
+++ tools/llvm-symbolizer/llvm-symbolizer.cpp
@@ -246,7 +246,6 @@
   }
   if (ClOutputStyle == DIPrinter::OutputStyle::LLVM)
     outs() << "\n";
-  outs().flush();
 }
 
 int main(int argc, char **argv) {
@@ -291,8 +290,10 @@
     const int kMaxInputStringLength = 1024;
     char InputString[kMaxInputStringLength];
 
-    while (fgets(InputString, sizeof(InputString), stdin))
+    while (fgets(InputString, sizeof(InputString), stdin)) {
       symbolizeInput(InputString, Symbolizer, Printer);
+      outs().flush();
+    }
   } else {
     for (StringRef Address : ClInputAddresses)
       symbolizeInput(Address, Symbolizer, Printer);
Index: test/tools/llvm-symbolizer/flush-output.s
===================================================================
--- test/tools/llvm-symbolizer/flush-output.s
+++ test/tools/llvm-symbolizer/flush-output.s
@@ -0,0 +1,16 @@
+# REQUIRES: x86-registered-target
+
+## If a process spawns llvm-symbolizer, and wishes to feed it addresses one at a
+## time, llvm-symbolizer needs to flush its output after each input has been
+## processed or the parent process will not be able to read the output and may
+## deadlock. This test runs a script that simulates this situation for both a
+## a good and bad input.
+
+foo:
+    nop
+
+# RUN: llvm-mc -filetype=obj -triple=x86_64-pc-linux %s -o %t.o -g
+# RUN: %python %p/Inputs/flush-output.py llvm-symbolizer %t.o 
+
+# CHECK: flush-output.s:10
+# CHECK: bad
Index: test/tools/llvm-symbolizer/Inputs/flush-output.py
===================================================================
--- test/tools/llvm-symbolizer/Inputs/flush-output.py
+++ test/tools/llvm-symbolizer/Inputs/flush-output.py
@@ -0,0 +1,24 @@
+from __future__ import print_function
+import os
+import subprocess
+import sys
+import threading
+
+def kill_subprocess(process):
+    process.kill()
+    os._exit(1)
+
+# Pass -f=none and --output-style=GNU to get only one line of output per input.
+cmd = subprocess.Popen([sys.argv[1],
+                        '--obj=' + sys.argv[2],
+                        '-f=none',
+                        '--output-style=GNU'], stdout=subprocess.PIPE, stdin=subprocess.PIPE)
+watchdog = threading.Timer(2, kill_subprocess, args=[cmd])
+watchdog.start()
+cmd.stdin.write(b'0\n')
+cmd.stdin.flush()
+print(cmd.stdout.readline())
+cmd.stdin.write(b'bad\n')
+cmd.stdin.flush()
+print(cmd.stdout.readline())
+watchdog.cancel()


-------------- next part --------------
A non-text attachment was scrubbed...
Name: D62371.202937.patch
Type: text/x-patch
Size: 2574 bytes
Desc: not available
URL: <http://lists.llvm.org/pipermail/llvm-commits/attachments/20190604/68009e70/attachment.bin>


More information about the llvm-commits mailing list