1 // Copyright 2023 gRPC authors.
2 //
3 // Licensed under the Apache License, Version 2.0 (the "License");
4 // you may not use this file except in compliance with the License.
5 // You may obtain a copy of the License at
6 //
7 // http://www.apache.org/licenses/LICENSE-2.0
8 //
9 // Unless required by applicable law or agreed to in writing, software
10 // distributed under the License is distributed on an "AS IS" BASIS,
11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 // See the License for the specific language governing permissions and
13 // limitations under the License.
14
15 #include <inttypes.h>
16 #include <string.h>
17
18 #include <algorithm>
19 #include <atomic>
20 #include <functional>
21 #include <memory>
22 #include <regex>
23 #include <string>
24 #include <utility>
25 #include <vector>
26
27 #include "absl/base/thread_annotations.h"
28 #include "absl/functional/any_invocable.h"
29 #include "absl/meta/type_traits.h"
30 #include "absl/random/random.h"
31 #include "absl/status/status.h"
32 #include "absl/strings/str_format.h"
33 #include "absl/types/optional.h"
34 #include "gtest/gtest.h"
35
36 #include <grpc/compression.h>
37 #include <grpc/grpc.h>
38 #include <grpc/grpc_posix.h>
39 #include <grpc/grpc_security.h>
40 #include <grpc/grpc_security_constants.h>
41 #include <grpc/impl/channel_arg_names.h>
42 #include <grpc/slice.h>
43 #include <grpc/status.h>
44 #include <grpc/support/log.h>
45 #include <grpc/support/time.h>
46
47 #include "src/core/ext/transport/chaotic_good/client/chaotic_good_connector.h"
48 #include "src/core/ext/transport/chaotic_good/server/chaotic_good_server.h"
49 #include "src/core/lib/channel/channel_args.h"
50 #include "src/core/lib/debug/trace.h"
51 #include "src/core/lib/gprpp/env.h"
52 #include "src/core/lib/gprpp/host_port.h"
53 #include "src/core/lib/gprpp/no_destruct.h"
54 #include "src/core/lib/gprpp/sync.h"
55 #include "src/core/lib/iomgr/error.h"
56 #include "src/core/lib/iomgr/exec_ctx.h"
57 #include "src/core/lib/iomgr/port.h"
58 #include "src/core/lib/security/credentials/fake/fake_credentials.h"
59 #include "test/core/end2end/end2end_tests.h"
60 #include "test/core/end2end/fixtures/h2_oauth2_common.h"
61 #include "test/core/end2end/fixtures/h2_ssl_cred_reload_fixture.h"
62 #include "test/core/end2end/fixtures/h2_ssl_tls_common.h"
63 #include "test/core/end2end/fixtures/h2_tls_common.h"
64 #include "test/core/end2end/fixtures/http_proxy_fixture.h"
65 #include "test/core/end2end/fixtures/inproc_fixture.h"
66 #include "test/core/end2end/fixtures/local_util.h"
67 #include "test/core/end2end/fixtures/proxy.h"
68 #include "test/core/end2end/fixtures/secure_fixture.h"
69 #include "test/core/end2end/fixtures/sockpair_fixture.h"
70 #include "test/core/util/port.h"
71 #include "test/core/util/test_config.h"
72 #include "test/core/util/tls_utils.h"
73
74 // IWYU pragma: no_include <unistd.h>
75
76 #ifdef GRPC_POSIX_SOCKET
77 #include <fcntl.h>
78
79 #include "src/core/lib/iomgr/socket_utils_posix.h"
80 #include "src/core/lib/iomgr/unix_sockets_posix.h"
81 #endif
82
83 #ifdef GRPC_POSIX_WAKEUP_FD
84 #include "src/core/lib/iomgr/wakeup_fd_posix.h"
85 #endif
86
87 #define CA_CERT_PATH "src/core/tsi/test_creds/ca.pem"
88 #define SERVER_CERT_PATH "src/core/tsi/test_creds/server1.pem"
89 #define SERVER_KEY_PATH "src/core/tsi/test_creds/server1.key"
90
91 namespace grpc_core {
92
93 namespace {
94
Rand()95 uint64_t Rand() {
96 struct State {
97 Mutex mu;
98 absl::BitGen gen ABSL_GUARDED_BY(mu);
99 };
100 static State* const state = new State;
101 MutexLock lock(&state->mu);
102 return absl::Uniform<uint64_t>(state->gen);
103 }
104
105 std::atomic<uint64_t> unique{Rand()};
106
ProcessAuthFailure(void * state,grpc_auth_context *,const grpc_metadata *,size_t,grpc_process_auth_metadata_done_cb cb,void * user_data)107 void ProcessAuthFailure(void* state, grpc_auth_context* /*ctx*/,
108 const grpc_metadata* /*md*/, size_t /*md_count*/,
109 grpc_process_auth_metadata_done_cb cb,
110 void* user_data) {
111 GPR_ASSERT(state == nullptr);
112 cb(user_data, nullptr, 0, nullptr, 0, GRPC_STATUS_UNAUTHENTICATED, nullptr);
113 }
114
AddFailAuthCheckIfNeeded(const ChannelArgs & args,grpc_server_credentials * creds)115 void AddFailAuthCheckIfNeeded(const ChannelArgs& args,
116 grpc_server_credentials* creds) {
117 if (args.Contains(FAIL_AUTH_CHECK_SERVER_ARG_NAME)) {
118 grpc_auth_metadata_processor processor = {ProcessAuthFailure, nullptr,
119 nullptr};
120 grpc_server_credentials_set_auth_metadata_processor(creds, processor);
121 }
122 }
123
124 } // namespace
125
126 class CensusFixture : public CoreTestFixture {
127 private:
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)128 grpc_server* MakeServer(
129 const ChannelArgs& args, grpc_completion_queue* cq,
130 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
131 grpc_server_credentials* server_creds =
132 grpc_insecure_server_credentials_create();
133 auto* server = grpc_server_create(
134 args.Set(GRPC_ARG_ENABLE_CENSUS, true).ToC().get(), nullptr);
135 grpc_server_register_completion_queue(server, cq, nullptr);
136 GPR_ASSERT(
137 grpc_server_add_http2_port(server, localaddr_.c_str(), server_creds));
138 grpc_server_credentials_release(server_creds);
139 pre_server_start(server);
140 grpc_server_start(server);
141 return server;
142 }
MakeClient(const ChannelArgs & args,grpc_completion_queue *)143 grpc_channel* MakeClient(const ChannelArgs& args,
144 grpc_completion_queue*) override {
145 auto* creds = grpc_insecure_credentials_create();
146 auto* client =
147 grpc_channel_create(localaddr_.c_str(), creds,
148 args.Set(GRPC_ARG_ENABLE_CENSUS, true).ToC().get());
149 grpc_channel_credentials_release(creds);
150 return client;
151 }
152 const std::string localaddr_ =
153 JoinHostPort("localhost", grpc_pick_unused_port_or_die());
154 };
155
156 class CompressionFixture : public CoreTestFixture {
157 private:
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)158 grpc_server* MakeServer(
159 const ChannelArgs& args, grpc_completion_queue* cq,
160 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
161 auto* server = grpc_server_create(
162 args.SetIfUnset(GRPC_COMPRESSION_CHANNEL_DEFAULT_ALGORITHM,
163 GRPC_COMPRESS_GZIP)
164 .ToC()
165 .get(),
166 nullptr);
167 grpc_server_register_completion_queue(server, cq, nullptr);
168 grpc_server_credentials* server_creds =
169 grpc_insecure_server_credentials_create();
170 GPR_ASSERT(
171 grpc_server_add_http2_port(server, localaddr_.c_str(), server_creds));
172 grpc_server_credentials_release(server_creds);
173 pre_server_start(server);
174 grpc_server_start(server);
175 return server;
176 }
MakeClient(const ChannelArgs & args,grpc_completion_queue *)177 grpc_channel* MakeClient(const ChannelArgs& args,
178 grpc_completion_queue*) override {
179 grpc_channel_credentials* creds = grpc_insecure_credentials_create();
180 auto* client = grpc_channel_create(
181 localaddr_.c_str(), creds,
182 args.SetIfUnset(GRPC_COMPRESSION_CHANNEL_DEFAULT_ALGORITHM,
183 GRPC_COMPRESS_GZIP)
184 .ToC()
185 .get());
186 grpc_channel_credentials_release(creds);
187 return client;
188 }
189
190 std::string localaddr_ =
191 JoinHostPort("localhost", grpc_pick_unused_port_or_die());
192 };
193
194 class FakesecFixture : public SecureFixture {
195 private:
MakeClientCreds(const ChannelArgs &)196 grpc_channel_credentials* MakeClientCreds(const ChannelArgs&) override {
197 return grpc_fake_transport_security_credentials_create();
198 }
MakeServerCreds(const ChannelArgs & args)199 grpc_server_credentials* MakeServerCreds(const ChannelArgs& args) override {
200 grpc_server_credentials* fake_ts_creds =
201 grpc_fake_transport_security_server_credentials_create();
202 AddFailAuthCheckIfNeeded(args, fake_ts_creds);
203 return fake_ts_creds;
204 }
205 };
206
207 class InsecureCredsFixture : public InsecureFixture {
208 private:
MakeServerCreds(const ChannelArgs & args)209 grpc_server_credentials* MakeServerCreds(const ChannelArgs& args) override {
210 auto* creds = grpc_insecure_server_credentials_create();
211 AddFailAuthCheckIfNeeded(args, creds);
212 return creds;
213 }
214 };
215
216 class SockpairWithMinstackFixture : public SockpairFixture {
217 public:
218 using SockpairFixture::SockpairFixture;
219
220 private:
MutateClientArgs(ChannelArgs args)221 ChannelArgs MutateClientArgs(ChannelArgs args) override {
222 return args.Set(GRPC_ARG_MINIMAL_STACK, true);
223 }
MutateServerArgs(ChannelArgs args)224 ChannelArgs MutateServerArgs(ChannelArgs args) override {
225 return args.Set(GRPC_ARG_MINIMAL_STACK, true);
226 }
227 };
228
229 class Sockpair1Byte : public SockpairFixture {
230 public:
Sockpair1Byte()231 Sockpair1Byte()
232 : SockpairFixture(ChannelArgs()
233 .Set(GRPC_ARG_TCP_READ_CHUNK_SIZE, 1)
234 .Set(GRPC_ARG_TCP_MIN_READ_CHUNK_SIZE, 1)
235 .Set(GRPC_ARG_TCP_MAX_READ_CHUNK_SIZE, 1)) {
236 g_fixture_slowdown_factor = 2;
237 }
~Sockpair1Byte()238 ~Sockpair1Byte() override { g_fixture_slowdown_factor = 1; }
239
240 private:
MutateClientArgs(ChannelArgs args)241 ChannelArgs MutateClientArgs(ChannelArgs args) override {
242 return args.Set(GRPC_ARG_MINIMAL_STACK, true);
243 }
MutateServerArgs(ChannelArgs args)244 ChannelArgs MutateServerArgs(ChannelArgs args) override {
245 return args.Set(GRPC_ARG_MINIMAL_STACK, true);
246 }
247 };
248
249 #ifdef GRPC_POSIX_SOCKET
250
251 class FdFixture : public CoreTestFixture {
252 public:
FdFixture()253 FdFixture() { create_sockets(fd_pair_); }
254
255 private:
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)256 grpc_server* MakeServer(
257 const ChannelArgs& args, grpc_completion_queue* cq,
258 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
259 ExecCtx exec_ctx;
260 auto* server = grpc_server_create(args.ToC().get(), nullptr);
261 grpc_server_register_completion_queue(server, cq, nullptr);
262 pre_server_start(server);
263 grpc_server_start(server);
264 grpc_server_credentials* creds = grpc_insecure_server_credentials_create();
265 grpc_server_add_channel_from_fd(server, fd_pair_[1], creds);
266 grpc_server_credentials_release(creds);
267 return server;
268 }
MakeClient(const ChannelArgs & args,grpc_completion_queue *)269 grpc_channel* MakeClient(const ChannelArgs& args,
270 grpc_completion_queue*) override {
271 ExecCtx exec_ctx;
272 grpc_channel_credentials* creds = grpc_insecure_credentials_create();
273 auto* client = grpc_channel_create_from_fd("fixture_client", fd_pair_[0],
274 creds, args.ToC().get());
275 grpc_channel_credentials_release(creds);
276 return client;
277 }
278
create_sockets(int sv[2])279 static void create_sockets(int sv[2]) {
280 int flags;
281 grpc_create_socketpair_if_unix(sv);
282 flags = fcntl(sv[0], F_GETFL, 0);
283 GPR_ASSERT(fcntl(sv[0], F_SETFL, flags | O_NONBLOCK) == 0);
284 flags = fcntl(sv[1], F_GETFL, 0);
285 GPR_ASSERT(fcntl(sv[1], F_SETFL, flags | O_NONBLOCK) == 0);
286 GPR_ASSERT(grpc_set_socket_no_sigpipe_if_possible(sv[0]) ==
287 absl::OkStatus());
288 GPR_ASSERT(grpc_set_socket_no_sigpipe_if_possible(sv[1]) ==
289 absl::OkStatus());
290 }
291
292 int fd_pair_[2];
293 };
294 #endif
295
296 class NoRetryFixture : public InsecureFixture {
297 private:
MutateClientArgs(ChannelArgs args)298 ChannelArgs MutateClientArgs(ChannelArgs args) override {
299 return args.Set(GRPC_ARG_ENABLE_RETRIES, false);
300 }
301 };
302
303 class HttpProxyFilter : public CoreTestFixture {
304 public:
HttpProxyFilter(const ChannelArgs & client_args)305 explicit HttpProxyFilter(const ChannelArgs& client_args)
306 : proxy_(grpc_end2end_http_proxy_create(client_args.ToC().get())) {}
~HttpProxyFilter()307 ~HttpProxyFilter() override { grpc_end2end_http_proxy_destroy(proxy_); }
308
309 private:
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)310 grpc_server* MakeServer(
311 const ChannelArgs& args, grpc_completion_queue* cq,
312 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
313 auto* server = grpc_server_create(args.ToC().get(), nullptr);
314 grpc_server_register_completion_queue(server, cq, nullptr);
315 grpc_server_credentials* server_creds =
316 grpc_insecure_server_credentials_create();
317 GPR_ASSERT(
318 grpc_server_add_http2_port(server, server_addr_.c_str(), server_creds));
319 grpc_server_credentials_release(server_creds);
320 pre_server_start(server);
321 grpc_server_start(server);
322 return server;
323 }
324
MakeClient(const ChannelArgs & args,grpc_completion_queue *)325 grpc_channel* MakeClient(const ChannelArgs& args,
326 grpc_completion_queue*) override {
327 // If testing for proxy auth, add credentials to proxy uri
328 absl::optional<std::string> proxy_auth_str =
329 args.GetOwnedString(GRPC_ARG_HTTP_PROXY_AUTH_CREDS);
330 std::string proxy_uri;
331 if (!proxy_auth_str.has_value()) {
332 proxy_uri = absl::StrFormat(
333 "http://%s", grpc_end2end_http_proxy_get_proxy_name(proxy_));
334 } else {
335 proxy_uri =
336 absl::StrFormat("http://%s@%s", proxy_auth_str->c_str(),
337 grpc_end2end_http_proxy_get_proxy_name(proxy_));
338 }
339 grpc_channel_credentials* creds = grpc_insecure_credentials_create();
340 auto* client = grpc_channel_create(
341 server_addr_.c_str(), creds,
342 args.Set(GRPC_ARG_HTTP_PROXY, proxy_uri).ToC().get());
343 grpc_channel_credentials_release(creds);
344 GPR_ASSERT(client);
345 return client;
346 }
347
348 std::string server_addr_ =
349 JoinHostPort("localhost", grpc_pick_unused_port_or_die());
350 grpc_end2end_http_proxy* proxy_;
351 };
352
353 class ProxyFixture : public CoreTestFixture {
354 public:
ProxyFixture(const ChannelArgs & client_args,const ChannelArgs & server_args)355 ProxyFixture(const ChannelArgs& client_args, const ChannelArgs& server_args)
356 : proxy_(grpc_end2end_proxy_create(&proxy_def_, client_args.ToC().get(),
357 server_args.ToC().get())) {}
~ProxyFixture()358 ~ProxyFixture() override { grpc_end2end_proxy_destroy(proxy_); }
359
360 private:
CreateProxyServer(const char * port,const grpc_channel_args * server_args)361 static grpc_server* CreateProxyServer(const char* port,
362 const grpc_channel_args* server_args) {
363 grpc_server* s = grpc_server_create(server_args, nullptr);
364 grpc_server_credentials* server_creds =
365 grpc_insecure_server_credentials_create();
366 GPR_ASSERT(grpc_server_add_http2_port(s, port, server_creds));
367 grpc_server_credentials_release(server_creds);
368 return s;
369 }
370
CreateProxyClient(const char * target,const grpc_channel_args * client_args)371 static grpc_channel* CreateProxyClient(const char* target,
372 const grpc_channel_args* client_args) {
373 grpc_channel_credentials* creds = grpc_insecure_credentials_create();
374 grpc_channel* channel = grpc_channel_create(target, creds, client_args);
375 grpc_channel_credentials_release(creds);
376 return channel;
377 }
378
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)379 grpc_server* MakeServer(
380 const ChannelArgs& args, grpc_completion_queue* cq,
381 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
382 auto* server = grpc_server_create(args.ToC().get(), nullptr);
383 grpc_server_register_completion_queue(server, cq, nullptr);
384 grpc_server_credentials* server_creds =
385 grpc_insecure_server_credentials_create();
386 GPR_ASSERT(grpc_server_add_http2_port(
387 server, grpc_end2end_proxy_get_server_port(proxy_), server_creds));
388 grpc_server_credentials_release(server_creds);
389 pre_server_start(server);
390 grpc_server_start(server);
391 return server;
392 }
393
MakeClient(const ChannelArgs & args,grpc_completion_queue *)394 grpc_channel* MakeClient(const ChannelArgs& args,
395 grpc_completion_queue*) override {
396 grpc_channel_credentials* creds = grpc_insecure_credentials_create();
397 auto* client = grpc_channel_create(
398 grpc_end2end_proxy_get_client_target(proxy_), creds, args.ToC().get());
399 grpc_channel_credentials_release(creds);
400 GPR_ASSERT(client);
401 return client;
402 }
403 const grpc_end2end_proxy_def proxy_def_ = {CreateProxyServer,
404 CreateProxyClient};
405 grpc_end2end_proxy* proxy_;
406 };
407
408 class SslProxyFixture : public CoreTestFixture {
409 public:
SslProxyFixture(const ChannelArgs & client_args,const ChannelArgs & server_args)410 SslProxyFixture(const ChannelArgs& client_args,
411 const ChannelArgs& server_args)
412 : proxy_(grpc_end2end_proxy_create(&proxy_def_, client_args.ToC().get(),
413 server_args.ToC().get())) {}
~SslProxyFixture()414 ~SslProxyFixture() override { grpc_end2end_proxy_destroy(proxy_); }
415
416 private:
CreateProxyServer(const char * port,const grpc_channel_args * server_args)417 static grpc_server* CreateProxyServer(const char* port,
418 const grpc_channel_args* server_args) {
419 grpc_server* s = grpc_server_create(server_args, nullptr);
420 std::string server_cert = testing::GetFileContents(SERVER_CERT_PATH);
421 std::string server_key = testing::GetFileContents(SERVER_KEY_PATH);
422 grpc_ssl_pem_key_cert_pair pem_key_cert_pair = {server_key.c_str(),
423 server_cert.c_str()};
424 grpc_server_credentials* ssl_creds = grpc_ssl_server_credentials_create(
425 nullptr, &pem_key_cert_pair, 1, 0, nullptr);
426 GPR_ASSERT(grpc_server_add_http2_port(s, port, ssl_creds));
427 grpc_server_credentials_release(ssl_creds);
428 return s;
429 }
430
CreateProxyClient(const char * target,const grpc_channel_args * client_args)431 static grpc_channel* CreateProxyClient(const char* target,
432 const grpc_channel_args* client_args) {
433 grpc_channel* channel;
434 grpc_channel_credentials* ssl_creds =
435 grpc_ssl_credentials_create(nullptr, nullptr, nullptr, nullptr);
436 grpc_arg ssl_name_override = {
437 GRPC_ARG_STRING,
438 const_cast<char*>(GRPC_SSL_TARGET_NAME_OVERRIDE_ARG),
439 {const_cast<char*>("foo.test.google.fr")}};
440 const grpc_channel_args* new_client_args =
441 grpc_channel_args_copy_and_add(client_args, &ssl_name_override, 1);
442 channel = grpc_channel_create(target, ssl_creds, new_client_args);
443 grpc_channel_credentials_release(ssl_creds);
444 {
445 ExecCtx exec_ctx;
446 grpc_channel_args_destroy(new_client_args);
447 }
448 return channel;
449 }
450
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)451 grpc_server* MakeServer(
452 const ChannelArgs& args, grpc_completion_queue* cq,
453 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
454 std::string server_cert = testing::GetFileContents(SERVER_CERT_PATH);
455 std::string server_key = testing::GetFileContents(SERVER_KEY_PATH);
456 grpc_ssl_pem_key_cert_pair pem_key_cert_pair = {server_key.c_str(),
457 server_cert.c_str()};
458 grpc_server_credentials* ssl_creds = grpc_ssl_server_credentials_create(
459 nullptr, &pem_key_cert_pair, 1, 0, nullptr);
460 if (args.Contains(FAIL_AUTH_CHECK_SERVER_ARG_NAME)) {
461 grpc_auth_metadata_processor processor = {ProcessAuthFailure, nullptr,
462 nullptr};
463 grpc_server_credentials_set_auth_metadata_processor(ssl_creds, processor);
464 }
465
466 auto* server = grpc_server_create(args.ToC().get(), nullptr);
467 grpc_server_register_completion_queue(server, cq, nullptr);
468 GPR_ASSERT(grpc_server_add_http2_port(
469 server, grpc_end2end_proxy_get_server_port(proxy_), ssl_creds));
470 grpc_server_credentials_release(ssl_creds);
471 pre_server_start(server);
472 grpc_server_start(server);
473 return server;
474 }
475
MakeClient(const ChannelArgs & args,grpc_completion_queue *)476 grpc_channel* MakeClient(const ChannelArgs& args,
477 grpc_completion_queue*) override {
478 grpc_channel_credentials* ssl_creds =
479 grpc_ssl_credentials_create(nullptr, nullptr, nullptr, nullptr);
480 auto* client = grpc_channel_create(
481 grpc_end2end_proxy_get_client_target(proxy_), ssl_creds,
482 args.Set(GRPC_SSL_TARGET_NAME_OVERRIDE_ARG, "foo.test.google.fr")
483 .ToC()
484 .get());
485 GPR_ASSERT(client != nullptr);
486 grpc_channel_credentials_release(ssl_creds);
487 return client;
488 }
489 const grpc_end2end_proxy_def proxy_def_ = {CreateProxyServer,
490 CreateProxyClient};
491 grpc_end2end_proxy* proxy_;
492 };
493
494 class FixtureWithTracing final : public CoreTestFixture {
495 public:
FixtureWithTracing(std::unique_ptr<CoreTestFixture> fixture)496 explicit FixtureWithTracing(std::unique_ptr<CoreTestFixture> fixture)
497 : fixture_(std::move(fixture)) {
498 // g_fixture_slowdown_factor = 10;
499 EXPECT_FALSE(grpc_tracer_set_enabled("doesnt-exist", 0));
500 EXPECT_TRUE(grpc_tracer_set_enabled("http", 1));
501 EXPECT_TRUE(grpc_tracer_set_enabled("all", 1));
502 }
~FixtureWithTracing()503 ~FixtureWithTracing() override {
504 saved_trace_flags_.Restore();
505 // g_fixture_slowdown_factor = 1;
506 }
507
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)508 grpc_server* MakeServer(
509 const ChannelArgs& args, grpc_completion_queue* cq,
510 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
511 return fixture_->MakeServer(args, cq, pre_server_start);
512 }
513
MakeClient(const ChannelArgs & args,grpc_completion_queue * cq)514 grpc_channel* MakeClient(const ChannelArgs& args,
515 grpc_completion_queue* cq) override {
516 return fixture_->MakeClient(args, cq);
517 }
518
519 private:
520 SavedTraceFlags saved_trace_flags_;
521 std::unique_ptr<CoreTestFixture> fixture_;
522 };
523
524 class ChaoticGoodFixture final : public CoreTestFixture {
525 public:
ChaoticGoodFixture(std::string localaddr=JoinHostPort ("localhost",grpc_pick_unused_port_or_die ()))526 explicit ChaoticGoodFixture(std::string localaddr = JoinHostPort(
527 "localhost", grpc_pick_unused_port_or_die()))
528 : localaddr_(std::move(localaddr)) {}
529
530 protected:
localaddr() const531 const std::string& localaddr() const { return localaddr_; }
532
533 private:
MakeServer(const ChannelArgs & args,grpc_completion_queue * cq,absl::AnyInvocable<void (grpc_server *)> & pre_server_start)534 grpc_server* MakeServer(
535 const ChannelArgs& args, grpc_completion_queue* cq,
536 absl::AnyInvocable<void(grpc_server*)>& pre_server_start) override {
537 auto* server = grpc_server_create(args.ToC().get(), nullptr);
538 grpc_server_register_completion_queue(server, cq, nullptr);
539 GPR_ASSERT(grpc_server_add_chaotic_good_port(server, localaddr_.c_str()));
540 pre_server_start(server);
541 grpc_server_start(server);
542 return server;
543 }
544
MakeClient(const ChannelArgs & args,grpc_completion_queue *)545 grpc_channel* MakeClient(const ChannelArgs& args,
546 grpc_completion_queue*) override {
547 auto* client = grpc_chaotic_good_channel_create(
548 localaddr_.c_str(),
549 args.Set(GRPC_ARG_ENABLE_RETRIES, false).ToC().get());
550 return client;
551 }
552
553 std::string localaddr_;
554 };
555
556 #ifdef GRPC_POSIX_WAKEUP_FD
557 class InsecureFixtureWithPipeForWakeupFd : public InsecureFixture {
558 public:
InsecureFixtureWithPipeForWakeupFd()559 InsecureFixtureWithPipeForWakeupFd()
560 : old_value_(std::exchange(grpc_allow_specialized_wakeup_fd, 0)) {}
561
~InsecureFixtureWithPipeForWakeupFd()562 ~InsecureFixtureWithPipeForWakeupFd() override {
563 grpc_allow_specialized_wakeup_fd = old_value_;
564 }
565
566 private:
567 const int old_value_;
568 };
569 #endif
570
571 // Returns the temp directory to create uds in this test.
GetTempDir()572 std::string GetTempDir() {
573 #ifdef GPR_WINDOWS
574 // Windows temp dir usually exceeds uds max paht length,
575 // so we create a short dir for this test.
576 // TODO: find a better solution.
577 std::string temp_dir = "C:/tmp/";
578 if (CreateDirectoryA(temp_dir.c_str(), NULL) == 0 &&
579 ERROR_ALREADY_EXISTS != GetLastError()) {
580 Crash(absl::StrCat("Could not create temp dir: ", temp_dir));
581 }
582 return temp_dir;
583 #else
584 return "/tmp/";
585 #endif // GPR_WINDOWS
586 }
587
588 const std::string temp_dir = GetTempDir();
589
DefaultConfigs()590 std::vector<CoreTestConfiguration> DefaultConfigs() {
591 return std::vector<CoreTestConfiguration> {
592 #ifdef GRPC_POSIX_SOCKET
593 CoreTestConfiguration{"Chttp2Fd",
594 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_DO_NOT_FUZZ |
595 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
596 nullptr,
597 [](const ChannelArgs&, const ChannelArgs&) {
598 return std::make_unique<FdFixture>();
599 }},
600 #endif
601 CoreTestConfiguration{
602 "Chttp2FakeSecurityFullstack",
603 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
604 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS_LEVEL_INSECURE |
605 FEATURE_MASK_IS_HTTP2,
606 nullptr,
607 [](const ChannelArgs&, const ChannelArgs&) {
608 return std::make_unique<FakesecFixture>();
609 }},
610 CoreTestConfiguration{
611 "Chttp2Fullstack",
612 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2,
613 nullptr,
614 [](const ChannelArgs& /*client_args*/,
615 const ChannelArgs& /*server_args*/) {
616 return std::make_unique<InsecureFixture>();
617 }},
618 CoreTestConfiguration{
619 "Chttp2FullstackCompression",
620 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2,
621 nullptr,
622 [](const ChannelArgs&, const ChannelArgs&) {
623 return std::make_unique<CompressionFixture>();
624 }},
625 #ifdef GPR_LINUX
626 CoreTestConfiguration{
627 "Chttp2FullstackLocalAbstractUdsPercentEncoded",
628 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
629 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
630 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_DO_NOT_FUZZ |
631 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
632 nullptr,
633 [](const ChannelArgs& /*client_args*/,
634 const ChannelArgs& /*server_args*/) {
635 gpr_timespec now = gpr_now(GPR_CLOCK_MONOTONIC);
636 return std::make_unique<LocalTestFixture>(
637 absl::StrFormat(
638 "unix-abstract:grpc_fullstack_test.%%00.%d.%" PRId64
639 ".%" PRId32 ".%" PRId64 ".%" PRId64,
640 getpid(), now.tv_sec, now.tv_nsec,
641 unique.fetch_add(1, std::memory_order_relaxed), Rand()),
642 UDS);
643 }},
644 #endif
645 CoreTestConfiguration{"Chttp2FullstackLocalIpv4",
646 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
647 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
648 FEATURE_MASK_IS_HTTP2 |
649 FEATURE_MASK_DO_NOT_FUZZ |
650 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
651 nullptr,
652 [](const ChannelArgs& /*client_args*/,
653 const ChannelArgs& /*server_args*/) {
654 int port = grpc_pick_unused_port_or_die();
655 return std::make_unique<LocalTestFixture>(
656 JoinHostPort("127.0.0.1", port), LOCAL_TCP);
657 }},
658 CoreTestConfiguration{"Chttp2FullstackLocalIpv6",
659 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
660 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
661 FEATURE_MASK_IS_HTTP2 |
662 FEATURE_MASK_DO_NOT_FUZZ |
663 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
664 nullptr,
665 [](const ChannelArgs& /*client_args*/,
666 const ChannelArgs& /*server_args*/) {
667 int port = grpc_pick_unused_port_or_die();
668 return std::make_unique<LocalTestFixture>(
669 JoinHostPort("[::1]", port), LOCAL_TCP);
670 }},
671 #ifdef GRPC_HAVE_UNIX_SOCKET
672 CoreTestConfiguration{
673 "Chttp2FullstackLocalUdsPercentEncoded",
674 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
675 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
676 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_DO_NOT_FUZZ |
677 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
678 nullptr,
679 [](const ChannelArgs& /*client_args*/,
680 const ChannelArgs& /*server_args*/) {
681 gpr_timespec now = gpr_now(GPR_CLOCK_MONOTONIC);
682 return std::make_unique<LocalTestFixture>(
683 absl::StrFormat(
684 "unix:%s"
685 "grpc_fullstack_test.%%25.%d.%" PRId64 ".%" PRId32
686 ".%" PRId64 ".%" PRId64,
687 temp_dir, getpid(), now.tv_sec, now.tv_nsec,
688 unique.fetch_add(1, std::memory_order_relaxed), Rand()),
689 UDS);
690 }},
691 CoreTestConfiguration{
692 "Chttp2FullstackLocalUds",
693 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
694 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
695 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_DO_NOT_FUZZ |
696 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
697 nullptr,
698 [](const ChannelArgs& /*client_args*/,
699 const ChannelArgs& /*server_args*/) {
700 gpr_timespec now = gpr_now(GPR_CLOCK_REALTIME);
701 return std::make_unique<LocalTestFixture>(
702 absl::StrFormat(
703 "unix:%s"
704 "grpc_fullstack_test.%d.%" PRId64 ".%" PRId32 ".%" PRId64
705 ".%" PRId64,
706 temp_dir, getpid(), now.tv_sec, now.tv_nsec,
707 unique.fetch_add(1, std::memory_order_relaxed), Rand()),
708 UDS);
709 }},
710 #endif
711 CoreTestConfiguration{"Chttp2FullstackNoRetry",
712 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
713 FEATURE_MASK_IS_HTTP2 |
714 FEATURE_MASK_DOES_NOT_SUPPORT_RETRY,
715 nullptr,
716 [](const ChannelArgs& /*client_args*/,
717 const ChannelArgs& /*server_args*/) {
718 return std::make_unique<NoRetryFixture>();
719 }},
720 CoreTestConfiguration{
721 "Chttp2FullstackWithCensus",
722 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2,
723 nullptr,
724 [](const ChannelArgs&, const ChannelArgs&) {
725 return std::make_unique<CensusFixture>();
726 }},
727 CoreTestConfiguration{
728 "Chttp2FullstackWithProxy",
729 FEATURE_MASK_SUPPORTS_REQUEST_PROXYING |
730 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
731 FEATURE_MASK_DO_NOT_FUZZ,
732 nullptr,
733 [](const ChannelArgs& client_args, const ChannelArgs& server_args) {
734 return std::make_unique<ProxyFixture>(client_args, server_args);
735 }},
736 CoreTestConfiguration{
737 "Chttp2HttpProxy",
738 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
739 FEATURE_MASK_DO_NOT_FUZZ,
740 nullptr,
741 [](const ChannelArgs& client_args, const ChannelArgs&) {
742 return std::make_unique<HttpProxyFilter>(client_args);
743 }},
744 CoreTestConfiguration{
745 "Chttp2SslProxy",
746 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_SECURE |
747 FEATURE_MASK_SUPPORTS_REQUEST_PROXYING |
748 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
749 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_DO_NOT_FUZZ,
750 "foo.test.google.fr",
751 [](const ChannelArgs& client_args, const ChannelArgs& server_args) {
752 return std::make_unique<SslProxyFixture>(client_args,
753 server_args);
754 }},
755 CoreTestConfiguration{
756 "Chttp2InsecureCredentials",
757 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
758 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS_LEVEL_INSECURE |
759 FEATURE_MASK_IS_HTTP2 |
760 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
761 nullptr,
762 [](const ChannelArgs&, const ChannelArgs&) {
763 return std::make_unique<InsecureCredsFixture>();
764 },
765 },
766 CoreTestConfiguration{
767 "Chttp2SimpleSslWithOauth2FullstackTls12",
768 FEATURE_MASK_IS_SECURE |
769 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
770 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
771 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
772 "foo.test.google.fr",
773 [](const ChannelArgs&, const ChannelArgs&) {
774 return std::make_unique<Oauth2Fixture>(grpc_tls_version::TLS1_2);
775 }},
776 CoreTestConfiguration{
777 "Chttp2SimpleSslWithOauth2FullstackTls13",
778 FEATURE_MASK_IS_SECURE |
779 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
780 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2,
781 "foo.test.google.fr",
782 [](const ChannelArgs&, const ChannelArgs&) {
783 return std::make_unique<Oauth2Fixture>(grpc_tls_version::TLS1_3);
784 }},
785 CoreTestConfiguration{
786 "Chttp2SimplSslFullstackTls12",
787 FEATURE_MASK_IS_SECURE |
788 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
789 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
790 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
791 "foo.test.google.fr",
792 [](const ChannelArgs&, const ChannelArgs&) {
793 return std::make_unique<SslTlsFixture>(grpc_tls_version::TLS1_2);
794 }},
795 CoreTestConfiguration{
796 "Chttp2SimplSslFullstackTls13",
797 FEATURE_MASK_IS_SECURE |
798 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
799 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
800 FEATURE_MASK_DOES_NOT_SUPPORT_CLIENT_HANDSHAKE_COMPLETE_FIRST |
801 FEATURE_MASK_IS_HTTP2,
802 "foo.test.google.fr",
803 [](const ChannelArgs&, const ChannelArgs&) {
804 return std::make_unique<SslTlsFixture>(grpc_tls_version::TLS1_3);
805 }},
806 CoreTestConfiguration{
807 "Chttp2SocketPair",
808 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_DO_NOT_FUZZ |
809 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
810 nullptr,
811 [](const ChannelArgs&, const ChannelArgs&) {
812 return std::make_unique<SockpairFixture>(ChannelArgs());
813 }},
814 CoreTestConfiguration{
815 "Chttp2SocketPair1ByteAtATime",
816 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_1BYTE_AT_A_TIME |
817 FEATURE_MASK_DO_NOT_FUZZ |
818 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
819 nullptr,
820 [](const ChannelArgs&, const ChannelArgs&) {
821 return std::make_unique<SockpairFixture>(
822 ChannelArgs()
823 .Set(GRPC_ARG_TCP_READ_CHUNK_SIZE, 1)
824 .Set(GRPC_ARG_TCP_MIN_READ_CHUNK_SIZE, 1)
825 .Set(GRPC_ARG_TCP_MAX_READ_CHUNK_SIZE, 1));
826 }},
827 CoreTestConfiguration{
828 "Chttp2SocketPairMinstack",
829 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_IS_MINSTACK |
830 FEATURE_MASK_DO_NOT_FUZZ,
831 nullptr,
832 [](const ChannelArgs&, const ChannelArgs&) {
833 return std::make_unique<SockpairWithMinstackFixture>(
834 ChannelArgs());
835 }},
836 CoreTestConfiguration{
837 "Inproc",
838 FEATURE_MASK_DOES_NOT_SUPPORT_WRITE_BUFFERING,
839 nullptr,
840 [](const ChannelArgs&, const ChannelArgs&) {
841 return std::make_unique<InprocFixture>();
842 },
843 },
844 CoreTestConfiguration{
845 "Chttp2SslCredReloadTls12",
846 FEATURE_MASK_IS_SECURE |
847 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
848 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
849 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
850 "foo.test.google.fr",
851 [](const ChannelArgs&, const ChannelArgs&) {
852 return std::make_unique<SslCredReloadFixture>(TLS1_2);
853 }},
854 CoreTestConfiguration{
855 "Chttp2SslCredReloadTls13",
856 FEATURE_MASK_IS_SECURE | FEATURE_MASK_IS_HTTP2 |
857 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS |
858 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
859 FEATURE_MASK_DOES_NOT_SUPPORT_CLIENT_HANDSHAKE_COMPLETE_FIRST,
860 "foo.test.google.fr",
861 [](const ChannelArgs&, const ChannelArgs&) {
862 return std::make_unique<SslCredReloadFixture>(TLS1_3);
863 }},
864 CoreTestConfiguration{
865 // client: certificate watcher provider + async external verifier
866 // server: certificate watcher provider + async external verifier
867 // extra: TLS 1.3
868 "Chttp2CertWatcherProviderAsyncVerifierTls13",
869 kH2TLSFeatureMask | FEATURE_MASK_DO_NOT_FUZZ |
870 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
871 "foo.test.google.fr",
872 [](const ChannelArgs&, const ChannelArgs&) {
873 return std::make_unique<TlsFixture>(
874 SecurityPrimitives::TlsVersion::V_13,
875 SecurityPrimitives::ProviderType::FILE_PROVIDER,
876 SecurityPrimitives::VerifierType::EXTERNAL_ASYNC_VERIFIER);
877 },
878 },
879 CoreTestConfiguration{
880 // client: certificate watcher provider + hostname verifier
881 // server: certificate watcher provider + sync external verifier
882 // extra: TLS 1.2
883 "Chttp2CertWatcherProviderSyncVerifierTls12",
884 kH2TLSFeatureMask | FEATURE_MASK_DO_NOT_FUZZ |
885 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
886 "foo.test.google.fr",
887 [](const ChannelArgs&, const ChannelArgs&) {
888 return std::make_unique<TlsFixture>(
889 SecurityPrimitives::TlsVersion::V_12,
890 SecurityPrimitives::ProviderType::FILE_PROVIDER,
891 SecurityPrimitives::VerifierType::HOSTNAME_VERIFIER);
892 },
893 },
894 CoreTestConfiguration{
895 // client: static data provider + sync external verifier
896 // server: static data provider + sync external verifier
897 // extra: TLS 1.2
898 "Chttp2SimpleSslFullstack",
899 kH2TLSFeatureMask,
900 "foo.test.google.fr",
901 [](const ChannelArgs&, const ChannelArgs&) {
902 return std::make_unique<TlsFixture>(
903 SecurityPrimitives::TlsVersion::V_12,
904 SecurityPrimitives::ProviderType::STATIC_PROVIDER,
905 SecurityPrimitives::VerifierType::EXTERNAL_SYNC_VERIFIER);
906 },
907 },
908 CoreTestConfiguration{
909 // client: static data provider + async external verifier
910 // server: static data provider + async external verifier
911 // extra: TLS 1.3
912 "Chttp2StaticProviderAsyncVerifierTls13",
913 kH2TLSFeatureMask | FEATURE_MASK_DO_NOT_FUZZ |
914 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
915 "foo.test.google.fr",
916 [](const ChannelArgs&, const ChannelArgs&) {
917 return std::make_unique<TlsFixture>(
918 SecurityPrimitives::TlsVersion::V_13,
919 SecurityPrimitives::ProviderType::STATIC_PROVIDER,
920 SecurityPrimitives::VerifierType::EXTERNAL_ASYNC_VERIFIER);
921 },
922 },
923 #ifdef GPR_LINUX
924 CoreTestConfiguration{
925 "Chttp2FullstackUdsAbstractNamespace",
926 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
927 FEATURE_MASK_DO_NOT_FUZZ |
928 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
929 nullptr,
930 [](const ChannelArgs&, const ChannelArgs&) {
931 gpr_timespec now = gpr_now(GPR_CLOCK_REALTIME);
932 return std::make_unique<InsecureFixture>(absl::StrFormat(
933 "unix-abstract:grpc_fullstack_test.%d.%" PRId64 ".%" PRId32
934 ".%" PRId64,
935 getpid(), now.tv_sec, now.tv_nsec,
936 unique.fetch_add(1, std::memory_order_relaxed)));
937 }},
938 #endif
939 #ifdef GRPC_HAVE_UNIX_SOCKET
940 CoreTestConfiguration{
941 "Chttp2FullstackUds",
942 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
943 FEATURE_MASK_DO_NOT_FUZZ,
944 nullptr,
945 [](const ChannelArgs&, const ChannelArgs&) {
946 gpr_timespec now = gpr_now(GPR_CLOCK_REALTIME);
947 return std::make_unique<InsecureFixture>(absl::StrFormat(
948 "unix:%s"
949 "grpc_fullstack_test.%d.%" PRId64 ".%" PRId32 ".%" PRId64
950 ".%" PRId64,
951 temp_dir, getpid(), now.tv_sec, now.tv_nsec,
952 unique.fetch_add(1, std::memory_order_relaxed), Rand()));
953 }},
954 #endif
955 // TODO(ctiller): these got inadvertently disabled when the project
956 // switched to Bazel in 2016, and have not been re-enabled since and are now
957 // quite broken. We should re-enable them however, as they provide defense in
958 // depth that enabling tracers is safe. When doing so, we'll need to re-enable
959 // the windows setvbuf statement in main().
960 #if 0
961 CoreTestConfiguration{
962 "Chttp2SocketPairWithTrace",
963 FEATURE_MASK_IS_HTTP2 | FEATURE_MASK_ENABLES_TRACES, nullptr,
964 [](const ChannelArgs&, const ChannelArgs&) {
965 return std::make_unique<FixtureWithTracing>(
966 std::make_unique<SockpairFixture>(ChannelArgs()));
967 }},
968 CoreTestConfiguration{"Chttp2FullstackWithTrace",
969 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
970 FEATURE_MASK_IS_HTTP2 |
971 FEATURE_MASK_ENABLES_TRACES,
972 nullptr,
973 [](const ChannelArgs& /*client_args*/,
974 const ChannelArgs& /*server_args*/) {
975 return std::make_unique<FixtureWithTracing>(
976 std::make_unique<InsecureFixture>());
977 }},
978 #endif
979 #ifdef GRPC_POSIX_WAKEUP_FD
980 CoreTestConfiguration{
981 "Chttp2FullstackWithPipeWakeup",
982 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL | FEATURE_MASK_IS_HTTP2 |
983 FEATURE_MASK_DO_NOT_FUZZ |
984 FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS,
985 nullptr,
986 [](const ChannelArgs& /*client_args*/,
987 const ChannelArgs& /*server_args*/) {
988 return std::make_unique<InsecureFixtureWithPipeForWakeupFd>();
989 }},
990 #endif
991 };
992 }
993
ChaoticGoodFixtures()994 std::vector<CoreTestConfiguration> ChaoticGoodFixtures() {
995 return std::vector<CoreTestConfiguration>{
996 CoreTestConfiguration{"ChaoticGoodFullStack",
997 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL |
998 FEATURE_MASK_DOES_NOT_SUPPORT_RETRY |
999 FEATURE_MASK_DOES_NOT_SUPPORT_WRITE_BUFFERING,
1000 nullptr,
1001 [](const ChannelArgs& /*client_args*/,
1002 const ChannelArgs& /*server_args*/) {
1003 return std::make_unique<ChaoticGoodFixture>();
1004 }}};
1005 }
1006
AllConfigs()1007 std::vector<CoreTestConfiguration> AllConfigs() {
1008 std::vector<CoreTestConfiguration> configs;
1009 if (IsExperimentEnabledInConfiguration(kExperimentIdChaoticGood)) {
1010 configs = ChaoticGoodFixtures();
1011 } else {
1012 configs = DefaultConfigs();
1013 }
1014 std::sort(configs.begin(), configs.end(),
1015 [](const CoreTestConfiguration& a, const CoreTestConfiguration& b) {
1016 return strcmp(a.name, b.name) < 0;
1017 });
1018 return configs;
1019 }
1020
1021 // A ConfigQuery queries a database a set of test configurations
1022 // that match some criteria.
1023 class ConfigQuery {
1024 public:
ConfigQuery()1025 ConfigQuery() {
1026 if (GetEnv("GRPC_CI_EXPERIMENTS").has_value()) {
1027 exclude_features_ |= FEATURE_MASK_EXCLUDE_FROM_EXPERIMENT_RUNS;
1028 }
1029 }
1030 ConfigQuery(const ConfigQuery&) = delete;
1031 ConfigQuery& operator=(const ConfigQuery&) = delete;
1032 // Enforce that the returned configurations have the given features.
EnforceFeatures(uint32_t features)1033 ConfigQuery& EnforceFeatures(uint32_t features) {
1034 enforce_features_ |= features;
1035 return *this;
1036 }
1037 // Envorce that the returned configurations do not have the given features.
ExcludeFeatures(uint32_t features)1038 ConfigQuery& ExcludeFeatures(uint32_t features) {
1039 exclude_features_ |= features;
1040 return *this;
1041 }
1042 // Enforce that the returned configurations have the given name (regex).
AllowName(const std::string & name)1043 ConfigQuery& AllowName(const std::string& name) {
1044 allowed_names_.emplace_back(
1045 std::regex(name, std::regex_constants::ECMAScript));
1046 return *this;
1047 }
1048 // Enforce that the returned configurations do not have the given name
1049 // (regex).
ExcludeName(const std::string & name)1050 ConfigQuery& ExcludeName(const std::string& name) {
1051 excluded_names_.emplace_back(
1052 std::regex(name, std::regex_constants::ECMAScript));
1053 return *this;
1054 }
1055
Run() const1056 auto Run() const {
1057 static NoDestruct<std::vector<CoreTestConfiguration>> kConfigs(
1058 AllConfigs());
1059 std::vector<const CoreTestConfiguration*> out;
1060 for (const CoreTestConfiguration& config : *kConfigs) {
1061 if ((config.feature_mask & enforce_features_) == enforce_features_ &&
1062 (config.feature_mask & exclude_features_) == 0) {
1063 bool allowed = allowed_names_.empty();
1064 for (const std::regex& re : allowed_names_) {
1065 if (std::regex_match(config.name, re)) {
1066 allowed = true;
1067 break;
1068 }
1069 }
1070 for (const std::regex& re : excluded_names_) {
1071 if (std::regex_match(config.name, re)) {
1072 allowed = false;
1073 break;
1074 }
1075 }
1076 if (allowed) {
1077 out.push_back(&config);
1078 }
1079 }
1080 }
1081 return out;
1082 }
1083
1084 private:
1085 uint32_t enforce_features_ = 0;
1086 uint32_t exclude_features_ = 0;
1087 std::vector<std::regex> allowed_names_;
1088 std::vector<std::regex> excluded_names_;
1089 };
1090
1091 CORE_END2END_TEST_SUITE(CoreEnd2endTest, ConfigQuery().Run());
1092
1093 CORE_END2END_TEST_SUITE(
1094 SecureEnd2endTest,
1095 ConfigQuery().EnforceFeatures(FEATURE_MASK_IS_SECURE).Run());
1096
1097 CORE_END2END_TEST_SUITE(CoreLargeSendTest,
1098 ConfigQuery()
1099 .ExcludeFeatures(FEATURE_MASK_1BYTE_AT_A_TIME |
1100 FEATURE_MASK_ENABLES_TRACES)
1101 .Run());
1102
1103 CORE_END2END_TEST_SUITE(
1104 CoreDeadlineTest,
1105 ConfigQuery().ExcludeFeatures(FEATURE_MASK_IS_MINSTACK).Run());
1106
1107 CORE_END2END_TEST_SUITE(
1108 CoreDeadlineSingleHopTest,
1109 ConfigQuery()
1110 .ExcludeFeatures(FEATURE_MASK_SUPPORTS_REQUEST_PROXYING |
1111 FEATURE_MASK_IS_MINSTACK)
1112 .Run());
1113
1114 CORE_END2END_TEST_SUITE(
1115 CoreClientChannelTest,
1116 ConfigQuery().EnforceFeatures(FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL).Run());
1117
1118 CORE_END2END_TEST_SUITE(
1119 Http2SingleHopTest,
1120 ConfigQuery()
1121 .EnforceFeatures(FEATURE_MASK_IS_HTTP2)
1122 .ExcludeFeatures(FEATURE_MASK_SUPPORTS_REQUEST_PROXYING |
1123 FEATURE_MASK_ENABLES_TRACES)
1124 .Run());
1125
1126 CORE_END2END_TEST_SUITE(
1127 Http2FullstackSingleHopTest,
1128 ConfigQuery()
1129 .EnforceFeatures(FEATURE_MASK_IS_HTTP2)
1130 .EnforceFeatures(FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL)
1131 .ExcludeFeatures(FEATURE_MASK_SUPPORTS_REQUEST_PROXYING)
1132 .Run());
1133
1134 CORE_END2END_TEST_SUITE(
1135 RetryTest, ConfigQuery()
1136 .EnforceFeatures(FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL)
1137 .ExcludeFeatures(FEATURE_MASK_DOES_NOT_SUPPORT_RETRY)
1138 .Run());
1139
1140 CORE_END2END_TEST_SUITE(
1141 WriteBufferingTest,
1142 ConfigQuery()
1143 .ExcludeFeatures(FEATURE_MASK_DOES_NOT_SUPPORT_WRITE_BUFFERING)
1144 .Run());
1145
1146 CORE_END2END_TEST_SUITE(
1147 Http2Test, ConfigQuery().EnforceFeatures(FEATURE_MASK_IS_HTTP2).Run());
1148
1149 CORE_END2END_TEST_SUITE(
1150 RetryHttp2Test, ConfigQuery()
1151 .EnforceFeatures(FEATURE_MASK_IS_HTTP2 |
1152 FEATURE_MASK_SUPPORTS_CLIENT_CHANNEL)
1153 .ExcludeFeatures(FEATURE_MASK_DOES_NOT_SUPPORT_RETRY |
1154 FEATURE_MASK_SUPPORTS_REQUEST_PROXYING)
1155 .Run());
1156
1157 CORE_END2END_TEST_SUITE(
1158 ResourceQuotaTest,
1159 ConfigQuery()
1160 .ExcludeFeatures(FEATURE_MASK_SUPPORTS_REQUEST_PROXYING |
1161 FEATURE_MASK_1BYTE_AT_A_TIME)
1162 .ExcludeName("Chttp2.*Uds.*")
1163 .ExcludeName("Chttp2HttpProxy")
1164 .Run());
1165
1166 CORE_END2END_TEST_SUITE(
1167 PerCallCredsTest,
1168 ConfigQuery()
1169 .EnforceFeatures(FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS)
1170 .Run());
1171
1172 CORE_END2END_TEST_SUITE(
1173 PerCallCredsOnInsecureTest,
1174 ConfigQuery()
1175 .EnforceFeatures(
1176 FEATURE_MASK_SUPPORTS_PER_CALL_CREDENTIALS_LEVEL_INSECURE)
1177 .Run());
1178
1179 CORE_END2END_TEST_SUITE(
1180 NoLoggingTest,
1181 ConfigQuery().ExcludeFeatures(FEATURE_MASK_ENABLES_TRACES).Run());
1182
1183 CORE_END2END_TEST_SUITE(ProxyAuthTest,
1184 ConfigQuery().AllowName("Chttp2HttpProxy").Run());
1185
EnsureSuitesLinked()1186 void EnsureSuitesLinked() {}
1187
1188 } // namespace grpc_core
1189