3 * Copyright 2015 gRPC authors.
5 * Licensed under the Apache License, Version 2.0 (the "License");
6 * you may not use this file except in compliance with the License.
7 * You may obtain a copy of the License at
9 * http://www.apache.org/licenses/LICENSE-2.0
11 * Unless required by applicable law or agreed to in writing, software
12 * distributed under the License is distributed on an "AS IS" BASIS,
13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14 * See the License for the specific language governing permissions and
15 * limitations under the License.
19 /* This benchmark exists to ensure that the benchmark integration is
22 #include <benchmark/benchmark.h>
23 #include <grpc/grpc.h>
24 #include <grpc/support/log.h>
25 #include <grpcpp/completion_queue.h>
26 #include <grpcpp/impl/grpc_library.h>
27 #include "test/cpp/microbenchmarks/helpers.h"
28 #include "test/cpp/util/test_config.h"
30 #include "src/core/lib/surface/completion_queue.h"
35 static void BM_CreateDestroyCpp(benchmark::State& state) {
36 TrackCounters track_counters;
37 while (state.KeepRunning()) {
40 track_counters.Finish(state);
42 BENCHMARK(BM_CreateDestroyCpp);
44 /* Create cq using a different constructor */
45 static void BM_CreateDestroyCpp2(benchmark::State& state) {
46 TrackCounters track_counters;
47 while (state.KeepRunning()) {
48 grpc_completion_queue* core_cq =
49 grpc_completion_queue_create_for_next(nullptr);
50 CompletionQueue cq(core_cq);
52 track_counters.Finish(state);
54 BENCHMARK(BM_CreateDestroyCpp2);
56 static void BM_CreateDestroyCore(benchmark::State& state) {
57 TrackCounters track_counters;
58 while (state.KeepRunning()) {
59 // TODO: sreek Templatize this benchmark and pass completion type and
60 // polling type as parameters
61 grpc_completion_queue_destroy(
62 grpc_completion_queue_create_for_next(nullptr));
64 track_counters.Finish(state);
66 BENCHMARK(BM_CreateDestroyCore);
68 static void DoneWithCompletionOnStack(void* arg,
69 grpc_cq_completion* completion) {}
71 class DummyTag final : public internal::CompletionQueueTag {
73 bool FinalizeResult(void** tag, bool* status) override { return true; }
76 static void BM_Pass1Cpp(benchmark::State& state) {
77 TrackCounters track_counters;
79 grpc_completion_queue* c_cq = cq.cq();
80 while (state.KeepRunning()) {
81 grpc_cq_completion completion;
83 grpc_core::ExecCtx exec_ctx;
84 GPR_ASSERT(grpc_cq_begin_op(c_cq, &dummy_tag));
85 grpc_cq_end_op(c_cq, &dummy_tag, GRPC_ERROR_NONE, DoneWithCompletionOnStack,
86 nullptr, &completion);
92 track_counters.Finish(state);
94 BENCHMARK(BM_Pass1Cpp);
96 static void BM_Pass1Core(benchmark::State& state) {
97 TrackCounters track_counters;
98 // TODO: sreek Templatize this benchmark and pass polling_type as a param
99 grpc_completion_queue* cq = grpc_completion_queue_create_for_next(nullptr);
100 gpr_timespec deadline = gpr_inf_future(GPR_CLOCK_MONOTONIC);
101 while (state.KeepRunning()) {
102 grpc_cq_completion completion;
103 grpc_core::ExecCtx exec_ctx;
104 GPR_ASSERT(grpc_cq_begin_op(cq, nullptr));
105 grpc_cq_end_op(cq, nullptr, GRPC_ERROR_NONE, DoneWithCompletionOnStack,
106 nullptr, &completion);
108 grpc_completion_queue_next(cq, deadline, nullptr);
110 grpc_completion_queue_destroy(cq);
111 track_counters.Finish(state);
113 BENCHMARK(BM_Pass1Core);
115 static void BM_Pluck1Core(benchmark::State& state) {
116 TrackCounters track_counters;
117 // TODO: sreek Templatize this benchmark and pass polling_type as a param
118 grpc_completion_queue* cq = grpc_completion_queue_create_for_pluck(nullptr);
119 gpr_timespec deadline = gpr_inf_future(GPR_CLOCK_MONOTONIC);
120 while (state.KeepRunning()) {
121 grpc_cq_completion completion;
122 grpc_core::ExecCtx exec_ctx;
123 GPR_ASSERT(grpc_cq_begin_op(cq, nullptr));
124 grpc_cq_end_op(cq, nullptr, GRPC_ERROR_NONE, DoneWithCompletionOnStack,
125 nullptr, &completion);
127 grpc_completion_queue_pluck(cq, nullptr, deadline, nullptr);
129 grpc_completion_queue_destroy(cq);
130 track_counters.Finish(state);
132 BENCHMARK(BM_Pluck1Core);
134 static void BM_EmptyCore(benchmark::State& state) {
135 TrackCounters track_counters;
136 // TODO: sreek Templatize this benchmark and pass polling_type as a param
137 grpc_completion_queue* cq = grpc_completion_queue_create_for_next(nullptr);
138 gpr_timespec deadline = gpr_inf_past(GPR_CLOCK_MONOTONIC);
139 while (state.KeepRunning()) {
140 grpc_completion_queue_next(cq, deadline, nullptr);
142 grpc_completion_queue_destroy(cq);
143 track_counters.Finish(state);
145 BENCHMARK(BM_EmptyCore);
147 } // namespace testing
150 // Some distros have RunSpecifiedBenchmarks under the benchmark namespace,
151 // and others do not. This allows us to support both modes.
152 namespace benchmark {
153 void RunTheBenchmarksNamespaced() { RunSpecifiedBenchmarks(); }
154 } // namespace benchmark
156 int main(int argc, char** argv) {
157 LibraryInitializer libInit;
158 ::benchmark::Initialize(&argc, argv);
159 ::grpc::testing::InitTest(&argc, &argv, false);
160 benchmark::RunTheBenchmarksNamespaced();