blob: 7b3ec5147d4c386ef0a7bf68366e9832f8011eda [file] [log] [blame]
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +00001// Copyright 2017 Google Inc.
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////////////////////////////////////////////////////////////////////////////////
16
ambrosin510315e2023-03-02 05:51:13 -080017#include "tink/internal/registry_impl.h"
18
19#include <stdint.h>
20
ksteff83c0b2021-04-06 03:12:44 -070021#include <memory>
juergb8243c62022-08-15 09:38:16 -070022#include <sstream>
tholenstcf2ff242022-01-10 00:18:32 -080023#include <string>
Thai Duongce6cffc2017-04-12 18:07:48 -070024#include <thread> // NOLINT(build/c++11)
ambrosin510315e2023-03-02 05:51:13 -080025#include <typeinfo>
tholenstcf2ff242022-01-10 00:18:32 -080026#include <utility>
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +000027
tholenst7997b262019-04-10 08:13:35 -070028#include "gmock/gmock.h"
Haris Andrianakisa7c0b6f2018-07-11 07:58:16 -070029#include "gtest/gtest.h"
Bartosz Przydatek65a8bf12018-04-04 12:04:38 -070030#include "absl/memory/memory.h"
lizatretyakova62f2f0d2021-10-29 04:41:48 -070031#include "absl/status/status.h"
ambrosin510315e2023-03-02 05:51:13 -080032#include "absl/status/statusor.h"
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +020033#include "absl/strings/string_view.h"
ksteff83c0b2021-04-06 03:12:44 -070034#include "openssl/crypto.h"
Bartosz Przydatek3cd62692018-03-16 12:45:04 -070035#include "tink/aead.h"
tholenst8e19ab52018-10-25 03:24:16 -070036#include "tink/aead/aead_wrapper.h"
Bartosz Przydatek3cd62692018-03-16 12:45:04 -070037#include "tink/aead/aes_gcm_key_manager.h"
tholenstb9615a32019-08-06 08:47:31 -070038#include "tink/core/key_manager_impl.h"
tholenst6ddf0912019-07-29 06:11:04 -070039#include "tink/core/key_type_manager.h"
ambrosin510315e2023-03-02 05:51:13 -080040#include "tink/core/private_key_manager_impl.h"
41#include "tink/core/private_key_type_manager.h"
42#include "tink/core/template_util.h"
tholenst8e19ab52018-10-25 03:24:16 -070043#include "tink/hybrid/ecies_aead_hkdf_private_key_manager.h"
44#include "tink/hybrid/ecies_aead_hkdf_public_key_manager.h"
ambrosin510315e2023-03-02 05:51:13 -080045#include "tink/hybrid_decrypt.h"
46#include "tink/input_stream.h"
47#include "tink/internal/fips_utils.h"
48#include "tink/key_manager.h"
ambrosin510315e2023-03-02 05:51:13 -080049#include "tink/mac.h"
ambrosin78946022022-04-04 05:46:26 -070050#include "tink/monitoring/monitoring_client_mocks.h"
ambrosin510315e2023-03-02 05:51:13 -080051#include "tink/primitive_set.h"
52#include "tink/primitive_wrapper.h"
ksteff83c0b2021-04-06 03:12:44 -070053#include "tink/registry.h"
tholenst7ea3c182019-06-17 04:35:05 -070054#include "tink/subtle/aes_gcm_boringssl.h"
55#include "tink/subtle/random.h"
ambrosin510315e2023-03-02 05:51:13 -080056#include "tink/util/input_stream_util.h"
tholenst92a53962019-11-04 01:08:16 -080057#include "tink/util/istream_input_stream.h"
Haris Andrianakis290eb9a2018-04-16 12:52:22 -070058#include "tink/util/protobuf_helper.h"
wiktorg89c97e82020-05-06 01:58:04 -070059#include "tink/util/secret_data.h"
Bartosz Przydatek3cd62692018-03-16 12:45:04 -070060#include "tink/util/status.h"
61#include "tink/util/statusor.h"
tholenst7ea3c182019-06-17 04:35:05 -070062#include "tink/util/test_matchers.h"
Bartosz Przydatek3cd62692018-03-16 12:45:04 -070063#include "tink/util/test_util.h"
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +000064#include "proto/aes_ctr_hmac_aead.pb.h"
65#include "proto/aes_gcm.pb.h"
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -070066#include "proto/common.pb.h"
tholenst95120392019-07-10 03:30:39 -070067#include "proto/ecdsa.pb.h"
ambrosin510315e2023-03-02 05:51:13 -080068#include "proto/ecies_aead_hkdf.pb.h"
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +000069#include "proto/tink.pb.h"
70
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -070071namespace crypto {
72namespace tink {
tholenst05a834c2021-03-18 06:24:20 -070073namespace internal {
74
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -070075namespace {
76
tholenst95120392019-07-10 03:30:39 -070077using ::crypto::tink::test::AddLegacyKey;
78using ::crypto::tink::test::AddRawKey;
79using ::crypto::tink::test::AddTinkKey;
80using ::crypto::tink::test::DummyAead;
81using ::crypto::tink::test::IsOk;
82using ::crypto::tink::test::StatusIs;
83using ::crypto::tink::util::Status;
84using ::google::crypto::tink::AesCtrHmacAeadKey;
85using ::google::crypto::tink::AesGcmKey;
86using ::google::crypto::tink::AesGcmKeyFormat;
87using ::google::crypto::tink::EcdsaKeyFormat;
88using ::google::crypto::tink::EcdsaPrivateKey;
89using ::google::crypto::tink::EcdsaPublicKey;
90using ::google::crypto::tink::EcdsaSignatureEncoding;
91using ::google::crypto::tink::EcPointFormat;
92using ::google::crypto::tink::EllipticCurveType;
93using ::google::crypto::tink::HashType;
94using ::google::crypto::tink::KeyData;
95using ::google::crypto::tink::Keyset;
tholenst815e5c32020-10-09 04:45:35 -070096using ::google::crypto::tink::KeysetInfo;
tholenst95120392019-07-10 03:30:39 -070097using ::google::crypto::tink::KeyStatusType;
98using ::google::crypto::tink::KeyTemplate;
99using ::google::crypto::tink::OutputPrefixType;
100using ::portable_proto::MessageLite;
tholenst7ea3c182019-06-17 04:35:05 -0700101using ::testing::Eq;
tholenst7997b262019-04-10 08:13:35 -0700102using ::testing::HasSubstr;
ambrosinff8f7c92022-03-01 09:07:49 -0800103using ::testing::IsNull;
tholenst8730bbe2020-11-30 03:03:51 -0800104using ::testing::Not;
tholenst7ea3c182019-06-17 04:35:05 -0700105using ::testing::SizeIs;
Bartosz Przydatekcc8d6272017-08-31 17:52:12 +0200106
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000107class RegistryTest : public ::testing::Test {
108 protected:
cinlin063c4ea2023-03-07 12:43:13 -0800109 void SetUp() override { Registry::Reset(); }
kste752fc1f2021-04-07 04:04:06 -0700110
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000111 void TearDown() override {
kste752fc1f2021-04-07 04:04:06 -0700112 // Reset is needed here to ensure Mock objects get deleted and do not leak.
113 Registry::Reset();
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000114 }
115};
116
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200117class TestKeyFactory : public KeyFactory {
118 public:
tholenstee831612019-06-04 01:59:51 -0700119 explicit TestKeyFactory(const std::string& key_type) : key_type_(key_type) {}
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200120
Bartosz Przydatekb6dc8842018-06-28 13:02:03 -0700121 util::StatusOr<std::unique_ptr<portable_proto::MessageLite>> NewKey(
122 const MessageLite& key_format) const override {
lizatretyakova7c775b72021-09-22 03:50:44 -0700123 return util::Status(absl::StatusCode::kUnknown,
124 "TestKeyFactory cannot produce a key");
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200125 }
126
Bartosz Przydatekb6dc8842018-06-28 13:02:03 -0700127 util::StatusOr<std::unique_ptr<portable_proto::MessageLite>> NewKey(
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200128 absl::string_view serialized_key_format) const override {
lizatretyakova7c775b72021-09-22 03:50:44 -0700129 return util::Status(absl::StatusCode::kUnknown,
130 "TestKeyFactory cannot produce a key");
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200131 }
132
133 util::StatusOr<std::unique_ptr<KeyData>> NewKeyData(
134 absl::string_view serialized_key_format) const override {
Bartosz Przydatek65a8bf12018-04-04 12:04:38 -0700135 auto key_data = absl::make_unique<KeyData>();
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200136 key_data->set_type_url(key_type_);
137 key_data->set_value(std::string(serialized_key_format));
138 return std::move(key_data);
139 }
140
141 private:
142 std::string key_type_;
143};
144
Bartosz Przydateka6c43342017-03-23 16:37:56 +0000145class TestAeadKeyManager : public KeyManager<Aead> {
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000146 public:
tholenstee831612019-06-04 01:59:51 -0700147 explicit TestAeadKeyManager(const std::string& key_type)
148 : key_type_(key_type), key_factory_(key_type) {}
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000149
cinlin063c4ea2023-03-07 12:43:13 -0800150 util::StatusOr<std::unique_ptr<Aead>> GetPrimitive(
151 const KeyData& key) const override {
Bartosz Przydatek7a13a302017-04-03 14:03:30 +0000152 std::unique_ptr<Aead> aead(new DummyAead(key_type_));
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000153 return std::move(aead);
154 }
155
cinlin063c4ea2023-03-07 12:43:13 -0800156 util::StatusOr<std::unique_ptr<Aead>> GetPrimitive(
157 const MessageLite& key) const override {
lizatretyakova7c775b72021-09-22 03:50:44 -0700158 return util::Status(absl::StatusCode::kUnknown,
159 "TestKeyFactory cannot construct an aead");
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000160 }
161
cinlin063c4ea2023-03-07 12:43:13 -0800162 uint32_t get_version() const override { return 0; }
Bartosz Przydatek7a13a302017-04-03 14:03:30 +0000163
tholenst1ec72ed2019-10-25 13:04:33 -0700164 const std::string& get_key_type() const override { return key_type_; }
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000165
cinlin063c4ea2023-03-07 12:43:13 -0800166 const KeyFactory& get_key_factory() const override { return key_factory_; }
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200167
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000168 private:
Bartosz Przydatek7a13a302017-04-03 14:03:30 +0000169 std::string key_type_;
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200170 TestKeyFactory key_factory_;
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000171};
172
tholenst8730bbe2020-11-30 03:03:51 -0800173// A class for testing. We will construct objects from an aead key, so that we
174// can check that a keymanager can handle multiple primitives. It is really
175// insecure, as it does nothing except provide access to the key.
176class AeadVariant {
177 public:
178 explicit AeadVariant(std::string s) : s_(s) {}
179
180 std::string get() { return s_; }
181
182 private:
183 std::string s_;
184};
185
186class ExampleKeyTypeManager : public KeyTypeManager<AesGcmKey, AesGcmKeyFormat,
187 List<Aead, AeadVariant>> {
188 public:
189 class AeadFactory : public PrimitiveFactory<Aead> {
190 public:
191 crypto::tink::util::StatusOr<std::unique_ptr<Aead>> Create(
192 const AesGcmKey& key) const override {
193 // Ignore the key and returned one with a fixed size for this test.
194 return {subtle::AesGcmBoringSsl::New(
195 util::SecretDataFromStringView(key.key_value()))};
196 }
197 };
198
199 class AeadVariantFactory : public PrimitiveFactory<AeadVariant> {
200 public:
201 crypto::tink::util::StatusOr<std::unique_ptr<AeadVariant>> Create(
202 const AesGcmKey& key) const override {
203 return absl::make_unique<AeadVariant>(key.key_value());
204 }
205 };
206
207 ExampleKeyTypeManager()
208 : KeyTypeManager(absl::make_unique<AeadFactory>(),
209 absl::make_unique<AeadVariantFactory>()) {}
210
211 google::crypto::tink::KeyData::KeyMaterialType key_material_type()
212 const override {
213 return google::crypto::tink::KeyData::SYMMETRIC;
214 }
215
216 uint32_t get_version() const override { return kVersion; }
217
218 const std::string& get_key_type() const override { return kKeyType; }
219
220 crypto::tink::util::Status ValidateKey(const AesGcmKey& key) const override {
221 return util::OkStatus();
222 }
223
224 crypto::tink::util::Status ValidateKeyFormat(
225 const AesGcmKeyFormat& key_format) const override {
226 return util::OkStatus();
227 }
228
229 crypto::tink::util::StatusOr<AesGcmKey> CreateKey(
230 const AesGcmKeyFormat& key_format) const override {
231 AesGcmKey result;
232 result.set_key_value(subtle::Random::GetRandomBytes(key_format.key_size()));
233 return result;
234 }
235
236 crypto::tink::util::StatusOr<AesGcmKey> DeriveKey(
237 const AesGcmKeyFormat& key_format,
238 InputStream* input_stream) const override {
239 // Note: in an actual key type manager we need to do more work, e.g., test
240 // that the generated key is long enough.
241 crypto::tink::util::StatusOr<std::string> randomness =
242 ReadBytesFromStream(key_format.key_size(), input_stream);
243 if (!randomness.status().ok()) {
244 return randomness.status();
245 }
246 AesGcmKey key;
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700247 key.set_key_value(randomness.value());
tholenst8730bbe2020-11-30 03:03:51 -0800248 return key;
249 }
250
ksteff83c0b2021-04-06 03:12:44 -0700251 MOCK_METHOD(FipsCompatibility, FipsStatus, (), (const, override));
252
tholenst8730bbe2020-11-30 03:03:51 -0800253 private:
254 static constexpr int kVersion = 0;
255 const std::string kKeyType =
256 "type.googleapis.com/google.crypto.tink.AesGcmKey";
257};
258
259template <typename P, typename Q = P>
260class TestWrapper : public PrimitiveWrapper<P, Q> {
tholenst8e19ab52018-10-25 03:24:16 -0700261 public:
wiktorgbaa4f202022-12-16 04:52:28 -0800262 TestWrapper() = default;
tholenst8730bbe2020-11-30 03:03:51 -0800263 crypto::tink::util::StatusOr<std::unique_ptr<Q>> Wrap(
tholenst8e19ab52018-10-25 03:24:16 -0700264 std::unique_ptr<PrimitiveSet<P>> primitive_set) const override {
lizatretyakova92fbd252021-10-19 12:41:52 -0700265 return util::Status(absl::StatusCode::kUnimplemented,
266 "This is a test wrapper.");
tholenst8e19ab52018-10-25 03:24:16 -0700267 }
268};
269
tholenst8730bbe2020-11-30 03:03:51 -0800270class AeadVariantWrapper : public PrimitiveWrapper<AeadVariant, AeadVariant> {
271 public:
272 crypto::tink::util::StatusOr<std::unique_ptr<AeadVariant>> Wrap(
273 std::unique_ptr<PrimitiveSet<AeadVariant>> primitive_set) const override {
274 return absl::make_unique<AeadVariant>(
275 primitive_set->get_primary()->get_primitive().get());
276 }
277};
278
279class AeadVariantToStringWrapper
280 : public PrimitiveWrapper<AeadVariant, std::string> {
281 public:
282 crypto::tink::util::StatusOr<std::unique_ptr<std::string>> Wrap(
283 std::unique_ptr<PrimitiveSet<AeadVariant>> primitive_set) const override {
284 return absl::make_unique<std::string>(
285 primitive_set->get_primary()->get_primitive().get());
286 }
287};
288
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200289void register_test_managers(const std::string& key_type_prefix,
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000290 int manager_count) {
291 for (int i = 0; i < manager_count; i++) {
292 std::string key_type = key_type_prefix + std::to_string(i);
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200293 util::Status status = Registry::RegisterKeyManager(
cinlin41cd6f72023-03-02 19:32:12 -0800294 absl::make_unique<TestAeadKeyManager>(key_type),
295 /* new_key_allowed= */ true);
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000296 EXPECT_TRUE(status.ok()) << status;
297 }
298}
299
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200300void verify_test_managers(const std::string& key_type_prefix,
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000301 int manager_count) {
302 for (int i = 0; i < manager_count; i++) {
303 std::string key_type = key_type_prefix + std::to_string(i);
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200304 auto manager_result = Registry::get_key_manager<Aead>(key_type);
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000305 EXPECT_TRUE(manager_result.ok()) << manager_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700306 auto manager = manager_result.value();
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000307 EXPECT_EQ(key_type, manager->get_key_type());
308 }
309}
310
Veronika Slivova44b89602018-07-04 08:24:16 -0700311TEST_F(RegistryTest, testRegisterKeyManagerMoreRestrictiveNewKeyAllowed) {
312 std::string key_type = "some_key_type";
313 KeyTemplate key_template;
314 key_template.set_type_url(key_type);
315
316 // Register the key manager with new_key_allowed == true and verify that
317 // new key data can be created.
318 util::Status status = Registry::RegisterKeyManager(
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700319 absl::make_unique<TestAeadKeyManager>(key_type),
320 /* new_key_allowed= */ true);
Veronika Slivova44b89602018-07-04 08:24:16 -0700321 EXPECT_TRUE(status.ok()) << status;
322
323 auto result_before = Registry::NewKeyData(key_template);
Thomas Holensteinb5e9a882018-10-03 12:06:57 -0400324 EXPECT_TRUE(result_before.ok()) << result_before.status();
Veronika Slivova44b89602018-07-04 08:24:16 -0700325
326 // Re-register the key manager with new_key_allowed == false and check the
327 // restriction (i.e. new key data cannot be created).
328 status = Registry::RegisterKeyManager(
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700329 absl::make_unique<TestAeadKeyManager>(key_type),
330 /* new_key_allowed= */ false);
Veronika Slivova44b89602018-07-04 08:24:16 -0700331 EXPECT_TRUE(status.ok()) << status;
332
333 auto result_after = Registry::NewKeyData(key_template);
334 EXPECT_FALSE(result_after.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700335 EXPECT_EQ(absl::StatusCode::kInvalidArgument, result_after.status().code());
Veronika Slivova44b89602018-07-04 08:24:16 -0700336 EXPECT_PRED_FORMAT2(testing::IsSubstring, key_type,
lizatretyakova32291ec2021-11-01 09:19:03 -0700337 std::string(result_after.status().message()));
Veronika Slivova44b89602018-07-04 08:24:16 -0700338 EXPECT_PRED_FORMAT2(testing::IsSubstring, "does not allow",
lizatretyakova32291ec2021-11-01 09:19:03 -0700339 std::string(result_after.status().message()));
Veronika Slivova44b89602018-07-04 08:24:16 -0700340}
341
342TEST_F(RegistryTest, testRegisterKeyManagerLessRestrictiveNewKeyAllowed) {
343 std::string key_type = "some_key_type";
344 KeyTemplate key_template;
345 key_template.set_type_url(key_type);
346
347 // Register the key manager with new_key_allowed == false.
348 util::Status status = Registry::RegisterKeyManager(
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700349 absl::make_unique<TestAeadKeyManager>(key_type),
350 /* new_key_allowed= */ false);
Veronika Slivova44b89602018-07-04 08:24:16 -0700351 EXPECT_TRUE(status.ok()) << status;
352
353 // Verify that re-registering the key manager with new_key_allowed == true is
354 // not possible and that the restriction still holds after that operation
355 // (i.e. new key data cannot be created).
Bartosz Przydatekeeadc542018-07-09 13:08:49 -0700356 status = Registry::RegisterKeyManager(
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700357 absl::make_unique<TestAeadKeyManager>(key_type),
358 /* new_key_allowed= */ true);
Veronika Slivova44b89602018-07-04 08:24:16 -0700359 EXPECT_FALSE(status.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700360 EXPECT_EQ(absl::StatusCode::kAlreadyExists, status.code()) << status;
Veronika Slivova44b89602018-07-04 08:24:16 -0700361 EXPECT_PRED_FORMAT2(testing::IsSubstring, key_type,
lizatretyakova32291ec2021-11-01 09:19:03 -0700362 std::string(status.message()))
363 << status;
364 EXPECT_PRED_FORMAT2(testing::IsSubstring, "forbidden new key operation",
365 std::string(status.message()))
366 << status;
Veronika Slivova44b89602018-07-04 08:24:16 -0700367
368 auto result_after = Registry::NewKeyData(key_template);
369 EXPECT_FALSE(result_after.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700370 EXPECT_EQ(absl::StatusCode::kInvalidArgument, result_after.status().code());
Veronika Slivova44b89602018-07-04 08:24:16 -0700371 EXPECT_PRED_FORMAT2(testing::IsSubstring, key_type,
lizatretyakova32291ec2021-11-01 09:19:03 -0700372 std::string(result_after.status().message()));
Veronika Slivova44b89602018-07-04 08:24:16 -0700373 EXPECT_PRED_FORMAT2(testing::IsSubstring, "does not allow",
lizatretyakova32291ec2021-11-01 09:19:03 -0700374 std::string(result_after.status().message()));
Veronika Slivova44b89602018-07-04 08:24:16 -0700375}
376
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000377TEST_F(RegistryTest, testConcurrentRegistration) {
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000378 std::string key_type_prefix_a = "key_type_a_";
379 std::string key_type_prefix_b = "key_type_b_";
380 int count_a = 42;
381 int count_b = 72;
382
383 // Register some managers.
cinlin063c4ea2023-03-07 12:43:13 -0800384 std::thread register_a(register_test_managers, key_type_prefix_a, count_a);
385 std::thread register_b(register_test_managers, key_type_prefix_b, count_b);
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000386 register_a.join();
387 register_b.join();
388
tholenst77b67402019-11-08 04:45:41 -0800389 // Check that the managers were registered. Also, keep registering new
390 // versions while we check.
391 std::thread register_more_a(register_test_managers, key_type_prefix_a,
392 count_a);
393 std::thread register_more_b(register_test_managers, key_type_prefix_b,
394 count_b);
395 std::thread verify_a(verify_test_managers, key_type_prefix_a, count_a);
396 std::thread verify_b(verify_test_managers, key_type_prefix_b, count_b);
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000397 verify_a.join();
398 verify_b.join();
tholenst77b67402019-11-08 04:45:41 -0800399 register_more_a.join();
400 register_more_b.join();
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000401
402 // Check that there are no extra managers.
tholenst1ec72ed2019-10-25 13:04:33 -0700403 std::string key_type = key_type_prefix_a + std::to_string(count_a - 1);
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200404 auto manager_result = Registry::get_key_manager<Aead>(key_type);
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000405 EXPECT_TRUE(manager_result.ok()) << manager_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700406 EXPECT_EQ(key_type, manager_result.value()->get_key_type());
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000407
408 key_type = key_type_prefix_a + std::to_string(count_a);
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200409 manager_result = Registry::get_key_manager<Aead>(key_type);
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000410 EXPECT_FALSE(manager_result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700411 EXPECT_EQ(absl::StatusCode::kNotFound, manager_result.status().code());
Bartosz Przydatekffaa21c2017-04-13 00:46:14 +0000412}
413
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000414TEST_F(RegistryTest, testBasic) {
Bartosz Przydatekb6dc8842018-06-28 13:02:03 -0700415 std::string key_type_1 = "google.crypto.tink.AesCtrHmacAeadKey";
416 std::string key_type_2 = "google.crypto.tink.AesGcmKey";
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200417 auto manager_result = Registry::get_key_manager<Aead>(key_type_1);
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000418 EXPECT_FALSE(manager_result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700419 EXPECT_EQ(absl::StatusCode::kNotFound, manager_result.status().code());
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000420
Bartosz Przydatekeeadc542018-07-09 13:08:49 -0700421 auto status = Registry::RegisterKeyManager(
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700422 absl::make_unique<TestAeadKeyManager>(key_type_1), true);
423
Bartosz Przydateka6c43342017-03-23 16:37:56 +0000424 EXPECT_TRUE(status.ok()) << status;
425
Bartosz Przydatekeeadc542018-07-09 13:08:49 -0700426 status = Registry::RegisterKeyManager(
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700427 absl::make_unique<TestAeadKeyManager>(key_type_2), true);
Bartosz Przydateka6c43342017-03-23 16:37:56 +0000428 EXPECT_TRUE(status.ok()) << status;
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000429
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200430 manager_result = Registry::get_key_manager<Aead>(key_type_1);
Bartosz Przydateka6c43342017-03-23 16:37:56 +0000431 EXPECT_TRUE(manager_result.ok()) << manager_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700432 auto manager = manager_result.value();
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000433 EXPECT_TRUE(manager->DoesSupport(key_type_1));
434 EXPECT_FALSE(manager->DoesSupport(key_type_2));
435
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200436 manager_result = Registry::get_key_manager<Aead>(key_type_2);
Bartosz Przydateka6c43342017-03-23 16:37:56 +0000437 EXPECT_TRUE(manager_result.ok()) << manager_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700438 manager = manager_result.value();
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +0000439 EXPECT_TRUE(manager->DoesSupport(key_type_2));
440 EXPECT_FALSE(manager->DoesSupport(key_type_1));
441}
442
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200443TEST_F(RegistryTest, testRegisterKeyManager) {
tholenstb9615a32019-08-06 08:47:31 -0700444 std::string key_type_1 = AesGcmKeyManager().get_key_type();
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200445
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700446 std::unique_ptr<TestAeadKeyManager> null_key_manager = nullptr;
447 auto status = Registry::RegisterKeyManager(std::move(null_key_manager), true);
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200448 EXPECT_FALSE(status.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700449 EXPECT_EQ(absl::StatusCode::kInvalidArgument, status.code()) << status;
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200450
451 // Register a key manager.
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700452 status = Registry::RegisterKeyManager(
453 absl::make_unique<TestAeadKeyManager>(key_type_1), true);
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200454 EXPECT_TRUE(status.ok()) << status;
455
456 // Register the same key manager again, it should work (idempotence).
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700457 status = Registry::RegisterKeyManager(
458 absl::make_unique<TestAeadKeyManager>(key_type_1), true);
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200459 EXPECT_TRUE(status.ok()) << status;
460
461 // Try overriding a key manager.
tholenstb9615a32019-08-06 08:47:31 -0700462 AesGcmKeyManager key_type_manager;
463 status = Registry::RegisterKeyManager(
464 crypto::tink::internal::MakeKeyManager<Aead>(&key_type_manager), true);
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200465 EXPECT_FALSE(status.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700466 EXPECT_EQ(absl::StatusCode::kAlreadyExists, status.code()) << status;
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200467
468 // Check the key manager is still registered.
469 auto manager_result = Registry::get_key_manager<Aead>(key_type_1);
470 EXPECT_TRUE(manager_result.ok()) << manager_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700471 auto manager = manager_result.value();
Bartosz Przydatek8e331022017-10-04 20:37:11 +0200472 EXPECT_TRUE(manager->DoesSupport(key_type_1));
473}
474
tholenst77b67402019-11-08 04:45:41 -0800475// Tests that if we register a key manager once more after a call to
476// get_key_manager, the key manager previously obtained with "get_key_manager()"
477// remains valid.
478TEST_F(RegistryTest, GetKeyManagerRemainsValid) {
479 std::string key_type = AesGcmKeyManager().get_key_type();
480 EXPECT_THAT(Registry::RegisterKeyManager(
cinlin063c4ea2023-03-07 12:43:13 -0800481 absl::make_unique<TestAeadKeyManager>(key_type), true),
482 IsOk());
tholenst77b67402019-11-08 04:45:41 -0800483
484 crypto::tink::util::StatusOr<const KeyManager<Aead>*> key_manager =
485 Registry::get_key_manager<Aead>(key_type);
kste52259432022-06-22 02:44:47 -0700486 ASSERT_THAT(key_manager, IsOk());
tholenst77b67402019-11-08 04:45:41 -0800487 EXPECT_THAT(Registry::RegisterKeyManager(
488 absl::make_unique<TestAeadKeyManager>(key_type), true),
489 IsOk());
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700490 EXPECT_THAT(key_manager.value()->get_key_type(), Eq(key_type));
tholenst77b67402019-11-08 04:45:41 -0800491}
492
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000493TEST_F(RegistryTest, testGettingPrimitives) {
Bartosz Przydatekb6dc8842018-06-28 13:02:03 -0700494 std::string key_type_1 = "google.crypto.tink.AesCtrHmacAeadKey";
495 std::string key_type_2 = "google.crypto.tink.AesGcmKey";
Bartosz Przydatek16e07af2017-05-06 14:32:26 +0000496 AesCtrHmacAeadKey dummy_key_1;
497 AesGcmKey dummy_key_2;
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000498
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000499 // Prepare keyset.
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000500 Keyset keyset;
501
502 uint32_t key_id_1 = 1234543;
Bartosz Przydatek16e07af2017-05-06 14:32:26 +0000503 AddTinkKey(key_type_1, key_id_1, dummy_key_1, KeyStatusType::ENABLED,
504 KeyData::SYMMETRIC, &keyset);
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000505
506 uint32_t key_id_2 = 726329;
Bartosz Przydatek16e07af2017-05-06 14:32:26 +0000507 AddTinkKey(key_type_2, key_id_2, dummy_key_2, KeyStatusType::DISABLED,
508 KeyData::SYMMETRIC, &keyset);
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000509
510 uint32_t key_id_3 = 7213743;
Bartosz Przydatek16e07af2017-05-06 14:32:26 +0000511 AddLegacyKey(key_type_2, key_id_3, dummy_key_2, KeyStatusType::ENABLED,
512 KeyData::SYMMETRIC, &keyset);
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000513
514 uint32_t key_id_4 = 6268492;
Bartosz Przydatek16e07af2017-05-06 14:32:26 +0000515 AddRawKey(key_type_1, key_id_4, dummy_key_1, KeyStatusType::ENABLED,
516 KeyData::SYMMETRIC, &keyset);
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000517
518 uint32_t key_id_5 = 42;
Bartosz Przydatek16e07af2017-05-06 14:32:26 +0000519 AddRawKey(key_type_2, key_id_5, dummy_key_2, KeyStatusType::ENABLED,
520 KeyData::SYMMETRIC, &keyset);
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000521
522 keyset.set_primary_key_id(key_id_3);
523
524 // Register key managers.
Bartosz Przydatekcc8d6272017-08-31 17:52:12 +0200525 util::Status status;
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700526 status = Registry::RegisterKeyManager(
527 absl::make_unique<TestAeadKeyManager>(key_type_1), true);
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000528 EXPECT_TRUE(status.ok()) << status;
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700529 status = Registry::RegisterKeyManager(
530 absl::make_unique<TestAeadKeyManager>(key_type_2), true);
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000531 EXPECT_TRUE(status.ok()) << status;
532
533 // Get and use primitives.
534 std::string plaintext = "some data";
535 std::string aad = "aad";
536
537 // Key #1.
538 {
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200539 auto result = Registry::GetPrimitive<Aead>(keyset.key(0).key_data());
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000540 EXPECT_TRUE(result.ok()) << result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700541 auto aead = std::move(result.value());
542 EXPECT_EQ(DummyAead(key_type_1).Encrypt(plaintext, aad).value(),
543 aead->Encrypt(plaintext, aad).value());
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000544 }
545
546 // Key #3.
547 {
Bartosz Przydatek6256d7c2017-10-04 14:58:28 +0200548 auto result = Registry::GetPrimitive<Aead>(keyset.key(2).key_data());
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000549 EXPECT_TRUE(result.ok()) << result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700550 auto aead = std::move(result.value());
551 EXPECT_EQ(DummyAead(key_type_2).Encrypt(plaintext, aad).value(),
552 aead->Encrypt(plaintext, aad).value());
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000553 }
Bartosz Przydatek94925e32017-03-28 15:03:13 +0000554}
555
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200556TEST_F(RegistryTest, testNewKeyData) {
Bartosz Przydatekb6dc8842018-06-28 13:02:03 -0700557 std::string key_type_1 = "google.crypto.tink.AesCtrHmacAeadKey";
558 std::string key_type_2 = "google.crypto.tink.AesGcmKey";
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200559 std::string key_type_3 = "yet/another/keytype";
560
561 // Register key managers.
562 util::Status status;
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700563 status = Registry::RegisterKeyManager(
564 absl::make_unique<TestAeadKeyManager>(key_type_1),
565 /*new_key_allowed=*/true);
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200566 EXPECT_TRUE(status.ok()) << status;
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700567 status = Registry::RegisterKeyManager(
568 absl::make_unique<TestAeadKeyManager>(key_type_2),
569 /*new_key_allowed=*/true);
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200570 EXPECT_TRUE(status.ok()) << status;
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700571 status = Registry::RegisterKeyManager(
572 absl::make_unique<TestAeadKeyManager>(key_type_3),
573 /*new_key_allowed=*/false);
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200574 EXPECT_TRUE(status.ok()) << status;
575
576 { // A supported key type.
577 KeyTemplate key_template;
578 key_template.set_type_url(key_type_1);
579 key_template.set_value("test value 42");
580 auto new_key_data_result = Registry::NewKeyData(key_template);
581 EXPECT_TRUE(new_key_data_result.ok()) << new_key_data_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700582 EXPECT_EQ(key_type_1, new_key_data_result.value()->type_url());
583 EXPECT_EQ(key_template.value(), new_key_data_result.value()->value());
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200584 }
585
586 { // Another supported key type.
587 KeyTemplate key_template;
588 key_template.set_type_url(key_type_2);
589 key_template.set_value("yet another test value 42");
590 auto new_key_data_result = Registry::NewKeyData(key_template);
591 EXPECT_TRUE(new_key_data_result.ok()) << new_key_data_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700592 EXPECT_EQ(key_type_2, new_key_data_result.value()->type_url());
593 EXPECT_EQ(key_template.value(), new_key_data_result.value()->value());
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200594 }
595
596 { // A key type that does not allow NewKey-operations.
597 KeyTemplate key_template;
598 key_template.set_type_url(key_type_3);
599 key_template.set_value("some other value 72");
600 auto new_key_data_result = Registry::NewKeyData(key_template);
601 EXPECT_FALSE(new_key_data_result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700602 EXPECT_EQ(absl::StatusCode::kInvalidArgument,
603 new_key_data_result.status().code());
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200604 EXPECT_PRED_FORMAT2(testing::IsSubstring, key_type_3,
lizatretyakova32291ec2021-11-01 09:19:03 -0700605 std::string(new_key_data_result.status().message()));
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200606 EXPECT_PRED_FORMAT2(testing::IsSubstring, "does not allow",
lizatretyakova32291ec2021-11-01 09:19:03 -0700607 std::string(new_key_data_result.status().message()));
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200608 }
609
610 { // A key type that is not supported.
611 KeyTemplate key_template;
612 std::string bad_type_url = "some key type that is not supported";
613 key_template.set_type_url(bad_type_url);
614 key_template.set_value("some totally other value 42");
615 auto new_key_data_result = Registry::NewKeyData(key_template);
616 EXPECT_FALSE(new_key_data_result.ok());
cinlin063c4ea2023-03-07 12:43:13 -0800617 EXPECT_EQ(absl::StatusCode::kNotFound, new_key_data_result.status().code());
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200618 EXPECT_PRED_FORMAT2(testing::IsSubstring, bad_type_url,
lizatretyakova32291ec2021-11-01 09:19:03 -0700619 std::string(new_key_data_result.status().message()));
Bartosz Przydatekd0bd5002017-10-12 13:33:28 +0200620 }
621}
622
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700623TEST_F(RegistryTest, testGetPublicKeyData) {
624 // Setup the registry.
625 Registry::Reset();
tholenst12f99702019-08-20 07:52:02 -0700626 auto private_key_type_manager =
627 absl::make_unique<EciesAeadHkdfPrivateKeyManager>();
628 auto public_key_type_manager =
629 absl::make_unique<EciesAeadHkdfPublicKeyManager>();
630
Thomas Holenstein42a021f2018-10-04 02:41:27 -0700631 auto status = Registry::RegisterKeyManager(
tholenst12f99702019-08-20 07:52:02 -0700632 internal::MakePrivateKeyManager<HybridDecrypt>(
633 private_key_type_manager.get(), public_key_type_manager.get()),
634 true);
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700635 ASSERT_TRUE(status.ok()) << status;
tholenstb9615a32019-08-06 08:47:31 -0700636 AesGcmKeyManager key_type_manager;
637 status = Registry::RegisterKeyManager(
638 crypto::tink::internal::MakeKeyManager<Aead>(&key_type_manager), true);
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700639 ASSERT_TRUE(status.ok()) << status;
640
641 // Get a test private key.
642 auto ecies_key = test::GetEciesAesGcmHkdfTestKey(
643 EllipticCurveType::NIST_P256, EcPointFormat::UNCOMPRESSED,
644 HashType::SHA256, /* aes_gcm_key_size= */ 24);
645
646 // Extract public key data and check.
647 auto public_key_data_result = Registry::GetPublicKeyData(
tholenst12f99702019-08-20 07:52:02 -0700648 EciesAeadHkdfPrivateKeyManager().get_key_type(),
Thomas Holenstein5ff42362018-09-27 09:24:36 -0700649 ecies_key.SerializeAsString());
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700650 EXPECT_TRUE(public_key_data_result.ok()) << public_key_data_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700651 auto public_key_data = std::move(public_key_data_result.value());
tholenst12f99702019-08-20 07:52:02 -0700652 EXPECT_EQ(EciesAeadHkdfPublicKeyManager().get_key_type(),
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700653 public_key_data->type_url());
654 EXPECT_EQ(KeyData::ASYMMETRIC_PUBLIC, public_key_data->key_material_type());
655 EXPECT_EQ(ecies_key.public_key().SerializeAsString(),
656 public_key_data->value());
657
658 // Try with a wrong key type.
659 auto wrong_key_type_result = Registry::GetPublicKeyData(
tholenstb9615a32019-08-06 08:47:31 -0700660 AesGcmKeyManager().get_key_type(), ecies_key.SerializeAsString());
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700661 EXPECT_FALSE(wrong_key_type_result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700662 EXPECT_EQ(absl::StatusCode::kInvalidArgument,
663 wrong_key_type_result.status().code());
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700664 EXPECT_PRED_FORMAT2(testing::IsSubstring, "PrivateKeyFactory",
lizatretyakova32291ec2021-11-01 09:19:03 -0700665 std::string(wrong_key_type_result.status().message()));
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700666
667 // Try with a bad serialized key.
668 auto bad_key_result = Registry::GetPublicKeyData(
tholenst12f99702019-08-20 07:52:02 -0700669 EciesAeadHkdfPrivateKeyManager().get_key_type(),
Thomas Holenstein5ff42362018-09-27 09:24:36 -0700670 "some bad serialized key");
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700671 EXPECT_FALSE(bad_key_result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700672 EXPECT_EQ(absl::StatusCode::kInvalidArgument, bad_key_result.status().code());
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700673 EXPECT_PRED_FORMAT2(testing::IsSubstring, "Could not parse",
lizatretyakova32291ec2021-11-01 09:19:03 -0700674 std::string(bad_key_result.status().message()));
Bartosz Przydatekf8ebc9f2018-07-27 00:27:34 -0700675}
676
tholenst8e19ab52018-10-25 03:24:16 -0700677// Tests that if we register the same type of wrapper twice, the second call
678// succeeds.
679TEST_F(RegistryTest, RegisterWrapperTwice) {
680 EXPECT_TRUE(
681 Registry::RegisterPrimitiveWrapper(absl::make_unique<AeadWrapper>())
682 .ok());
683 EXPECT_TRUE(
684 Registry::RegisterPrimitiveWrapper(absl::make_unique<AeadWrapper>())
685 .ok());
686}
687
tholenst8730bbe2020-11-30 03:03:51 -0800688// Tests that if we register the same type of wrapper twice, the second call
689// succeeds.
690TEST_F(RegistryTest, RegisterTransformingWrapperTwice) {
691 EXPECT_TRUE(Registry::RegisterPrimitiveWrapper(
692 absl::make_unique<AeadVariantToStringWrapper>())
693 .ok());
694 EXPECT_TRUE(Registry::RegisterPrimitiveWrapper(
695 absl::make_unique<AeadVariantToStringWrapper>())
696 .ok());
697}
698
699// Test that if we register a second wrapper, wrapping to the same type as a
700// previous wrapper it will fail.
701TEST_F(RegistryTest, RegisterTransformingWrapperTwiceMixing) {
702 EXPECT_TRUE(Registry::RegisterPrimitiveWrapper(
703 absl::make_unique<AeadVariantToStringWrapper>())
704 .ok());
705 // We cannot register a different wrapper creating a std::string.
706 EXPECT_THAT(Registry::RegisterPrimitiveWrapper(
707 absl::make_unique<TestWrapper<std::string>>()),
708 Not(IsOk()));
709 // But one creating an Aead.
710 EXPECT_THAT(Registry::RegisterPrimitiveWrapper(
711 absl::make_unique<TestWrapper<AeadVariant>>()),
712 IsOk());
713}
714
715// Test that if we register a second wrapper, wrapping to the same type as a
716// previous wrapper it will fail (order swapped).
717TEST_F(RegistryTest, RegisterTransformingWrapperTwiceMixingBackwards) {
718 EXPECT_THAT(Registry::RegisterPrimitiveWrapper(
719 absl::make_unique<TestWrapper<std::string>>()),
720 IsOk());
721 // We cannot register another wrapper producing strings.
722 EXPECT_THAT(Registry::RegisterPrimitiveWrapper(
723 absl::make_unique<AeadVariantToStringWrapper>()),
724 Not(IsOk()));
725}
726
tholenst8e19ab52018-10-25 03:24:16 -0700727// Tests that if we register different wrappers for the same primitive twice,
728// the second call fails.
729TEST_F(RegistryTest, RegisterDifferentWrappers) {
730 EXPECT_TRUE(
731 Registry::RegisterPrimitiveWrapper(absl::make_unique<AeadWrapper>())
732 .ok());
733 util::Status result = Registry::RegisterPrimitiveWrapper(
734 absl::make_unique<TestWrapper<Aead>>());
735 EXPECT_FALSE(result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700736 EXPECT_EQ(absl::StatusCode::kAlreadyExists, result.code());
tholenst8e19ab52018-10-25 03:24:16 -0700737}
738
739// Tests that if we register different wrappers for different primitives, this
740// returns ok.
741TEST_F(RegistryTest, RegisterDifferentWrappersDifferentPrimitives) {
742 EXPECT_TRUE(
743 Registry::RegisterPrimitiveWrapper(absl::make_unique<TestWrapper<Aead>>())
744 .ok());
745 EXPECT_TRUE(
746 Registry::RegisterPrimitiveWrapper(absl::make_unique<TestWrapper<Mac>>())
747 .ok());
748}
749
750// Tests that if we do not register a wrapper, then calls to Wrap
751// fail with "No wrapper registered" -- even if there is a wrapper for a
752// different primitive registered.
753TEST_F(RegistryTest, NoWrapperRegistered) {
754 EXPECT_TRUE(
755 Registry::RegisterPrimitiveWrapper(absl::make_unique<TestWrapper<Mac>>())
756 .ok());
757
758 crypto::tink::util::StatusOr<std::unique_ptr<Aead>> result =
759 Registry::Wrap<Aead>(absl::make_unique<PrimitiveSet<Aead>>());
760 EXPECT_FALSE(result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700761 EXPECT_EQ(absl::StatusCode::kNotFound, result.status().code());
tholenst8e19ab52018-10-25 03:24:16 -0700762 EXPECT_PRED_FORMAT2(testing::IsSubstring, "No wrapper registered",
lizatretyakova32291ec2021-11-01 09:19:03 -0700763 std::string(result.status().message()));
tholenst8e19ab52018-10-25 03:24:16 -0700764}
765
766// Tests that if the wrapper fails, the error of the wrapped is forwarded
767// in GetWrappedPrimitive.
768TEST_F(RegistryTest, WrapperFails) {
769 EXPECT_TRUE(
770 Registry::RegisterPrimitiveWrapper(absl::make_unique<TestWrapper<Aead>>())
771 .ok());
772
773 crypto::tink::util::StatusOr<std::unique_ptr<Aead>> result =
774 Registry::Wrap<Aead>(absl::make_unique<PrimitiveSet<Aead>>());
775 EXPECT_FALSE(result.ok());
776 EXPECT_PRED_FORMAT2(testing::IsSubstring, "This is a test wrapper",
lizatretyakova32291ec2021-11-01 09:19:03 -0700777 std::string(result.status().message()));
tholenst8e19ab52018-10-25 03:24:16 -0700778}
779
780// Tests that wrapping works as expected in the usual case.
781TEST_F(RegistryTest, UsualWrappingTest) {
tholenst815e5c32020-10-09 04:45:35 -0700782 KeysetInfo keyset_info;
tholenst8e19ab52018-10-25 03:24:16 -0700783
tholenst815e5c32020-10-09 04:45:35 -0700784 keyset_info.add_key_info();
785 keyset_info.mutable_key_info(0)->set_output_prefix_type(
786 OutputPrefixType::TINK);
787 keyset_info.mutable_key_info(0)->set_key_id(1234543);
788 keyset_info.mutable_key_info(0)->set_status(KeyStatusType::ENABLED);
789 keyset_info.add_key_info();
790 keyset_info.mutable_key_info(1)->set_output_prefix_type(
791 OutputPrefixType::LEGACY);
792 keyset_info.mutable_key_info(1)->set_key_id(726329);
793 keyset_info.mutable_key_info(1)->set_status(KeyStatusType::ENABLED);
794 keyset_info.add_key_info();
795 keyset_info.mutable_key_info(2)->set_output_prefix_type(
796 OutputPrefixType::TINK);
797 keyset_info.mutable_key_info(2)->set_key_id(7213743);
798 keyset_info.mutable_key_info(2)->set_status(KeyStatusType::ENABLED);
tholenst8e19ab52018-10-25 03:24:16 -0700799
800 auto primitive_set = absl::make_unique<PrimitiveSet<Aead>>();
tholenst815e5c32020-10-09 04:45:35 -0700801 ASSERT_TRUE(primitive_set
802 ->AddPrimitive(absl::make_unique<DummyAead>("aead0"),
803 keyset_info.key_info(0))
804 .ok());
805 ASSERT_TRUE(primitive_set
806 ->AddPrimitive(absl::make_unique<DummyAead>("aead1"),
807 keyset_info.key_info(1))
808 .ok());
tholenst8e19ab52018-10-25 03:24:16 -0700809 auto entry_result = primitive_set->AddPrimitive(
tholenst815e5c32020-10-09 04:45:35 -0700810 absl::make_unique<DummyAead>("primary_aead"), keyset_info.key_info(2));
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700811 ASSERT_THAT(primitive_set->set_primary(entry_result.value()), IsOk());
tholenst8e19ab52018-10-25 03:24:16 -0700812
813 EXPECT_TRUE(
814 Registry::RegisterPrimitiveWrapper(absl::make_unique<AeadWrapper>())
815 .ok());
816
817 auto aead_result = Registry::Wrap<Aead>(std::move(primitive_set));
818 EXPECT_TRUE(aead_result.ok()) << aead_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700819 std::unique_ptr<Aead> aead = std::move(aead_result.value());
tholenst8e19ab52018-10-25 03:24:16 -0700820 std::string plaintext = "some_plaintext";
821 std::string aad = "some_aad";
822
823 auto encrypt_result = aead->Encrypt(plaintext, aad);
824 EXPECT_TRUE(encrypt_result.ok()) << encrypt_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700825 std::string ciphertext = encrypt_result.value();
tholenst8e19ab52018-10-25 03:24:16 -0700826 EXPECT_PRED_FORMAT2(testing::IsSubstring, "primary_aead", ciphertext);
827
828 auto decrypt_result = aead->Decrypt(ciphertext, aad);
829 EXPECT_TRUE(decrypt_result.ok()) << decrypt_result.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700830 EXPECT_EQ(plaintext, decrypt_result.value());
tholenst8e19ab52018-10-25 03:24:16 -0700831
832 decrypt_result = aead->Decrypt("some bad ciphertext", aad);
833 EXPECT_FALSE(decrypt_result.ok());
lizatretyakovaf8494972021-09-23 06:01:32 -0700834 EXPECT_EQ(absl::StatusCode::kInvalidArgument, decrypt_result.status().code());
tholenst8e19ab52018-10-25 03:24:16 -0700835 EXPECT_PRED_FORMAT2(testing::IsSubstring, "decryption failed",
lizatretyakova32291ec2021-11-01 09:19:03 -0700836 std::string(decrypt_result.status().message()));
tholenst8e19ab52018-10-25 03:24:16 -0700837}
838
tholenst8730bbe2020-11-30 03:03:51 -0800839std::string AddAesGcmKey(uint32_t key_id, OutputPrefixType output_prefix_type,
840 KeyStatusType key_status_type,
841 Keyset& modified_keyset) {
842 AesGcmKey key;
843 key.set_version(0);
844 key.set_key_value(subtle::Random::GetRandomBytes(16));
845 KeyData key_data;
846 key_data.set_value(key.SerializeAsString());
847 key_data.set_type_url("type.googleapis.com/google.crypto.tink.AesGcmKey");
848 test::AddKeyData(key_data, key_id, output_prefix_type, key_status_type,
849 &modified_keyset);
850 return key.key_value();
851}
852
853// Tests that wrapping of a keyset works in the usual case.
854TEST_F(RegistryTest, KeysetWrappingTest) {
ambrosin113db292023-04-20 06:13:22 -0700855 if (!IsFipsEnabledInSsl()) {
ksteff83c0b2021-04-06 03:12:44 -0700856 GTEST_SKIP() << "Not supported when BoringSSL is not built in FIPS-mode.";
857 }
858
tholenst8730bbe2020-11-30 03:03:51 -0800859 Keyset keyset;
860 std::string raw_key =
861 AddAesGcmKey(13, OutputPrefixType::TINK, KeyStatusType::ENABLED, keyset);
862 keyset.set_primary_key_id(13);
863
ksteff83c0b2021-04-06 03:12:44 -0700864 auto fips_key_manager = absl::make_unique<ExampleKeyTypeManager>();
865
866 ON_CALL(*fips_key_manager, FipsStatus())
867 .WillByDefault(testing::Return(FipsCompatibility::kRequiresBoringCrypto));
868
cinlin063c4ea2023-03-07 12:43:13 -0800869 ASSERT_THAT(
870 Registry::RegisterKeyTypeManager(std::move(fips_key_manager), true),
871 IsOk());
tholenst8730bbe2020-11-30 03:03:51 -0800872 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
873 absl::make_unique<AeadVariantWrapper>()),
874 IsOk());
875
876 crypto::tink::util::StatusOr<std::unique_ptr<AeadVariant>> aead_variant =
ambrosincd84da62022-03-30 07:44:28 -0700877 RegistryImpl::GlobalInstance().WrapKeyset<AeadVariant>(
878 keyset, /*annotations=*/{});
kste52259432022-06-22 02:44:47 -0700879 EXPECT_THAT(aead_variant, IsOk());
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700880 EXPECT_THAT(aead_variant.value()->get(), Eq(raw_key));
tholenst8730bbe2020-11-30 03:03:51 -0800881}
882
883// Tests that wrapping of a keyset works.
884TEST_F(RegistryTest, TransformingKeysetWrappingTest) {
ksteff83c0b2021-04-06 03:12:44 -0700885 if (kUseOnlyFips) {
886 GTEST_SKIP() << "Not supported in FIPS-only mode";
887 }
888
tholenst8730bbe2020-11-30 03:03:51 -0800889 Keyset keyset;
890 std::string raw_key =
891 AddAesGcmKey(13, OutputPrefixType::TINK, KeyStatusType::ENABLED, keyset);
892 keyset.set_primary_key_id(13);
893
894 ASSERT_THAT(Registry::RegisterKeyTypeManager(
895 absl::make_unique<ExampleKeyTypeManager>(), true),
896 IsOk());
897 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
898 absl::make_unique<AeadVariantToStringWrapper>()),
899 IsOk());
900
901 crypto::tink::util::StatusOr<std::unique_ptr<std::string>> string_primitive =
ambrosincd84da62022-03-30 07:44:28 -0700902 RegistryImpl::GlobalInstance().WrapKeyset<std::string>(
903 keyset, /*annotations=*/{});
kste52259432022-06-22 02:44:47 -0700904 EXPECT_THAT(string_primitive, IsOk());
lizatretyakovaf7ea7c62022-03-21 04:40:31 -0700905 EXPECT_THAT(*string_primitive.value(), Eq(raw_key));
tholenst8730bbe2020-11-30 03:03:51 -0800906}
907
908// Tests that when we ask the registry to wrap a PrimitiveSet<Aead> into an
909// Aead, but the wrapper is in fact from something else into Aead, we give a
910// correct error message.
911TEST_F(RegistryTest, TransformingPrimitiveWrapperCustomKeyManager) {
ksteff83c0b2021-04-06 03:12:44 -0700912 if (kUseOnlyFips) {
913 GTEST_SKIP() << "Not supported in FIPS-only mode";
914 }
915
tholenst8730bbe2020-11-30 03:03:51 -0800916 ASSERT_THAT(Registry::RegisterKeyTypeManager(
917 absl::make_unique<ExampleKeyTypeManager>(), true),
918 IsOk());
919 // Register a transforming wrapper taking strings and making Aeads.
920 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
921 absl::make_unique<TestWrapper<std::string, Aead>>()),
922 IsOk());
923
924 KeysetInfo keyset_info;
925 keyset_info.add_key_info();
926 keyset_info.mutable_key_info(0)->set_output_prefix_type(
927 OutputPrefixType::TINK);
928 keyset_info.mutable_key_info(0)->set_key_id(1234543);
929 keyset_info.mutable_key_info(0)->set_status(KeyStatusType::ENABLED);
930 keyset_info.set_primary_key_id(1234543);
931
932 auto primitive_set = absl::make_unique<PrimitiveSet<Aead>>();
933 ASSERT_TRUE(primitive_set
934 ->AddPrimitive(absl::make_unique<DummyAead>("aead0"),
935 keyset_info.key_info(0))
936 .ok());
937
938 EXPECT_THAT(Registry::Wrap<Aead>(std::move(primitive_set)).status(),
lizatretyakova89e7db92021-10-21 03:39:12 -0700939 StatusIs(absl::StatusCode::kFailedPrecondition,
tholenst8730bbe2020-11-30 03:03:51 -0800940 HasSubstr("custom key manager")));
941}
942
tholenst7997b262019-04-10 08:13:35 -0700943// Tests that the error message in GetKeyManager contains the type_id.name() of
944// the primitive for which the key manager was actually registered.
945TEST_F(RegistryTest, GetKeyManagerErrorMessage) {
tholenstb9615a32019-08-06 08:47:31 -0700946 AesGcmKeyManager key_type_manager;
tholenst7997b262019-04-10 08:13:35 -0700947 EXPECT_TRUE(
tholenstb9615a32019-08-06 08:47:31 -0700948 Registry::RegisterKeyManager(
949 crypto::tink::internal::MakeKeyManager<Aead>(&key_type_manager), true)
tholenst7997b262019-04-10 08:13:35 -0700950 .ok());
951 auto result =
952 Registry::get_key_manager<int>(AesGcmKeyManager().get_key_type());
953 EXPECT_FALSE(result.ok());
lizatretyakova32291ec2021-11-01 09:19:03 -0700954 EXPECT_THAT(std::string(result.status().message()),
tholensteba05212019-06-04 01:50:34 -0700955 HasSubstr(AesGcmKeyManager().get_key_type()));
tholenst7997b262019-04-10 08:13:35 -0700956 // Note: The C++ standard does not guarantee the next line. If some toolchain
957 // update fails it, one can delete it.
lizatretyakova32291ec2021-11-01 09:19:03 -0700958 EXPECT_THAT(std::string(result.status().message()),
959 HasSubstr(typeid(Aead).name()));
tholenst7997b262019-04-10 08:13:35 -0700960}
961
tholenst6ddf0912019-07-29 06:11:04 -0700962TEST_F(RegistryTest, RegisterKeyTypeManager) {
ksteff83c0b2021-04-06 03:12:44 -0700963 if (kUseOnlyFips) {
964 GTEST_SKIP() << "Not supported in FIPS-only mode";
965 }
966
tholenst6ddf0912019-07-29 06:11:04 -0700967 EXPECT_THAT(Registry::RegisterKeyTypeManager(
968 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -0700969 IsOk());
970}
971
ksteff83c0b2021-04-06 03:12:44 -0700972TEST_F(RegistryTest, RegisterFipsKeyTypeManager) {
ambrosin113db292023-04-20 06:13:22 -0700973 if (!kUseOnlyFips || !IsFipsEnabledInSsl()) {
ksteff83c0b2021-04-06 03:12:44 -0700974 GTEST_SKIP() << "Only supported in FIPS-mode with BoringCrypto available.";
975 }
976
977 auto fips_key_manager = absl::make_unique<ExampleKeyTypeManager>();
978
979 ON_CALL(*fips_key_manager, FipsStatus())
980 .WillByDefault(testing::Return(FipsCompatibility::kRequiresBoringCrypto));
981
982 EXPECT_THAT(
983 Registry::RegisterKeyTypeManager(std::move(fips_key_manager), true),
984 IsOk());
985}
986
987TEST_F(RegistryTest, RegisterFipsKeyTypeManagerNoBoringCrypto) {
ambrosin113db292023-04-20 06:13:22 -0700988 if (!kUseOnlyFips || IsFipsEnabledInSsl()) {
ksteff83c0b2021-04-06 03:12:44 -0700989 GTEST_SKIP()
990 << "Only supported in FIPS-mode with BoringCrypto not available.";
991 }
992
993 auto fips_key_manager = absl::make_unique<ExampleKeyTypeManager>();
994
995 ON_CALL(*fips_key_manager, FipsStatus())
996 .WillByDefault(testing::Return(FipsCompatibility::kNotFips));
997
998 EXPECT_THAT(
999 Registry::RegisterKeyTypeManager(std::move(fips_key_manager), true),
lizatretyakova456657f2021-11-01 05:48:32 -07001000 StatusIs(absl::StatusCode::kInternal));
ksteff83c0b2021-04-06 03:12:44 -07001001}
1002
tholenst6ddf0912019-07-29 06:11:04 -07001003TEST_F(RegistryTest, KeyTypeManagerGetFirstKeyManager) {
ksteff83c0b2021-04-06 03:12:44 -07001004 if (kUseOnlyFips) {
1005 GTEST_SKIP() << "Not supported in FIPS-only mode";
1006 }
1007
tholenst6ddf0912019-07-29 06:11:04 -07001008 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1009 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001010 IsOk());
1011 AesGcmKeyFormat format;
1012 format.set_key_size(16);
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001013 AesGcmKey key = ExampleKeyTypeManager().CreateKey(format).value();
tholenst7ea3c182019-06-17 04:35:05 -07001014 auto aead = Registry::get_key_manager<Aead>(
1015 "type.googleapis.com/google.crypto.tink.AesGcmKey")
lizatretyakova22913ee2022-03-23 06:45:43 -07001016 .value()
tholenst7ea3c182019-06-17 04:35:05 -07001017 ->GetPrimitive(key)
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001018 .value();
1019 std::string encryption = aead->Encrypt("TESTMESSAGE", "").value();
1020 std::string decryption = aead->Decrypt(encryption, "").value();
tholenst7ea3c182019-06-17 04:35:05 -07001021 EXPECT_THAT(decryption, Eq("TESTMESSAGE"));
1022}
1023
tholenst6ddf0912019-07-29 06:11:04 -07001024TEST_F(RegistryTest, KeyTypeManagerGetSecondKeyManager) {
ksteff83c0b2021-04-06 03:12:44 -07001025 if (kUseOnlyFips) {
1026 GTEST_SKIP() << "Not supported in FIPS-only mode";
1027 }
1028
tholenst6ddf0912019-07-29 06:11:04 -07001029 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1030 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001031 IsOk());
1032 AesGcmKeyFormat format;
1033 format.set_key_size(16);
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001034 AesGcmKey key = ExampleKeyTypeManager().CreateKey(format).value();
tholenst7ea3c182019-06-17 04:35:05 -07001035 auto aead_variant = Registry::get_key_manager<AeadVariant>(
1036 "type.googleapis.com/google.crypto.tink.AesGcmKey")
lizatretyakova22913ee2022-03-23 06:45:43 -07001037 .value()
tholenst7ea3c182019-06-17 04:35:05 -07001038 ->GetPrimitive(key)
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001039 .value();
tholenst7ea3c182019-06-17 04:35:05 -07001040 EXPECT_THAT(aead_variant->get(), Eq(key.key_value()));
1041}
1042
tholenst6ddf0912019-07-29 06:11:04 -07001043TEST_F(RegistryTest, KeyTypeManagerNotSupportedPrimitive) {
ksteff83c0b2021-04-06 03:12:44 -07001044 if (kUseOnlyFips) {
1045 GTEST_SKIP() << "Not supported in FIPS-only mode";
1046 }
1047
tholenst6ddf0912019-07-29 06:11:04 -07001048 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1049 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001050 IsOk());
1051 EXPECT_THAT(Registry::get_key_manager<Mac>(
1052 "type.googleapis.com/google.crypto.tink.AesGcmKey")
1053 .status(),
lizatretyakova01f69192021-11-05 09:10:40 -07001054 StatusIs(absl::StatusCode::kInvalidArgument,
tholenst7ea3c182019-06-17 04:35:05 -07001055 HasSubstr("not among supported primitives")));
1056}
1057
tholenst77b67402019-11-08 04:45:41 -08001058// Tests that if we register a key manager once more after a call to
1059// get_key_manager, the key manager previously obtained with "get_key_manager()"
1060// remains valid.
1061TEST_F(RegistryTest, GetKeyManagerRemainsValidForKeyTypeManagers) {
ksteff83c0b2021-04-06 03:12:44 -07001062 if (kUseOnlyFips) {
1063 GTEST_SKIP() << "Not supported in FIPS-only mode";
1064 }
1065
tholenst77b67402019-11-08 04:45:41 -08001066 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1067 absl::make_unique<ExampleKeyTypeManager>(), true),
1068 IsOk());
1069
1070 crypto::tink::util::StatusOr<const KeyManager<Aead>*> key_manager =
1071 Registry::get_key_manager<Aead>(ExampleKeyTypeManager().get_key_type());
kste52259432022-06-22 02:44:47 -07001072 ASSERT_THAT(key_manager, IsOk());
tholenst77b67402019-11-08 04:45:41 -08001073 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1074 absl::make_unique<ExampleKeyTypeManager>(), true),
1075 IsOk());
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001076 EXPECT_THAT(key_manager.value()->get_key_type(),
tholenst77b67402019-11-08 04:45:41 -08001077 Eq(ExampleKeyTypeManager().get_key_type()));
1078}
1079
tholenst6ddf0912019-07-29 06:11:04 -07001080TEST_F(RegistryTest, KeyTypeManagerNewKey) {
ksteff83c0b2021-04-06 03:12:44 -07001081 if (kUseOnlyFips) {
1082 GTEST_SKIP() << "Not supported in FIPS-only mode";
1083 }
1084
tholenst6ddf0912019-07-29 06:11:04 -07001085 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1086 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001087 IsOk());
1088
1089 AesGcmKeyFormat format;
1090 format.set_key_size(32);
1091 KeyTemplate key_template;
1092 key_template.set_type_url("type.googleapis.com/google.crypto.tink.AesGcmKey");
1093 key_template.set_value(format.SerializeAsString());
1094
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001095 KeyData key_data = *Registry::NewKeyData(key_template).value();
tholenst7ea3c182019-06-17 04:35:05 -07001096 EXPECT_THAT(key_data.type_url(),
1097 Eq("type.googleapis.com/google.crypto.tink.AesGcmKey"));
1098 EXPECT_THAT(key_data.key_material_type(),
1099 Eq(google::crypto::tink::KeyData::SYMMETRIC));
1100 AesGcmKey key;
1101 key.ParseFromString(key_data.value());
1102 EXPECT_THAT(key.key_value(), SizeIs(32));
1103}
1104
tholenst6ddf0912019-07-29 06:11:04 -07001105TEST_F(RegistryTest, KeyTypeManagerNewKeyInvalidSize) {
ksteff83c0b2021-04-06 03:12:44 -07001106 if (kUseOnlyFips) {
1107 GTEST_SKIP() << "Not supported in FIPS-only mode";
1108 }
1109
tholenst6ddf0912019-07-29 06:11:04 -07001110 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1111 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001112 IsOk());
1113
1114 AesGcmKeyFormat format;
1115 format.set_key_size(33);
1116 KeyTemplate key_template;
1117 key_template.set_type_url("type.googleapis.com/google.crypto.tink.AesGcmKey");
1118 key_template.set_value(format.SerializeAsString());
1119
kste52259432022-06-22 02:44:47 -07001120 EXPECT_THAT(Registry::NewKeyData(key_template), IsOk());
tholenst7ea3c182019-06-17 04:35:05 -07001121}
1122
tholenst92a53962019-11-04 01:08:16 -08001123TEST_F(RegistryTest, KeyTypeManagerDeriveKey) {
ksteff83c0b2021-04-06 03:12:44 -07001124 if (kUseOnlyFips) {
1125 GTEST_SKIP() << "Not supported in FIPS-only mode";
1126 }
1127
tholenst92a53962019-11-04 01:08:16 -08001128 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1129 absl::make_unique<ExampleKeyTypeManager>(), true),
1130 IsOk());
1131
1132 AesGcmKeyFormat format;
1133 format.set_key_size(32);
1134 KeyTemplate key_template;
1135 key_template.set_type_url("type.googleapis.com/google.crypto.tink.AesGcmKey");
1136 key_template.set_value(format.SerializeAsString());
1137
1138 crypto::tink::util::IstreamInputStream input_stream{
1139 absl::make_unique<std::stringstream>(
1140 "0123456789012345678901234567890123456789")};
1141
1142 auto key_data_or =
1143 RegistryImpl::GlobalInstance().DeriveKey(key_template, &input_stream);
kste52259432022-06-22 02:44:47 -07001144 ASSERT_THAT(key_data_or, IsOk());
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001145 EXPECT_THAT(key_data_or.value().type_url(), Eq(key_template.type_url()));
tholenst92a53962019-11-04 01:08:16 -08001146 AesGcmKey key;
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001147 EXPECT_TRUE(key.ParseFromString(key_data_or.value().value()));
tholenst92a53962019-11-04 01:08:16 -08001148 // 32 byte prefix of above string.
1149 EXPECT_THAT(key.key_value(), Eq("01234567890123456789012345678901"));
1150}
1151
1152// The same, but we register the key manager twice. This should catch some of
1153// the possible lifetime issues.
1154TEST_F(RegistryTest, KeyTypeManagerDeriveKeyRegisterTwice) {
ksteff83c0b2021-04-06 03:12:44 -07001155 if (kUseOnlyFips) {
1156 GTEST_SKIP() << "Not supported in FIPS-only mode";
1157 }
1158
tholenst92a53962019-11-04 01:08:16 -08001159 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1160 absl::make_unique<ExampleKeyTypeManager>(), true),
1161 IsOk());
1162 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1163 absl::make_unique<ExampleKeyTypeManager>(), true),
1164 IsOk());
1165
1166 AesGcmKeyFormat format;
1167 format.set_key_size(32);
1168 KeyTemplate key_template;
1169 key_template.set_type_url("type.googleapis.com/google.crypto.tink.AesGcmKey");
1170 key_template.set_value(format.SerializeAsString());
1171
1172 crypto::tink::util::IstreamInputStream input_stream{
1173 absl::make_unique<std::stringstream>(
1174 "0123456789012345678901234567890123456789")};
1175
1176 auto key_data_or =
1177 RegistryImpl::GlobalInstance().DeriveKey(key_template, &input_stream);
kste52259432022-06-22 02:44:47 -07001178 ASSERT_THAT(key_data_or, IsOk());
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001179 EXPECT_THAT(key_data_or.value().type_url(), Eq(key_template.type_url()));
tholenst92a53962019-11-04 01:08:16 -08001180 AesGcmKey key;
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001181 EXPECT_TRUE(key.ParseFromString(key_data_or.value().value()));
tholenst92a53962019-11-04 01:08:16 -08001182 // 32 byte prefix of above string.
1183 EXPECT_THAT(key.key_value(), Eq("01234567890123456789012345678901"));
1184}
1185
1186// Tests that if we register a KeyManager instead of a KeyTypeManager, DeriveKey
1187// fails properly.
1188TEST_F(RegistryTest, KeyManagerDeriveKeyFail) {
1189 std::string key_type = "type.googleapis.com/google.crypto.tink.AesGcmKey";
1190 ASSERT_THAT(Registry::RegisterKeyManager(
cinlin063c4ea2023-03-07 12:43:13 -08001191 absl::make_unique<TestAeadKeyManager>(key_type),
1192 /* new_key_allowed= */ true),
1193 IsOk());
tholenst92a53962019-11-04 01:08:16 -08001194
1195 KeyTemplate key_template;
1196 key_template.set_type_url("type.googleapis.com/google.crypto.tink.AesGcmKey");
1197
1198 EXPECT_THAT(
1199 RegistryImpl::GlobalInstance().DeriveKey(key_template, nullptr).status(),
lizatretyakova01f69192021-11-05 09:10:40 -07001200 StatusIs(absl::StatusCode::kInvalidArgument, HasSubstr("cannot derive")));
tholenst92a53962019-11-04 01:08:16 -08001201}
1202
1203TEST_F(RegistryTest, KeyManagerDeriveNotRegistered) {
1204 KeyTemplate key_template;
1205 key_template.set_type_url("some_inexistent_keytype");
1206
1207 EXPECT_THAT(
1208 RegistryImpl::GlobalInstance().DeriveKey(key_template, nullptr).status(),
lizatretyakova62f2f0d2021-10-29 04:41:48 -07001209 StatusIs(absl::StatusCode::kNotFound, HasSubstr("No manager")));
tholenst92a53962019-11-04 01:08:16 -08001210}
1211
tholenst6ddf0912019-07-29 06:11:04 -07001212TEST_F(RegistryTest, RegisterKeyTypeManagerTwiceMoreRestrictive) {
ksteff83c0b2021-04-06 03:12:44 -07001213 if (kUseOnlyFips) {
1214 GTEST_SKIP() << "Not supported in FIPS-only mode";
1215 }
1216
tholenst6ddf0912019-07-29 06:11:04 -07001217 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1218 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001219 IsOk());
tholenst6ddf0912019-07-29 06:11:04 -07001220 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1221 absl::make_unique<ExampleKeyTypeManager>(), false),
tholenst7ea3c182019-06-17 04:35:05 -07001222 IsOk());
1223}
1224
tholenst6ddf0912019-07-29 06:11:04 -07001225TEST_F(RegistryTest, RegisterKeyTypeManagerTwice) {
ksteff83c0b2021-04-06 03:12:44 -07001226 if (kUseOnlyFips) {
1227 GTEST_SKIP() << "Not supported in FIPS-only mode";
1228 }
1229
tholenst6ddf0912019-07-29 06:11:04 -07001230 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1231 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001232 IsOk());
tholenst6ddf0912019-07-29 06:11:04 -07001233 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1234 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001235 IsOk());
tholenst6ddf0912019-07-29 06:11:04 -07001236 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1237 absl::make_unique<ExampleKeyTypeManager>(), false),
tholenst7ea3c182019-06-17 04:35:05 -07001238 IsOk());
tholenst6ddf0912019-07-29 06:11:04 -07001239 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1240 absl::make_unique<ExampleKeyTypeManager>(), false),
tholenst7ea3c182019-06-17 04:35:05 -07001241 IsOk());
1242}
1243
tholenst6ddf0912019-07-29 06:11:04 -07001244TEST_F(RegistryTest, RegisterKeyTypeManagerLessRestrictive) {
ksteff83c0b2021-04-06 03:12:44 -07001245 if (kUseOnlyFips) {
1246 GTEST_SKIP() << "Not supported in FIPS-only mode";
1247 }
1248
tholenst6ddf0912019-07-29 06:11:04 -07001249 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1250 absl::make_unique<ExampleKeyTypeManager>(), false),
tholenst7ea3c182019-06-17 04:35:05 -07001251 IsOk());
tholenst6ddf0912019-07-29 06:11:04 -07001252 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1253 absl::make_unique<ExampleKeyTypeManager>(), true),
lizatretyakova6e2829b2021-10-29 08:11:49 -07001254 StatusIs(absl::StatusCode::kAlreadyExists));
tholenst7ea3c182019-06-17 04:35:05 -07001255}
1256
tholenst6ddf0912019-07-29 06:11:04 -07001257TEST_F(RegistryTest, RegisterKeyTypeManagerBeforeKeyManager) {
ksteff83c0b2021-04-06 03:12:44 -07001258 if (kUseOnlyFips) {
1259 GTEST_SKIP() << "Not supported in FIPS-only mode";
1260 }
1261
tholenst6ddf0912019-07-29 06:11:04 -07001262 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1263 absl::make_unique<ExampleKeyTypeManager>(), true),
tholenst7ea3c182019-06-17 04:35:05 -07001264 IsOk());
1265 EXPECT_THAT(Registry::RegisterKeyManager(
1266 absl::make_unique<TestAeadKeyManager>(
1267 "type.googleapis.com/google.crypto.tink.AesGcmKey"),
1268 true),
lizatretyakova6e2829b2021-10-29 08:11:49 -07001269 StatusIs(absl::StatusCode::kAlreadyExists));
tholenst7ea3c182019-06-17 04:35:05 -07001270}
1271
tholenst6ddf0912019-07-29 06:11:04 -07001272TEST_F(RegistryTest, RegisterKeyTypeManagerAfterKeyManager) {
ksteff83c0b2021-04-06 03:12:44 -07001273 if (kUseOnlyFips) {
1274 GTEST_SKIP() << "Not supported in FIPS-only mode";
1275 }
1276
tholenst7ea3c182019-06-17 04:35:05 -07001277 EXPECT_THAT(Registry::RegisterKeyManager(
1278 absl::make_unique<TestAeadKeyManager>(
1279 "type.googleapis.com/google.crypto.tink.AesGcmKey"),
1280 true),
1281 IsOk());
tholenst6ddf0912019-07-29 06:11:04 -07001282 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1283 absl::make_unique<ExampleKeyTypeManager>(), true),
lizatretyakova6e2829b2021-10-29 08:11:49 -07001284 StatusIs(absl::StatusCode::kAlreadyExists));
tholenst7ea3c182019-06-17 04:35:05 -07001285}
1286
ambrosin400ef412023-02-02 04:32:09 -08001287} // namespace
1288
1289// NOTE: These are outside of the anonymous namespace to allow compiling with
1290// MSVC.
tholenst95120392019-07-10 03:30:39 -07001291class PrivatePrimitiveA {};
1292class PrivatePrimitiveB {};
1293
ambrosin400ef412023-02-02 04:32:09 -08001294namespace {
1295
tholenst6ddf0912019-07-29 06:11:04 -07001296class TestPrivateKeyTypeManager
1297 : public PrivateKeyTypeManager<EcdsaPrivateKey, EcdsaKeyFormat,
1298 EcdsaPublicKey,
1299 List<PrivatePrimitiveA, PrivatePrimitiveB>> {
tholenst95120392019-07-10 03:30:39 -07001300 public:
1301 class PrivatePrimitiveAFactory : public PrimitiveFactory<PrivatePrimitiveA> {
1302 public:
1303 crypto::tink::util::StatusOr<std::unique_ptr<PrivatePrimitiveA>> Create(
1304 const EcdsaPrivateKey& key) const override {
lizatretyakova92fbd252021-10-19 12:41:52 -07001305 return util::Status(absl::StatusCode::kUnimplemented, "Not implemented");
tholenst95120392019-07-10 03:30:39 -07001306 }
1307 };
1308 class PrivatePrimitiveBFactory : public PrimitiveFactory<PrivatePrimitiveB> {
1309 public:
1310 crypto::tink::util::StatusOr<std::unique_ptr<PrivatePrimitiveB>> Create(
1311 const EcdsaPrivateKey& key) const override {
lizatretyakova92fbd252021-10-19 12:41:52 -07001312 return util::Status(absl::StatusCode::kUnimplemented, "Not implemented");
tholenst95120392019-07-10 03:30:39 -07001313 }
1314 };
1315
tholenst6ddf0912019-07-29 06:11:04 -07001316 TestPrivateKeyTypeManager()
1317 : PrivateKeyTypeManager(absl::make_unique<PrivatePrimitiveAFactory>(),
1318 absl::make_unique<PrivatePrimitiveBFactory>()) {}
tholenst95120392019-07-10 03:30:39 -07001319
1320 google::crypto::tink::KeyData::KeyMaterialType key_material_type()
1321 const override {
1322 return google::crypto::tink::KeyData::ASYMMETRIC_PRIVATE;
1323 }
1324
1325 uint32_t get_version() const override { return 0; }
1326 crypto::tink::util::Status ValidateKey(
1327 const EcdsaPrivateKey& key) const override {
lizatretyakova220adc22021-09-22 08:17:14 -07001328 return crypto::tink::util::OkStatus();
tholenst95120392019-07-10 03:30:39 -07001329 }
1330 crypto::tink::util::Status ValidateKeyFormat(
1331 const EcdsaKeyFormat& key) const override {
lizatretyakova220adc22021-09-22 08:17:14 -07001332 return crypto::tink::util::OkStatus();
tholenst95120392019-07-10 03:30:39 -07001333 }
1334
1335 const std::string& get_key_type() const override { return kKeyType; }
1336
1337 crypto::tink::util::StatusOr<EcdsaPrivateKey> CreateKey(
1338 const EcdsaKeyFormat& key_format) const override {
1339 EcdsaPublicKey public_key;
1340 *public_key.mutable_params() = key_format.params();
1341 EcdsaPrivateKey result;
1342 *result.mutable_public_key() = public_key;
1343 return result;
1344 }
1345
1346 crypto::tink::util::StatusOr<EcdsaPublicKey> GetPublicKey(
1347 const EcdsaPrivateKey& private_key) const override {
1348 return private_key.public_key();
1349 }
1350
kste752fc1f2021-04-07 04:04:06 -07001351 MOCK_METHOD(FipsCompatibility, FipsStatus, (), (const, override));
1352
tholenst95120392019-07-10 03:30:39 -07001353 private:
1354 const std::string kKeyType =
1355 "type.googleapis.com/google.crypto.tink.EcdsaPrivateKey";
1356};
1357
ambrosin400ef412023-02-02 04:32:09 -08001358} // namespace
1359
1360// NOTE: These are outside of the anonymous namespace to allow compiling with
1361// MSVC.
tholenst95120392019-07-10 03:30:39 -07001362class PublicPrimitiveA {};
1363class PublicPrimitiveB {};
1364
ambrosin400ef412023-02-02 04:32:09 -08001365namespace {
1366
tholenst6ddf0912019-07-29 06:11:04 -07001367class TestPublicKeyTypeManager
1368 : public KeyTypeManager<EcdsaPublicKey, void,
1369 List<PublicPrimitiveA, PublicPrimitiveB>> {
tholenst95120392019-07-10 03:30:39 -07001370 public:
1371 class PublicPrimitiveAFactory : public PrimitiveFactory<PublicPrimitiveA> {
1372 public:
1373 crypto::tink::util::StatusOr<std::unique_ptr<PublicPrimitiveA>> Create(
1374 const EcdsaPublicKey& key) const override {
lizatretyakova92fbd252021-10-19 12:41:52 -07001375 return util::Status(absl::StatusCode::kUnimplemented, "Not implemented");
tholenst95120392019-07-10 03:30:39 -07001376 }
1377 };
1378 class PublicPrimitiveBFactory : public PrimitiveFactory<PublicPrimitiveB> {
1379 public:
1380 crypto::tink::util::StatusOr<std::unique_ptr<PublicPrimitiveB>> Create(
1381 const EcdsaPublicKey& key) const override {
lizatretyakova92fbd252021-10-19 12:41:52 -07001382 return util::Status(absl::StatusCode::kUnimplemented, "Not implemented");
tholenst95120392019-07-10 03:30:39 -07001383 }
1384 };
1385
tholenst6ddf0912019-07-29 06:11:04 -07001386 TestPublicKeyTypeManager()
1387 : KeyTypeManager(absl::make_unique<PublicPrimitiveAFactory>(),
1388 absl::make_unique<PublicPrimitiveBFactory>()) {}
tholenst95120392019-07-10 03:30:39 -07001389
1390 google::crypto::tink::KeyData::KeyMaterialType key_material_type()
1391 const override {
1392 return google::crypto::tink::KeyData::ASYMMETRIC_PRIVATE;
1393 }
1394
1395 uint32_t get_version() const override { return 0; }
1396 crypto::tink::util::Status ValidateKey(
1397 const EcdsaPublicKey& key) const override {
lizatretyakova220adc22021-09-22 08:17:14 -07001398 return crypto::tink::util::OkStatus();
tholenst95120392019-07-10 03:30:39 -07001399 }
1400
1401 const std::string& get_key_type() const override { return kKeyType; }
1402
kste752fc1f2021-04-07 04:04:06 -07001403 MOCK_METHOD(FipsCompatibility, FipsStatus, (), (const, override));
1404
tholenst95120392019-07-10 03:30:39 -07001405 private:
1406 const std::string kKeyType =
1407 "type.googleapis.com/google.crypto.tink.EcdsaPublicKey";
1408};
1409
kste752fc1f2021-04-07 04:04:06 -07001410std::unique_ptr<TestPrivateKeyTypeManager>
1411CreateTestPrivateKeyManagerFipsCompatible() {
1412 auto private_key_manager = absl::make_unique<TestPrivateKeyTypeManager>();
1413 ON_CALL(*private_key_manager, FipsStatus())
1414 .WillByDefault(testing::Return(FipsCompatibility::kRequiresBoringCrypto));
1415 return private_key_manager;
1416}
1417
1418std::unique_ptr<TestPublicKeyTypeManager>
1419CreateTestPublicKeyManagerFipsCompatible() {
1420 auto public_key_manager = absl::make_unique<TestPublicKeyTypeManager>();
1421 ON_CALL(*public_key_manager, FipsStatus())
1422 .WillByDefault(testing::Return(FipsCompatibility::kRequiresBoringCrypto));
1423 return public_key_manager;
1424}
1425
tholenst95120392019-07-10 03:30:39 -07001426TEST_F(RegistryTest, RegisterAsymmetricKeyManagers) {
ambrosin113db292023-04-20 06:13:22 -07001427 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001428 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1429 "not available";
1430 }
1431
tholenst95120392019-07-10 03:30:39 -07001432 crypto::tink::util::Status status = Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001433 CreateTestPrivateKeyManagerFipsCompatible(),
1434 CreateTestPublicKeyManagerFipsCompatible(), true);
tholenst95120392019-07-10 03:30:39 -07001435 ASSERT_TRUE(status.ok()) << status;
1436}
1437
1438TEST_F(RegistryTest, AsymmetricMoreRestrictiveNewKey) {
ambrosin113db292023-04-20 06:13:22 -07001439 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001440 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1441 "not available";
1442 }
1443
tholenst95120392019-07-10 03:30:39 -07001444 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001445 CreateTestPrivateKeyManagerFipsCompatible(),
1446 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001447 .ok());
kste752fc1f2021-04-07 04:04:06 -07001448
tholenst95120392019-07-10 03:30:39 -07001449 crypto::tink::util::Status status = Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001450 CreateTestPrivateKeyManagerFipsCompatible(),
1451 CreateTestPublicKeyManagerFipsCompatible(), false);
tholenst95120392019-07-10 03:30:39 -07001452 ASSERT_TRUE(status.ok()) << status;
1453}
1454
1455TEST_F(RegistryTest, AsymmetricSameNewKey) {
ambrosin113db292023-04-20 06:13:22 -07001456 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001457 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1458 "not available";
1459 }
1460
tholenst95120392019-07-10 03:30:39 -07001461 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001462 CreateTestPrivateKeyManagerFipsCompatible(),
1463 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001464 .ok());
1465 crypto::tink::util::Status status = Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001466 CreateTestPrivateKeyManagerFipsCompatible(),
1467 CreateTestPublicKeyManagerFipsCompatible(), true);
tholenst95120392019-07-10 03:30:39 -07001468 ASSERT_TRUE(status.ok()) << status;
1469
1470 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001471 CreateTestPrivateKeyManagerFipsCompatible(),
1472 CreateTestPublicKeyManagerFipsCompatible(), false)
tholenst95120392019-07-10 03:30:39 -07001473 .ok());
1474 status = Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001475 CreateTestPrivateKeyManagerFipsCompatible(),
1476 CreateTestPublicKeyManagerFipsCompatible(), false);
tholenst95120392019-07-10 03:30:39 -07001477 ASSERT_TRUE(status.ok()) << status;
1478}
1479
1480TEST_F(RegistryTest, AsymmetricLessRestrictiveGivesError) {
ambrosin113db292023-04-20 06:13:22 -07001481 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001482 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1483 "not available";
1484 }
1485
tholenst95120392019-07-10 03:30:39 -07001486 crypto::tink::util::Status status = Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001487 CreateTestPrivateKeyManagerFipsCompatible(),
1488 CreateTestPublicKeyManagerFipsCompatible(), false);
tholenst95120392019-07-10 03:30:39 -07001489 ASSERT_TRUE(status.ok()) << status;
1490 EXPECT_THAT(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001491 CreateTestPrivateKeyManagerFipsCompatible(),
1492 CreateTestPublicKeyManagerFipsCompatible(), true),
lizatretyakova6e2829b2021-10-29 08:11:49 -07001493 StatusIs(absl::StatusCode::kAlreadyExists,
tholenst95120392019-07-10 03:30:39 -07001494 HasSubstr("forbidden new key operation")));
1495}
1496
tholenst77b67402019-11-08 04:45:41 -08001497// Tests that if we register asymmetric key managers once more after a call to
1498// get_key_manager, the key manager previously obtained with "get_key_manager()"
1499// remains valid.
1500
1501TEST_F(RegistryTest, RegisterAsymmetricKeyManagersGetKeyManagerStaysValid) {
ambrosin113db292023-04-20 06:13:22 -07001502 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001503 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1504 "not available";
1505 }
1506
tholenst77b67402019-11-08 04:45:41 -08001507 ASSERT_THAT(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001508 CreateTestPrivateKeyManagerFipsCompatible(),
1509 CreateTestPublicKeyManagerFipsCompatible(), true),
1510 IsOk());
tholenst77b67402019-11-08 04:45:41 -08001511
1512 crypto::tink::util::StatusOr<const KeyManager<PrivatePrimitiveA>*>
1513 private_key_manager = Registry::get_key_manager<PrivatePrimitiveA>(
1514 TestPrivateKeyTypeManager().get_key_type());
1515 crypto::tink::util::StatusOr<const KeyManager<PublicPrimitiveA>*>
1516 public_key_manager = Registry::get_key_manager<PublicPrimitiveA>(
1517 TestPublicKeyTypeManager().get_key_type());
1518
1519 ASSERT_THAT(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001520 CreateTestPrivateKeyManagerFipsCompatible(),
1521 CreateTestPublicKeyManagerFipsCompatible(), true),
1522 IsOk());
tholenst77b67402019-11-08 04:45:41 -08001523
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001524 EXPECT_THAT(private_key_manager.value()->get_key_type(),
tholenst77b67402019-11-08 04:45:41 -08001525 Eq(TestPrivateKeyTypeManager().get_key_type()));
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001526 EXPECT_THAT(public_key_manager.value()->get_key_type(),
tholenst77b67402019-11-08 04:45:41 -08001527 Eq(TestPublicKeyTypeManager().get_key_type()));
1528}
1529
tholenst95120392019-07-10 03:30:39 -07001530TEST_F(RegistryTest, AsymmetricPrivateRegisterAlone) {
ambrosin113db292023-04-20 06:13:22 -07001531 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001532 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1533 "not available";
ksteff83c0b2021-04-06 03:12:44 -07001534 }
1535
tholenst6ddf0912019-07-29 06:11:04 -07001536 ASSERT_TRUE(Registry::RegisterKeyTypeManager(
kste752fc1f2021-04-07 04:04:06 -07001537 CreateTestPrivateKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001538 .ok());
tholenst6ddf0912019-07-29 06:11:04 -07001539 ASSERT_TRUE(Registry::RegisterKeyTypeManager(
kste752fc1f2021-04-07 04:04:06 -07001540 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001541 .ok());
tholenst77b67402019-11-08 04:45:41 -08001542 // Registering the same as asymmetric key managers must fail, because doing so
1543 // would mean we invalidate key managers previously obtained with
1544 // get_key_manager().
1545 ASSERT_FALSE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001546 CreateTestPrivateKeyManagerFipsCompatible(),
1547 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst77b67402019-11-08 04:45:41 -08001548 .ok());
tholenst6ddf0912019-07-29 06:11:04 -07001549 ASSERT_TRUE(Registry::RegisterKeyTypeManager(
kste752fc1f2021-04-07 04:04:06 -07001550 CreateTestPrivateKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001551 .ok());
tholenst6ddf0912019-07-29 06:11:04 -07001552 ASSERT_TRUE(Registry::RegisterKeyTypeManager(
kste752fc1f2021-04-07 04:04:06 -07001553 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001554 .ok());
1555}
1556
1557TEST_F(RegistryTest, AsymmetricGetPrimitiveA) {
ambrosin113db292023-04-20 06:13:22 -07001558 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001559 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1560 "not available";
1561 }
1562
tholenst95120392019-07-10 03:30:39 -07001563 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001564 CreateTestPrivateKeyManagerFipsCompatible(),
1565 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001566 .ok());
1567 crypto::tink::util::StatusOr<const KeyManager<PrivatePrimitiveA>*> km =
1568 Registry::get_key_manager<PrivatePrimitiveA>(
tholenst6ddf0912019-07-29 06:11:04 -07001569 TestPrivateKeyTypeManager().get_key_type());
tholenst95120392019-07-10 03:30:39 -07001570 ASSERT_TRUE(km.ok()) << km.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001571 EXPECT_THAT(km.value()->get_key_type(),
tholenst6ddf0912019-07-29 06:11:04 -07001572 Eq(TestPrivateKeyTypeManager().get_key_type()));
tholenst95120392019-07-10 03:30:39 -07001573}
1574
1575TEST_F(RegistryTest, AsymmetricGetPrimitiveB) {
ambrosin113db292023-04-20 06:13:22 -07001576 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001577 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1578 "not available";
1579 }
1580
tholenst95120392019-07-10 03:30:39 -07001581 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001582 CreateTestPrivateKeyManagerFipsCompatible(),
1583 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001584 .ok());
1585 crypto::tink::util::StatusOr<const KeyManager<PrivatePrimitiveB>*> km =
1586 Registry::get_key_manager<PrivatePrimitiveB>(
tholenst6ddf0912019-07-29 06:11:04 -07001587 TestPrivateKeyTypeManager().get_key_type());
tholenst95120392019-07-10 03:30:39 -07001588 ASSERT_TRUE(km.ok()) << km.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001589 EXPECT_THAT(km.value()->get_key_type(),
tholenst6ddf0912019-07-29 06:11:04 -07001590 Eq(TestPrivateKeyTypeManager().get_key_type()));
tholenst95120392019-07-10 03:30:39 -07001591}
1592
1593TEST_F(RegistryTest, AsymmetricGetPublicPrimitiveA) {
ambrosin113db292023-04-20 06:13:22 -07001594 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001595 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1596 "not available";
1597 }
1598
tholenst95120392019-07-10 03:30:39 -07001599 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001600 CreateTestPrivateKeyManagerFipsCompatible(),
1601 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001602 .ok());
1603 crypto::tink::util::StatusOr<const KeyManager<PublicPrimitiveA>*> km =
1604 Registry::get_key_manager<PublicPrimitiveA>(
tholenst6ddf0912019-07-29 06:11:04 -07001605 TestPublicKeyTypeManager().get_key_type());
tholenst95120392019-07-10 03:30:39 -07001606 ASSERT_TRUE(km.ok()) << km.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001607 EXPECT_THAT(km.value()->get_key_type(),
tholenst6ddf0912019-07-29 06:11:04 -07001608 Eq(TestPublicKeyTypeManager().get_key_type()));
tholenst95120392019-07-10 03:30:39 -07001609}
1610
1611TEST_F(RegistryTest, AsymmetricGetPublicPrimitiveB) {
ambrosin113db292023-04-20 06:13:22 -07001612 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001613 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1614 "not available";
1615 }
1616
tholenst95120392019-07-10 03:30:39 -07001617 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001618 CreateTestPrivateKeyManagerFipsCompatible(),
1619 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001620 .ok());
1621 crypto::tink::util::StatusOr<const KeyManager<PublicPrimitiveB>*> km =
1622 Registry::get_key_manager<PublicPrimitiveB>(
tholenst6ddf0912019-07-29 06:11:04 -07001623 TestPublicKeyTypeManager().get_key_type());
tholenst95120392019-07-10 03:30:39 -07001624 ASSERT_TRUE(km.ok()) << km.status();
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001625 EXPECT_THAT(km.value()->get_key_type(),
tholenst6ddf0912019-07-29 06:11:04 -07001626 Eq(TestPublicKeyTypeManager().get_key_type()));
tholenst95120392019-07-10 03:30:39 -07001627}
1628
1629TEST_F(RegistryTest, AsymmetricGetWrongPrimitiveError) {
ambrosin113db292023-04-20 06:13:22 -07001630 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001631 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1632 "not available";
1633 }
1634
tholenst95120392019-07-10 03:30:39 -07001635 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001636 CreateTestPrivateKeyManagerFipsCompatible(),
1637 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001638 .ok());
1639 crypto::tink::util::StatusOr<const KeyManager<PublicPrimitiveA>*> km =
1640 Registry::get_key_manager<PublicPrimitiveA>(
tholenst6ddf0912019-07-29 06:11:04 -07001641 TestPrivateKeyTypeManager().get_key_type());
tholenst95120392019-07-10 03:30:39 -07001642 EXPECT_THAT(km.status(),
lizatretyakova01f69192021-11-05 09:10:40 -07001643 StatusIs(absl::StatusCode::kInvalidArgument,
tholenst95120392019-07-10 03:30:39 -07001644 HasSubstr("not among supported primitives")));
1645}
1646
tholenst00016522020-06-15 08:47:54 -07001647class PrivateKeyManagerImplTest : public testing::Test {
cinlin063c4ea2023-03-07 12:43:13 -08001648 void SetUp() override { Registry::Reset(); }
kste752fc1f2021-04-07 04:04:06 -07001649
1650 void TearDown() override {
1651 // Reset is needed here to ensure Mock objects get deleted and do not leak.
1652 Registry::Reset();
1653 }
tholenst00016522020-06-15 08:47:54 -07001654};
1655
1656TEST_F(PrivateKeyManagerImplTest, AsymmetricFactoryNewKeyFromMessage) {
ambrosin113db292023-04-20 06:13:22 -07001657 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001658 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1659 "not available";
1660 }
1661
tholenst95120392019-07-10 03:30:39 -07001662 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001663 CreateTestPrivateKeyManagerFipsCompatible(),
1664 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001665 .ok());
1666
1667 EcdsaKeyFormat key_format;
1668 key_format.mutable_params()->set_encoding(EcdsaSignatureEncoding::DER);
1669 KeyTemplate key_template;
tholenst6ddf0912019-07-29 06:11:04 -07001670 key_template.set_type_url(TestPrivateKeyTypeManager().get_key_type());
tholenst95120392019-07-10 03:30:39 -07001671 key_template.set_value(key_format.SerializeAsString());
1672 key_template.set_output_prefix_type(OutputPrefixType::TINK);
1673 std::unique_ptr<KeyData> key_data =
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001674 Registry::NewKeyData(key_template).value();
tholenst95120392019-07-10 03:30:39 -07001675 EXPECT_THAT(key_data->type_url(),
tholenst6ddf0912019-07-29 06:11:04 -07001676 Eq(TestPrivateKeyTypeManager().get_key_type()));
tholenst95120392019-07-10 03:30:39 -07001677 EcdsaPrivateKey private_key;
1678 private_key.ParseFromString(key_data->value());
1679 EXPECT_THAT(private_key.public_key().params().encoding(),
1680 Eq(EcdsaSignatureEncoding::DER));
1681}
1682
tholenst00016522020-06-15 08:47:54 -07001683TEST_F(PrivateKeyManagerImplTest, AsymmetricNewKeyDisallowed) {
ambrosin113db292023-04-20 06:13:22 -07001684 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001685 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1686 "not available";
1687 }
1688
tholenst95120392019-07-10 03:30:39 -07001689 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001690 CreateTestPrivateKeyManagerFipsCompatible(),
1691 CreateTestPublicKeyManagerFipsCompatible(), true)
tholenst95120392019-07-10 03:30:39 -07001692 .ok());
1693 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001694 CreateTestPrivateKeyManagerFipsCompatible(),
1695 CreateTestPublicKeyManagerFipsCompatible(), false)
tholenst95120392019-07-10 03:30:39 -07001696 .ok());
1697
1698 KeyTemplate key_template;
tholenst6ddf0912019-07-29 06:11:04 -07001699 key_template.set_type_url(TestPrivateKeyTypeManager().get_key_type());
lizatretyakova01f69192021-11-05 09:10:40 -07001700 EXPECT_THAT(
1701 Registry::NewKeyData(key_template).status(),
1702 StatusIs(absl::StatusCode::kInvalidArgument, HasSubstr("not allow")));
tholenst95120392019-07-10 03:30:39 -07001703}
1704
1705TEST_F(RegistryTest, AsymmetricGetPublicKeyData) {
ambrosin113db292023-04-20 06:13:22 -07001706 if (kUseOnlyFips && !IsFipsEnabledInSsl()) {
kste752fc1f2021-04-07 04:04:06 -07001707 GTEST_SKIP() << "Not supported if FIPS-mode is used and BoringCrypto is "
1708 "not available";
1709 }
1710
tholenst95120392019-07-10 03:30:39 -07001711 crypto::tink::util::Status status = Registry::RegisterAsymmetricKeyManagers(
kste752fc1f2021-04-07 04:04:06 -07001712 CreateTestPrivateKeyManagerFipsCompatible(),
1713 CreateTestPublicKeyManagerFipsCompatible(), true);
tholenst95120392019-07-10 03:30:39 -07001714 EcdsaPrivateKey private_key;
1715 private_key.mutable_public_key()->mutable_params()->set_encoding(
1716 EcdsaSignatureEncoding::DER);
1717
1718 std::unique_ptr<KeyData> key_data =
tholenst6ddf0912019-07-29 06:11:04 -07001719 Registry::GetPublicKeyData(TestPrivateKeyTypeManager().get_key_type(),
tholenst95120392019-07-10 03:30:39 -07001720 private_key.SerializeAsString())
lizatretyakovaf7ea7c62022-03-21 04:40:31 -07001721 .value();
tholenst95120392019-07-10 03:30:39 -07001722 ASSERT_THAT(key_data->type_url(),
tholenst6ddf0912019-07-29 06:11:04 -07001723 Eq(TestPublicKeyTypeManager().get_key_type()));
tholenst95120392019-07-10 03:30:39 -07001724 EcdsaPublicKey public_key;
1725 public_key.ParseFromString(key_data->value());
1726 EXPECT_THAT(public_key.params().encoding(), Eq(EcdsaSignatureEncoding::DER));
1727}
1728
tholenst6ddf0912019-07-29 06:11:04 -07001729class TestPrivateKeyTypeManager2 : public TestPrivateKeyTypeManager {};
1730class TestPublicKeyTypeManager2 : public TestPublicKeyTypeManager {};
tholenst95120392019-07-10 03:30:39 -07001731
1732TEST_F(RegistryTest, RegisterAssymmetricReregistrationWithWrongClasses) {
ksteff83c0b2021-04-06 03:12:44 -07001733 if (kUseOnlyFips) {
1734 GTEST_SKIP() << "Not supported in FIPS-only mode";
1735 }
1736
tholenst95120392019-07-10 03:30:39 -07001737 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
tholenst6ddf0912019-07-29 06:11:04 -07001738 absl::make_unique<TestPrivateKeyTypeManager>(),
1739 absl::make_unique<TestPublicKeyTypeManager>(), true)
tholenst95120392019-07-10 03:30:39 -07001740 .ok());
lizatretyakova6e2829b2021-10-29 08:11:49 -07001741 EXPECT_THAT(Registry::RegisterAsymmetricKeyManagers(
1742 absl::make_unique<TestPrivateKeyTypeManager2>(),
1743 absl::make_unique<TestPublicKeyTypeManager>(), true),
1744 StatusIs(absl::StatusCode::kAlreadyExists,
1745 HasSubstr("already registered")));
1746 EXPECT_THAT(Registry::RegisterAsymmetricKeyManagers(
1747 absl::make_unique<TestPrivateKeyTypeManager>(),
1748 absl::make_unique<TestPublicKeyTypeManager2>(), true),
1749 StatusIs(absl::StatusCode::kAlreadyExists,
1750 HasSubstr("already registered")));
1751 EXPECT_THAT(Registry::RegisterAsymmetricKeyManagers(
1752 absl::make_unique<TestPrivateKeyTypeManager2>(),
1753 absl::make_unique<TestPublicKeyTypeManager2>(), true),
1754 StatusIs(absl::StatusCode::kAlreadyExists,
1755 HasSubstr("already registered")));
1756 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1757 absl::make_unique<TestPrivateKeyTypeManager2>(), true),
1758 StatusIs(absl::StatusCode::kAlreadyExists,
1759 HasSubstr("already registered")));
1760 EXPECT_THAT(Registry::RegisterKeyTypeManager(
1761 absl::make_unique<TestPublicKeyTypeManager2>(), true),
1762 StatusIs(absl::StatusCode::kAlreadyExists,
1763 HasSubstr("already registered")));
tholenst95120392019-07-10 03:30:39 -07001764}
1765
tholenst6ddf0912019-07-29 06:11:04 -07001766class TestPublicKeyTypeManagerWithDifferentKeyType
1767 : public TestPublicKeyTypeManager {
tholenst95120392019-07-10 03:30:39 -07001768 const std::string& get_key_type() const override { return kKeyType; }
1769
1770 private:
1771 const std::string kKeyType = "bla";
1772};
1773
1774TEST_F(RegistryTest, RegisterAssymmetricReregistrationWithNewKeyType) {
kste752fc1f2021-04-07 04:04:06 -07001775 if (kUseOnlyFips) {
1776 GTEST_SKIP() << "Not supported in FIPS-only mode";
1777 }
1778
tholenst95120392019-07-10 03:30:39 -07001779 ASSERT_TRUE(Registry::RegisterAsymmetricKeyManagers(
tholenst6ddf0912019-07-29 06:11:04 -07001780 absl::make_unique<TestPrivateKeyTypeManager>(),
1781 absl::make_unique<TestPublicKeyTypeManager>(), true)
tholenst95120392019-07-10 03:30:39 -07001782 .ok());
1783 EXPECT_THAT(
1784 Registry::RegisterAsymmetricKeyManagers(
tholenst6ddf0912019-07-29 06:11:04 -07001785 absl::make_unique<TestPrivateKeyTypeManager>(),
1786 absl::make_unique<TestPublicKeyTypeManagerWithDifferentKeyType>(),
tholenst95120392019-07-10 03:30:39 -07001787 true),
lizatretyakova01f69192021-11-05 09:10:40 -07001788 StatusIs(absl::StatusCode::kInvalidArgument,
tholenst77b67402019-11-08 04:45:41 -08001789 HasSubstr("impossible to register")));
tholenst95120392019-07-10 03:30:39 -07001790}
1791
tholenstdab78662019-11-08 08:59:47 -08001792// The DelegatingKeyTypeManager calls the registry
1793class DelegatingKeyTypeManager
1794 : public PrivateKeyTypeManager<EcdsaPrivateKey, EcdsaKeyFormat,
1795 EcdsaPublicKey, List<>> {
1796 public:
1797 DelegatingKeyTypeManager() : PrivateKeyTypeManager() {}
1798
1799 void set_registry(RegistryImpl* registry) { registry_ = registry; }
1800
1801 google::crypto::tink::KeyData::KeyMaterialType key_material_type()
1802 const override {
1803 return google::crypto::tink::KeyData::SYMMETRIC;
1804 }
1805
1806 uint32_t get_version() const override { return kVersion; }
1807
1808 const std::string& get_key_type() const override { return kKeyType; }
1809
1810 crypto::tink::util::Status ValidateKey(
1811 const EcdsaPrivateKey& key) const override {
1812 return util::OkStatus();
1813 }
1814
1815 crypto::tink::util::Status ValidateKeyFormat(
1816 const EcdsaKeyFormat& key_format) const override {
1817 return util::OkStatus();
1818 }
1819
1820 crypto::tink::util::StatusOr<EcdsaPrivateKey> CreateKey(
1821 const EcdsaKeyFormat& key_format) const override {
1822 AesGcmKeyFormat format;
1823 KeyTemplate key_template;
1824 key_template.set_type_url(
1825 "type.googleapis.com/google.crypto.tink.AesGcmKey");
1826 key_template.set_value(format.SerializeAsString());
1827 auto result = registry_->NewKeyData(key_template);
1828 if (!result.ok()) return result.status();
1829 // Return a string we can check for.
lizatretyakova717bd212021-10-29 08:48:10 -07001830 return util::Status(absl::StatusCode::kDeadlineExceeded,
1831 "CreateKey worked");
tholenstdab78662019-11-08 08:59:47 -08001832 }
1833
1834 crypto::tink::util::StatusOr<EcdsaPrivateKey> DeriveKey(
1835 const EcdsaKeyFormat& key_format,
1836 InputStream* input_stream) const override {
1837 AesGcmKeyFormat format;
1838 KeyTemplate key_template;
1839 key_template.set_type_url(
1840 "type.googleapis.com/google.crypto.tink.AesGcmKey");
1841 key_template.set_value(format.SerializeAsString());
1842
1843 auto result = registry_->DeriveKey(key_template, input_stream);
1844 if (!result.ok()) return result.status();
1845 // Return a string we can check for.
lizatretyakova717bd212021-10-29 08:48:10 -07001846 return util::Status(absl::StatusCode::kDeadlineExceeded,
1847 "DeriveKey worked");
tholenstdab78662019-11-08 08:59:47 -08001848 }
1849
1850 crypto::tink::util::StatusOr<EcdsaPublicKey> GetPublicKey(
1851 const EcdsaPrivateKey& private_key) const override {
1852 AesGcmKeyFormat format;
1853 KeyTemplate key_template;
1854 key_template.set_type_url(
1855 "type.googleapis.com/google.crypto.tink.AesGcmKey");
1856 key_template.set_value(format.SerializeAsString());
1857 auto result = registry_->NewKeyData(key_template);
1858 if (!result.ok()) return result.status();
1859 // Return a string we can check for.
lizatretyakova717bd212021-10-29 08:48:10 -07001860 return util::Status(absl::StatusCode::kDeadlineExceeded,
1861 "GetPublicKey worked");
tholenstdab78662019-11-08 08:59:47 -08001862 }
1863
1864 private:
1865 RegistryImpl* registry_;
1866
Tink Teamee7e9362020-04-20 23:52:07 -07001867 static constexpr int kVersion = 0;
tholenstdab78662019-11-08 08:59:47 -08001868 const std::string kKeyType =
1869 "type.googleapis.com/google.crypto.tink.EcdsaPrivateKey";
1870};
1871
juergedc8d842021-09-15 02:40:47 -07001872class RegistryImplTest : public ::testing::Test {
1873 protected:
1874 void TearDown() override {
1875 // Calling RestrictToFipsIfEmpty() may call SetFipsRestricted(), which
1876 // set a global variable to true. We have to reset that after the test.
1877 UnSetFipsRestricted();
1878 }
1879};
1880
tholenstdab78662019-11-08 08:59:47 -08001881// Check that we can call the registry again from within NewKeyData
juergedc8d842021-09-15 02:40:47 -07001882TEST_F(RegistryImplTest, CanDelegateCreateKey) {
ksteff83c0b2021-04-06 03:12:44 -07001883 if (kUseOnlyFips) {
1884 GTEST_SKIP() << "Not supported in FIPS-only mode";
1885 }
1886
tholenstdab78662019-11-08 08:59:47 -08001887 RegistryImpl registry_impl;
1888 auto delegating_key_manager = absl::make_unique<DelegatingKeyTypeManager>();
1889 delegating_key_manager->set_registry(&registry_impl);
1890 auto status =
1891 registry_impl
1892 .RegisterKeyTypeManager<EcdsaPrivateKey, EcdsaKeyFormat, List<>>(
1893 std::move(delegating_key_manager), true);
1894 EXPECT_THAT(status, IsOk());
1895 status = registry_impl.RegisterKeyTypeManager<AesGcmKey, AesGcmKeyFormat,
cinlin063c4ea2023-03-07 12:43:13 -08001896 List<Aead, AeadVariant>>(
1897 absl::make_unique<ExampleKeyTypeManager>(), true);
tholenstdab78662019-11-08 08:59:47 -08001898 EXPECT_THAT(status, IsOk());
1899
1900 EcdsaKeyFormat format;
1901 KeyTemplate key_template;
1902 key_template.set_type_url(
1903 "type.googleapis.com/google.crypto.tink.EcdsaPrivateKey");
1904 key_template.set_value(format.SerializeAsString());
1905 EXPECT_THAT(registry_impl.NewKeyData(key_template).status(),
lizatretyakova717bd212021-10-29 08:48:10 -07001906 StatusIs(absl::StatusCode::kDeadlineExceeded,
tholenstdab78662019-11-08 08:59:47 -08001907 HasSubstr("CreateKey worked")));
1908}
1909
1910// Check that we can call the registry again from within NewKeyData
juergedc8d842021-09-15 02:40:47 -07001911TEST_F(RegistryImplTest, CanDelegateDeriveKey) {
ksteff83c0b2021-04-06 03:12:44 -07001912 if (kUseOnlyFips) {
1913 GTEST_SKIP() << "Not supported in FIPS-only mode";
1914 }
1915
tholenstdab78662019-11-08 08:59:47 -08001916 RegistryImpl registry_impl;
1917 auto delegating_key_manager = absl::make_unique<DelegatingKeyTypeManager>();
1918 delegating_key_manager->set_registry(&registry_impl);
1919 auto status =
1920 registry_impl
1921 .RegisterKeyTypeManager<EcdsaPrivateKey, EcdsaKeyFormat, List<>>(
1922 std::move(delegating_key_manager), true);
1923 EXPECT_THAT(status, IsOk());
1924 status = registry_impl.RegisterKeyTypeManager<AesGcmKey, AesGcmKeyFormat,
cinlin063c4ea2023-03-07 12:43:13 -08001925 List<Aead, AeadVariant>>(
1926 absl::make_unique<ExampleKeyTypeManager>(), true);
tholenstdab78662019-11-08 08:59:47 -08001927 EXPECT_THAT(status, IsOk());
1928
1929 EcdsaKeyFormat format;
1930 KeyTemplate key_template;
1931 key_template.set_type_url(
1932 "type.googleapis.com/google.crypto.tink.EcdsaPrivateKey");
1933 key_template.set_value(format.SerializeAsString());
lizatretyakova717bd212021-10-29 08:48:10 -07001934 EXPECT_THAT(registry_impl.DeriveKey(key_template, nullptr).status(),
1935 StatusIs(absl::StatusCode::kDeadlineExceeded,
1936 HasSubstr("DeriveKey worked")));
tholenstdab78662019-11-08 08:59:47 -08001937}
1938
juergedc8d842021-09-15 02:40:47 -07001939TEST_F(RegistryImplTest, CanDelegateGetPublicKey) {
ksteff83c0b2021-04-06 03:12:44 -07001940 if (kUseOnlyFips) {
1941 GTEST_SKIP() << "Not supported in FIPS-only mode";
1942 }
1943
tholenstdab78662019-11-08 08:59:47 -08001944 RegistryImpl registry_impl;
1945 auto delegating_key_manager = absl::make_unique<DelegatingKeyTypeManager>();
1946 delegating_key_manager->set_registry(&registry_impl);
1947 auto status = registry_impl.RegisterAsymmetricKeyManagers(
1948 delegating_key_manager.release(),
1949 absl::make_unique<TestPublicKeyTypeManager>().release(), true);
1950 EXPECT_THAT(status, IsOk());
1951 status = registry_impl.RegisterKeyTypeManager<AesGcmKey, AesGcmKeyFormat,
cinlin063c4ea2023-03-07 12:43:13 -08001952 List<Aead, AeadVariant>>(
1953 absl::make_unique<ExampleKeyTypeManager>(), true);
tholenstdab78662019-11-08 08:59:47 -08001954 EXPECT_THAT(status, IsOk());
1955
1956 EcdsaPrivateKey private_key;
1957 private_key.mutable_public_key()->mutable_params()->set_encoding(
1958 EcdsaSignatureEncoding::DER);
1959
1960 EXPECT_THAT(registry_impl
1961 .GetPublicKeyData(DelegatingKeyTypeManager().get_key_type(),
1962 private_key.SerializeAsString())
1963 .status(),
lizatretyakova717bd212021-10-29 08:48:10 -07001964 StatusIs(absl::StatusCode::kDeadlineExceeded,
tholenstdab78662019-11-08 08:59:47 -08001965 HasSubstr("GetPublicKey worked")));
1966}
1967
kste8779b602022-10-18 02:03:41 -07001968TEST_F(RegistryImplTest, FipsRestrictionSucceedsOnEmptyRegistry) {
ksted0795b22021-04-16 08:25:15 -07001969 RegistryImpl registry_impl;
1970 EXPECT_THAT(registry_impl.RestrictToFipsIfEmpty(), IsOk());
1971}
1972
kste8779b602022-10-18 02:03:41 -07001973TEST_F(RegistryImplTest, FipsRestrictionSucceedsWhenSettingMultipleTimes) {
1974 RegistryImpl registry_impl;
1975 EXPECT_THAT(registry_impl.RestrictToFipsIfEmpty(), IsOk());
1976 EXPECT_THAT(registry_impl.RestrictToFipsIfEmpty(), IsOk());
1977 EXPECT_THAT(registry_impl.RestrictToFipsIfEmpty(), IsOk());
1978}
1979
1980TEST_F(RegistryImplTest, FipsRestrictionSucceedsIfBuildInFipsMode) {
1981 if (!kUseOnlyFips) {
1982 GTEST_SKIP() << "Not supported when Tink is not built in FIPS mode.";
1983 }
1984 RegistryImpl registry_impl;
1985 EXPECT_THAT(registry_impl.RestrictToFipsIfEmpty(), IsOk());
1986}
1987
juergedc8d842021-09-15 02:40:47 -07001988TEST_F(RegistryImplTest, FipsFailsIfNotEmpty) {
kste8779b602022-10-18 02:03:41 -07001989 if (kUseOnlyFips) {
1990 GTEST_SKIP() << "Not supported in FIPS-only mode";
ksted0795b22021-04-16 08:25:15 -07001991 }
1992
1993 auto fips_key_manager = absl::make_unique<ExampleKeyTypeManager>();
1994 ON_CALL(*fips_key_manager, FipsStatus())
1995 .WillByDefault(testing::Return(FipsCompatibility::kRequiresBoringCrypto));
1996
1997 RegistryImpl registry_impl;
1998 auto status = registry_impl.RegisterKeyTypeManager<AesGcmKey, AesGcmKeyFormat,
cinlin063c4ea2023-03-07 12:43:13 -08001999 List<Aead, AeadVariant>>(
2000 std::move(fips_key_manager), true);
ksted0795b22021-04-16 08:25:15 -07002001 EXPECT_THAT(status, IsOk());
2002 EXPECT_THAT(registry_impl.RestrictToFipsIfEmpty(),
lizatretyakova456657f2021-11-01 05:48:32 -07002003 StatusIs(absl::StatusCode::kInternal));
ksted0795b22021-04-16 08:25:15 -07002004}
2005
ambrosinff8f7c92022-03-01 09:07:49 -08002006TEST_F(RegistryImplTest, CanRegisterOnlyOneMonitoringFactory) {
2007 auto monitoring_client_factory =
ambrosin78946022022-04-04 05:46:26 -07002008 absl::make_unique<MockMonitoringClientFactory>();
ambrosinff8f7c92022-03-01 09:07:49 -08002009
2010 RegistryImpl registry_impl;
2011 EXPECT_THAT(registry_impl.RegisterMonitoringClientFactory(
2012 std::move(monitoring_client_factory)),
2013 IsOk());
2014 ASSERT_THAT(registry_impl.GetMonitoringClientFactory(), Not(IsNull()));
2015 EXPECT_THAT(registry_impl.RegisterMonitoringClientFactory(
2016 std::move(monitoring_client_factory)),
2017 StatusIs(absl::StatusCode::kAlreadyExists));
2018}
2019
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +00002020} // namespace
tholenst05a834c2021-03-18 06:24:20 -07002021} // namespace internal
Bartosz Przydatek32cdbb22017-03-23 11:16:36 +00002022} // namespace tink
2023} // namespace crypto
OSZAR »