1 /*
2  * Copyright 2014 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include <keymaster/km_openssl/rsa_operation.h>
18 
19 #include <utility>
20 
21 #include <limits.h>
22 
23 #include <openssl/err.h>
24 
25 #include <keymaster/km_openssl/openssl_err.h>
26 #include <keymaster/km_openssl/openssl_utils.h>
27 #include <keymaster/km_openssl/rsa_key.h>
28 #include <keymaster/logger.h>
29 
30 namespace keymaster {
31 
32 const size_t kPssOverhead = 2;
33 
34 // Overhead for PKCS#1 v1.5 signature padding of undigested messages.  Digested messages have
35 // additional overhead, for the digest algorithmIdentifier required by PKCS#1.
36 const size_t kPkcs1UndigestedSignaturePaddingOverhead = 11;
37 
38 /* static */
GetRsaKey(const Key & key,keymaster_error_t * error)39 EVP_PKEY* RsaOperationFactory::GetRsaKey(const Key& key, keymaster_error_t* error) {
40     const RsaKey& rsa_key = static_cast<const RsaKey&>(key);
41     if (!rsa_key.key()) {
42         *error = KM_ERROR_UNKNOWN_ERROR;
43         return nullptr;
44     }
45 
46     EVP_PKEY_Ptr pkey(rsa_key.InternalToEvp());
47     if (pkey.get() == nullptr) {
48         *error = KM_ERROR_UNKNOWN_ERROR;
49         return nullptr;
50     }
51     return pkey.release();
52 }
53 
54 static const keymaster_digest_t supported_digests[] = {
55     KM_DIGEST_NONE,      KM_DIGEST_MD5,       KM_DIGEST_SHA1,     KM_DIGEST_SHA_2_224,
56     KM_DIGEST_SHA_2_256, KM_DIGEST_SHA_2_384, KM_DIGEST_SHA_2_512};
57 
SupportedDigests(size_t * digest_count) const58 const keymaster_digest_t* RsaOperationFactory::SupportedDigests(size_t* digest_count) const {
59     *digest_count = array_length(supported_digests);
60     return supported_digests;
61 }
62 
CreateRsaOperation(Key && key,const AuthorizationSet & begin_params,keymaster_error_t * error)63 RsaOperation* RsaOperationFactory::CreateRsaOperation(Key&& key,
64                                                       const AuthorizationSet& begin_params,
65                                                       keymaster_error_t* error) {
66     keymaster_padding_t padding;
67     if (!GetAndValidatePadding(begin_params, key, &padding, error)) return nullptr;
68 
69     bool require_digest = (purpose() == KM_PURPOSE_SIGN || purpose() == KM_PURPOSE_VERIFY ||
70                            padding == KM_PAD_RSA_OAEP);
71 
72     keymaster_digest_t digest = KM_DIGEST_NONE;
73 
74     if (require_digest && !GetAndValidateDigest(begin_params, key, &digest, error, true)) {
75         return nullptr;
76     }
77 
78     UniquePtr<EVP_PKEY, EVP_PKEY_Delete> rsa(GetRsaKey(key, error));
79     if (!rsa.get()) return nullptr;
80 
81     RsaOperation* op = InstantiateOperation(key.hw_enforced_move(), key.sw_enforced_move(), digest,
82                                             padding, rsa.release());
83     if (!op) *error = KM_ERROR_MEMORY_ALLOCATION_FAILED;
84     return op;
85 }
86 
87 static const keymaster_padding_t supported_sig_padding[] = {KM_PAD_NONE, KM_PAD_RSA_PKCS1_1_5_SIGN,
88                                                             KM_PAD_RSA_PSS};
89 const keymaster_padding_t*
SupportedPaddingModes(size_t * padding_mode_count) const90 RsaDigestingOperationFactory::SupportedPaddingModes(size_t* padding_mode_count) const {
91     *padding_mode_count = array_length(supported_sig_padding);
92     return supported_sig_padding;
93 }
94 
CreateRsaOperation(Key && key,const AuthorizationSet & begin_params,keymaster_error_t * error)95 RsaOperation* RsaCryptingOperationFactory::CreateRsaOperation(Key&& key,
96                                                               const AuthorizationSet& begin_params,
97                                                               keymaster_error_t* error) {
98     keymaster_digest_t mgf_digest = KM_DIGEST_NONE;
99     key.authorizations().GetTagValue(TAG_RSA_OAEP_MGF_DIGEST, &mgf_digest);
100     *error = GetAndValidateMgfDigest(begin_params, key, &mgf_digest);
101     if (*error != KM_ERROR_OK) return nullptr;
102     UniquePtr<RsaOperation> op(
103         RsaOperationFactory::CreateRsaOperation(std::move(key), begin_params, error));
104     if (op.get()) {
105         switch (op->padding()) {
106         case KM_PAD_NONE:
107         case KM_PAD_RSA_PKCS1_1_5_ENCRYPT:
108             if (op->digest() != KM_DIGEST_NONE) {
109                 *error = KM_ERROR_INCOMPATIBLE_DIGEST;
110                 return nullptr;
111             }
112             break;
113 
114         case KM_PAD_RSA_OAEP:
115             if (op->digest() == KM_DIGEST_NONE) {
116                 *error = KM_ERROR_INCOMPATIBLE_DIGEST;
117                 return nullptr;
118             }
119             static_cast<RsaCryptOperation*>(op.get())->setOaepMgfDigest(mgf_digest);
120             break;
121 
122         default:
123             *error = KM_ERROR_UNSUPPORTED_PADDING_MODE;
124             return nullptr;
125         }
126     }
127     return op.release();
128 }
129 
GetAndValidateMgfDigest(const AuthorizationSet & begin_params,const Key & key,keymaster_digest_t * digest) const130 keymaster_error_t RsaCryptingOperationFactory::GetAndValidateMgfDigest(
131     const AuthorizationSet& begin_params, const Key& key, keymaster_digest_t* digest) const {
132     *digest = KM_DIGEST_SHA1;
133     if (!begin_params.Contains(TAG_PADDING, KM_PAD_RSA_OAEP)) {
134         *digest = KM_DIGEST_NONE;
135         return KM_ERROR_OK;
136     }
137     // If begin params does not specify any mgf digest
138     if (!begin_params.GetTagValue(TAG_RSA_OAEP_MGF_DIGEST, digest)) {
139         // And the authorizations has MGF Digest tag specified.
140         if (key.authorizations().GetTagCount(TAG_RSA_OAEP_MGF_DIGEST) > 0) {
141             // And key authorizations does not contain SHA1 for Mgf digest.
142             if (!key.authorizations().Contains(TAG_RSA_OAEP_MGF_DIGEST, KM_DIGEST_SHA1)) {
143                 // Then it is an error.
144                 LOG_E("%zu MGF digests specified in begin params and SHA1 not authorized",
145                       begin_params.GetTagCount(TAG_RSA_OAEP_MGF_DIGEST));
146                 return KM_ERROR_UNSUPPORTED_MGF_DIGEST;
147             }
148         }
149     } else if (!supported(*digest) || (*digest == KM_DIGEST_NONE)) {
150         LOG_E("MGF Digest %d not supported", *digest);
151         return KM_ERROR_UNSUPPORTED_MGF_DIGEST;
152     } else if (!key.authorizations().Contains(TAG_RSA_OAEP_MGF_DIGEST, *digest)) {
153         LOG_E("MGF Digest %d was specified, but not authorized by key", *digest);
154         return KM_ERROR_INCOMPATIBLE_MGF_DIGEST;
155     }
156     return KM_ERROR_OK;
157 }
158 
159 static const keymaster_padding_t supported_crypt_padding[] = {KM_PAD_NONE, KM_PAD_RSA_OAEP,
160                                                               KM_PAD_RSA_PKCS1_1_5_ENCRYPT};
161 const keymaster_padding_t*
SupportedPaddingModes(size_t * padding_mode_count) const162 RsaCryptingOperationFactory::SupportedPaddingModes(size_t* padding_mode_count) const {
163     *padding_mode_count = array_length(supported_crypt_padding);
164     return supported_crypt_padding;
165 }
166 
~RsaOperation()167 RsaOperation::~RsaOperation() {
168     if (rsa_key_ != nullptr) EVP_PKEY_free(rsa_key_);
169 }
170 
Begin(const AuthorizationSet &,AuthorizationSet *)171 keymaster_error_t RsaOperation::Begin(const AuthorizationSet& /* input_params */,
172                                       AuthorizationSet* /* output_params */) {
173     auto rc = GenerateRandom(reinterpret_cast<uint8_t*>(&operation_handle_),
174                              (size_t)sizeof(operation_handle_));
175     if (rc != KM_ERROR_OK) return rc;
176 
177     return InitDigest();
178 }
179 
Update(const AuthorizationSet &,const Buffer & input,AuthorizationSet *,Buffer *,size_t * input_consumed)180 keymaster_error_t RsaOperation::Update(const AuthorizationSet& /* additional_params */,
181                                        const Buffer& input, AuthorizationSet* /* output_params */,
182                                        Buffer* /* output */, size_t* input_consumed) {
183     assert(input_consumed);
184     switch (purpose()) {
185     default:
186         return KM_ERROR_UNIMPLEMENTED;
187     case KM_PURPOSE_SIGN:
188     case KM_PURPOSE_VERIFY:
189     case KM_PURPOSE_ENCRYPT:
190     case KM_PURPOSE_DECRYPT:
191         return StoreData(input, input_consumed);
192     }
193 }
194 
StoreData(const Buffer & input,size_t * input_consumed)195 keymaster_error_t RsaOperation::StoreData(const Buffer& input, size_t* input_consumed) {
196     assert(input_consumed);
197 
198     if (!data_.reserve(EVP_PKEY_size(rsa_key_))) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
199     // If the write fails, it's because input length exceeds key size.
200     if (!data_.write(input.peek_read(), input.available_read())) {
201         LOG_E("Input too long: cannot operate on %zu bytes of data with %u-byte RSA key",
202               input.available_read() + data_.available_read(), EVP_PKEY_size(rsa_key_));
203         return KM_ERROR_INVALID_INPUT_LENGTH;
204     }
205 
206     *input_consumed = input.available_read();
207     return KM_ERROR_OK;
208 }
209 
SetRsaPaddingInEvpContext(EVP_PKEY_CTX * pkey_ctx,bool signing)210 keymaster_error_t RsaOperation::SetRsaPaddingInEvpContext(EVP_PKEY_CTX* pkey_ctx, bool signing) {
211     keymaster_error_t error;
212     int openssl_padding = GetOpensslPadding(&error);
213     if (error != KM_ERROR_OK) return error;
214 
215     if (EVP_PKEY_CTX_set_rsa_padding(pkey_ctx, openssl_padding) <= 0)
216         return TranslateLastOpenSslError();
217 
218     if (signing && openssl_padding == RSA_PKCS1_PSS_PADDING) {
219         // Also need to set the length of the salt used in the padding generation.  We set it equal
220         // to the length of the selected digest.
221         assert(digest_algorithm_);
222         if (EVP_PKEY_CTX_set_rsa_pss_saltlen(pkey_ctx, EVP_MD_size(digest_algorithm_)) <= 0)
223             return TranslateLastOpenSslError();
224     }
225 
226     return KM_ERROR_OK;
227 }
228 
InitDigest()229 keymaster_error_t RsaOperation::InitDigest() {
230     if (digest_ == KM_DIGEST_NONE) {
231         if (require_digest()) return KM_ERROR_INCOMPATIBLE_DIGEST;
232         return KM_ERROR_OK;
233     }
234     digest_algorithm_ = KmDigestToEvpDigest(digest_);
235     if (digest_algorithm_ == nullptr) {
236         return KM_ERROR_UNSUPPORTED_DIGEST;
237     }
238     return KM_ERROR_OK;
239 }
240 
RsaDigestingOperation(AuthorizationSet && hw_enforced,AuthorizationSet && sw_enforced,keymaster_purpose_t purpose,keymaster_digest_t digest,keymaster_padding_t padding,EVP_PKEY * key)241 RsaDigestingOperation::RsaDigestingOperation(AuthorizationSet&& hw_enforced,
242                                              AuthorizationSet&& sw_enforced,
243                                              keymaster_purpose_t purpose, keymaster_digest_t digest,
244                                              keymaster_padding_t padding, EVP_PKEY* key)
245     : RsaOperation(std::move(hw_enforced), std::move(sw_enforced), purpose, digest, padding, key) {
246     EVP_MD_CTX_init(&digest_ctx_);
247 }
~RsaDigestingOperation()248 RsaDigestingOperation::~RsaDigestingOperation() {
249     EVP_MD_CTX_cleanup(&digest_ctx_);
250 }
251 
GetOpensslPadding(keymaster_error_t * error)252 int RsaDigestingOperation::GetOpensslPadding(keymaster_error_t* error) {
253     *error = KM_ERROR_OK;
254     switch (padding_) {
255     case KM_PAD_NONE:
256         return RSA_NO_PADDING;
257     case KM_PAD_RSA_PKCS1_1_5_SIGN:
258         return RSA_PKCS1_PADDING;
259     case KM_PAD_RSA_PSS:
260         if (digest_ == KM_DIGEST_NONE) {
261             *error = KM_ERROR_INCOMPATIBLE_PADDING_MODE;
262             return -1;
263         }
264         if (EVP_MD_size(digest_algorithm_) * 2 + kPssOverhead > (size_t)EVP_PKEY_size(rsa_key_)) {
265             LOG_E("Input too long: %zu-byte digest cannot be used with %d-byte RSA key in PSS "
266                   "padding mode",
267                   EVP_MD_size(digest_algorithm_), EVP_PKEY_size(rsa_key_));
268             *error = KM_ERROR_INCOMPATIBLE_DIGEST;
269             return -1;
270         }
271         return RSA_PKCS1_PSS_PADDING;
272     default:
273         return -1;
274     }
275 }
276 
Begin(const AuthorizationSet & input_params,AuthorizationSet * output_params)277 keymaster_error_t RsaSignOperation::Begin(const AuthorizationSet& input_params,
278                                           AuthorizationSet* output_params) {
279     keymaster_error_t error = RsaDigestingOperation::Begin(input_params, output_params);
280     if (error != KM_ERROR_OK) return error;
281 
282     if (digest_ == KM_DIGEST_NONE) return KM_ERROR_OK;
283 
284     EVP_PKEY_CTX* pkey_ctx;
285     if (EVP_DigestSignInit(&digest_ctx_, &pkey_ctx, digest_algorithm_, nullptr /* engine */,
286                            rsa_key_) != 1)
287         return TranslateLastOpenSslError();
288     return SetRsaPaddingInEvpContext(pkey_ctx, true /* signing */);
289 }
290 
Update(const AuthorizationSet & additional_params,const Buffer & input,AuthorizationSet * output_params,Buffer * output,size_t * input_consumed)291 keymaster_error_t RsaSignOperation::Update(const AuthorizationSet& additional_params,
292                                            const Buffer& input, AuthorizationSet* output_params,
293                                            Buffer* output, size_t* input_consumed) {
294     if (digest_ == KM_DIGEST_NONE)
295         // Just buffer the data.
296         return RsaOperation::Update(additional_params, input, output_params, output,
297                                     input_consumed);
298 
299     if (EVP_DigestSignUpdate(&digest_ctx_, input.peek_read(), input.available_read()) != 1)
300         return TranslateLastOpenSslError();
301     *input_consumed = input.available_read();
302     return KM_ERROR_OK;
303 }
304 
Finish(const AuthorizationSet & additional_params,const Buffer & input,const Buffer &,AuthorizationSet *,Buffer * output)305 keymaster_error_t RsaSignOperation::Finish(const AuthorizationSet& additional_params,
306                                            const Buffer& input, const Buffer& /* signature */,
307                                            AuthorizationSet* /* output_params */, Buffer* output) {
308     assert(output);
309 
310     keymaster_error_t error = UpdateForFinish(additional_params, input);
311     if (error != KM_ERROR_OK) return error;
312 
313     if (digest_ == KM_DIGEST_NONE)
314         return SignUndigested(output);
315     else
316         return SignDigested(output);
317 }
318 
zero_pad_left(UniquePtr<uint8_t[]> * dest,size_t padded_len,Buffer & src)319 static keymaster_error_t zero_pad_left(UniquePtr<uint8_t[]>* dest, size_t padded_len, Buffer& src) {
320     assert(padded_len > src.available_read());
321 
322     dest->reset(new (std::nothrow) uint8_t[padded_len]);
323     if (!dest->get()) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
324 
325     size_t padding_len = padded_len - src.available_read();
326     memset(dest->get(), 0, padding_len);
327     if (!src.read(dest->get() + padding_len, src.available_read())) return KM_ERROR_UNKNOWN_ERROR;
328 
329     return KM_ERROR_OK;
330 }
331 
SignUndigested(Buffer * output)332 keymaster_error_t RsaSignOperation::SignUndigested(Buffer* output) {
333     UniquePtr<RSA, RSA_Delete> rsa(EVP_PKEY_get1_RSA(const_cast<EVP_PKEY*>(rsa_key_)));
334     if (!rsa.get()) return TranslateLastOpenSslError();
335 
336     if (!output->Reinitialize(RSA_size(rsa.get()))) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
337 
338     size_t key_len = EVP_PKEY_size(rsa_key_);
339     int bytes_encrypted;
340     switch (padding_) {
341     case KM_PAD_NONE: {
342         const uint8_t* to_encrypt = data_.peek_read();
343         UniquePtr<uint8_t[]> zero_padded;
344         if (data_.available_read() > key_len) {
345             return KM_ERROR_INVALID_INPUT_LENGTH;
346         } else if (data_.available_read() < key_len) {
347             keymaster_error_t error = zero_pad_left(&zero_padded, key_len, data_);
348             if (error != KM_ERROR_OK) return error;
349             to_encrypt = zero_padded.get();
350         }
351         bytes_encrypted = RSA_private_encrypt(key_len, to_encrypt, output->peek_write(), rsa.get(),
352                                               RSA_NO_PADDING);
353         break;
354     }
355     case KM_PAD_RSA_PKCS1_1_5_SIGN:
356         // Does PKCS1 padding without digesting even make sense?  Dunno.  We'll support it.
357         if (data_.available_read() + kPkcs1UndigestedSignaturePaddingOverhead > key_len) {
358             LOG_E("Input too long: cannot sign %zu-byte message with PKCS1 padding with %u-bit key",
359                   data_.available_read(), EVP_PKEY_size(rsa_key_) * 8);
360             return KM_ERROR_INVALID_INPUT_LENGTH;
361         }
362         bytes_encrypted = RSA_private_encrypt(data_.available_read(), data_.peek_read(),
363                                               output->peek_write(), rsa.get(), RSA_PKCS1_PADDING);
364         break;
365 
366     default:
367         return KM_ERROR_UNSUPPORTED_PADDING_MODE;
368     }
369 
370     if (bytes_encrypted <= 0) return TranslateLastOpenSslError();
371     if (!output->advance_write(bytes_encrypted)) return KM_ERROR_UNKNOWN_ERROR;
372     return KM_ERROR_OK;
373 }
374 
SignDigested(Buffer * output)375 keymaster_error_t RsaSignOperation::SignDigested(Buffer* output) {
376     size_t siglen;
377     if (EVP_DigestSignFinal(&digest_ctx_, nullptr /* signature */, &siglen) != 1)
378         return TranslateLastOpenSslError();
379 
380     if (!output->Reinitialize(siglen)) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
381 
382     if (EVP_DigestSignFinal(&digest_ctx_, output->peek_write(), &siglen) <= 0)
383         return TranslateLastOpenSslError();
384     if (!output->advance_write(siglen)) return KM_ERROR_UNKNOWN_ERROR;
385 
386     return KM_ERROR_OK;
387 }
388 
Begin(const AuthorizationSet & input_params,AuthorizationSet * output_params)389 keymaster_error_t RsaVerifyOperation::Begin(const AuthorizationSet& input_params,
390                                             AuthorizationSet* output_params) {
391     keymaster_error_t error = RsaDigestingOperation::Begin(input_params, output_params);
392     if (error != KM_ERROR_OK) return error;
393 
394     if (digest_ == KM_DIGEST_NONE) return KM_ERROR_OK;
395 
396     EVP_PKEY_CTX* pkey_ctx;
397     if (EVP_DigestVerifyInit(&digest_ctx_, &pkey_ctx, digest_algorithm_, nullptr, rsa_key_) != 1)
398         return TranslateLastOpenSslError();
399     return SetRsaPaddingInEvpContext(pkey_ctx, false /* signing */);
400 }
401 
Update(const AuthorizationSet & additional_params,const Buffer & input,AuthorizationSet * output_params,Buffer * output,size_t * input_consumed)402 keymaster_error_t RsaVerifyOperation::Update(const AuthorizationSet& additional_params,
403                                              const Buffer& input, AuthorizationSet* output_params,
404                                              Buffer* output, size_t* input_consumed) {
405     if (digest_ == KM_DIGEST_NONE)
406         // Just buffer the data.
407         return RsaOperation::Update(additional_params, input, output_params, output,
408                                     input_consumed);
409 
410     if (EVP_DigestVerifyUpdate(&digest_ctx_, input.peek_read(), input.available_read()) != 1)
411         return TranslateLastOpenSslError();
412     *input_consumed = input.available_read();
413     return KM_ERROR_OK;
414 }
415 
Finish(const AuthorizationSet & additional_params,const Buffer & input,const Buffer & signature,AuthorizationSet *,Buffer *)416 keymaster_error_t RsaVerifyOperation::Finish(const AuthorizationSet& additional_params,
417                                              const Buffer& input, const Buffer& signature,
418                                              AuthorizationSet* /* output_params */,
419                                              Buffer* /* output */) {
420     keymaster_error_t error = UpdateForFinish(additional_params, input);
421     if (error != KM_ERROR_OK) return error;
422 
423     if (digest_ == KM_DIGEST_NONE)
424         return VerifyUndigested(signature);
425     else
426         return VerifyDigested(signature);
427 }
428 
VerifyUndigested(const Buffer & signature)429 keymaster_error_t RsaVerifyOperation::VerifyUndigested(const Buffer& signature) {
430     UniquePtr<RSA, RSA_Delete> rsa(EVP_PKEY_get1_RSA(const_cast<EVP_PKEY*>(rsa_key_)));
431     if (!rsa.get()) return KM_ERROR_UNKNOWN_ERROR;
432 
433     size_t key_len = RSA_size(rsa.get());
434     int openssl_padding;
435     switch (padding_) {
436     case KM_PAD_NONE:
437         if (data_.available_read() > key_len) return KM_ERROR_INVALID_INPUT_LENGTH;
438         if (key_len != signature.available_read()) return KM_ERROR_VERIFICATION_FAILED;
439         openssl_padding = RSA_NO_PADDING;
440         break;
441     case KM_PAD_RSA_PKCS1_1_5_SIGN:
442         if (data_.available_read() + kPkcs1UndigestedSignaturePaddingOverhead > key_len) {
443             LOG_E("Input too long: cannot verify %zu-byte message with PKCS1 padding + %zu-bit key",
444                   data_.available_read(), key_len * 8);
445             return KM_ERROR_INVALID_INPUT_LENGTH;
446         }
447         openssl_padding = RSA_PKCS1_PADDING;
448         break;
449     default:
450         return KM_ERROR_UNSUPPORTED_PADDING_MODE;
451     }
452 
453     UniquePtr<uint8_t[]> decrypted_data(new (std::nothrow) uint8_t[key_len]);
454     if (!decrypted_data.get()) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
455     int bytes_decrypted = RSA_public_decrypt(signature.available_read(), signature.peek_read(),
456                                              decrypted_data.get(), rsa.get(), openssl_padding);
457     if (bytes_decrypted < 0) return KM_ERROR_VERIFICATION_FAILED;
458 
459     const uint8_t* compare_pos = decrypted_data.get();
460     size_t bytes_to_compare = bytes_decrypted;
461     uint8_t zero_check_result = 0;
462     if (padding_ == KM_PAD_NONE && data_.available_read() < bytes_to_compare) {
463         // If the data is short, for "unpadded" signing we zero-pad to the left.  So during
464         // verification we should have zeros on the left of the decrypted data.  Do a constant-time
465         // check.
466         const uint8_t* zero_end = compare_pos + bytes_to_compare - data_.available_read();
467         while (compare_pos < zero_end)
468             zero_check_result |= *compare_pos++;
469         bytes_to_compare = data_.available_read();
470     }
471     if (memcmp_s(compare_pos, data_.peek_read(), bytes_to_compare) != 0 || zero_check_result != 0)
472         return KM_ERROR_VERIFICATION_FAILED;
473     return KM_ERROR_OK;
474 }
475 
VerifyDigested(const Buffer & signature)476 keymaster_error_t RsaVerifyOperation::VerifyDigested(const Buffer& signature) {
477     if (!EVP_DigestVerifyFinal(&digest_ctx_, signature.peek_read(), signature.available_read()))
478         return KM_ERROR_VERIFICATION_FAILED;
479     return KM_ERROR_OK;
480 }
481 
SetOaepDigestIfRequired(EVP_PKEY_CTX * pkey_ctx)482 keymaster_error_t RsaCryptOperation::SetOaepDigestIfRequired(EVP_PKEY_CTX* pkey_ctx) {
483     if (padding() != KM_PAD_RSA_OAEP) return KM_ERROR_OK;
484 
485     assert(digest_algorithm_ != nullptr);
486     if (!EVP_PKEY_CTX_set_rsa_oaep_md(pkey_ctx, digest_algorithm_)) {
487         return TranslateLastOpenSslError();
488     }
489     assert(mgf_digest_algorithm_ != nullptr);
490     // MGF1 MD is always SHA1.
491     if (!EVP_PKEY_CTX_set_rsa_mgf1_md(pkey_ctx, mgf_digest_algorithm_)) {
492         return TranslateLastOpenSslError();
493     }
494     return KM_ERROR_OK;
495 }
496 
Begin(const AuthorizationSet & input_params,AuthorizationSet * output_params)497 keymaster_error_t RsaCryptOperation::Begin(const AuthorizationSet& input_params,
498                                            AuthorizationSet* output_params) {
499     keymaster_error_t error = RsaOperation::Begin(input_params, output_params);
500     if (error != KM_ERROR_OK) return error;
501     return InitMgfDigest();
502 }
503 
GetOpensslPadding(keymaster_error_t * error)504 int RsaCryptOperation::GetOpensslPadding(keymaster_error_t* error) {
505     *error = KM_ERROR_OK;
506     switch (padding_) {
507     case KM_PAD_NONE:
508         return RSA_NO_PADDING;
509     case KM_PAD_RSA_PKCS1_1_5_ENCRYPT:
510         return RSA_PKCS1_PADDING;
511     case KM_PAD_RSA_OAEP:
512         return RSA_PKCS1_OAEP_PADDING;
513     default:
514         return -1;
515     }
516 }
517 
InitMgfDigest()518 keymaster_error_t RsaCryptOperation::InitMgfDigest() {
519     if (mgf_digest_ == KM_DIGEST_NONE) {
520         return KM_ERROR_OK;
521     }
522     mgf_digest_algorithm_ = KmDigestToEvpDigest(mgf_digest_);
523     if (mgf_digest_algorithm_ == nullptr) {
524         return KM_ERROR_UNSUPPORTED_DIGEST;
525     }
526     return KM_ERROR_OK;
527 }
528 
Finish(const AuthorizationSet & additional_params,const Buffer & input,const Buffer &,AuthorizationSet *,Buffer * output)529 keymaster_error_t RsaEncryptOperation::Finish(const AuthorizationSet& additional_params,
530                                               const Buffer& input, const Buffer& /* signature */,
531                                               AuthorizationSet* /* output_params */,
532                                               Buffer* output) {
533     if (!output) return KM_ERROR_OUTPUT_PARAMETER_NULL;
534 
535     keymaster_error_t error = UpdateForFinish(additional_params, input);
536     if (error != KM_ERROR_OK) return error;
537 
538     EVP_PKEY_CTX_Ptr ctx(EVP_PKEY_CTX_new(rsa_key_, nullptr /* engine */));
539     if (!ctx.get()) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
540 
541     if (EVP_PKEY_encrypt_init(ctx.get()) <= 0) return TranslateLastOpenSslError();
542 
543     error = SetRsaPaddingInEvpContext(ctx.get(), false /* signing */);
544     if (error != KM_ERROR_OK) return error;
545     error = SetOaepDigestIfRequired(ctx.get());
546     if (error != KM_ERROR_OK) return error;
547 
548     size_t outlen;
549     if (EVP_PKEY_encrypt(ctx.get(), nullptr /* out */, &outlen, data_.peek_read(),
550                          data_.available_read()) <= 0)
551         return TranslateLastOpenSslError();
552 
553     if (!output->Reinitialize(outlen)) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
554 
555     const uint8_t* to_encrypt = data_.peek_read();
556     size_t to_encrypt_len = data_.available_read();
557     UniquePtr<uint8_t[]> zero_padded;
558     if (padding_ == KM_PAD_NONE && to_encrypt_len < outlen) {
559         keymaster_error_t error = zero_pad_left(&zero_padded, outlen, data_);
560         if (error != KM_ERROR_OK) return error;
561         to_encrypt = zero_padded.get();
562         to_encrypt_len = outlen;
563     }
564 
565     if (EVP_PKEY_encrypt(ctx.get(), output->peek_write(), &outlen, to_encrypt, to_encrypt_len) <= 0)
566         return TranslateLastOpenSslError();
567     if (!output->advance_write(outlen)) return KM_ERROR_UNKNOWN_ERROR;
568 
569     return KM_ERROR_OK;
570 }
571 
Finish(const AuthorizationSet & additional_params,const Buffer & input,const Buffer &,AuthorizationSet *,Buffer * output)572 keymaster_error_t RsaDecryptOperation::Finish(const AuthorizationSet& additional_params,
573                                               const Buffer& input, const Buffer& /* signature */,
574                                               AuthorizationSet* /* output_params */,
575                                               Buffer* output) {
576     if (!output) return KM_ERROR_OUTPUT_PARAMETER_NULL;
577 
578     keymaster_error_t error = UpdateForFinish(additional_params, input);
579     if (error != KM_ERROR_OK) return error;
580 
581     EVP_PKEY_CTX_Ptr ctx(EVP_PKEY_CTX_new(rsa_key_, nullptr /* engine */));
582     if (!ctx.get()) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
583 
584     if (EVP_PKEY_decrypt_init(ctx.get()) <= 0) return TranslateLastOpenSslError();
585 
586     error = SetRsaPaddingInEvpContext(ctx.get(), false /* signing */);
587     if (error != KM_ERROR_OK) return error;
588     error = SetOaepDigestIfRequired(ctx.get());
589     if (error != KM_ERROR_OK) return error;
590 
591     size_t outlen;
592     if (EVP_PKEY_decrypt(ctx.get(), nullptr /* out */, &outlen, data_.peek_read(),
593                          data_.available_read()) <= 0)
594         return TranslateLastOpenSslError();
595 
596     if (!output->Reinitialize(outlen)) return KM_ERROR_MEMORY_ALLOCATION_FAILED;
597 
598     const uint8_t* to_decrypt = data_.peek_read();
599     size_t to_decrypt_len = data_.available_read();
600     UniquePtr<uint8_t[]> zero_padded;
601     if (padding_ == KM_PAD_NONE && to_decrypt_len < outlen) {
602         keymaster_error_t error = zero_pad_left(&zero_padded, outlen, data_);
603         if (error != KM_ERROR_OK) return error;
604         to_decrypt = zero_padded.get();
605         to_decrypt_len = outlen;
606     }
607 
608     if (EVP_PKEY_decrypt(ctx.get(), output->peek_write(), &outlen, to_decrypt, to_decrypt_len) <= 0)
609         return TranslateLastOpenSslError();
610     if (!output->advance_write(outlen)) return KM_ERROR_UNKNOWN_ERROR;
611 
612     return KM_ERROR_OK;
613 }
614 
615 }  // namespace keymaster
616