• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *
3  * Copyright 2017 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 
19 #ifndef GRPC_TEST_CORE_TSI_TRANSPORT_SECURITY_TEST_LIB_H_
20 #define GRPC_TEST_CORE_TSI_TRANSPORT_SECURITY_TEST_LIB_H_
21 
22 #include "src/core/tsi/transport_security_interface.h"
23 
24 #include <grpc/support/sync.h>
25 
26 #define TSI_TEST_TINY_HANDSHAKE_BUFFER_SIZE 32
27 #define TSI_TEST_SMALL_HANDSHAKE_BUFFER_SIZE 128
28 #define TSI_TEST_SMALL_READ_BUFFER_ALLOCATED_SIZE 41
29 #define TSI_TEST_SMALL_PROTECTED_BUFFER_SIZE 37
30 #define TSI_TEST_SMALL_MESSAGE_BUFFER_ALLOCATED_SIZE 42
31 #define TSI_TEST_SMALL_CLIENT_MAX_OUTPUT_PROTECTED_FRAME_SIZE 39
32 #define TSI_TEST_SMALL_SERVER_MAX_OUTPUT_PROTECTED_FRAME_SIZE 43
33 #define TSI_TEST_DEFAULT_BUFFER_SIZE 4096
34 #define TSI_TEST_DEFAULT_PROTECTED_BUFFER_SIZE 16384
35 #define TSI_TEST_DEFAULT_CHANNEL_SIZE 32768
36 #define TSI_TEST_BIG_MESSAGE_SIZE 17000
37 #define TSI_TEST_SMALL_MESSAGE_SIZE 10
38 #define TSI_TEST_NUM_OF_ARGUMENTS 7
39 #define TSI_TEST_NUM_OF_COMBINATIONS 128
40 #define TSI_TEST_UNUSED_BYTES "HELLO GOOGLE"
41 
42 /* ---  tsi_test_fixture object ---
43   The tests for specific TSI implementations should create their own
44   custom "subclass" of this fixture, which wraps all information
45   that will be used to test correctness of TSI handshakes and frame
46   protect/unprotect operations with respect to TSI implementations. */
47 typedef struct tsi_test_fixture tsi_test_fixture;
48 
49 /* ---  tsi_test_frame_protector_fixture object ---
50   The object wraps all necessary information used to test correctness of TSI
51   frame protector implementations. */
52 typedef struct tsi_test_frame_protector_fixture
53     tsi_test_frame_protector_fixture;
54 
55 /* ---  tsi_test_frame_protector_config object ---
56   This object is used to configure different parameters of TSI frame protector
57   APIs. */
58 typedef struct tsi_test_frame_protector_config tsi_test_frame_protector_config;
59 
60 /* ---  tsi_test_channel object ---
61   This object represents simulated channels between the client and server
62   from/to which they could read/write the exchanged information. */
63 typedef struct tsi_test_channel tsi_test_channel;
64 
65 /* V-table for tsi_test_fixture operations that are implemented differently in
66    different TSI implementations. */
67 typedef struct tsi_test_fixture_vtable {
68   void (*setup_handshakers)(tsi_test_fixture* fixture);
69   void (*check_handshaker_peers)(tsi_test_fixture* fixture);
70   void (*destruct)(tsi_test_fixture* fixture);
71 } tsi_test_fixture_vtable;
72 
73 struct tsi_test_fixture {
74   const tsi_test_fixture_vtable* vtable;
75   /* client/server TSI handshaker used to perform TSI handshakes, and will get
76      instantiated during the call to setup_handshakers. */
77   tsi_handshaker* client_handshaker;
78   tsi_handshaker* server_handshaker;
79   /* client/server TSI handshaker results used to store the result of TSI
80      handshake. If the handshake fails, the result will store NULL upon
81      finishing the handshake. */
82   tsi_handshaker_result* client_result;
83   tsi_handshaker_result* server_result;
84   /* size of buffer used to store data received from the peer. */
85   size_t handshake_buffer_size;
86   /* tsi_test_channel instance. */
87   tsi_test_channel* channel;
88   /* tsi_test_frame_protector_config instance */
89   tsi_test_frame_protector_config* config;
90   /* a flag indicating if client has finished TSI handshake first (i.e., before
91      server).
92      The flag should be referred if and only if TSI handshake finishes
93      successfully. */
94   bool has_client_finished_first;
95   /* a flag indicating whether to test tsi_handshaker_result_get_unused_bytes()
96      for TSI implementation. This field is true by default, and false
97      for SSL TSI implementation due to grpc issue #12164
98      (https://github.com/grpc/grpc/issues/12164).
99   */
100   bool test_unused_bytes;
101   /* These objects will be used coordinate client/server handshakers with TSI
102      thread to perform TSI handshakes in an asynchronous manner (for GTS TSI
103      implementations).
104   */
105   gpr_cv cv;
106   gpr_mu mu;
107   bool notified;
108 };
109 
110 struct tsi_test_frame_protector_fixture {
111   /* client/server TSI frame protectors whose ownership are transferred. */
112   tsi_frame_protector* client_frame_protector;
113   tsi_frame_protector* server_frame_protector;
114   /* tsi_test_channel instance. */
115   tsi_test_channel* channel;
116   /* tsi_test_frame_protector_config instance */
117   tsi_test_frame_protector_config* config;
118 };
119 
120 struct tsi_test_channel {
121   /* simulated channels between client and server. If the server (client)
122      wants to send data to the client (server), he will write data to
123      client_channel (server_channel), which will be read by client (server). */
124   uint8_t* client_channel;
125   uint8_t* server_channel;
126   /* size of data written to the client/server channel. */
127   size_t bytes_written_to_client_channel;
128   size_t bytes_written_to_server_channel;
129   /* size of data read from the client/server channel */
130   size_t bytes_read_from_client_channel;
131   size_t bytes_read_from_server_channel;
132 };
133 
134 struct tsi_test_frame_protector_config {
135   /* size of buffer used to store protected frames to be unprotected. */
136   size_t read_buffer_allocated_size;
137   /* size of buffer used to store bytes resulted from unprotect operations. */
138   size_t message_buffer_allocated_size;
139   /* size of buffer used to store frames resulted from protect operations. */
140   size_t protected_buffer_size;
141   /* size of client/server maximum frame size. */
142   size_t client_max_output_protected_frame_size;
143   size_t server_max_output_protected_frame_size;
144   /* pointer that points to client/server message to be protected. */
145   uint8_t* client_message;
146   uint8_t* server_message;
147   /* size of client/server message. */
148   size_t client_message_size;
149   size_t server_message_size;
150 };
151 
152 /* This method creates a tsi_test_frame_protector_config instance. Each
153    parameter of this function is a boolean value indicating whether to set the
154    corresponding parameter with a default value or not. If it's false, it will
155    be set with a specific value which is usually much smaller than the default.
156    Both values are defined with #define directive. */
157 tsi_test_frame_protector_config* tsi_test_frame_protector_config_create(
158     bool use_default_read_buffer_allocated_size,
159     bool use_default_message_buffer_allocated_size,
160     bool use_default_protected_buffer_size, bool use_default_client_message,
161     bool use_default_server_message,
162     bool use_default_client_max_output_protected_frame_size,
163     bool use_default_server_max_output_protected_frame_size);
164 
165 /* This method sets different buffer and frame sizes of a
166    tsi_test_frame_protector_config instance with user provided values. */
167 void tsi_test_frame_protector_config_set_buffer_size(
168     tsi_test_frame_protector_config* config, size_t read_buffer_allocated_size,
169     size_t message_buffer_allocated_size, size_t protected_buffer_size,
170     size_t client_max_output_protected_frame_size,
171     size_t server_max_output_protected_frame_size);
172 
173 /* This method destroys a tsi_test_frame_protector_config instance. */
174 void tsi_test_frame_protector_config_destroy(
175     tsi_test_frame_protector_config* config);
176 
177 /* This method initializes members of tsi_test_fixture instance.
178    Note that the struct instance should be allocated before making
179    this call. */
180 void tsi_test_fixture_init(tsi_test_fixture* fixture);
181 
182 /* This method destroys a tsi_test_fixture instance. Note that the
183    fixture intance must be dynamically allocated and will be freed by
184    this function. */
185 void tsi_test_fixture_destroy(tsi_test_fixture* fixture);
186 
187 /* This method creates a tsi_test_frame_protector_fixture instance. */
188 tsi_test_frame_protector_fixture* tsi_test_frame_protector_fixture_create();
189 
190 /* This method initializes members of tsi_test_frame_protector_fixture instance.
191    Note that the struct instance should be allocated before making
192    this call. */
193 void tsi_test_frame_protector_fixture_init(
194     tsi_test_frame_protector_fixture* fixture,
195     tsi_frame_protector* client_frame_protector,
196     tsi_frame_protector* server_frame_protector);
197 
198 /* This method destroys a tsi_test_frame_protector_fixture instance. Note that
199    the fixture intance must be dynamically allocated and will be freed by this
200    function. */
201 void tsi_test_frame_protector_fixture_destroy(
202     tsi_test_frame_protector_fixture* fixture);
203 
204 /* This method performs a protect opeation on raw data and sends the result to
205    peer. */
206 void tsi_test_frame_protector_send_message_to_peer(
207     tsi_test_frame_protector_config* config, tsi_test_channel* channel,
208     tsi_frame_protector* protector, bool is_client);
209 
210 /* This method receives message from peer and unprotects it. */
211 void tsi_test_frame_protector_receive_message_from_peer(
212     tsi_test_frame_protector_config* config, tsi_test_channel* channel,
213     tsi_frame_protector* protector, unsigned char* message,
214     size_t* bytes_received, bool is_client);
215 
216 /* This method performs a full TSI handshake between a client and a server.
217    Note that the test library will implement the new TSI handshaker API to
218    perform handshakes. */
219 void tsi_test_do_handshake(tsi_test_fixture* fixture);
220 
221 /* This method performs a round trip test between the client and the server.
222    That is, the client sends a protected message to a server who receives the
223    message, and unprotects it. The same operation is triggered again with
224    the client and server switching its role. */
225 void tsi_test_do_round_trip(tsi_test_fixture* fixture);
226 
227 /* This method performs the above round trip test without doing handshakes. */
228 void tsi_test_frame_protector_do_round_trip_no_handshake(
229     tsi_test_frame_protector_fixture* fixture);
230 
231 #endif  // GRPC_TEST_CORE_TSI_TRANSPORT_SECURITY_TEST_LIB_H_
232