compressed_payload.cc 26 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701
  1. /*
  2. *
  3. * Copyright 2015 gRPC authors.
  4. *
  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
  8. *
  9. * http://www.apache.org/licenses/LICENSE-2.0
  10. *
  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.
  16. *
  17. */
  18. #include <stdio.h>
  19. #include <string.h>
  20. #include <string>
  21. #include "absl/strings/str_format.h"
  22. #include <grpc/byte_buffer.h>
  23. #include <grpc/byte_buffer_reader.h>
  24. #include <grpc/compression.h>
  25. #include <grpc/support/alloc.h>
  26. #include <grpc/support/log.h>
  27. #include <grpc/support/time.h>
  28. #include "src/core/lib/channel/channel_args.h"
  29. #include "src/core/lib/surface/call.h"
  30. #include "src/core/lib/surface/call_test_only.h"
  31. #include "test/core/compression/args_utils.h"
  32. #include "test/core/end2end/cq_verifier.h"
  33. #include "test/core/end2end/end2end_tests.h"
  34. static void* tag(intptr_t t) { return reinterpret_cast<void*>(t); }
  35. static grpc_end2end_test_fixture begin_test(
  36. grpc_end2end_test_config config, const char* test_name,
  37. const grpc_channel_args* client_args, const grpc_channel_args* server_args,
  38. bool decompress_in_core) {
  39. grpc_end2end_test_fixture f;
  40. gpr_log(GPR_INFO, "Running test: %s%s/%s", test_name,
  41. decompress_in_core ? "" : "_with_decompression_disabled",
  42. config.name);
  43. f = config.create_fixture(client_args, server_args);
  44. config.init_server(&f, server_args);
  45. config.init_client(&f, client_args);
  46. return f;
  47. }
  48. static gpr_timespec n_seconds_from_now(int n) {
  49. return grpc_timeout_seconds_to_deadline(n);
  50. }
  51. static gpr_timespec five_seconds_from_now(void) {
  52. return n_seconds_from_now(5);
  53. }
  54. static void drain_cq(grpc_completion_queue* cq) {
  55. grpc_event ev;
  56. do {
  57. ev = grpc_completion_queue_next(cq, five_seconds_from_now(), nullptr);
  58. } while (ev.type != GRPC_QUEUE_SHUTDOWN);
  59. }
  60. static void shutdown_server(grpc_end2end_test_fixture* f) {
  61. if (!f->server) return;
  62. grpc_server_shutdown_and_notify(f->server, f->shutdown_cq, tag(1000));
  63. GPR_ASSERT(grpc_completion_queue_pluck(f->shutdown_cq, tag(1000),
  64. grpc_timeout_seconds_to_deadline(5),
  65. nullptr)
  66. .type == GRPC_OP_COMPLETE);
  67. grpc_server_destroy(f->server);
  68. f->server = nullptr;
  69. }
  70. static void shutdown_client(grpc_end2end_test_fixture* f) {
  71. if (!f->client) return;
  72. grpc_channel_destroy(f->client);
  73. f->client = nullptr;
  74. }
  75. static void end_test(grpc_end2end_test_fixture* f) {
  76. shutdown_server(f);
  77. shutdown_client(f);
  78. grpc_completion_queue_shutdown(f->cq);
  79. drain_cq(f->cq);
  80. grpc_completion_queue_destroy(f->cq);
  81. grpc_completion_queue_destroy(f->shutdown_cq);
  82. }
  83. static void request_for_disabled_algorithm(
  84. grpc_end2end_test_config config, const char* test_name,
  85. uint32_t send_flags_bitmask,
  86. grpc_compression_algorithm algorithm_to_disable,
  87. grpc_compression_algorithm requested_client_compression_algorithm,
  88. grpc_status_code expected_error, grpc_metadata* client_metadata,
  89. bool decompress_in_core) {
  90. grpc_call* c;
  91. grpc_call* s;
  92. grpc_slice request_payload_slice;
  93. grpc_byte_buffer* request_payload;
  94. const grpc_channel_args* client_args;
  95. const grpc_channel_args* server_args;
  96. grpc_end2end_test_fixture f;
  97. grpc_op ops[6];
  98. grpc_op* op;
  99. grpc_metadata_array initial_metadata_recv;
  100. grpc_metadata_array trailing_metadata_recv;
  101. grpc_metadata_array request_metadata_recv;
  102. grpc_byte_buffer* request_payload_recv = nullptr;
  103. grpc_call_details call_details;
  104. grpc_status_code status;
  105. grpc_call_error error;
  106. grpc_slice details;
  107. int was_cancelled = 2;
  108. cq_verifier* cqv;
  109. char str[1024];
  110. memset(str, 'x', 1023);
  111. str[1023] = '\0';
  112. request_payload_slice = grpc_slice_from_copied_string(str);
  113. request_payload = grpc_raw_byte_buffer_create(&request_payload_slice, 1);
  114. client_args = grpc_channel_args_set_channel_default_compression_algorithm(
  115. nullptr, requested_client_compression_algorithm);
  116. server_args = grpc_channel_args_set_channel_default_compression_algorithm(
  117. nullptr, GRPC_COMPRESS_NONE);
  118. server_args = grpc_channel_args_compression_algorithm_set_state(
  119. &server_args, algorithm_to_disable, false);
  120. if (!decompress_in_core) {
  121. grpc_arg disable_decompression_in_core_arg =
  122. grpc_channel_arg_integer_create(
  123. const_cast<char*>(GRPC_ARG_ENABLE_PER_MESSAGE_DECOMPRESSION), 0);
  124. const grpc_channel_args* old_client_args = client_args;
  125. const grpc_channel_args* old_server_args = server_args;
  126. client_args = grpc_channel_args_copy_and_add(
  127. client_args, &disable_decompression_in_core_arg, 1);
  128. server_args = grpc_channel_args_copy_and_add(
  129. server_args, &disable_decompression_in_core_arg, 1);
  130. grpc_channel_args_destroy(old_client_args);
  131. grpc_channel_args_destroy(old_server_args);
  132. }
  133. f = begin_test(config, test_name, client_args, server_args,
  134. decompress_in_core);
  135. cqv = cq_verifier_create(f.cq);
  136. gpr_timespec deadline = five_seconds_from_now();
  137. c = grpc_channel_create_call(f.client, nullptr, GRPC_PROPAGATE_DEFAULTS, f.cq,
  138. grpc_slice_from_static_string("/foo"), nullptr,
  139. deadline, nullptr);
  140. GPR_ASSERT(c);
  141. grpc_metadata_array_init(&initial_metadata_recv);
  142. grpc_metadata_array_init(&trailing_metadata_recv);
  143. grpc_metadata_array_init(&request_metadata_recv);
  144. grpc_call_details_init(&call_details);
  145. error =
  146. grpc_server_request_call(f.server, &s, &call_details,
  147. &request_metadata_recv, f.cq, f.cq, tag(101));
  148. GPR_ASSERT(GRPC_CALL_OK == error);
  149. memset(ops, 0, sizeof(ops));
  150. op = ops;
  151. op->op = GRPC_OP_SEND_INITIAL_METADATA;
  152. if (client_metadata != nullptr) {
  153. op->data.send_initial_metadata.count = 1;
  154. op->data.send_initial_metadata.metadata = client_metadata;
  155. } else {
  156. op->data.send_initial_metadata.count = 0;
  157. }
  158. op->flags = 0;
  159. op->reserved = nullptr;
  160. op++;
  161. op->op = GRPC_OP_SEND_MESSAGE;
  162. op->data.send_message.send_message = request_payload;
  163. op->flags = send_flags_bitmask;
  164. op->reserved = nullptr;
  165. op++;
  166. op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
  167. op->flags = 0;
  168. op->reserved = nullptr;
  169. op++;
  170. op->op = GRPC_OP_RECV_INITIAL_METADATA;
  171. op->data.recv_initial_metadata.recv_initial_metadata = &initial_metadata_recv;
  172. op->flags = 0;
  173. op->reserved = nullptr;
  174. op++;
  175. op->op = GRPC_OP_RECV_STATUS_ON_CLIENT;
  176. op->data.recv_status_on_client.trailing_metadata = &trailing_metadata_recv;
  177. op->data.recv_status_on_client.status = &status;
  178. op->data.recv_status_on_client.status_details = &details;
  179. op->flags = 0;
  180. op->reserved = nullptr;
  181. op++;
  182. error = grpc_call_start_batch(c, ops, static_cast<size_t>(op - ops), tag(1),
  183. nullptr);
  184. GPR_ASSERT(GRPC_CALL_OK == error);
  185. CQ_EXPECT_COMPLETION(cqv, tag(101), true);
  186. CQ_EXPECT_COMPLETION(cqv, tag(1), true);
  187. cq_verify(cqv);
  188. op = ops;
  189. op->op = GRPC_OP_SEND_INITIAL_METADATA;
  190. op->data.send_initial_metadata.count = 0;
  191. op->flags = 0;
  192. op->reserved = nullptr;
  193. op++;
  194. op->op = GRPC_OP_RECV_MESSAGE;
  195. op->data.recv_message.recv_message = &request_payload_recv;
  196. op->flags = 0;
  197. op->reserved = nullptr;
  198. op++;
  199. error = grpc_call_start_batch(s, ops, static_cast<size_t>(op - ops), tag(102),
  200. nullptr);
  201. GPR_ASSERT(GRPC_CALL_OK == error);
  202. CQ_EXPECT_COMPLETION(cqv, tag(102), false);
  203. op = ops;
  204. op->op = GRPC_OP_RECV_CLOSE_ON_SERVER;
  205. op->data.recv_close_on_server.cancelled = &was_cancelled;
  206. op->flags = 0;
  207. op->reserved = nullptr;
  208. op++;
  209. error = grpc_call_start_batch(s, ops, static_cast<size_t>(op - ops), tag(103),
  210. nullptr);
  211. GPR_ASSERT(GRPC_CALL_OK == error);
  212. CQ_EXPECT_COMPLETION(cqv, tag(103), true);
  213. cq_verify(cqv);
  214. /* call was cancelled (closed) ... */
  215. GPR_ASSERT(was_cancelled != 0);
  216. /* with a certain error */
  217. GPR_ASSERT(status == expected_error);
  218. const char* algo_name = nullptr;
  219. GPR_ASSERT(grpc_compression_algorithm_name(algorithm_to_disable, &algo_name));
  220. std::string expected_details =
  221. absl::StrFormat("Compression algorithm '%s' is disabled.", algo_name);
  222. /* and we expect a specific reason for it */
  223. GPR_ASSERT(0 == grpc_slice_str_cmp(details, expected_details.c_str()));
  224. GPR_ASSERT(0 == grpc_slice_str_cmp(call_details.method, "/foo"));
  225. grpc_slice_unref(details);
  226. grpc_metadata_array_destroy(&initial_metadata_recv);
  227. grpc_metadata_array_destroy(&trailing_metadata_recv);
  228. grpc_metadata_array_destroy(&request_metadata_recv);
  229. grpc_call_details_destroy(&call_details);
  230. grpc_call_unref(c);
  231. grpc_call_unref(s);
  232. cq_verifier_destroy(cqv);
  233. grpc_slice_unref(request_payload_slice);
  234. grpc_byte_buffer_destroy(request_payload);
  235. grpc_byte_buffer_destroy(request_payload_recv);
  236. grpc_channel_args_destroy(client_args);
  237. grpc_channel_args_destroy(server_args);
  238. end_test(&f);
  239. config.tear_down_data(&f);
  240. }
  241. static void request_with_payload_template_inner(
  242. grpc_end2end_test_config config, const char* test_name,
  243. uint32_t client_send_flags_bitmask,
  244. grpc_compression_algorithm default_client_channel_compression_algorithm,
  245. grpc_compression_algorithm default_server_channel_compression_algorithm,
  246. grpc_compression_algorithm expected_algorithm_from_client,
  247. grpc_compression_algorithm expected_algorithm_from_server,
  248. grpc_metadata* client_init_metadata, bool set_server_level,
  249. grpc_compression_level server_compression_level,
  250. bool send_message_before_initial_metadata, bool decompress_in_core) {
  251. grpc_call* c;
  252. grpc_call* s;
  253. grpc_slice request_payload_slice;
  254. grpc_byte_buffer* request_payload = nullptr;
  255. const grpc_channel_args* client_args;
  256. const grpc_channel_args* server_args;
  257. grpc_end2end_test_fixture f;
  258. grpc_op ops[6];
  259. grpc_op* op;
  260. grpc_metadata_array initial_metadata_recv;
  261. grpc_metadata_array trailing_metadata_recv;
  262. grpc_metadata_array request_metadata_recv;
  263. grpc_byte_buffer* request_payload_recv = nullptr;
  264. grpc_byte_buffer* response_payload;
  265. grpc_byte_buffer* response_payload_recv;
  266. grpc_call_details call_details;
  267. grpc_status_code status;
  268. grpc_call_error error;
  269. grpc_slice details;
  270. int was_cancelled = 2;
  271. cq_verifier* cqv;
  272. char request_str[1024];
  273. char response_str[1024];
  274. memset(request_str, 'x', 1023);
  275. request_str[1023] = '\0';
  276. memset(response_str, 'y', 1023);
  277. response_str[1023] = '\0';
  278. request_payload_slice = grpc_slice_from_copied_string(request_str);
  279. grpc_slice response_payload_slice =
  280. grpc_slice_from_copied_string(response_str);
  281. client_args = grpc_channel_args_set_channel_default_compression_algorithm(
  282. nullptr, default_client_channel_compression_algorithm);
  283. server_args = grpc_channel_args_set_channel_default_compression_algorithm(
  284. nullptr, default_server_channel_compression_algorithm);
  285. if (!decompress_in_core) {
  286. grpc_arg disable_decompression_in_core_arg =
  287. grpc_channel_arg_integer_create(
  288. const_cast<char*>(GRPC_ARG_ENABLE_PER_MESSAGE_DECOMPRESSION), 0);
  289. const grpc_channel_args* old_client_args = client_args;
  290. const grpc_channel_args* old_server_args = server_args;
  291. client_args = grpc_channel_args_copy_and_add(
  292. client_args, &disable_decompression_in_core_arg, 1);
  293. server_args = grpc_channel_args_copy_and_add(
  294. server_args, &disable_decompression_in_core_arg, 1);
  295. grpc_channel_args_destroy(old_client_args);
  296. grpc_channel_args_destroy(old_server_args);
  297. }
  298. f = begin_test(config, test_name, client_args, server_args,
  299. decompress_in_core);
  300. cqv = cq_verifier_create(f.cq);
  301. gpr_timespec deadline = five_seconds_from_now();
  302. c = grpc_channel_create_call(f.client, nullptr, GRPC_PROPAGATE_DEFAULTS, f.cq,
  303. grpc_slice_from_static_string("/foo"), nullptr,
  304. deadline, nullptr);
  305. GPR_ASSERT(c);
  306. grpc_metadata_array_init(&initial_metadata_recv);
  307. grpc_metadata_array_init(&trailing_metadata_recv);
  308. grpc_metadata_array_init(&request_metadata_recv);
  309. grpc_call_details_init(&call_details);
  310. if (send_message_before_initial_metadata) {
  311. request_payload = grpc_raw_byte_buffer_create(&request_payload_slice, 1);
  312. memset(ops, 0, sizeof(ops));
  313. op = ops;
  314. op->op = GRPC_OP_SEND_MESSAGE;
  315. op->data.send_message.send_message = request_payload;
  316. op->flags = client_send_flags_bitmask;
  317. op->reserved = nullptr;
  318. op++;
  319. error = grpc_call_start_batch(c, ops, static_cast<size_t>(op - ops), tag(2),
  320. nullptr);
  321. GPR_ASSERT(GRPC_CALL_OK == error);
  322. CQ_EXPECT_COMPLETION(cqv, tag(2), true);
  323. }
  324. memset(ops, 0, sizeof(ops));
  325. op = ops;
  326. op->op = GRPC_OP_SEND_INITIAL_METADATA;
  327. if (client_init_metadata != nullptr) {
  328. op->data.send_initial_metadata.count = 1;
  329. op->data.send_initial_metadata.metadata = client_init_metadata;
  330. } else {
  331. op->data.send_initial_metadata.count = 0;
  332. }
  333. op->flags = 0;
  334. op->reserved = nullptr;
  335. op++;
  336. op->op = GRPC_OP_RECV_INITIAL_METADATA;
  337. op->data.recv_initial_metadata.recv_initial_metadata = &initial_metadata_recv;
  338. op->flags = 0;
  339. op->reserved = nullptr;
  340. op++;
  341. op->op = GRPC_OP_RECV_STATUS_ON_CLIENT;
  342. op->data.recv_status_on_client.trailing_metadata = &trailing_metadata_recv;
  343. op->data.recv_status_on_client.status = &status;
  344. op->data.recv_status_on_client.status_details = &details;
  345. op->flags = 0;
  346. op->reserved = nullptr;
  347. op++;
  348. error = grpc_call_start_batch(c, ops, static_cast<size_t>(op - ops), tag(1),
  349. nullptr);
  350. GPR_ASSERT(GRPC_CALL_OK == error);
  351. error =
  352. grpc_server_request_call(f.server, &s, &call_details,
  353. &request_metadata_recv, f.cq, f.cq, tag(100));
  354. GPR_ASSERT(GRPC_CALL_OK == error);
  355. CQ_EXPECT_COMPLETION(cqv, tag(100), true);
  356. cq_verify(cqv);
  357. GPR_ASSERT(grpc_core::BitCount(
  358. grpc_call_test_only_get_encodings_accepted_by_peer(s)) ==
  359. GRPC_COMPRESS_ALGORITHMS_COUNT);
  360. GPR_ASSERT(
  361. grpc_core::GetBit(grpc_call_test_only_get_encodings_accepted_by_peer(s),
  362. GRPC_COMPRESS_NONE) != 0);
  363. GPR_ASSERT(
  364. grpc_core::GetBit(grpc_call_test_only_get_encodings_accepted_by_peer(s),
  365. GRPC_COMPRESS_DEFLATE) != 0);
  366. GPR_ASSERT(
  367. grpc_core::GetBit(grpc_call_test_only_get_encodings_accepted_by_peer(s),
  368. GRPC_COMPRESS_GZIP) != 0);
  369. memset(ops, 0, sizeof(ops));
  370. op = ops;
  371. op->op = GRPC_OP_SEND_INITIAL_METADATA;
  372. op->data.send_initial_metadata.count = 0;
  373. if (set_server_level) {
  374. op->data.send_initial_metadata.maybe_compression_level.is_set = true;
  375. op->data.send_initial_metadata.maybe_compression_level.level =
  376. server_compression_level;
  377. }
  378. op->flags = 0;
  379. op->reserved = nullptr;
  380. op++;
  381. op->op = GRPC_OP_RECV_CLOSE_ON_SERVER;
  382. op->data.recv_close_on_server.cancelled = &was_cancelled;
  383. op->flags = 0;
  384. op->reserved = nullptr;
  385. op++;
  386. error = grpc_call_start_batch(s, ops, static_cast<size_t>(op - ops), tag(101),
  387. nullptr);
  388. GPR_ASSERT(GRPC_CALL_OK == error);
  389. for (int i = 0; i < 2; i++) {
  390. response_payload = grpc_raw_byte_buffer_create(&response_payload_slice, 1);
  391. if (i > 0 || !send_message_before_initial_metadata) {
  392. request_payload = grpc_raw_byte_buffer_create(&request_payload_slice, 1);
  393. memset(ops, 0, sizeof(ops));
  394. op = ops;
  395. op->op = GRPC_OP_SEND_MESSAGE;
  396. op->data.send_message.send_message = request_payload;
  397. op->flags = client_send_flags_bitmask;
  398. op->reserved = nullptr;
  399. op++;
  400. error = grpc_call_start_batch(c, ops, static_cast<size_t>(op - ops),
  401. tag(2), nullptr);
  402. GPR_ASSERT(GRPC_CALL_OK == error);
  403. CQ_EXPECT_COMPLETION(cqv, tag(2), 1);
  404. }
  405. memset(ops, 0, sizeof(ops));
  406. op = ops;
  407. op->op = GRPC_OP_RECV_MESSAGE;
  408. op->data.recv_message.recv_message = &request_payload_recv;
  409. op->flags = 0;
  410. op->reserved = nullptr;
  411. op++;
  412. error = grpc_call_start_batch(s, ops, static_cast<size_t>(op - ops),
  413. tag(102), nullptr);
  414. GPR_ASSERT(GRPC_CALL_OK == error);
  415. CQ_EXPECT_COMPLETION(cqv, tag(102), 1);
  416. cq_verify(cqv);
  417. GPR_ASSERT(request_payload_recv->type == GRPC_BB_RAW);
  418. GPR_ASSERT(byte_buffer_eq_string(request_payload_recv, request_str));
  419. GPR_ASSERT(request_payload_recv->data.raw.compression ==
  420. (decompress_in_core ? GRPC_COMPRESS_NONE
  421. : expected_algorithm_from_client));
  422. memset(ops, 0, sizeof(ops));
  423. op = ops;
  424. op->op = GRPC_OP_SEND_MESSAGE;
  425. op->data.send_message.send_message = response_payload;
  426. op->flags = 0;
  427. op->reserved = nullptr;
  428. op++;
  429. error = grpc_call_start_batch(s, ops, static_cast<size_t>(op - ops),
  430. tag(103), nullptr);
  431. GPR_ASSERT(GRPC_CALL_OK == error);
  432. memset(ops, 0, sizeof(ops));
  433. op = ops;
  434. op->op = GRPC_OP_RECV_MESSAGE;
  435. op->data.recv_message.recv_message = &response_payload_recv;
  436. op->flags = 0;
  437. op->reserved = nullptr;
  438. op++;
  439. error = grpc_call_start_batch(c, ops, static_cast<size_t>(op - ops), tag(3),
  440. nullptr);
  441. GPR_ASSERT(GRPC_CALL_OK == error);
  442. CQ_EXPECT_COMPLETION(cqv, tag(103), 1);
  443. CQ_EXPECT_COMPLETION(cqv, tag(3), 1);
  444. cq_verify(cqv);
  445. GPR_ASSERT(response_payload_recv->type == GRPC_BB_RAW);
  446. GPR_ASSERT(byte_buffer_eq_string(response_payload_recv, response_str));
  447. if (server_compression_level > GRPC_COMPRESS_LEVEL_NONE) {
  448. const grpc_compression_algorithm algo_for_server_level =
  449. grpc_call_compression_for_level(s, server_compression_level);
  450. GPR_ASSERT(
  451. response_payload_recv->data.raw.compression ==
  452. (decompress_in_core ? GRPC_COMPRESS_NONE : algo_for_server_level));
  453. } else {
  454. GPR_ASSERT(response_payload_recv->data.raw.compression ==
  455. (decompress_in_core ? GRPC_COMPRESS_NONE
  456. : expected_algorithm_from_server));
  457. }
  458. grpc_byte_buffer_destroy(request_payload);
  459. grpc_byte_buffer_destroy(response_payload);
  460. grpc_byte_buffer_destroy(request_payload_recv);
  461. grpc_byte_buffer_destroy(response_payload_recv);
  462. }
  463. grpc_slice_unref(request_payload_slice);
  464. grpc_slice_unref(response_payload_slice);
  465. memset(ops, 0, sizeof(ops));
  466. op = ops;
  467. op->op = GRPC_OP_SEND_CLOSE_FROM_CLIENT;
  468. op->flags = 0;
  469. op->reserved = nullptr;
  470. op++;
  471. error = grpc_call_start_batch(c, ops, static_cast<size_t>(op - ops), tag(4),
  472. nullptr);
  473. GPR_ASSERT(GRPC_CALL_OK == error);
  474. memset(ops, 0, sizeof(ops));
  475. op = ops;
  476. op->op = GRPC_OP_SEND_STATUS_FROM_SERVER;
  477. op->data.send_status_from_server.trailing_metadata_count = 0;
  478. op->data.send_status_from_server.status = GRPC_STATUS_OK;
  479. grpc_slice status_details = grpc_slice_from_static_string("xyz");
  480. op->data.send_status_from_server.status_details = &status_details;
  481. op->flags = 0;
  482. op->reserved = nullptr;
  483. op++;
  484. error = grpc_call_start_batch(s, ops, static_cast<size_t>(op - ops), tag(104),
  485. nullptr);
  486. GPR_ASSERT(GRPC_CALL_OK == error);
  487. CQ_EXPECT_COMPLETION(cqv, tag(1), 1);
  488. CQ_EXPECT_COMPLETION(cqv, tag(4), 1);
  489. CQ_EXPECT_COMPLETION(cqv, tag(101), 1);
  490. CQ_EXPECT_COMPLETION(cqv, tag(104), 1);
  491. cq_verify(cqv);
  492. GPR_ASSERT(status == GRPC_STATUS_OK);
  493. GPR_ASSERT(0 == grpc_slice_str_cmp(details, "xyz"));
  494. GPR_ASSERT(0 == grpc_slice_str_cmp(call_details.method, "/foo"));
  495. GPR_ASSERT(was_cancelled == 0);
  496. grpc_slice_unref(details);
  497. grpc_metadata_array_destroy(&initial_metadata_recv);
  498. grpc_metadata_array_destroy(&trailing_metadata_recv);
  499. grpc_metadata_array_destroy(&request_metadata_recv);
  500. grpc_call_details_destroy(&call_details);
  501. grpc_call_unref(c);
  502. grpc_call_unref(s);
  503. cq_verifier_destroy(cqv);
  504. grpc_channel_args_destroy(client_args);
  505. grpc_channel_args_destroy(server_args);
  506. end_test(&f);
  507. config.tear_down_data(&f);
  508. }
  509. static void request_with_payload_template(
  510. grpc_end2end_test_config config, const char* test_name,
  511. uint32_t client_send_flags_bitmask,
  512. grpc_compression_algorithm default_client_channel_compression_algorithm,
  513. grpc_compression_algorithm default_server_channel_compression_algorithm,
  514. grpc_compression_algorithm expected_algorithm_from_client,
  515. grpc_compression_algorithm expected_algorithm_from_server,
  516. grpc_metadata* client_init_metadata, bool set_server_level,
  517. grpc_compression_level server_compression_level,
  518. bool send_message_before_initial_metadata) {
  519. request_with_payload_template_inner(
  520. config, test_name, client_send_flags_bitmask,
  521. default_client_channel_compression_algorithm,
  522. default_server_channel_compression_algorithm,
  523. expected_algorithm_from_client, expected_algorithm_from_server,
  524. client_init_metadata, set_server_level, server_compression_level,
  525. send_message_before_initial_metadata, false);
  526. request_with_payload_template_inner(
  527. config, test_name, client_send_flags_bitmask,
  528. default_client_channel_compression_algorithm,
  529. default_server_channel_compression_algorithm,
  530. expected_algorithm_from_client, expected_algorithm_from_server,
  531. client_init_metadata, set_server_level, server_compression_level,
  532. send_message_before_initial_metadata, true);
  533. }
  534. static void test_invoke_request_with_exceptionally_uncompressed_payload(
  535. grpc_end2end_test_config config) {
  536. request_with_payload_template(
  537. config, "test_invoke_request_with_exceptionally_uncompressed_payload",
  538. GRPC_WRITE_NO_COMPRESS, GRPC_COMPRESS_GZIP, GRPC_COMPRESS_GZIP,
  539. GRPC_COMPRESS_NONE, GRPC_COMPRESS_GZIP, nullptr, false,
  540. /* ignored */ GRPC_COMPRESS_LEVEL_NONE, false);
  541. }
  542. static void test_invoke_request_with_uncompressed_payload(
  543. grpc_end2end_test_config config) {
  544. request_with_payload_template(
  545. config, "test_invoke_request_with_uncompressed_payload", 0,
  546. GRPC_COMPRESS_NONE, GRPC_COMPRESS_NONE, GRPC_COMPRESS_NONE,
  547. GRPC_COMPRESS_NONE, nullptr, false,
  548. /* ignored */ GRPC_COMPRESS_LEVEL_NONE, false);
  549. }
  550. static void test_invoke_request_with_compressed_payload(
  551. grpc_end2end_test_config config) {
  552. request_with_payload_template(
  553. config, "test_invoke_request_with_compressed_payload", 0,
  554. GRPC_COMPRESS_GZIP, GRPC_COMPRESS_GZIP, GRPC_COMPRESS_GZIP,
  555. GRPC_COMPRESS_GZIP, nullptr, false,
  556. /* ignored */ GRPC_COMPRESS_LEVEL_NONE, false);
  557. }
  558. static void test_invoke_request_with_send_message_before_initial_metadata(
  559. grpc_end2end_test_config config) {
  560. request_with_payload_template(
  561. config, "test_invoke_request_with_compressed_payload", 0,
  562. GRPC_COMPRESS_GZIP, GRPC_COMPRESS_GZIP, GRPC_COMPRESS_GZIP,
  563. GRPC_COMPRESS_GZIP, nullptr, false,
  564. /* ignored */ GRPC_COMPRESS_LEVEL_NONE, true);
  565. }
  566. static void test_invoke_request_with_server_level(
  567. grpc_end2end_test_config config) {
  568. request_with_payload_template(
  569. config, "test_invoke_request_with_server_level", 0, GRPC_COMPRESS_NONE,
  570. GRPC_COMPRESS_NONE, GRPC_COMPRESS_NONE, GRPC_COMPRESS_NONE /* ignored */,
  571. nullptr, true, GRPC_COMPRESS_LEVEL_HIGH, false);
  572. }
  573. static void test_invoke_request_with_compressed_payload_md_override(
  574. grpc_end2end_test_config config) {
  575. grpc_metadata gzip_compression_override;
  576. grpc_metadata identity_compression_override;
  577. gzip_compression_override.key =
  578. grpc_slice_from_static_string("grpc-internal-encoding-request");
  579. gzip_compression_override.value = grpc_slice_from_static_string("gzip");
  580. memset(&gzip_compression_override.internal_data, 0,
  581. sizeof(gzip_compression_override.internal_data));
  582. identity_compression_override.key =
  583. grpc_slice_from_static_string("grpc-internal-encoding-request");
  584. identity_compression_override.value =
  585. grpc_slice_from_static_string("identity");
  586. memset(&identity_compression_override.internal_data, 0,
  587. sizeof(identity_compression_override.internal_data));
  588. /* Channel default NONE (aka IDENTITY), call override to GZIP */
  589. request_with_payload_template(
  590. config, "test_invoke_request_with_compressed_payload_md_override_1", 0,
  591. GRPC_COMPRESS_NONE, GRPC_COMPRESS_NONE, GRPC_COMPRESS_GZIP,
  592. GRPC_COMPRESS_NONE, &gzip_compression_override, false,
  593. /*ignored*/ GRPC_COMPRESS_LEVEL_NONE, false);
  594. /* Channel default DEFLATE, call override to GZIP */
  595. request_with_payload_template(
  596. config, "test_invoke_request_with_compressed_payload_md_override_2", 0,
  597. GRPC_COMPRESS_DEFLATE, GRPC_COMPRESS_NONE, GRPC_COMPRESS_GZIP,
  598. GRPC_COMPRESS_NONE, &gzip_compression_override, false,
  599. /*ignored*/ GRPC_COMPRESS_LEVEL_NONE, false);
  600. /* Channel default DEFLATE, call override to NONE (aka IDENTITY) */
  601. request_with_payload_template(
  602. config, "test_invoke_request_with_compressed_payload_md_override_3", 0,
  603. GRPC_COMPRESS_DEFLATE, GRPC_COMPRESS_NONE, GRPC_COMPRESS_NONE,
  604. GRPC_COMPRESS_NONE, &identity_compression_override, false,
  605. /*ignored*/ GRPC_COMPRESS_LEVEL_NONE, false);
  606. }
  607. static void test_invoke_request_with_disabled_algorithm(
  608. grpc_end2end_test_config config) {
  609. request_for_disabled_algorithm(config,
  610. "test_invoke_request_with_disabled_algorithm",
  611. 0, GRPC_COMPRESS_GZIP, GRPC_COMPRESS_GZIP,
  612. GRPC_STATUS_UNIMPLEMENTED, nullptr, false);
  613. request_for_disabled_algorithm(config,
  614. "test_invoke_request_with_disabled_algorithm",
  615. 0, GRPC_COMPRESS_GZIP, GRPC_COMPRESS_GZIP,
  616. GRPC_STATUS_UNIMPLEMENTED, nullptr, true);
  617. }
  618. void compressed_payload(grpc_end2end_test_config config) {
  619. test_invoke_request_with_exceptionally_uncompressed_payload(config);
  620. test_invoke_request_with_uncompressed_payload(config);
  621. test_invoke_request_with_compressed_payload(config);
  622. test_invoke_request_with_send_message_before_initial_metadata(config);
  623. test_invoke_request_with_server_level(config);
  624. test_invoke_request_with_compressed_payload_md_override(config);
  625. test_invoke_request_with_disabled_algorithm(config);
  626. }
  627. void compressed_payload_pre_init(void) {}