about summary refs log tree commit diff
path: root/src
diff options
context:
space:
mode:
authorEelco Dolstra <eelco.dolstra@logicblox.com>2014-08-20T12·17+0200
committerEelco Dolstra <eelco.dolstra@logicblox.com>2014-08-20T12·30+0200
commit954188af2747e796eb4428c493db9aa06ed1af38 (patch)
treec421e1baee854809f89146d45ace2f04b176ef4e /src
parent029424d17d0860e4423bbd409f22104f55ea65e0 (diff)
Filter Nix-specific ANSI escape sequences from stderr
The Nixpkgs stdenv prints some custom escape sequences to denote
nesting and stuff like that. Most terminals (e.g. xterm, konsole)
ignore them, but some do not (e.g. xfce4-terminal). So for the benefit
of the latter, filter them out.
Diffstat (limited to 'src')
-rw-r--r--src/libstore/build.cc38
1 files changed, 37 insertions, 1 deletions
diff --git a/src/libstore/build.cc b/src/libstore/build.cc
index aa539a1fa42b..ef0a304dea3b 100644
--- a/src/libstore/build.cc
+++ b/src/libstore/build.cc
@@ -2441,6 +2441,42 @@ void DerivationGoal::deleteTmpDir(bool force)
 }
 
 
+/* Filter out the special ANSI escape codes generated by Nixpkgs'
+   stdenv (used to denote nesting etc.). */
+static string filterNixEscapes(const string & s)
+{
+    string t, r;
+    enum { stTop, stEscape, stCSI } state = stTop;
+    for (auto c : s) {
+        if (state == stTop) {
+            if (c == '\e') {
+                state = stEscape;
+                r = c;
+            } else
+                t += c;
+        } else if (state == stEscape) {
+            r += c;
+            if (c == '[')
+                state = stCSI;
+            else {
+                t += r;
+                state = stTop;
+            }
+        } else {
+            r += c;
+            if (c >= 0x40 && c != 0x7e) {
+                if (c != 'p' && c != 'q' && c != 's' && c != 'a' && c != 'b')
+                    t += r;
+                state = stTop;
+                r.clear();
+            }
+        }
+    }
+    t += r;
+    return t;
+}
+
+
 void DerivationGoal::handleChildOutput(int fd, const string & data)
 {
     if ((hook && fd == hook->builderOut.readSide) ||
@@ -2455,7 +2491,7 @@ void DerivationGoal::handleChildOutput(int fd, const string & data)
             return;
         }
         if (verbosity >= settings.buildVerbosity)
-            writeToStderr(data);
+            writeToStderr(filterNixEscapes(data));
         if (bzLogFile) {
             int err;
             BZ2_bzWrite(&err, bzLogFile, (unsigned char *) data.data(), data.size());