1 // Copyright 2020 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 // Implementation of a Keyset Service.
18 #include "keyset_impl.h"
19
20 #include <ostream>
21 #include <memory>
22 #include <sstream>
23 #include <string>
24 #include <utility>
25
26 #include "tink/aead/aead_key_templates.h"
27 #include "tink/binary_keyset_reader.h"
28 #include "tink/binary_keyset_writer.h"
29 #include "tink/cleartext_keyset_handle.h"
30 #include "tink/daead/deterministic_aead_key_templates.h"
31 #include "tink/hybrid/hybrid_key_templates.h"
32 #include "tink/json_keyset_reader.h"
33 #include "tink/json_keyset_writer.h"
34 #include "tink/jwt/jwt_key_templates.h"
35 #include "tink/keyset_handle.h"
36 #include "tink/mac/mac_key_templates.h"
37 #include "tink/prf/prf_key_templates.h"
38 #include "tink/signature/signature_key_templates.h"
39 #include "tink/streamingaead/streaming_aead_key_templates.h"
40 #include "proto/tink.pb.h"
41
42 namespace tink_testing_api {
43
44 using ::crypto::tink::BinaryKeysetReader;
45 using ::crypto::tink::BinaryKeysetWriter;
46 using ::crypto::tink::CleartextKeysetHandle;
47 using ::crypto::tink::JsonKeysetReader;
48 using ::crypto::tink::JsonKeysetWriter;
49 using ::crypto::tink::KeysetHandle;
50 using ::crypto::tink::KeysetReader;
51 using ::crypto::tink::KeysetWriter;
52 using ::crypto::tink::util::StatusOr;
53 using ::google::crypto::tink::KeyTemplate;
54
KeysetImpl()55 KeysetImpl::KeysetImpl() {
56 key_templates_["AES128_EAX"] = crypto::tink::AeadKeyTemplates::Aes128Eax();
57 key_templates_["AES256_EAX"] = crypto::tink::AeadKeyTemplates::Aes256Eax();
58 key_templates_["AES128_GCM"] = crypto::tink::AeadKeyTemplates::Aes128Gcm();
59 key_templates_["AES128_GCM_RAW"] =
60 crypto::tink::AeadKeyTemplates::Aes128GcmNoPrefix();
61 key_templates_["AES256_GCM"] = crypto::tink::AeadKeyTemplates::Aes256Gcm();
62 key_templates_["AES256_GCM_RAW"] =
63 crypto::tink::AeadKeyTemplates::Aes256GcmNoPrefix();
64 key_templates_["AES128_GCM_SIV"] =
65 crypto::tink::AeadKeyTemplates::Aes128GcmSiv();
66 key_templates_["AES256_GCM_SIV"] =
67 crypto::tink::AeadKeyTemplates::Aes256GcmSiv();
68 key_templates_["AES128_CTR_HMAC_SHA256"] =
69 crypto::tink::AeadKeyTemplates::Aes128CtrHmacSha256();
70 key_templates_["AES256_CTR_HMAC_SHA256"] =
71 crypto::tink::AeadKeyTemplates::Aes256CtrHmacSha256();
72 key_templates_["CHACHA20_POLY1305"] =
73 crypto::tink::AeadKeyTemplates::XChaCha20Poly1305();
74 key_templates_["XCHACHA20_POLY1305"] =
75 crypto::tink::AeadKeyTemplates::XChaCha20Poly1305();
76 key_templates_["AES256_SIV"] =
77 crypto::tink::DeterministicAeadKeyTemplates::Aes256Siv();
78 key_templates_["AES128_CTR_HMAC_SHA256_4KB"] =
79 crypto::tink::StreamingAeadKeyTemplates::Aes128CtrHmacSha256Segment4KB();
80 key_templates_["AES128_CTR_HMAC_SHA256_1MB"] =
81 crypto::tink::StreamingAeadKeyTemplates::Aes128CtrHmacSha256Segment1MB();
82 key_templates_["AES256_CTR_HMAC_SHA256_4KB"] =
83 crypto::tink::StreamingAeadKeyTemplates::Aes256CtrHmacSha256Segment4KB();
84 key_templates_["AES256_CTR_HMAC_SHA256_1MB"] =
85 crypto::tink::StreamingAeadKeyTemplates::Aes256CtrHmacSha256Segment1MB();
86 key_templates_["AES128_GCM_HKDF_4KB"] =
87 crypto::tink::StreamingAeadKeyTemplates::Aes128GcmHkdf4KB();
88 key_templates_["AES256_GCM_HKDF_4KB"] =
89 crypto::tink::StreamingAeadKeyTemplates::Aes256GcmHkdf4KB();
90 key_templates_["AES256_GCM_HKDF_1MB"] =
91 crypto::tink::StreamingAeadKeyTemplates::Aes256GcmHkdf1MB();
92 key_templates_["ECIES_P256_HKDF_HMAC_SHA256_AES128_GCM"] =
93 crypto::tink::HybridKeyTemplates::EciesP256HkdfHmacSha256Aes128Gcm();
94 key_templates_["ECIES_P256_COMPRESSED_HKDF_HMAC_SHA256_AES128_GCM"] = crypto::
95 tink::HybridKeyTemplates::EciesP256CompressedHkdfHmacSha256Aes128Gcm();
96 key_templates_["ECIES_P256_HKDF_HMAC_SHA256_AES128_CTR_HMAC_SHA256"] =
97 crypto::tink::HybridKeyTemplates::
98 EciesP256HkdfHmacSha256Aes128CtrHmacSha256();
99 key_templates_
100 ["ECIES_P256_COMPRESSED_HKDF_HMAC_SHA256_AES128_CTR_HMAC_SHA256"] =
101 crypto::tink::HybridKeyTemplates::
102 EciesP256CompressedHkdfHmacSha256Aes128CtrHmacSha256();
103 key_templates_["DHKEM_X25519_HKDF_SHA256_HKDF_SHA256_AES_128_GCM"] =
104 crypto::tink::HybridKeyTemplates::HpkeX25519HkdfSha256Aes128Gcm();
105 key_templates_["DHKEM_X25519_HKDF_SHA256_HKDF_SHA256_AES_128_GCM_RAW"] =
106 crypto::tink::HybridKeyTemplates::HpkeX25519HkdfSha256Aes128GcmRaw();
107 key_templates_["DHKEM_X25519_HKDF_SHA256_HKDF_SHA256_AES_256_GCM"] =
108 crypto::tink::HybridKeyTemplates::HpkeX25519HkdfSha256Aes256Gcm();
109 key_templates_["DHKEM_X25519_HKDF_SHA256_HKDF_SHA256_AES_256_GCM_RAW"] =
110 crypto::tink::HybridKeyTemplates::HpkeX25519HkdfSha256Aes256GcmRaw();
111 key_templates_["DHKEM_X25519_HKDF_SHA256_HKDF_SHA256_CHACHA20_POLY1305"] =
112 crypto::tink::HybridKeyTemplates::HpkeX25519HkdfSha256ChaCha20Poly1305();
113 key_templates_["DHKEM_X25519_HKDF_SHA256_HKDF_SHA256_CHACHA20_POLY1305_RAW"] =
114 crypto::tink::HybridKeyTemplates::
115 HpkeX25519HkdfSha256ChaCha20Poly1305Raw();
116 key_templates_["AES_CMAC"] = crypto::tink::MacKeyTemplates::AesCmac();
117 key_templates_["HMAC_SHA256_128BITTAG"] =
118 crypto::tink::MacKeyTemplates::HmacSha256HalfSizeTag();
119 key_templates_["HMAC_SHA256_256BITTAG"] =
120 crypto::tink::MacKeyTemplates::HmacSha256();
121 key_templates_["HMAC_SHA512_256BITTAG"] =
122 crypto::tink::MacKeyTemplates::HmacSha512HalfSizeTag();
123 key_templates_["HMAC_SHA512_512BITTAG"] =
124 crypto::tink::MacKeyTemplates::HmacSha512();
125 key_templates_["ECDSA_P256"] =
126 crypto::tink::SignatureKeyTemplates::EcdsaP256();
127 key_templates_["ECDSA_P256_RAW"] =
128 crypto::tink::SignatureKeyTemplates::EcdsaP256Raw();
129 key_templates_["ECDSA_P384"] =
130 crypto::tink::SignatureKeyTemplates::EcdsaP384();
131 key_templates_["ECDSA_P384_SHA384"] =
132 crypto::tink::SignatureKeyTemplates::EcdsaP384Sha384();
133 key_templates_["ECDSA_P384_SHA512"] =
134 crypto::tink::SignatureKeyTemplates::EcdsaP384Sha512();
135 key_templates_["ECDSA_P521"] =
136 crypto::tink::SignatureKeyTemplates::EcdsaP521();
137 key_templates_["ECDSA_P256_IEEE_P1363"] =
138 crypto::tink::SignatureKeyTemplates::EcdsaP256Ieee();
139 key_templates_["ECDSA_P384_IEEE_P1363"] =
140 crypto::tink::SignatureKeyTemplates::EcdsaP384Ieee();
141 key_templates_["ECDSA_P521_IEEE_P1363"] =
142 crypto::tink::SignatureKeyTemplates::EcdsaP521Ieee();
143 key_templates_["ED25519"] = crypto::tink::SignatureKeyTemplates::Ed25519();
144 key_templates_["RSA_SSA_PKCS1_3072_SHA256_F4"] =
145 crypto::tink::SignatureKeyTemplates::RsaSsaPkcs13072Sha256F4();
146 key_templates_["RSA_SSA_PKCS1_4096_SHA512_F4"] =
147 crypto::tink::SignatureKeyTemplates::RsaSsaPkcs14096Sha512F4();
148 key_templates_["RSA_SSA_PSS_3072_SHA256_SHA256_32_F4"] =
149 crypto::tink::SignatureKeyTemplates::RsaSsaPss3072Sha256Sha256F4();
150 key_templates_["RSA_SSA_PSS_4096_SHA512_SHA512_64_F4"] =
151 crypto::tink::SignatureKeyTemplates::RsaSsaPss4096Sha512Sha512F4();
152 key_templates_["AES_CMAC_PRF"] = crypto::tink::PrfKeyTemplates::AesCmac();
153 key_templates_["HMAC_SHA256_PRF"] =
154 crypto::tink::PrfKeyTemplates::HmacSha256();
155 key_templates_["HMAC_SHA512_PRF"] =
156 crypto::tink::PrfKeyTemplates::HmacSha512();
157 key_templates_["HKDF_SHA256"] = crypto::tink::PrfKeyTemplates::HkdfSha256();
158 key_templates_["JWT_HS256"] = crypto::tink::JwtHs256Template();
159 key_templates_["JWT_HS256_RAW"] = crypto::tink::RawJwtHs256Template();
160 key_templates_["JWT_HS384"] = crypto::tink::JwtHs384Template();
161 key_templates_["JWT_HS384_RAW"] = crypto::tink::RawJwtHs384Template();
162 key_templates_["JWT_HS512"] = crypto::tink::JwtHs512Template();
163 key_templates_["JWT_HS512_RAW"] = crypto::tink::RawJwtHs512Template();
164 key_templates_["JWT_ES256"] = crypto::tink::JwtEs256Template();
165 key_templates_["JWT_ES256_RAW"] = crypto::tink::RawJwtEs256Template();
166 key_templates_["JWT_ES384"] = crypto::tink::JwtEs384Template();
167 key_templates_["JWT_ES384_RAW"] = crypto::tink::RawJwtEs384Template();
168 key_templates_["JWT_ES512"] = crypto::tink::JwtEs512Template();
169 key_templates_["JWT_ES512_RAW"] = crypto::tink::RawJwtEs512Template();
170 key_templates_["JWT_RS256_2048_F4"] =
171 crypto::tink::JwtRs256_2048_F4_Template();
172 key_templates_["JWT_RS256_2048_F4_RAW"] =
173 crypto::tink::RawJwtRs256_2048_F4_Template();
174 key_templates_["JWT_RS256_3072_F4"] =
175 crypto::tink::JwtRs256_3072_F4_Template();
176 key_templates_["JWT_RS256_3072_F4_RAW"] =
177 crypto::tink::RawJwtRs256_3072_F4_Template();
178 key_templates_["JWT_RS384_3072_F4"] =
179 crypto::tink::JwtRs384_3072_F4_Template();
180 key_templates_["JWT_RS384_3072_F4_RAW"] =
181 crypto::tink::RawJwtRs384_3072_F4_Template();
182 key_templates_["JWT_RS512_4096_F4"] =
183 crypto::tink::JwtRs512_4096_F4_Template();
184 key_templates_["JWT_RS512_4096_F4_RAW"] =
185 crypto::tink::RawJwtRs512_4096_F4_Template();
186 key_templates_["JWT_PS256_2048_F4"] =
187 crypto::tink::JwtPs256_2048_F4_Template();
188 key_templates_["JWT_PS256_2048_F4_RAW"] =
189 crypto::tink::RawJwtPs256_2048_F4_Template();
190 key_templates_["JWT_PS256_3072_F4"] =
191 crypto::tink::JwtPs256_3072_F4_Template();
192 key_templates_["JWT_PS256_3072_F4_RAW"] =
193 crypto::tink::RawJwtPs256_3072_F4_Template();
194 key_templates_["JWT_PS384_3072_F4"] =
195 crypto::tink::JwtPs384_3072_F4_Template();
196 key_templates_["JWT_PS384_3072_F4_RAW"] =
197 crypto::tink::RawJwtPs384_3072_F4_Template();
198 key_templates_["JWT_PS512_4096_F4"] =
199 crypto::tink::JwtPs512_4096_F4_Template();
200 key_templates_["JWT_PS512_4096_F4_RAW"] =
201 crypto::tink::RawJwtPs512_4096_F4_Template();
202 }
203
204 // Returns the key template for the given template name.
GetTemplate(grpc::ServerContext * context,const KeysetTemplateRequest * request,KeysetTemplateResponse * response)205 grpc::Status KeysetImpl::GetTemplate(grpc::ServerContext* context,
206 const KeysetTemplateRequest* request,
207 KeysetTemplateResponse* response) {
208 auto it = key_templates_.find(request->template_name());
209 if (it == key_templates_.end()) {
210 response->set_err(
211 absl::StrCat("key template not found: ", request->template_name()));
212 return grpc::Status::OK;
213 }
214 std::string templ;
215 if (!it->second.SerializeToString(&templ)) {
216 response->set_err("Failed to serialize template.");
217 return grpc::Status::OK;
218 }
219 response->set_key_template(templ);
220 return grpc::Status::OK;
221 }
222
223 // Generates a new keyset with one key from a template.
Generate(grpc::ServerContext * context,const KeysetGenerateRequest * request,KeysetGenerateResponse * response)224 grpc::Status KeysetImpl::Generate(grpc::ServerContext* context,
225 const KeysetGenerateRequest* request,
226 KeysetGenerateResponse* response) {
227 KeyTemplate key_template;
228 if (!key_template.ParseFromString(request->template_())) {
229 response->set_err("Could not parse the key template");
230 return grpc::Status::OK;
231 }
232 auto handle_result = ::crypto::tink::KeysetHandle::GenerateNew(key_template);
233 if (!handle_result.ok()) {
234 response->set_err(std::string(handle_result.status().message()));
235 return grpc::Status::OK;
236 }
237 std::stringbuf keyset;
238 auto writer_result =
239 BinaryKeysetWriter::New(absl::make_unique<std::ostream>(&keyset));
240 if (!writer_result.ok()) {
241 response->set_err(std::string(writer_result.status().message()));
242 return grpc::Status::OK;
243 }
244 auto status = CleartextKeysetHandle::Write(writer_result.value().get(),
245 *handle_result.value());
246 if (!status.ok()) {
247 response->set_err(std::string(status.message()));
248 return grpc::Status::OK;
249 }
250 response->set_keyset(keyset.str());
251 return grpc::Status::OK;
252 }
253
254 // Returns a public keyset for a given private keyset.
Public(grpc::ServerContext * context,const KeysetPublicRequest * request,KeysetPublicResponse * response)255 grpc::Status KeysetImpl::Public(grpc::ServerContext* context,
256 const KeysetPublicRequest* request,
257 KeysetPublicResponse* response) {
258 auto reader_result = BinaryKeysetReader::New(request->private_keyset());
259 if (!reader_result.ok()) {
260 response->set_err(std::string(reader_result.status().message()));
261 return grpc::Status::OK;
262 }
263 auto private_handle_result =
264 CleartextKeysetHandle::Read(std::move(reader_result.value()));
265 if (!private_handle_result.ok()) {
266 response->set_err(std::string(private_handle_result.status().message()));
267 return grpc::Status::OK;
268 }
269 auto public_handle_result =
270 private_handle_result.value()->GetPublicKeysetHandle();
271 if (!public_handle_result.ok()) {
272 response->set_err(std::string(public_handle_result.status().message()));
273 return grpc::Status::OK;
274 }
275 std::stringbuf public_keyset;
276 auto writer_result =
277 BinaryKeysetWriter::New(absl::make_unique<std::ostream>(&public_keyset));
278 if (!writer_result.ok()) {
279 response->set_err(std::string(writer_result.status().message()));
280 return grpc::Status::OK;
281 }
282 auto status = CleartextKeysetHandle::Write(writer_result.value().get(),
283 *public_handle_result.value());
284 if (!status.ok()) {
285 response->set_err(std::string(status.message()));
286 return grpc::Status::OK;
287 }
288 response->set_public_keyset(public_keyset.str());
289 return grpc::Status::OK;
290 }
291
292 // Converts a keyset from binary to JSON format.
ToJson(grpc::ServerContext * context,const KeysetToJsonRequest * request,KeysetToJsonResponse * response)293 grpc::Status KeysetImpl::ToJson(grpc::ServerContext* context,
294 const KeysetToJsonRequest* request,
295 KeysetToJsonResponse* response) {
296 auto reader_result = BinaryKeysetReader::New(request->keyset());
297 if (!reader_result.ok()) {
298 response->set_err(std::string(reader_result.status().message()));
299 return grpc::Status::OK;
300 }
301 auto handle_result =
302 CleartextKeysetHandle::Read(std::move(reader_result.value()));
303 if (!handle_result.ok()) {
304 response->set_err(std::string(handle_result.status().message()));
305 return grpc::Status::OK;
306 }
307 std::stringbuf json_keyset;
308 auto writer_result =
309 JsonKeysetWriter::New(absl::make_unique<std::ostream>(&json_keyset));
310 if (!writer_result.ok()) {
311 response->set_err(std::string(writer_result.status().message()));
312 return grpc::Status::OK;
313 }
314 auto status = CleartextKeysetHandle::Write(writer_result.value().get(),
315 *handle_result.value());
316 if (!status.ok()) {
317 response->set_err(std::string(status.message()));
318 return grpc::Status::OK;
319 }
320 response->set_json_keyset(json_keyset.str());
321 return grpc::Status::OK;
322 }
323
324 // Converts a keyset from JSON to binary format.
FromJson(grpc::ServerContext * context,const KeysetFromJsonRequest * request,KeysetFromJsonResponse * response)325 grpc::Status KeysetImpl::FromJson(grpc::ServerContext* context,
326 const KeysetFromJsonRequest* request,
327 KeysetFromJsonResponse* response) {
328 auto reader_result = JsonKeysetReader::New(request->json_keyset());
329 if (!reader_result.ok()) {
330 response->set_err(std::string(reader_result.status().message()));
331 return grpc::Status::OK;
332 }
333 auto handle_result =
334 CleartextKeysetHandle::Read(std::move(reader_result.value()));
335 if (!handle_result.ok()) {
336 response->set_err(std::string(handle_result.status().message()));
337 return grpc::Status::OK;
338 }
339 std::stringbuf keyset;
340 auto writer_result =
341 BinaryKeysetWriter::New(absl::make_unique<std::ostream>(&keyset));
342 if (!writer_result.ok()) {
343 response->set_err(std::string(writer_result.status().message()));
344 return grpc::Status::OK;
345 }
346 auto status = CleartextKeysetHandle::Write(writer_result.value().get(),
347 *handle_result.value());
348 if (!status.ok()) {
349 response->set_err(std::string(status.message()));
350 return grpc::Status::OK;
351 }
352 response->set_keyset(keyset.str());
353 return grpc::Status::OK;
354 }
355
WriteEncrypted(grpc::ServerContext * context,const KeysetWriteEncryptedRequest * request,KeysetWriteEncryptedResponse * response)356 grpc::Status KeysetImpl::WriteEncrypted(
357 grpc::ServerContext* context, const KeysetWriteEncryptedRequest* request,
358 KeysetWriteEncryptedResponse* response) {
359 StatusOr<std::unique_ptr<KeysetReader>>
360 master_keyset_reader = BinaryKeysetReader::New(request->master_keyset());
361 if (!master_keyset_reader.ok()) {
362 response->set_err(std::string(master_keyset_reader.status().message()));
363 return grpc::Status::OK;
364 }
365 StatusOr<std::unique_ptr<KeysetHandle>> master_keyset_handle =
366 CleartextKeysetHandle::Read(*std::move(master_keyset_reader));
367 if (!master_keyset_handle.ok()) {
368 response->set_err(std::string(master_keyset_handle.status().message()));
369 return grpc::Status::OK;
370 }
371 StatusOr<std::unique_ptr<crypto::tink::Aead>> master_aead =
372 (*master_keyset_handle)->GetPrimitive<crypto::tink::Aead>();
373 if (!master_aead.ok()) {
374 response->set_err(std::string(master_aead.status().message()));
375 return grpc::Status::OK;
376 }
377
378 StatusOr<std::unique_ptr<KeysetReader>> keyset_reader =
379 BinaryKeysetReader::New(request->keyset());
380 if (!keyset_reader.ok()) {
381 response->set_err(std::string(keyset_reader.status().message()));
382 return grpc::Status::OK;
383 }
384 StatusOr<std::unique_ptr<KeysetHandle>> keyset_handle =
385 CleartextKeysetHandle::Read(*std::move(keyset_reader));
386 if (!keyset_handle.ok()) {
387 response->set_err(std::string(keyset_handle.status().message()));
388 return grpc::Status::OK;
389 }
390
391 std::stringbuf encrypted_keyset;
392 std::unique_ptr<KeysetWriter> keyset_writer;
393
394 if (request->keyset_writer_type() == KEYSET_WRITER_BINARY) {
395 StatusOr<std::unique_ptr<BinaryKeysetWriter>> binary_keyset_writer =
396 BinaryKeysetWriter::New(
397 absl::make_unique<std::ostream>(&encrypted_keyset));
398 if (!binary_keyset_writer.ok()) {
399 response->set_err(std::string(binary_keyset_writer.status().message()));
400 return grpc::Status::OK;
401 }
402 keyset_writer = *std::move(binary_keyset_writer);
403 } else if (request->keyset_writer_type() == KEYSET_WRITER_JSON) {
404 StatusOr<std::unique_ptr<JsonKeysetWriter>> json_keyset_writer =
405 JsonKeysetWriter::New(
406 absl::make_unique<std::ostream>(&encrypted_keyset));
407 if (!json_keyset_writer.ok()) {
408 response->set_err(std::string(json_keyset_writer.status().message()));
409 return grpc::Status::OK;
410 }
411 keyset_writer = *std::move(json_keyset_writer);
412 } else {
413 return grpc::Status(grpc::StatusCode::INVALID_ARGUMENT,
414 "unknown keyset_writer_type");
415 }
416
417 if (request->has_associated_data()) {
418 crypto::tink::util::Status status =
419 (*keyset_handle)
420 ->WriteWithAssociatedData(keyset_writer.get(), **master_aead,
421 request->associated_data().value());
422 if (!status.ok()) {
423 response->set_err(std::string(status.message()));
424 return grpc::Status::OK;
425 }
426 } else {
427 crypto::tink::util::Status status =
428 (*keyset_handle)->Write(keyset_writer.get(), **master_aead);
429 if (!status.ok()) {
430 response->set_err(std::string(status.message()));
431 return grpc::Status::OK;
432 }
433 }
434 response->set_encrypted_keyset(encrypted_keyset.str());
435 return grpc::Status::OK;
436 }
437
ReadEncrypted(grpc::ServerContext * context,const KeysetReadEncryptedRequest * request,KeysetReadEncryptedResponse * response)438 grpc::Status KeysetImpl::ReadEncrypted(
439 grpc::ServerContext* context, const KeysetReadEncryptedRequest* request,
440 KeysetReadEncryptedResponse* response) {
441 StatusOr<std::unique_ptr<KeysetReader>> master_keyset_reader =
442 BinaryKeysetReader::New(request->master_keyset());
443 if (!master_keyset_reader.ok()) {
444 response->set_err(std::string(master_keyset_reader.status().message()));
445 return grpc::Status::OK;
446 }
447 StatusOr<std::unique_ptr<KeysetHandle>> master_keyset_handle =
448 CleartextKeysetHandle::Read(*std::move(master_keyset_reader));
449 if (!master_keyset_handle.ok()) {
450 response->set_err(std::string(master_keyset_handle.status().message()));
451 return grpc::Status::OK;
452 }
453 StatusOr<std::unique_ptr<crypto::tink::Aead>> master_aead =
454 (*master_keyset_handle)->GetPrimitive<crypto::tink::Aead>();
455 if (!master_aead.ok()) {
456 response->set_err(std::string(master_aead.status().message()));
457 return grpc::Status::OK;
458 }
459
460 std::unique_ptr<KeysetReader> keyset_reader;
461 if (request->keyset_reader_type() == KEYSET_READER_BINARY) {
462 StatusOr<std::unique_ptr<KeysetReader>> binary_keyset_reader =
463 BinaryKeysetReader::New(request->encrypted_keyset());
464 if (!binary_keyset_reader.ok()) {
465 response->set_err(std::string(binary_keyset_reader.status().message()));
466 return grpc::Status::OK;
467 }
468 keyset_reader = *std::move(binary_keyset_reader);
469 } else if (request->keyset_reader_type() == KEYSET_READER_JSON) {
470 StatusOr<std::unique_ptr<KeysetReader>> json_keyset_reader =
471 JsonKeysetReader::New(request->encrypted_keyset());
472 if (!json_keyset_reader.ok()) {
473 response->set_err(std::string(json_keyset_reader.status().message()));
474 return grpc::Status::OK;
475 }
476 keyset_reader = *std::move(json_keyset_reader);
477 } else {
478 return grpc::Status(grpc::StatusCode::INVALID_ARGUMENT,
479 "unknown keyset_writer_type");
480 }
481
482 std::unique_ptr<KeysetHandle> keyset_handle;
483 if (request->has_associated_data()) {
484 StatusOr<std::unique_ptr<KeysetHandle>> read_result =
485 ::crypto::tink::KeysetHandle::ReadWithAssociatedData(
486 std::move(keyset_reader), **master_aead,
487 request->associated_data().value());
488 if (!read_result.ok()) {
489 response->set_err(std::string(read_result.status().message()));
490 return grpc::Status::OK;
491 }
492 keyset_handle = *std::move(read_result);
493 } else {
494 StatusOr<std::unique_ptr<KeysetHandle>> read_result =
495 ::crypto::tink::KeysetHandle::Read(std::move(keyset_reader),
496 **master_aead);
497 if (!read_result.ok()) {
498 response->set_err(std::string(read_result.status().message()));
499 return grpc::Status::OK;
500 }
501 keyset_handle = *std::move(read_result);
502 }
503
504 std::stringbuf keyset;
505 StatusOr<std::unique_ptr<BinaryKeysetWriter>> keyset_writer =
506 BinaryKeysetWriter::New(absl::make_unique<std::ostream>(&keyset));
507 if (!keyset_writer.ok()) {
508 response->set_err(std::string(keyset_writer.status().message()));
509 return grpc::Status::OK;
510 }
511 crypto::tink::util::Status status =
512 CleartextKeysetHandle::Write(keyset_writer->get(), *keyset_handle);
513 if (!status.ok()) {
514 response->set_err(std::string(status.message()));
515 return grpc::Status::OK;
516 }
517 response->set_keyset(keyset.str());
518 return grpc::Status::OK;
519 }
520
521 } // namespace tink_testing_api
522