Coverage Report

Created: 2024-09-19 09:45

/proc/self/cwd/source/server/admin/profiling_handler.cc
Line
Count
Source (jump to first uncovered line)
1
#include "source/server/admin/profiling_handler.h"
2
3
#include "source/common/profiler/profiler.h"
4
#include "source/server/admin/utils.h"
5
6
namespace Envoy {
7
namespace Server {
8
9
4.47k
ProfilingHandler::ProfilingHandler(const std::string& profile_path) : profile_path_(profile_path) {}
10
11
Http::Code ProfilingHandler::handlerCpuProfiler(Http::ResponseHeaderMap&,
12
                                                Buffer::Instance& response,
13
0
                                                AdminStream& admin_stream) {
14
0
  Http::Utility::QueryParamsMulti query_params = admin_stream.queryParams();
15
0
  const auto enableVal = query_params.getFirstValue("enable");
16
0
  if (query_params.data().size() != 1 || !enableVal.has_value() ||
17
0
      (enableVal.value() != "y" && enableVal.value() != "n")) {
18
0
    response.add("?enable=<y|n>\n");
19
0
    return Http::Code::BadRequest;
20
0
  }
21
22
0
  bool enable = enableVal.value() == "y";
23
0
  if (enable && !Profiler::Cpu::profilerEnabled()) {
24
0
    if (!Profiler::Cpu::startProfiler(profile_path_)) {
25
0
      response.add("failure to start the profiler");
26
0
      return Http::Code::InternalServerError;
27
0
    }
28
29
0
  } else if (!enable && Profiler::Cpu::profilerEnabled()) {
30
0
    Profiler::Cpu::stopProfiler();
31
0
  }
32
33
0
  response.add("OK\n");
34
0
  return Http::Code::OK;
35
0
}
36
37
Http::Code ProfilingHandler::handlerHeapProfiler(Http::ResponseHeaderMap&,
38
                                                 Buffer::Instance& response,
39
0
                                                 AdminStream& admin_stream) {
40
0
  if (!Profiler::Heap::profilerEnabled()) {
41
0
    response.add("The current build does not support heap profiler");
42
0
    return Http::Code::NotImplemented;
43
0
  }
44
45
0
  Http::Utility::QueryParamsMulti query_params = admin_stream.queryParams();
46
0
  const auto enableVal = query_params.getFirstValue("enable");
47
0
  if (query_params.data().size() != 1 || !enableVal.has_value() ||
48
0
      (enableVal.value() != "y" && enableVal.value() != "n")) {
49
0
    response.add("?enable=<y|n>\n");
50
0
    return Http::Code::BadRequest;
51
0
  }
52
53
0
  Http::Code res = Http::Code::OK;
54
0
  bool enable = enableVal.value() == "y";
55
0
  if (enable) {
56
0
    if (Profiler::Heap::isProfilerStarted()) {
57
0
      response.add("Fail to start heap profiler: already started");
58
0
      res = Http::Code::BadRequest;
59
0
    } else if (!Profiler::Heap::startProfiler(profile_path_)) {
60
0
      response.add("Fail to start the heap profiler");
61
0
      res = Http::Code::InternalServerError;
62
0
    } else {
63
0
      response.add("Starting heap profiler");
64
0
      res = Http::Code::OK;
65
0
    }
66
0
  } else {
67
    // !enable
68
0
    if (!Profiler::Heap::isProfilerStarted()) {
69
0
      response.add("Fail to stop heap profiler: not started");
70
0
      res = Http::Code::BadRequest;
71
0
    } else {
72
0
      Profiler::Heap::stopProfiler();
73
0
      response.add(
74
0
          fmt::format("Heap profiler stopped and data written to {}. See "
75
0
                      "http://goog-perftools.sourceforge.net/doc/heap_profiler.html for details.",
76
0
                      profile_path_));
77
0
      res = Http::Code::OK;
78
0
    }
79
0
  }
80
0
  return res;
81
0
}
82
83
Http::Code TcmallocProfilingHandler::handlerHeapDump(Http::ResponseHeaderMap&,
84
0
                                                     Buffer::Instance& response, AdminStream&) {
85
0
  auto dump_result = Profiler::TcmallocProfiler::tcmallocHeapProfile();
86
87
0
  if (dump_result.ok()) {
88
0
    response.add(dump_result.value());
89
0
    return Http::Code::OK;
90
0
  }
91
92
0
  response.add(dump_result.status().message());
93
0
  return Http::Code::NotImplemented;
94
0
}
95
96
} // namespace Server
97
} // namespace Envoy