1 // Copyright 2019 Google LLC
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
17 #include "tink/keyderivation/key_derivation_key_templates.h"
18
19 #include <vector>
20
21 #include "gmock/gmock.h"
22 #include "gtest/gtest.h"
23 #include "absl/status/status.h"
24 #include "tink/aead/aead_key_templates.h"
25 #include "tink/aead/aes_gcm_key_manager.h"
26 #include "tink/keyderivation/internal/prf_based_deriver_key_manager.h"
27 #include "tink/keyderivation/keyset_deriver_wrapper.h"
28 #include "tink/prf/hkdf_prf_key_manager.h"
29 #include "tink/prf/prf_key_templates.h"
30 #include "tink/registry.h"
31 #include "tink/util/statusor.h"
32 #include "tink/util/test_matchers.h"
33 #include "proto/prf_based_deriver.pb.h"
34 #include "proto/tink.pb.h"
35
36 namespace crypto {
37 namespace tink {
38 namespace internal {
39 namespace {
40
41 using ::crypto::tink::test::IsOk;
42 using ::crypto::tink::test::StatusIs;
43 using ::google::crypto::tink::KeyTemplate;
44 using ::google::crypto::tink::OutputPrefixType;
45 using ::google::crypto::tink::PrfBasedDeriverKeyFormat;
46 using ::testing::Eq;
47 using ::testing::Not;
48
49 class KeyDerivationKeyTemplatesTest : public ::testing::Test {
50 protected:
TearDown()51 void TearDown() override { Registry::Reset(); }
52 };
53
TEST_F(KeyDerivationKeyTemplatesTest,CreatePrfBasedKeyTemplate)54 TEST_F(KeyDerivationKeyTemplatesTest, CreatePrfBasedKeyTemplate) {
55 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
56 absl::make_unique<KeysetDeriverWrapper>()),
57 IsOk());
58 ASSERT_THAT(Registry::RegisterKeyTypeManager(
59 absl::make_unique<internal::PrfBasedDeriverKeyManager>(),
60 /*new_key_allowed=*/true),
61 IsOk());
62 ASSERT_THAT(
63 Registry::RegisterKeyTypeManager(absl::make_unique<HkdfPrfKeyManager>(),
64 /*new_key_allowed=*/true),
65 IsOk());
66 ASSERT_THAT(
67 Registry::RegisterKeyTypeManager(absl::make_unique<AesGcmKeyManager>(),
68 /*new_key_allowed=*/true),
69 IsOk());
70
71 std::vector<OutputPrefixType> output_prefix_types = {
72 OutputPrefixType::RAW, OutputPrefixType::TINK, OutputPrefixType::LEGACY};
73 for (OutputPrefixType output_prefix_type : output_prefix_types) {
74 KeyTemplate derived_key_template = AeadKeyTemplates::Aes256Gcm();
75 derived_key_template.set_output_prefix_type(output_prefix_type);
76 util::StatusOr<KeyTemplate> key_template =
77 KeyDerivationKeyTemplates::CreatePrfBasedKeyTemplate(
78 PrfKeyTemplates::HkdfSha256(), derived_key_template);
79
80 ASSERT_THAT(key_template, IsOk());
81 EXPECT_THAT(
82 key_template->type_url(),
83 Eq("type.googleapis.com/google.crypto.tink.PrfBasedDeriverKey"));
84 EXPECT_THAT(key_template->type_url(),
85 Eq(internal::PrfBasedDeriverKeyManager().get_key_type()));
86 EXPECT_THAT(key_template->output_prefix_type(), Eq(output_prefix_type));
87
88 PrfBasedDeriverKeyFormat key_format;
89 EXPECT_TRUE(key_format.ParseFromString(key_template->value()));
90 EXPECT_THAT(
91 internal::PrfBasedDeriverKeyManager().ValidateKeyFormat(key_format),
92 IsOk());
93 }
94 }
95
TEST_F(KeyDerivationKeyTemplatesTest,CreatePrfBasedKeyTemplateInvalidPrfKey)96 TEST_F(KeyDerivationKeyTemplatesTest, CreatePrfBasedKeyTemplateInvalidPrfKey) {
97 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
98 absl::make_unique<KeysetDeriverWrapper>()),
99 IsOk());
100 ASSERT_THAT(Registry::RegisterKeyTypeManager(
101 absl::make_unique<internal::PrfBasedDeriverKeyManager>(),
102 /*new_key_allowed=*/true),
103 IsOk());
104 ASSERT_THAT(
105 Registry::RegisterKeyTypeManager(absl::make_unique<HkdfPrfKeyManager>(),
106 /*new_key_allowed=*/true),
107 IsOk());
108 ASSERT_THAT(
109 Registry::RegisterKeyTypeManager(absl::make_unique<AesGcmKeyManager>(),
110 /*new_key_allowed=*/true),
111 IsOk());
112
113 EXPECT_THAT(KeyDerivationKeyTemplates::CreatePrfBasedKeyTemplate(
114 AeadKeyTemplates::Aes256Gcm(), AeadKeyTemplates::Aes256Gcm())
115 .status(),
116 StatusIs(absl::StatusCode::kInvalidArgument));
117 }
118
TEST_F(KeyDerivationKeyTemplatesTest,CreatePrfBasedKeyTemplateInvalidDerivedKeyTemplate)119 TEST_F(KeyDerivationKeyTemplatesTest,
120 CreatePrfBasedKeyTemplateInvalidDerivedKeyTemplate) {
121 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
122 absl::make_unique<KeysetDeriverWrapper>()),
123 IsOk());
124 ASSERT_THAT(Registry::RegisterKeyTypeManager(
125 absl::make_unique<internal::PrfBasedDeriverKeyManager>(),
126 /*new_key_allowed=*/true),
127 IsOk());
128 ASSERT_THAT(
129 Registry::RegisterKeyTypeManager(absl::make_unique<HkdfPrfKeyManager>(),
130 /*new_key_allowed=*/true),
131 IsOk());
132 ASSERT_THAT(
133 Registry::RegisterKeyTypeManager(absl::make_unique<AesGcmKeyManager>(),
134 /*new_key_allowed=*/true),
135 IsOk());
136
137 util::StatusOr<KeyTemplate> derived_key_template =
138 KeyDerivationKeyTemplates::CreatePrfBasedKeyTemplate(
139 PrfKeyTemplates::HkdfSha256(), AeadKeyTemplates::Aes256Gcm());
140 EXPECT_THAT(KeyDerivationKeyTemplates::CreatePrfBasedKeyTemplate(
141 PrfKeyTemplates::HkdfSha256(), *derived_key_template)
142 .status(),
143 StatusIs(absl::StatusCode::kUnimplemented));
144 }
145
TEST_F(KeyDerivationKeyTemplatesTest,CreatePrfBasedKeyTemplateNoPrfBasedDeriverKeyManager)146 TEST_F(KeyDerivationKeyTemplatesTest,
147 CreatePrfBasedKeyTemplateNoPrfBasedDeriverKeyManager) {
148 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
149 absl::make_unique<KeysetDeriverWrapper>()),
150 IsOk());
151 ASSERT_THAT(
152 Registry::RegisterKeyTypeManager(absl::make_unique<HkdfPrfKeyManager>(),
153 /*new_key_allowed=*/true),
154 IsOk());
155 ASSERT_THAT(
156 Registry::RegisterKeyTypeManager(absl::make_unique<AesGcmKeyManager>(),
157 /*new_key_allowed=*/true),
158 IsOk());
159
160 EXPECT_THAT(KeyDerivationKeyTemplates::CreatePrfBasedKeyTemplate(
161 PrfKeyTemplates::HkdfSha256(), AeadKeyTemplates::Aes256Gcm()),
162 Not(IsOk()));
163 }
164
TEST_F(KeyDerivationKeyTemplatesTest,CreatePrfBasedKeyTemplateNoHkdfPrfKeyManager)165 TEST_F(KeyDerivationKeyTemplatesTest,
166 CreatePrfBasedKeyTemplateNoHkdfPrfKeyManager) {
167 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
168 absl::make_unique<KeysetDeriverWrapper>()),
169 IsOk());
170 ASSERT_THAT(Registry::RegisterKeyTypeManager(
171 absl::make_unique<internal::PrfBasedDeriverKeyManager>(),
172 /*new_key_allowed=*/true),
173 IsOk());
174 ASSERT_THAT(
175 Registry::RegisterKeyTypeManager(absl::make_unique<AesGcmKeyManager>(),
176 /*new_key_allowed=*/true),
177 IsOk());
178
179 EXPECT_THAT(KeyDerivationKeyTemplates::CreatePrfBasedKeyTemplate(
180 PrfKeyTemplates::HkdfSha256(), AeadKeyTemplates::Aes256Gcm()),
181 Not(IsOk()));
182 }
183
TEST_F(KeyDerivationKeyTemplatesTest,CreatePrfBasedKeyTemplateNoAesGcmKeyManager)184 TEST_F(KeyDerivationKeyTemplatesTest,
185 CreatePrfBasedKeyTemplateNoAesGcmKeyManager) {
186 ASSERT_THAT(Registry::RegisterPrimitiveWrapper(
187 absl::make_unique<KeysetDeriverWrapper>()),
188 IsOk());
189 ASSERT_THAT(Registry::RegisterKeyTypeManager(
190 absl::make_unique<internal::PrfBasedDeriverKeyManager>(),
191 /*new_key_allowed=*/true),
192 IsOk());
193 ASSERT_THAT(
194 Registry::RegisterKeyTypeManager(absl::make_unique<HkdfPrfKeyManager>(),
195 /*new_key_allowed=*/true),
196 IsOk());
197
198 EXPECT_THAT(KeyDerivationKeyTemplates::CreatePrfBasedKeyTemplate(
199 PrfKeyTemplates::HkdfSha256(), AeadKeyTemplates::Aes256Gcm()),
200 Not(IsOk()));
201 }
202
203 } // namespace
204 } // namespace internal
205 } // namespace tink
206 } // namespace crypto
207