security_connector_test.cc 31 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729
  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 "src/core/lib/security/security_connector/security_connector.h"
  19. #include <stdio.h>
  20. #include <string.h>
  21. #include <grpc/grpc_security.h>
  22. #include <grpc/support/alloc.h>
  23. #include <grpc/support/log.h>
  24. #include <grpc/support/string_util.h>
  25. #include "src/core/lib/gpr/string.h"
  26. #include "src/core/lib/gpr/tmpfile.h"
  27. #include "src/core/lib/gprpp/ref_counted_ptr.h"
  28. #include "src/core/lib/security/context/security_context.h"
  29. #include "src/core/lib/security/security_connector/ssl_utils.h"
  30. #include "src/core/lib/slice/slice_string_helpers.h"
  31. #include "src/core/tsi/ssl_transport_security.h"
  32. #include "src/core/tsi/transport_security.h"
  33. #include "test/core/util/test_config.h"
  34. #ifndef TSI_OPENSSL_ALPN_SUPPORT
  35. #define TSI_OPENSSL_ALPN_SUPPORT 1
  36. #endif
  37. static int check_peer_property(const tsi_peer* peer,
  38. const tsi_peer_property* expected) {
  39. size_t i;
  40. for (i = 0; i < peer->property_count; i++) {
  41. const tsi_peer_property* prop = &peer->properties[i];
  42. if ((strcmp(prop->name, expected->name) == 0) &&
  43. (prop->value.length == expected->value.length) &&
  44. (memcmp(prop->value.data, expected->value.data,
  45. expected->value.length) == 0)) {
  46. return 1;
  47. }
  48. }
  49. return 0; /* Not found... */
  50. }
  51. static int check_ssl_peer_equivalence(const tsi_peer* original,
  52. const tsi_peer* reconstructed) {
  53. /* The reconstructed peer only has CN, SAN and pem cert properties. */
  54. size_t i;
  55. for (i = 0; i < original->property_count; i++) {
  56. const tsi_peer_property* prop = &original->properties[i];
  57. if ((strcmp(prop->name, TSI_X509_SUBJECT_COMMON_NAME_PEER_PROPERTY) == 0) ||
  58. (strcmp(prop->name, TSI_X509_SUBJECT_ALTERNATIVE_NAME_PEER_PROPERTY) ==
  59. 0) ||
  60. (strcmp(prop->name, TSI_X509_PEM_CERT_PROPERTY) == 0)) {
  61. if (!check_peer_property(reconstructed, prop)) return 0;
  62. }
  63. }
  64. return 1;
  65. }
  66. static int check_property(const grpc_auth_context* ctx,
  67. const char* expected_property_name,
  68. const char* expected_property_value) {
  69. grpc_auth_property_iterator it =
  70. grpc_auth_context_find_properties_by_name(ctx, expected_property_name);
  71. const grpc_auth_property* prop = grpc_auth_property_iterator_next(&it);
  72. if (prop == nullptr) {
  73. gpr_log(GPR_ERROR, "Expected value %s not found.", expected_property_value);
  74. return 0;
  75. }
  76. if (strncmp(prop->value, expected_property_value, prop->value_length) != 0) {
  77. gpr_log(GPR_ERROR, "Expected value %s and got %s for property %s.",
  78. expected_property_value, prop->value, expected_property_name);
  79. return 0;
  80. }
  81. if (grpc_auth_property_iterator_next(&it) != nullptr) {
  82. gpr_log(GPR_ERROR, "Expected only one property for %s.",
  83. expected_property_name);
  84. return 0;
  85. }
  86. return 1;
  87. }
  88. static int check_properties(
  89. const grpc_auth_context* ctx, const char* expected_property_name,
  90. const std::vector<std::string>& expected_property_values) {
  91. grpc_auth_property_iterator it =
  92. grpc_auth_context_find_properties_by_name(ctx, expected_property_name);
  93. for (const auto& property_value : expected_property_values) {
  94. const grpc_auth_property* prop = grpc_auth_property_iterator_next(&it);
  95. if (prop == nullptr) {
  96. gpr_log(GPR_ERROR, "Expected value %s not found.",
  97. property_value.c_str());
  98. return 0;
  99. }
  100. if (strcmp(prop->name, expected_property_name) != 0) {
  101. gpr_log(GPR_ERROR, "Expected peer property name %s and got %s.",
  102. expected_property_name, prop->name);
  103. return 0;
  104. }
  105. if (strncmp(prop->value, property_value.c_str(), prop->value_length) != 0) {
  106. gpr_log(GPR_ERROR, "Expected peer property value %s and got %s.",
  107. property_value.c_str(), prop->value);
  108. return 0;
  109. }
  110. }
  111. if (grpc_auth_property_iterator_next(&it) != nullptr) {
  112. gpr_log(GPR_ERROR, "Expected only %zu property values.",
  113. expected_property_values.size());
  114. return 0;
  115. }
  116. return 1;
  117. }
  118. static int check_spiffe_id(const grpc_auth_context* ctx,
  119. const char* expected_spiffe_id,
  120. bool expect_spiffe_id) {
  121. grpc_auth_property_iterator it = grpc_auth_context_find_properties_by_name(
  122. ctx, GRPC_PEER_SPIFFE_ID_PROPERTY_NAME);
  123. const grpc_auth_property* prop = grpc_auth_property_iterator_next(&it);
  124. if (prop == nullptr && !expect_spiffe_id) {
  125. return 1;
  126. }
  127. if (prop != nullptr && !expect_spiffe_id) {
  128. gpr_log(GPR_ERROR, "SPIFFE ID not expected, but got %s.", prop->value);
  129. return 0;
  130. }
  131. if (prop == nullptr && expect_spiffe_id) {
  132. gpr_log(GPR_ERROR, "SPIFFE ID expected, but got nullptr.");
  133. return 0;
  134. }
  135. if (strncmp(prop->value, expected_spiffe_id, prop->value_length) != 0) {
  136. gpr_log(GPR_ERROR, "Expected SPIFFE ID %s but got %s.", expected_spiffe_id,
  137. prop->value);
  138. return 0;
  139. }
  140. if (grpc_auth_property_iterator_next(&it) != nullptr) {
  141. gpr_log(GPR_ERROR, "Expected only one property for SPIFFE ID.");
  142. return 0;
  143. }
  144. return 1;
  145. }
  146. static void test_unauthenticated_ssl_peer(void) {
  147. tsi_peer peer;
  148. tsi_peer rpeer;
  149. GPR_ASSERT(tsi_construct_peer(2, &peer) == TSI_OK);
  150. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  151. TSI_CERTIFICATE_TYPE_PEER_PROPERTY, TSI_X509_CERTIFICATE_TYPE,
  152. &peer.properties[0]) == TSI_OK);
  153. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  154. TSI_SECURITY_LEVEL_PEER_PROPERTY,
  155. tsi_security_level_to_string(TSI_PRIVACY_AND_INTEGRITY),
  156. &peer.properties[1]) == TSI_OK);
  157. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  158. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  159. GPR_ASSERT(ctx != nullptr);
  160. GPR_ASSERT(!grpc_auth_context_peer_is_authenticated(ctx.get()));
  161. GPR_ASSERT(check_property(ctx.get(),
  162. GRPC_TRANSPORT_SECURITY_TYPE_PROPERTY_NAME,
  163. GRPC_SSL_TRANSPORT_SECURITY_TYPE));
  164. rpeer = grpc_shallow_peer_from_ssl_auth_context(ctx.get());
  165. GPR_ASSERT(check_ssl_peer_equivalence(&peer, &rpeer));
  166. grpc_shallow_peer_destruct(&rpeer);
  167. tsi_peer_destruct(&peer);
  168. ctx.reset(DEBUG_LOCATION, "test");
  169. }
  170. static void test_cn_only_ssl_peer_to_auth_context(void) {
  171. tsi_peer peer;
  172. tsi_peer rpeer;
  173. const char* expected_cn = "cn1";
  174. const char* expected_pem_cert = "pem_cert1";
  175. const char* expected_pem_cert_chain = "pem_cert1_chain";
  176. GPR_ASSERT(tsi_construct_peer(5, &peer) == TSI_OK);
  177. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  178. TSI_CERTIFICATE_TYPE_PEER_PROPERTY, TSI_X509_CERTIFICATE_TYPE,
  179. &peer.properties[0]) == TSI_OK);
  180. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  181. TSI_X509_SUBJECT_COMMON_NAME_PEER_PROPERTY, expected_cn,
  182. &peer.properties[1]) == TSI_OK);
  183. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  184. TSI_X509_PEM_CERT_PROPERTY, expected_pem_cert,
  185. &peer.properties[2]) == TSI_OK);
  186. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  187. TSI_SECURITY_LEVEL_PEER_PROPERTY,
  188. tsi_security_level_to_string(TSI_PRIVACY_AND_INTEGRITY),
  189. &peer.properties[3]) == TSI_OK);
  190. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  191. TSI_X509_PEM_CERT_CHAIN_PROPERTY, expected_pem_cert_chain,
  192. &peer.properties[4]) == TSI_OK);
  193. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  194. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  195. GPR_ASSERT(ctx != nullptr);
  196. GPR_ASSERT(grpc_auth_context_peer_is_authenticated(ctx.get()));
  197. GPR_ASSERT(
  198. check_property(ctx.get(), GRPC_X509_CN_PROPERTY_NAME, expected_cn));
  199. GPR_ASSERT(check_property(ctx.get(),
  200. GRPC_TRANSPORT_SECURITY_TYPE_PROPERTY_NAME,
  201. GRPC_SSL_TRANSPORT_SECURITY_TYPE));
  202. GPR_ASSERT(
  203. check_property(ctx.get(), GRPC_X509_CN_PROPERTY_NAME, expected_cn));
  204. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_PROPERTY_NAME,
  205. expected_pem_cert));
  206. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_CHAIN_PROPERTY_NAME,
  207. expected_pem_cert_chain));
  208. rpeer = grpc_shallow_peer_from_ssl_auth_context(ctx.get());
  209. GPR_ASSERT(check_ssl_peer_equivalence(&peer, &rpeer));
  210. grpc_shallow_peer_destruct(&rpeer);
  211. tsi_peer_destruct(&peer);
  212. ctx.reset(DEBUG_LOCATION, "test");
  213. }
  214. static void test_cn_and_one_san_ssl_peer_to_auth_context(void) {
  215. tsi_peer peer;
  216. tsi_peer rpeer;
  217. const char* expected_cn = "cn1";
  218. const std::vector<std::string> expected_sans = {"san1"};
  219. const char* expected_pem_cert = "pem_cert1";
  220. const char* expected_pem_cert_chain = "pem_cert1_chain";
  221. GPR_ASSERT(tsi_construct_peer(6, &peer) == TSI_OK);
  222. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  223. TSI_CERTIFICATE_TYPE_PEER_PROPERTY, TSI_X509_CERTIFICATE_TYPE,
  224. &peer.properties[0]) == TSI_OK);
  225. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  226. TSI_X509_SUBJECT_COMMON_NAME_PEER_PROPERTY, expected_cn,
  227. &peer.properties[1]) == TSI_OK);
  228. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  229. TSI_X509_PEM_CERT_PROPERTY, expected_pem_cert,
  230. &peer.properties[2]) == TSI_OK);
  231. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  232. TSI_SECURITY_LEVEL_PEER_PROPERTY,
  233. tsi_security_level_to_string(TSI_PRIVACY_AND_INTEGRITY),
  234. &peer.properties[3]) == TSI_OK);
  235. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  236. TSI_X509_PEM_CERT_CHAIN_PROPERTY, expected_pem_cert_chain,
  237. &peer.properties[4]) == TSI_OK);
  238. for (size_t i = 0; i < expected_sans.size(); i++) {
  239. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  240. TSI_X509_SUBJECT_ALTERNATIVE_NAME_PEER_PROPERTY,
  241. expected_sans[i].c_str(),
  242. &peer.properties[5 + i]) == TSI_OK);
  243. }
  244. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  245. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  246. GPR_ASSERT(ctx != nullptr);
  247. GPR_ASSERT(grpc_auth_context_peer_is_authenticated(ctx.get()));
  248. GPR_ASSERT(
  249. check_properties(ctx.get(), GRPC_X509_SAN_PROPERTY_NAME, expected_sans));
  250. GPR_ASSERT(check_property(ctx.get(),
  251. GRPC_TRANSPORT_SECURITY_TYPE_PROPERTY_NAME,
  252. GRPC_SSL_TRANSPORT_SECURITY_TYPE));
  253. GPR_ASSERT(
  254. check_property(ctx.get(), GRPC_X509_CN_PROPERTY_NAME, expected_cn));
  255. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_PROPERTY_NAME,
  256. expected_pem_cert));
  257. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_CHAIN_PROPERTY_NAME,
  258. expected_pem_cert_chain));
  259. rpeer = grpc_shallow_peer_from_ssl_auth_context(ctx.get());
  260. GPR_ASSERT(check_ssl_peer_equivalence(&peer, &rpeer));
  261. grpc_shallow_peer_destruct(&rpeer);
  262. tsi_peer_destruct(&peer);
  263. ctx.reset(DEBUG_LOCATION, "test");
  264. }
  265. static void test_cn_and_multiple_sans_ssl_peer_to_auth_context(void) {
  266. tsi_peer peer;
  267. tsi_peer rpeer;
  268. const char* expected_cn = "cn1";
  269. const std::vector<std::string> expected_sans = {"san1", "san2", "san3"};
  270. const char* expected_pem_cert = "pem_cert1";
  271. const char* expected_pem_cert_chain = "pem_cert1_chain";
  272. size_t i;
  273. GPR_ASSERT(tsi_construct_peer(5 + expected_sans.size(), &peer) == TSI_OK);
  274. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  275. TSI_CERTIFICATE_TYPE_PEER_PROPERTY, TSI_X509_CERTIFICATE_TYPE,
  276. &peer.properties[0]) == TSI_OK);
  277. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  278. TSI_X509_SUBJECT_COMMON_NAME_PEER_PROPERTY, expected_cn,
  279. &peer.properties[1]) == TSI_OK);
  280. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  281. TSI_X509_PEM_CERT_PROPERTY, expected_pem_cert,
  282. &peer.properties[2]) == TSI_OK);
  283. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  284. TSI_SECURITY_LEVEL_PEER_PROPERTY,
  285. tsi_security_level_to_string(TSI_PRIVACY_AND_INTEGRITY),
  286. &peer.properties[3]) == TSI_OK);
  287. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  288. TSI_X509_PEM_CERT_CHAIN_PROPERTY, expected_pem_cert_chain,
  289. &peer.properties[4]) == TSI_OK);
  290. for (i = 0; i < expected_sans.size(); i++) {
  291. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  292. TSI_X509_SUBJECT_ALTERNATIVE_NAME_PEER_PROPERTY,
  293. expected_sans[i].c_str(),
  294. &peer.properties[5 + i]) == TSI_OK);
  295. }
  296. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  297. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  298. GPR_ASSERT(ctx != nullptr);
  299. GPR_ASSERT(grpc_auth_context_peer_is_authenticated(ctx.get()));
  300. GPR_ASSERT(
  301. check_properties(ctx.get(), GRPC_X509_SAN_PROPERTY_NAME, expected_sans));
  302. GPR_ASSERT(check_property(ctx.get(),
  303. GRPC_TRANSPORT_SECURITY_TYPE_PROPERTY_NAME,
  304. GRPC_SSL_TRANSPORT_SECURITY_TYPE));
  305. GPR_ASSERT(
  306. check_property(ctx.get(), GRPC_X509_CN_PROPERTY_NAME, expected_cn));
  307. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_PROPERTY_NAME,
  308. expected_pem_cert));
  309. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_CHAIN_PROPERTY_NAME,
  310. expected_pem_cert_chain));
  311. rpeer = grpc_shallow_peer_from_ssl_auth_context(ctx.get());
  312. GPR_ASSERT(check_ssl_peer_equivalence(&peer, &rpeer));
  313. grpc_shallow_peer_destruct(&rpeer);
  314. tsi_peer_destruct(&peer);
  315. ctx.reset(DEBUG_LOCATION, "test");
  316. }
  317. static void test_cn_and_multiple_sans_and_others_ssl_peer_to_auth_context(
  318. void) {
  319. tsi_peer peer;
  320. tsi_peer rpeer;
  321. const char* expected_cn = "cn1";
  322. const char* expected_pem_cert = "pem_cert1";
  323. const char* expected_pem_cert_chain = "pem_cert1_chain";
  324. const std::vector<std::string> expected_sans = {"san1", "san2", "san3"};
  325. size_t i;
  326. GPR_ASSERT(tsi_construct_peer(7 + expected_sans.size(), &peer) == TSI_OK);
  327. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  328. TSI_CERTIFICATE_TYPE_PEER_PROPERTY, TSI_X509_CERTIFICATE_TYPE,
  329. &peer.properties[0]) == TSI_OK);
  330. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  331. "foo", "bar", &peer.properties[1]) == TSI_OK);
  332. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  333. TSI_X509_SUBJECT_COMMON_NAME_PEER_PROPERTY, expected_cn,
  334. &peer.properties[2]) == TSI_OK);
  335. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  336. "chapi", "chapo", &peer.properties[3]) == TSI_OK);
  337. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  338. TSI_X509_PEM_CERT_PROPERTY, expected_pem_cert,
  339. &peer.properties[4]) == TSI_OK);
  340. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  341. TSI_SECURITY_LEVEL_PEER_PROPERTY,
  342. tsi_security_level_to_string(TSI_PRIVACY_AND_INTEGRITY),
  343. &peer.properties[5]) == TSI_OK);
  344. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  345. TSI_X509_PEM_CERT_CHAIN_PROPERTY, expected_pem_cert_chain,
  346. &peer.properties[6]) == TSI_OK);
  347. for (i = 0; i < expected_sans.size(); i++) {
  348. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  349. TSI_X509_SUBJECT_ALTERNATIVE_NAME_PEER_PROPERTY,
  350. expected_sans[i].c_str(),
  351. &peer.properties[7 + i]) == TSI_OK);
  352. }
  353. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  354. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  355. GPR_ASSERT(ctx != nullptr);
  356. GPR_ASSERT(grpc_auth_context_peer_is_authenticated(ctx.get()));
  357. GPR_ASSERT(
  358. check_properties(ctx.get(), GRPC_X509_SAN_PROPERTY_NAME, expected_sans));
  359. GPR_ASSERT(check_property(ctx.get(),
  360. GRPC_TRANSPORT_SECURITY_TYPE_PROPERTY_NAME,
  361. GRPC_SSL_TRANSPORT_SECURITY_TYPE));
  362. GPR_ASSERT(
  363. check_property(ctx.get(), GRPC_X509_CN_PROPERTY_NAME, expected_cn));
  364. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_PROPERTY_NAME,
  365. expected_pem_cert));
  366. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_PEM_CERT_CHAIN_PROPERTY_NAME,
  367. expected_pem_cert_chain));
  368. rpeer = grpc_shallow_peer_from_ssl_auth_context(ctx.get());
  369. GPR_ASSERT(check_ssl_peer_equivalence(&peer, &rpeer));
  370. grpc_shallow_peer_destruct(&rpeer);
  371. tsi_peer_destruct(&peer);
  372. ctx.reset(DEBUG_LOCATION, "test");
  373. }
  374. static void test_dns_peer_to_auth_context(void) {
  375. tsi_peer peer;
  376. const std::vector<std::string> expected_dns = {"dns1", "dns2", "dns3"};
  377. GPR_ASSERT(tsi_construct_peer(expected_dns.size(), &peer) == TSI_OK);
  378. for (size_t i = 0; i < expected_dns.size(); ++i) {
  379. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  380. TSI_X509_DNS_PEER_PROPERTY, expected_dns[i].c_str(),
  381. &peer.properties[i]) == TSI_OK);
  382. }
  383. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  384. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  385. GPR_ASSERT(ctx != nullptr);
  386. GPR_ASSERT(
  387. check_properties(ctx.get(), GRPC_PEER_DNS_PROPERTY_NAME, expected_dns));
  388. tsi_peer_destruct(&peer);
  389. ctx.reset(DEBUG_LOCATION, "test");
  390. }
  391. static void test_uri_peer_to_auth_context(void) {
  392. tsi_peer peer;
  393. const std::vector<std::string> expected_uri = {"uri1", "uri2", "uri3"};
  394. GPR_ASSERT(tsi_construct_peer(expected_uri.size(), &peer) == TSI_OK);
  395. for (size_t i = 0; i < expected_uri.size(); ++i) {
  396. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  397. TSI_X509_URI_PEER_PROPERTY, expected_uri[i].c_str(),
  398. &peer.properties[i]) == TSI_OK);
  399. }
  400. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  401. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  402. GPR_ASSERT(ctx != nullptr);
  403. GPR_ASSERT(
  404. check_properties(ctx.get(), GRPC_PEER_URI_PROPERTY_NAME, expected_uri));
  405. tsi_peer_destruct(&peer);
  406. ctx.reset(DEBUG_LOCATION, "test");
  407. }
  408. static void test_email_peer_to_auth_context(void) {
  409. tsi_peer peer;
  410. const std::vector<std::string> expected_emails = {"email1", "email2"};
  411. GPR_ASSERT(tsi_construct_peer(expected_emails.size(), &peer) == TSI_OK);
  412. for (size_t i = 0; i < expected_emails.size(); ++i) {
  413. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  414. TSI_X509_EMAIL_PEER_PROPERTY, expected_emails[i].c_str(),
  415. &peer.properties[i]) == TSI_OK);
  416. }
  417. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  418. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  419. GPR_ASSERT(ctx != nullptr);
  420. GPR_ASSERT(check_properties(ctx.get(), GRPC_PEER_EMAIL_PROPERTY_NAME,
  421. expected_emails));
  422. tsi_peer_destruct(&peer);
  423. ctx.reset(DEBUG_LOCATION, "test");
  424. }
  425. static void test_ip_peer_to_auth_context(void) {
  426. tsi_peer peer;
  427. const std::vector<std::string> expected_ips = {"128.128.128.128",
  428. "255.255.255.255"};
  429. GPR_ASSERT(tsi_construct_peer(expected_ips.size(), &peer) == TSI_OK);
  430. for (size_t i = 0; i < expected_ips.size(); ++i) {
  431. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  432. TSI_X509_IP_PEER_PROPERTY, expected_ips[i].c_str(),
  433. &peer.properties[i]) == TSI_OK);
  434. }
  435. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  436. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  437. GPR_ASSERT(ctx != nullptr);
  438. GPR_ASSERT(
  439. check_properties(ctx.get(), GRPC_PEER_IP_PROPERTY_NAME, expected_ips));
  440. tsi_peer_destruct(&peer);
  441. ctx.reset(DEBUG_LOCATION, "test");
  442. }
  443. static void test_spiffe_id_peer_to_auth_context(void) {
  444. // Invalid SPIFFE IDs should not be plumbed.
  445. std::string long_id(2050, 'x');
  446. std::string long_domain(256, 'x');
  447. tsi_peer invalid_peer;
  448. std::vector<std::string> invalid_spiffe_id = {
  449. "",
  450. "spi://",
  451. "sfiffe://domain/wl",
  452. "spiffe://domain",
  453. "spiffe://domain/",
  454. long_id,
  455. "spiffe://" + long_domain + "/wl"};
  456. size_t i;
  457. GPR_ASSERT(tsi_construct_peer(invalid_spiffe_id.size(), &invalid_peer) ==
  458. TSI_OK);
  459. for (i = 0; i < invalid_spiffe_id.size(); i++) {
  460. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  461. TSI_X509_URI_PEER_PROPERTY, invalid_spiffe_id[i].c_str(),
  462. &invalid_peer.properties[i]) == TSI_OK);
  463. }
  464. grpc_core::RefCountedPtr<grpc_auth_context> invalid_ctx =
  465. grpc_ssl_peer_to_auth_context(&invalid_peer,
  466. GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  467. GPR_ASSERT(invalid_ctx != nullptr);
  468. GPR_ASSERT(check_spiffe_id(invalid_ctx.get(), nullptr, false));
  469. tsi_peer_destruct(&invalid_peer);
  470. invalid_ctx.reset(DEBUG_LOCATION, "test");
  471. // A valid SPIFFE ID should be plumbed.
  472. tsi_peer valid_peer;
  473. std::string valid_spiffe_id = "spiffe://foo.bar.com/wl";
  474. GPR_ASSERT(tsi_construct_peer(1, &valid_peer) == TSI_OK);
  475. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  476. TSI_X509_URI_PEER_PROPERTY, valid_spiffe_id.c_str(),
  477. &valid_peer.properties[0]) == TSI_OK);
  478. grpc_core::RefCountedPtr<grpc_auth_context> valid_ctx =
  479. grpc_ssl_peer_to_auth_context(&valid_peer,
  480. GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  481. GPR_ASSERT(valid_ctx != nullptr);
  482. GPR_ASSERT(check_spiffe_id(valid_ctx.get(), "spiffe://foo.bar.com/wl", true));
  483. tsi_peer_destruct(&valid_peer);
  484. valid_ctx.reset(DEBUG_LOCATION, "test");
  485. // Multiple SPIFFE IDs should not be plumbed.
  486. tsi_peer multiple_peer;
  487. std::vector<std::string> multiple_spiffe_id = {
  488. "spiffe://foo.bar.com/wl", "https://xyz", "spiffe://foo.bar.com/wl2"};
  489. GPR_ASSERT(tsi_construct_peer(multiple_spiffe_id.size(), &multiple_peer) ==
  490. TSI_OK);
  491. for (i = 0; i < multiple_spiffe_id.size(); i++) {
  492. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  493. TSI_X509_URI_PEER_PROPERTY, multiple_spiffe_id[i].c_str(),
  494. &multiple_peer.properties[i]) == TSI_OK);
  495. }
  496. grpc_core::RefCountedPtr<grpc_auth_context> multiple_ctx =
  497. grpc_ssl_peer_to_auth_context(&multiple_peer,
  498. GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  499. GPR_ASSERT(multiple_ctx != nullptr);
  500. GPR_ASSERT(check_spiffe_id(multiple_ctx.get(), nullptr, false));
  501. tsi_peer_destruct(&multiple_peer);
  502. multiple_ctx.reset(DEBUG_LOCATION, "test");
  503. // A valid SPIFFE certificate should only has one URI SAN field.
  504. // SPIFFE ID should not be plumbed if there are multiple URIs.
  505. tsi_peer multiple_uri_peer;
  506. std::vector<std::string> multiple_uri = {"spiffe://foo.bar.com/wl",
  507. "https://xyz", "ssh://foo.bar.com/"};
  508. GPR_ASSERT(tsi_construct_peer(multiple_uri.size(), &multiple_uri_peer) ==
  509. TSI_OK);
  510. for (i = 0; i < multiple_spiffe_id.size(); i++) {
  511. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  512. TSI_X509_URI_PEER_PROPERTY, multiple_uri[i].c_str(),
  513. &multiple_uri_peer.properties[i]) == TSI_OK);
  514. }
  515. grpc_core::RefCountedPtr<grpc_auth_context> multiple_uri_ctx =
  516. grpc_ssl_peer_to_auth_context(&multiple_uri_peer,
  517. GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  518. GPR_ASSERT(multiple_uri_ctx != nullptr);
  519. GPR_ASSERT(check_spiffe_id(multiple_uri_ctx.get(), nullptr, false));
  520. tsi_peer_destruct(&multiple_uri_peer);
  521. multiple_uri_ctx.reset(DEBUG_LOCATION, "test");
  522. }
  523. static void test_subject_to_auth_context(void) {
  524. tsi_peer peer;
  525. const char* expected_subject = "subject1";
  526. GPR_ASSERT(tsi_construct_peer(1, &peer) == TSI_OK);
  527. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  528. TSI_X509_SUBJECT_PEER_PROPERTY, expected_subject,
  529. &peer.properties[0]) == TSI_OK);
  530. grpc_core::RefCountedPtr<grpc_auth_context> ctx =
  531. grpc_ssl_peer_to_auth_context(&peer, GRPC_SSL_TRANSPORT_SECURITY_TYPE);
  532. GPR_ASSERT(ctx != nullptr);
  533. GPR_ASSERT(check_property(ctx.get(), GRPC_X509_SUBJECT_PROPERTY_NAME,
  534. expected_subject));
  535. tsi_peer_destruct(&peer);
  536. ctx.reset(DEBUG_LOCATION, "test");
  537. }
  538. static const char* roots_for_override_api = "roots for override api";
  539. static grpc_ssl_roots_override_result override_roots_success(
  540. char** pem_root_certs) {
  541. *pem_root_certs = gpr_strdup(roots_for_override_api);
  542. return GRPC_SSL_ROOTS_OVERRIDE_OK;
  543. }
  544. static grpc_ssl_roots_override_result override_roots_permanent_failure(
  545. char** /*pem_root_certs*/) {
  546. return GRPC_SSL_ROOTS_OVERRIDE_FAIL_PERMANENTLY;
  547. }
  548. static void test_ipv6_address_san(void) {
  549. const char* addresses[] = {
  550. "2001:db8::1", "fe80::abcd:ef65:4321%em0", "fd11:feed:beef:0:cafe::4",
  551. "128.10.0.1:8888", "[2001:db8::1]:8080", "[2001:db8::1%em1]:8080",
  552. };
  553. const char* san_ips[] = {
  554. "2001:db8::1", "fe80::abcd:ef65:4321", "fd11:feed:beef:0:cafe::4",
  555. "128.10.0.1", "2001:db8::1", "2001:db8::1",
  556. };
  557. tsi_peer peer;
  558. GPR_ASSERT(tsi_construct_peer(1, &peer) == TSI_OK);
  559. for (size_t i = 0; i < GPR_ARRAY_SIZE(addresses); i++) {
  560. GPR_ASSERT(tsi_construct_string_peer_property_from_cstring(
  561. TSI_X509_SUBJECT_ALTERNATIVE_NAME_PEER_PROPERTY, san_ips[i],
  562. &peer.properties[0]) == TSI_OK);
  563. GPR_ASSERT(grpc_ssl_host_matches_name(&peer, addresses[i]));
  564. tsi_peer_property_destruct(&peer.properties[0]);
  565. }
  566. tsi_peer_destruct(&peer);
  567. }
  568. namespace grpc_core {
  569. namespace {
  570. class TestDefaultSslRootStore : public DefaultSslRootStore {
  571. public:
  572. static grpc_slice ComputePemRootCertsForTesting() {
  573. return ComputePemRootCerts();
  574. }
  575. };
  576. } // namespace
  577. } // namespace grpc_core
  578. // TODO(unknown): Convert this test to C++ test when security_connector
  579. // implementation is converted to C++.
  580. static void test_default_ssl_roots(void) {
  581. const char* roots_for_env_var = "roots for env var";
  582. char* roots_env_var_file_path;
  583. FILE* roots_env_var_file =
  584. gpr_tmpfile("test_roots_for_env_var", &roots_env_var_file_path);
  585. fwrite(roots_for_env_var, 1, strlen(roots_for_env_var), roots_env_var_file);
  586. fclose(roots_env_var_file);
  587. /* First let's get the root through the override: set the env to an invalid
  588. value. */
  589. GPR_GLOBAL_CONFIG_SET(grpc_default_ssl_roots_file_path, "");
  590. grpc_set_ssl_roots_override_callback(override_roots_success);
  591. grpc_slice roots =
  592. grpc_core::TestDefaultSslRootStore::ComputePemRootCertsForTesting();
  593. char* roots_contents = grpc_slice_to_c_string(roots);
  594. grpc_slice_unref(roots);
  595. GPR_ASSERT(strcmp(roots_contents, roots_for_override_api) == 0);
  596. gpr_free(roots_contents);
  597. /* Now let's set the env var: We should get the contents pointed value
  598. instead. */
  599. GPR_GLOBAL_CONFIG_SET(grpc_default_ssl_roots_file_path,
  600. roots_env_var_file_path);
  601. roots = grpc_core::TestDefaultSslRootStore::ComputePemRootCertsForTesting();
  602. roots_contents = grpc_slice_to_c_string(roots);
  603. grpc_slice_unref(roots);
  604. GPR_ASSERT(strcmp(roots_contents, roots_for_env_var) == 0);
  605. gpr_free(roots_contents);
  606. /* Now reset the env var. We should fall back to the value overridden using
  607. the api. */
  608. GPR_GLOBAL_CONFIG_SET(grpc_default_ssl_roots_file_path, "");
  609. roots = grpc_core::TestDefaultSslRootStore::ComputePemRootCertsForTesting();
  610. roots_contents = grpc_slice_to_c_string(roots);
  611. grpc_slice_unref(roots);
  612. GPR_ASSERT(strcmp(roots_contents, roots_for_override_api) == 0);
  613. gpr_free(roots_contents);
  614. /* Now setup a permanent failure for the overridden roots and we should get
  615. an empty slice. */
  616. GPR_GLOBAL_CONFIG_SET(grpc_not_use_system_ssl_roots, true);
  617. grpc_set_ssl_roots_override_callback(override_roots_permanent_failure);
  618. roots = grpc_core::TestDefaultSslRootStore::ComputePemRootCertsForTesting();
  619. GPR_ASSERT(GRPC_SLICE_IS_EMPTY(roots));
  620. const tsi_ssl_root_certs_store* root_store =
  621. grpc_core::TestDefaultSslRootStore::GetRootStore();
  622. GPR_ASSERT(root_store == nullptr);
  623. /* Cleanup. */
  624. remove(roots_env_var_file_path);
  625. gpr_free(roots_env_var_file_path);
  626. }
  627. static void test_peer_alpn_check(void) {
  628. #if TSI_OPENSSL_ALPN_SUPPORT
  629. tsi_peer peer;
  630. const char* alpn = "grpc";
  631. const char* wrong_alpn = "wrong";
  632. // peer does not have a TSI_SSL_ALPN_SELECTED_PROTOCOL property.
  633. GPR_ASSERT(tsi_construct_peer(1, &peer) == TSI_OK);
  634. GPR_ASSERT(tsi_construct_string_peer_property("wrong peer property name",
  635. alpn, strlen(alpn),
  636. &peer.properties[0]) == TSI_OK);
  637. grpc_error_handle error = grpc_ssl_check_alpn(&peer);
  638. GPR_ASSERT(error != GRPC_ERROR_NONE);
  639. tsi_peer_destruct(&peer);
  640. GRPC_ERROR_UNREF(error);
  641. // peer has a TSI_SSL_ALPN_SELECTED_PROTOCOL property but with an incorrect
  642. // property value.
  643. GPR_ASSERT(tsi_construct_peer(1, &peer) == TSI_OK);
  644. GPR_ASSERT(tsi_construct_string_peer_property(TSI_SSL_ALPN_SELECTED_PROTOCOL,
  645. wrong_alpn, strlen(wrong_alpn),
  646. &peer.properties[0]) == TSI_OK);
  647. error = grpc_ssl_check_alpn(&peer);
  648. GPR_ASSERT(error != GRPC_ERROR_NONE);
  649. tsi_peer_destruct(&peer);
  650. GRPC_ERROR_UNREF(error);
  651. // peer has a TSI_SSL_ALPN_SELECTED_PROTOCOL property with a correct property
  652. // value.
  653. GPR_ASSERT(tsi_construct_peer(1, &peer) == TSI_OK);
  654. GPR_ASSERT(tsi_construct_string_peer_property(TSI_SSL_ALPN_SELECTED_PROTOCOL,
  655. alpn, strlen(alpn),
  656. &peer.properties[0]) == TSI_OK);
  657. GPR_ASSERT(grpc_ssl_check_alpn(&peer) == GRPC_ERROR_NONE);
  658. tsi_peer_destruct(&peer);
  659. #else
  660. GPR_ASSERT(grpc_ssl_check_alpn(nullptr) == GRPC_ERROR_NONE);
  661. #endif
  662. }
  663. int main(int argc, char** argv) {
  664. grpc::testing::TestEnvironment env(argc, argv);
  665. grpc_init();
  666. test_unauthenticated_ssl_peer();
  667. test_cn_only_ssl_peer_to_auth_context();
  668. test_cn_and_one_san_ssl_peer_to_auth_context();
  669. test_cn_and_multiple_sans_ssl_peer_to_auth_context();
  670. test_cn_and_multiple_sans_and_others_ssl_peer_to_auth_context();
  671. test_dns_peer_to_auth_context();
  672. test_uri_peer_to_auth_context();
  673. test_email_peer_to_auth_context();
  674. test_ip_peer_to_auth_context();
  675. test_spiffe_id_peer_to_auth_context();
  676. test_subject_to_auth_context();
  677. test_ipv6_address_san();
  678. test_default_ssl_roots();
  679. test_peer_alpn_check();
  680. grpc_shutdown();
  681. return 0;
  682. }