about summary refs log tree commit diff
path: root/src/libutil/util.cc
diff options
context:
space:
mode:
Diffstat (limited to 'src/libutil/util.cc')
-rw-r--r--src/libutil/util.cc12
1 files changed, 9 insertions, 3 deletions
diff --git a/src/libutil/util.cc b/src/libutil/util.cc
index 0a5f796e4eaa..bc66b0c53223 100644
--- a/src/libutil/util.cc
+++ b/src/libutil/util.cc
@@ -870,11 +870,14 @@ string runProgram(Path program, bool searchPath, const Strings & args,
 
     out.writeSide = -1;
 
-    /* FIXME: This can deadlock if the input is too long. */
+    std::thread writerThread;
+
     if (!input.empty()) {
         in.readSide = -1;
-        writeFull(in.writeSide.get(), input);
-        in.writeSide = -1;
+        writerThread = std::thread([&]() {
+            writeFull(in.writeSide.get(), input);
+            in.writeSide = -1;
+        });
     }
 
     string result = drainFD(out.readSide.get());
@@ -885,6 +888,9 @@ string runProgram(Path program, bool searchPath, const Strings & args,
         throw ExecError(status, format("program ‘%1%’ %2%")
             % program % statusToString(status));
 
+    if (!input.empty())
+        writerThread.join();
+
     return result;
 }