Line | Count | Source (jump to first uncovered line) |
1 | | /* |
2 | | * Copyright (c) 2021 Yubico AB. All rights reserved. |
3 | | * Use of this source code is governed by a BSD-style |
4 | | * license that can be found in the LICENSE file. |
5 | | */ |
6 | | |
7 | | #include <openssl/rsa.h> |
8 | | #include <openssl/obj_mac.h> |
9 | | |
10 | | #include "fido.h" |
11 | | |
12 | | #if defined(LIBRESSL_VERSION_NUMBER) |
13 | | static EVP_MD * |
14 | | rs1_get_EVP_MD(void) |
15 | | { |
16 | | const EVP_MD *from; |
17 | | EVP_MD *to = NULL; |
18 | | |
19 | | if ((from = EVP_sha1()) != NULL && (to = malloc(sizeof(*to))) != NULL) |
20 | | memcpy(to, from, sizeof(*to)); |
21 | | |
22 | | return (to); |
23 | | } |
24 | | |
25 | | static void |
26 | | rs1_free_EVP_MD(EVP_MD *md) |
27 | | { |
28 | | freezero(md, sizeof(*md)); |
29 | | } |
30 | | #elif OPENSSL_VERSION_NUMBER >= 0x30000000 |
31 | | static EVP_MD * |
32 | | rs1_get_EVP_MD(void) |
33 | | { |
34 | | return (EVP_MD_fetch(NULL, "SHA-1", NULL)); |
35 | | } |
36 | | |
37 | | static void |
38 | | rs1_free_EVP_MD(EVP_MD *md) |
39 | | { |
40 | | EVP_MD_free(md); |
41 | | } |
42 | | #else |
43 | | static EVP_MD * |
44 | | rs1_get_EVP_MD(void) |
45 | 11 | { |
46 | 11 | const EVP_MD *md; |
47 | | |
48 | 11 | if ((md = EVP_sha1()) == NULL) |
49 | 11 | return (NULL); |
50 | | |
51 | 10 | return (EVP_MD_meth_dup(md)); |
52 | 10 | } |
53 | | |
54 | | static void |
55 | | rs1_free_EVP_MD(EVP_MD *md) |
56 | 12 | { |
57 | 12 | EVP_MD_meth_free(md); |
58 | 12 | } |
59 | | #endif /* LIBRESSL_VERSION_NUMBER */ |
60 | | |
61 | | int |
62 | | rs1_verify_sig(const fido_blob_t *dgst, EVP_PKEY *pkey, |
63 | | const fido_blob_t *sig) |
64 | 12 | { |
65 | 12 | EVP_PKEY_CTX *pctx = NULL; |
66 | 12 | EVP_MD *md = NULL; |
67 | 12 | int ok = -1; |
68 | | |
69 | 12 | if (EVP_PKEY_base_id(pkey) != EVP_PKEY_RSA) { |
70 | 1 | fido_log_debug("%s: EVP_PKEY_base_id", __func__); |
71 | 1 | goto fail; |
72 | 1 | } |
73 | | |
74 | 11 | if ((md = rs1_get_EVP_MD()) == NULL) { |
75 | 1 | fido_log_debug("%s: rs1_get_EVP_MD", __func__); |
76 | 1 | goto fail; |
77 | 1 | } |
78 | | |
79 | 10 | if ((pctx = EVP_PKEY_CTX_new(pkey, NULL)) == NULL || |
80 | 10 | EVP_PKEY_verify_init(pctx) != 1 || |
81 | 10 | EVP_PKEY_CTX_set_rsa_padding(pctx, RSA_PKCS1_PADDING) != 1 || |
82 | 10 | EVP_PKEY_CTX_set_signature_md(pctx, md) != 1) { |
83 | 4 | fido_log_debug("%s: EVP_PKEY_CTX", __func__); |
84 | 4 | goto fail; |
85 | 4 | } |
86 | | |
87 | 6 | if (EVP_PKEY_verify(pctx, sig->ptr, sig->len, dgst->ptr, |
88 | 6 | dgst->len) != 1) { |
89 | 0 | fido_log_debug("%s: EVP_PKEY_verify", __func__); |
90 | 0 | goto fail; |
91 | 0 | } |
92 | | |
93 | 6 | ok = 0; |
94 | 12 | fail: |
95 | 12 | EVP_PKEY_CTX_free(pctx); |
96 | 12 | rs1_free_EVP_MD(md); |
97 | | |
98 | 12 | return (ok); |
99 | 6 | } |