rsa/rsa_oaep.c: remove memcpy calls from RSA_padding_check_PKCS1_OAEP.
[oweals/openssl.git] / crypto / evp / m_sigver.c
1 /*
2  * Copyright 2006-2016 The OpenSSL Project Authors. All Rights Reserved.
3  *
4  * Licensed under the OpenSSL license (the "License").  You may not use
5  * this file except in compliance with the License.  You can obtain a copy
6  * in the file LICENSE in the source distribution or at
7  * https://www.openssl.org/source/license.html
8  */
9
10 #include <stdio.h>
11 #include "internal/cryptlib.h"
12 #include <openssl/evp.h>
13 #include <openssl/objects.h>
14 #include <openssl/x509.h>
15 #include "internal/evp_int.h"
16 #include "evp_locl.h"
17
18 static int do_sigver_init(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx,
19                           const EVP_MD *type, ENGINE *e, EVP_PKEY *pkey,
20                           int ver)
21 {
22     if (ctx->pctx == NULL)
23         ctx->pctx = EVP_PKEY_CTX_new(pkey, e);
24     if (ctx->pctx == NULL)
25         return 0;
26
27     if (!(ctx->pctx->pmeth->flags & EVP_PKEY_FLAG_SIGCTX_CUSTOM)) {
28
29         if (type == NULL) {
30             int def_nid;
31             if (EVP_PKEY_get_default_digest_nid(pkey, &def_nid) > 0)
32                 type = EVP_get_digestbynid(def_nid);
33         }
34
35         if (type == NULL) {
36             EVPerr(EVP_F_DO_SIGVER_INIT, EVP_R_NO_DEFAULT_DIGEST);
37             return 0;
38         }
39     }
40
41     if (ver) {
42         if (ctx->pctx->pmeth->verifyctx_init) {
43             if (ctx->pctx->pmeth->verifyctx_init(ctx->pctx, ctx) <= 0)
44                 return 0;
45             ctx->pctx->operation = EVP_PKEY_OP_VERIFYCTX;
46         } else if (EVP_PKEY_verify_init(ctx->pctx) <= 0)
47             return 0;
48     } else {
49         if (ctx->pctx->pmeth->signctx_init) {
50             if (ctx->pctx->pmeth->signctx_init(ctx->pctx, ctx) <= 0)
51                 return 0;
52             ctx->pctx->operation = EVP_PKEY_OP_SIGNCTX;
53         } else if (EVP_PKEY_sign_init(ctx->pctx) <= 0)
54             return 0;
55     }
56     if (EVP_PKEY_CTX_set_signature_md(ctx->pctx, type) <= 0)
57         return 0;
58     if (pctx)
59         *pctx = ctx->pctx;
60     if (ctx->pctx->pmeth->flags & EVP_PKEY_FLAG_SIGCTX_CUSTOM)
61         return 1;
62     if (!EVP_DigestInit_ex(ctx, type, e))
63         return 0;
64     return 1;
65 }
66
67 int EVP_DigestSignInit(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx,
68                        const EVP_MD *type, ENGINE *e, EVP_PKEY *pkey)
69 {
70     return do_sigver_init(ctx, pctx, type, e, pkey, 0);
71 }
72
73 int EVP_DigestVerifyInit(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx,
74                          const EVP_MD *type, ENGINE *e, EVP_PKEY *pkey)
75 {
76     return do_sigver_init(ctx, pctx, type, e, pkey, 1);
77 }
78
79 int EVP_DigestSignFinal(EVP_MD_CTX *ctx, unsigned char *sigret,
80                         size_t *siglen)
81 {
82     int sctx = 0, r = 0;
83     EVP_PKEY_CTX *pctx = ctx->pctx;
84     if (pctx->pmeth->flags & EVP_PKEY_FLAG_SIGCTX_CUSTOM) {
85         if (!sigret)
86             return pctx->pmeth->signctx(pctx, sigret, siglen, ctx);
87         if (ctx->flags & EVP_MD_CTX_FLAG_FINALISE)
88             r = pctx->pmeth->signctx(pctx, sigret, siglen, ctx);
89         else {
90             EVP_PKEY_CTX *dctx = EVP_PKEY_CTX_dup(ctx->pctx);
91             if (!dctx)
92                 return 0;
93             r = dctx->pmeth->signctx(dctx, sigret, siglen, ctx);
94             EVP_PKEY_CTX_free(dctx);
95         }
96         return r;
97     }
98     if (pctx->pmeth->signctx)
99         sctx = 1;
100     else
101         sctx = 0;
102     if (sigret) {
103         unsigned char md[EVP_MAX_MD_SIZE];
104         unsigned int mdlen = 0;
105         if (ctx->flags & EVP_MD_CTX_FLAG_FINALISE) {
106             if (sctx)
107                 r = ctx->pctx->pmeth->signctx(ctx->pctx, sigret, siglen, ctx);
108             else
109                 r = EVP_DigestFinal_ex(ctx, md, &mdlen);
110         } else {
111             EVP_MD_CTX *tmp_ctx = EVP_MD_CTX_new();
112             if (tmp_ctx == NULL)
113                 return 0;
114             if (!EVP_MD_CTX_copy_ex(tmp_ctx, ctx)) {
115                 EVP_MD_CTX_free(tmp_ctx);
116                 return 0;
117             }
118             if (sctx)
119                 r = tmp_ctx->pctx->pmeth->signctx(tmp_ctx->pctx,
120                                                   sigret, siglen, tmp_ctx);
121             else
122                 r = EVP_DigestFinal_ex(tmp_ctx, md, &mdlen);
123             EVP_MD_CTX_free(tmp_ctx);
124         }
125         if (sctx || !r)
126             return r;
127         if (EVP_PKEY_sign(ctx->pctx, sigret, siglen, md, mdlen) <= 0)
128             return 0;
129     } else {
130         if (sctx) {
131             if (pctx->pmeth->signctx(pctx, sigret, siglen, ctx) <= 0)
132                 return 0;
133         } else {
134             int s = EVP_MD_size(ctx->digest);
135             if (s < 0 || EVP_PKEY_sign(pctx, sigret, siglen, NULL, s) <= 0)
136                 return 0;
137         }
138     }
139     return 1;
140 }
141
142 int EVP_DigestVerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sig,
143                           size_t siglen)
144 {
145     unsigned char md[EVP_MAX_MD_SIZE];
146     int r = 0;
147     unsigned int mdlen = 0;
148     int vctx = 0;
149
150     if (ctx->pctx->pmeth->verifyctx)
151         vctx = 1;
152     else
153         vctx = 0;
154     if (ctx->flags & EVP_MD_CTX_FLAG_FINALISE) {
155         if (vctx) {
156             r = ctx->pctx->pmeth->verifyctx(ctx->pctx, sig, siglen, ctx);
157         } else
158             r = EVP_DigestFinal_ex(ctx, md, &mdlen);
159     } else {
160         EVP_MD_CTX *tmp_ctx = EVP_MD_CTX_new();
161         if (tmp_ctx == NULL)
162             return -1;
163         if (!EVP_MD_CTX_copy_ex(tmp_ctx, ctx)) {
164             EVP_MD_CTX_free(tmp_ctx);
165             return -1;
166         }
167         if (vctx) {
168             r = tmp_ctx->pctx->pmeth->verifyctx(tmp_ctx->pctx,
169                                                 sig, siglen, tmp_ctx);
170         } else
171             r = EVP_DigestFinal_ex(tmp_ctx, md, &mdlen);
172         EVP_MD_CTX_free(tmp_ctx);
173     }
174     if (vctx || !r)
175         return r;
176     return EVP_PKEY_verify(ctx->pctx, sig, siglen, md, mdlen);
177 }