Skip to content

Commit da0a7d5

Browse files
committed
Add support for the NO_COLOR environment variable
Clang currently supports disabling color diagnostic output via -fno-color-diagnostics. However, there is a somewhat long-standing push to support use of an environment variable to override color output so that users can set up their terminal such that most color output is disabled (largely for accessibility reasons). There are two competing de facto standards to accomplish this: NO_COLOR (https://no-color.org/) and CLICOLOR/CLICOLOR_FORCE (http://bixense.com/clicolors/). This patch adds support for NO_COLOR as that appears to be the more commonly supported feature, at least when comparing issues and pull requests: https://github.com/search?q=NO_COLOR&type=issues (2.2k issues, 35k pull requests) https://github.com/search?q=CLICOLOR&type=issues (1k issues, 3k pull requests) It's also the more straightforward and thoroughly-specified of the two options. If NO_COLOR is present as an environment variable (regardless of value), color output is suppressed unless the command line specifies use of color output (command line takes precedence over the environment variable). Differential Revision: https://reviews.llvm.org/D152285
1 parent 774b336 commit da0a7d5

File tree

4 files changed

+35
-1
lines changed

4 files changed

+35
-1
lines changed

clang/docs/ReleaseNotes.rst

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -222,6 +222,8 @@ Non-comprehensive list of changes in this release
222222
- Clang now support ``__builtin_FUNCSIG()`` which returns the same information
223223
as the ``__FUNCSIG__`` macro (available only with ``-fms-extensions`` flag).
224224
This fixes (`#58951 <https://github.com/llvm/llvm-project/issues/58951>`_).
225+
- Clang now supports the `NO_COLOR <https://no-color.org/>`_ environment
226+
variable as a way to disable color diagnostics.
225227

226228
New Compiler Flags
227229
------------------

clang/docs/UsersManual.rst

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -251,6 +251,11 @@ output format of the diagnostics that it generates.
251251
^
252252
//
253253

254+
If the ``NO_COLOR`` environment variable is defined and not empty
255+
(regardless of value), color diagnostics are disabled. If ``NO_COLOR`` is
256+
defined and ``-fcolor-diagnostics`` is passed on the command line, Clang
257+
will honor the command line argument.
258+
254259
.. option:: -fansi-escape-codes
255260

256261
Controls whether ANSI escape codes are used instead of the Windows Console

clang/lib/Frontend/CompilerInvocation.cpp

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2341,10 +2341,20 @@ clang::CreateAndPopulateDiagOpts(ArrayRef<const char *> Argv) {
23412341
unsigned MissingArgIndex, MissingArgCount;
23422342
InputArgList Args = getDriverOptTable().ParseArgs(
23432343
Argv.slice(1), MissingArgIndex, MissingArgCount);
2344+
2345+
bool ShowColors = true;
2346+
if (std::optional<std::string> NoColor =
2347+
llvm::sys::Process::GetEnv("NO_COLOR");
2348+
NoColor && !NoColor->empty()) {
2349+
// If the user set the NO_COLOR environment variable, we'll honor that
2350+
// unless the command line overrides it.
2351+
ShowColors = false;
2352+
}
2353+
23442354
// We ignore MissingArgCount and the return value of ParseDiagnosticArgs.
23452355
// Any errors that would be diagnosed here will also be diagnosed later,
23462356
// when the DiagnosticsEngine actually exists.
2347-
(void)ParseDiagnosticArgs(*DiagOpts, Args);
2357+
(void)ParseDiagnosticArgs(*DiagOpts, Args, /*Diags=*/nullptr, ShowColors);
23482358
return DiagOpts;
23492359
}
23502360

clang/test/Driver/no-color.c

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
// RUN: env NO_COLOR=1 %clang -### %s 2>&1 | FileCheck --check-prefix=NO-COLOR %s
2+
// RUN: env NO_COLOR=1 %clang -fcolor-diagnostics -### %s 2>&1 | FileCheck --check-prefix=COLOR %s
3+
// RUN: env NO_COLOR=1 %clang -fdiagnostics-color=auto -### %s 2>&1 | FileCheck --check-prefix=NO-COLOR %s
4+
// RUN: env NO_COLOR=1 %clang -fdiagnostics-color=always -### %s 2>&1 | FileCheck --check-prefix=COLOR %s
5+
// RUN: env NO_COLOR=1 %clang -fdiagnostics-color=never -### %s 2>&1 | FileCheck --check-prefix=NO-COLOR %s
6+
7+
// Note, the value of the environment variable does not matter, only that it is defined and not empty.
8+
// RUN: env NO_COLOR=0 %clang -### %s 2>&1 | FileCheck --check-prefix=NO-COLOR %s
9+
// Note, an empty value means we automatically decide whether to enable colors or not, and lit tests
10+
// are not run in a PTY, so colors are disabled by default. There is no easy way for us to test this
11+
// configuration where auto enables colors.
12+
// RUN: env NO_COLOR= %clang -### %s 2>&1 | FileCheck --check-prefix=NO-COLOR %s
13+
14+
int main(void) {}
15+
16+
// COLOR: -fcolor-diagnostics
17+
// NO-COLOR-NOT: -fcolor-diagnostics

0 commit comments

Comments
 (0)