GCC Code Coverage Report


ernie/
Coverage:
low: ≥ 0%
medium: ≥ 75.0%
high: ≥ 90.0%
Lines:
30 / 31
96.8%
Branches:
13 / 24
54.2%
Functions:
6 / 6
100.0%

util/log.cpp
Line Branch Exec Source
1 // SPDX-License-Identifier: BSD-3-Clause
2 /// @file log.cpp
3 /// @brief Verbosity and console messages.
4 #include "ernie/util/log.h"
5
6 #include <atomic>
7 #include <cstdio>
8 #include <cstdlib>
9 #include <mutex>
10
11 namespace ernie::log {
12
13 namespace {
14
15 /// -1 until first read from the environment.
16 std::atomic<int> level{-1};
17 std::mutex output;
18
19 2 bool Set(const char* variable) {
20 2 const char* value = std::getenv(variable);
21
1/6
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
2 return value != nullptr && *value != '\0' && std::string_view(value) != "0";
22 }
23
24 5 void Print(Verbosity at, std::string_view message) {
25
2/2
✓ Branch 1 taken 3 times.
✓ Branch 2 taken 2 times.
5 if (GetVerbosity() < at) {
26 3 return;
27 }
28 // Whole lines, from any thread.
29 2 const std::lock_guard lock(output);
30
1/2
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
2 std::fwrite(message.data(), 1, message.size(), stdout);
31
1/2
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
2 std::fputc('\n', stdout);
32
1/2
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
2 std::fflush(stdout);
33 2 }
34
35 } // namespace
36
37 6 Verbosity GetVerbosity() {
38
2/2
✓ Branch 0 taken 1 time.
✓ Branch 1 taken 5 times.
6 int current = level.load(std::memory_order_relaxed);
39
2/2
✓ Branch 0 taken 1 time.
✓ Branch 1 taken 5 times.
6 if (current < 0) {
40
1/2
✓ Branch 1 taken 1 time.
✗ Branch 2 not taken.
1 const Verbosity initial = Set("ERNIE_QUIET") ? Verbosity::Quiet
41
1/2
✓ Branch 1 taken 1 time.
✗ Branch 2 not taken.
1 : Set("ERNIE_VERBOSE") ? Verbosity::Verbose
42 1 : Verbosity::Normal;
43 1 current = static_cast<int>(initial);
44 1 int unset = -1;
45 // Unless set meanwhile.
46
1/2
✗ Branch 1 not taken.
✓ Branch 2 taken 1 time.
1 if (!level.compare_exchange_strong(unset, current)) {
47 ✗ current = unset;
48 }
49 }
50 6 return static_cast<Verbosity>(current);
51 }
52
53 4 void SetVerbosity(Verbosity verbosity) {
54 4 level.store(static_cast<int>(verbosity), std::memory_order_relaxed);
55 4 }
56
57 2 void Info(std::string_view message) {
58 2 Print(Verbosity::Normal, message);
59 2 }
60
61 3 void Detail(std::string_view message) {
62 3 Print(Verbosity::Verbose, message);
63 3 }
64
65 } // namespace ernie::log
66