2016-05-18 02:24:46 +08:00
|
|
|
/*
|
2021-04-22 21:38:44 +08:00
|
|
|
* Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved.
|
2015-01-22 11:40:55 +08:00
|
|
|
*
|
2018-12-06 20:40:06 +08:00
|
|
|
* Licensed under the Apache License 2.0 (the "License"). You may not use
|
2016-05-18 02:24:46 +08:00
|
|
|
* this file except in compliance with the License. You can obtain a copy
|
|
|
|
* in the file LICENSE in the source distribution or at
|
|
|
|
* https://www.openssl.org/source/license.html
|
1998-12-21 18:52:47 +08:00
|
|
|
*/
|
|
|
|
|
|
|
|
#include <stdio.h>
|
|
|
|
#include <errno.h>
|
1999-04-24 06:13:45 +08:00
|
|
|
#include <openssl/buffer.h>
|
|
|
|
#include <openssl/evp.h>
|
2016-03-22 17:21:29 +08:00
|
|
|
#include "internal/bio.h"
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2015-01-22 11:40:55 +08:00
|
|
|
/*
|
|
|
|
* BIO_put and BIO_get both add to the digest, BIO_gets returns the digest
|
|
|
|
*/
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2000-05-16 06:54:43 +08:00
|
|
|
static int md_write(BIO *h, char const *buf, int num);
|
|
|
|
static int md_read(BIO *h, char *buf, int size);
|
|
|
|
static int md_gets(BIO *h, char *str, int size);
|
|
|
|
static long md_ctrl(BIO *h, int cmd, long arg1, void *arg2);
|
1998-12-21 18:52:47 +08:00
|
|
|
static int md_new(BIO *h);
|
|
|
|
static int md_free(BIO *data);
|
2017-12-16 02:33:48 +08:00
|
|
|
static long md_callback_ctrl(BIO *h, int cmd, BIO_info_cb *fp);
|
2000-02-21 07:43:02 +08:00
|
|
|
|
2016-03-20 00:32:14 +08:00
|
|
|
static const BIO_METHOD methods_md = {
|
2017-12-08 15:20:10 +08:00
|
|
|
BIO_TYPE_MD,
|
|
|
|
"message digest",
|
2016-10-20 22:18:39 +08:00
|
|
|
bwrite_conv,
|
2015-01-22 11:40:55 +08:00
|
|
|
md_write,
|
2016-09-06 00:26:58 +08:00
|
|
|
bread_conv,
|
2015-01-22 11:40:55 +08:00
|
|
|
md_read,
|
|
|
|
NULL, /* md_puts, */
|
|
|
|
md_gets,
|
|
|
|
md_ctrl,
|
|
|
|
md_new,
|
|
|
|
md_free,
|
|
|
|
md_callback_ctrl,
|
|
|
|
};
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2016-03-20 00:32:14 +08:00
|
|
|
const BIO_METHOD *BIO_f_md(void)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
2017-10-17 22:04:09 +08:00
|
|
|
return &methods_md;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
1998-12-21 18:52:47 +08:00
|
|
|
|
1999-04-20 05:31:43 +08:00
|
|
|
static int md_new(BIO *bi)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
|
|
|
EVP_MD_CTX *ctx;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2015-12-02 07:49:35 +08:00
|
|
|
ctx = EVP_MD_CTX_new();
|
2015-01-22 11:40:55 +08:00
|
|
|
if (ctx == NULL)
|
2017-10-17 22:04:09 +08:00
|
|
|
return 0;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO_set_init(bi, 1);
|
|
|
|
BIO_set_data(bi, ctx);
|
|
|
|
|
|
|
|
return 1;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
1998-12-21 18:52:47 +08:00
|
|
|
|
1999-04-20 05:31:43 +08:00
|
|
|
static int md_free(BIO *a)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
|
|
|
if (a == NULL)
|
2017-10-17 22:04:09 +08:00
|
|
|
return 0;
|
2016-03-22 17:21:29 +08:00
|
|
|
EVP_MD_CTX_free(BIO_get_data(a));
|
|
|
|
BIO_set_data(a, NULL);
|
|
|
|
BIO_set_init(a, 0);
|
|
|
|
|
|
|
|
return 1;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
|
|
|
|
1999-04-20 05:31:43 +08:00
|
|
|
static int md_read(BIO *b, char *out, int outl)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
|
|
|
int ret = 0;
|
|
|
|
EVP_MD_CTX *ctx;
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO *next;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2015-01-22 11:40:55 +08:00
|
|
|
if (out == NULL)
|
2017-10-17 22:04:09 +08:00
|
|
|
return 0;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2016-03-22 17:21:29 +08:00
|
|
|
ctx = BIO_get_data(b);
|
|
|
|
next = BIO_next(b);
|
|
|
|
|
|
|
|
if ((ctx == NULL) || (next == NULL))
|
2017-10-17 22:04:09 +08:00
|
|
|
return 0;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2016-03-22 17:21:29 +08:00
|
|
|
ret = BIO_read(next, out, outl);
|
|
|
|
if (BIO_get_init(b)) {
|
2015-01-22 11:40:55 +08:00
|
|
|
if (ret > 0) {
|
|
|
|
if (EVP_DigestUpdate(ctx, (unsigned char *)out,
|
|
|
|
(unsigned int)ret) <= 0)
|
2017-10-17 22:04:09 +08:00
|
|
|
return -1;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
|
|
|
}
|
|
|
|
BIO_clear_retry_flags(b);
|
|
|
|
BIO_copy_next_retry(b);
|
2017-10-17 22:04:09 +08:00
|
|
|
return ret;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2000-05-16 06:54:43 +08:00
|
|
|
static int md_write(BIO *b, const char *in, int inl)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
|
|
|
int ret = 0;
|
|
|
|
EVP_MD_CTX *ctx;
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO *next;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2015-01-22 11:40:55 +08:00
|
|
|
if ((in == NULL) || (inl <= 0))
|
2016-03-22 17:21:29 +08:00
|
|
|
return 0;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2016-03-22 17:21:29 +08:00
|
|
|
ctx = BIO_get_data(b);
|
|
|
|
next = BIO_next(b);
|
|
|
|
if ((ctx != NULL) && (next != NULL))
|
|
|
|
ret = BIO_write(next, in, inl);
|
|
|
|
|
|
|
|
if (BIO_get_init(b)) {
|
2015-01-22 11:40:55 +08:00
|
|
|
if (ret > 0) {
|
|
|
|
if (!EVP_DigestUpdate(ctx, (const unsigned char *)in,
|
|
|
|
(unsigned int)ret)) {
|
|
|
|
BIO_clear_retry_flags(b);
|
|
|
|
return 0;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
2016-03-22 17:21:29 +08:00
|
|
|
if (next != NULL) {
|
2015-01-22 11:40:55 +08:00
|
|
|
BIO_clear_retry_flags(b);
|
|
|
|
BIO_copy_next_retry(b);
|
|
|
|
}
|
2016-03-22 17:21:29 +08:00
|
|
|
return ret;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2000-05-16 06:54:43 +08:00
|
|
|
static long md_ctrl(BIO *b, int cmd, long num, void *ptr)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
|
|
|
EVP_MD_CTX *ctx, *dctx, **pctx;
|
|
|
|
const EVP_MD **ppmd;
|
|
|
|
EVP_MD *md;
|
|
|
|
long ret = 1;
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO *dbio, *next;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2016-03-22 17:21:29 +08:00
|
|
|
|
|
|
|
ctx = BIO_get_data(b);
|
|
|
|
next = BIO_next(b);
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2015-01-22 11:40:55 +08:00
|
|
|
switch (cmd) {
|
|
|
|
case BIO_CTRL_RESET:
|
2016-03-22 17:21:29 +08:00
|
|
|
if (BIO_get_init(b))
|
Add "origin" field to EVP_CIPHER, EVP_MD
Add a "where did this EVP_{CIPHER,MD} come from" flag: global, via fetch,
or via EVP_{CIPHER,MD}_meth_new. Update EVP_{CIPHER,MD}_free to handle all
three origins. The flag is deliberately right before some function pointers,
so that compile-time failures (int/pointer) will occur, as opposed to
taking a bit in the existing "flags" field. The "global variable" flag
is non-zero, so the default case of using OPENSSL_zalloc (for provider
ciphers), will do the right thing. Ref-counting is a no-op for
Make up_ref no-op for global MD and CIPHER objects
Deprecate EVP_MD_CTX_md(). Added EVP_MD_CTX_get0_md() (same semantics as
the deprecated function) and EVP_MD_CTX_get1_md(). Likewise, deprecate
EVP_CIPHER_CTX_cipher() in favor of EVP_CIPHER_CTX_get0_cipher(), and add
EVP_CIPHER_CTX_get1_CIPHER().
Refactor EVP_MD_free() and EVP_MD_meth_free() to call new common
evp_md_free_int() function.
Refactor EVP_CIPHER_free() and EVP_CIPHER_meth_free() to call new common
evp_cipher_free_int() function.
Also change some flags tests to explicit test == or != zero. E.g.,
if (flags & x) --> if ((flags & x) != 0)
if (!(flags & x)) --> if ((flags & x) == 0)
Only done for those lines where "get0_cipher" calls were made.
Reviewed-by: Matt Caswell <matt@openssl.org>
Reviewed-by: Richard Levitte <levitte@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/14193)
2021-02-17 06:51:56 +08:00
|
|
|
ret = EVP_DigestInit_ex(ctx, EVP_MD_CTX_get0_md(ctx), NULL);
|
2015-01-22 11:40:55 +08:00
|
|
|
else
|
|
|
|
ret = 0;
|
|
|
|
if (ret > 0)
|
2016-03-22 17:21:29 +08:00
|
|
|
ret = BIO_ctrl(next, cmd, num, ptr);
|
2015-01-22 11:40:55 +08:00
|
|
|
break;
|
|
|
|
case BIO_C_GET_MD:
|
2016-03-22 17:21:29 +08:00
|
|
|
if (BIO_get_init(b)) {
|
2015-01-22 11:40:55 +08:00
|
|
|
ppmd = ptr;
|
Add "origin" field to EVP_CIPHER, EVP_MD
Add a "where did this EVP_{CIPHER,MD} come from" flag: global, via fetch,
or via EVP_{CIPHER,MD}_meth_new. Update EVP_{CIPHER,MD}_free to handle all
three origins. The flag is deliberately right before some function pointers,
so that compile-time failures (int/pointer) will occur, as opposed to
taking a bit in the existing "flags" field. The "global variable" flag
is non-zero, so the default case of using OPENSSL_zalloc (for provider
ciphers), will do the right thing. Ref-counting is a no-op for
Make up_ref no-op for global MD and CIPHER objects
Deprecate EVP_MD_CTX_md(). Added EVP_MD_CTX_get0_md() (same semantics as
the deprecated function) and EVP_MD_CTX_get1_md(). Likewise, deprecate
EVP_CIPHER_CTX_cipher() in favor of EVP_CIPHER_CTX_get0_cipher(), and add
EVP_CIPHER_CTX_get1_CIPHER().
Refactor EVP_MD_free() and EVP_MD_meth_free() to call new common
evp_md_free_int() function.
Refactor EVP_CIPHER_free() and EVP_CIPHER_meth_free() to call new common
evp_cipher_free_int() function.
Also change some flags tests to explicit test == or != zero. E.g.,
if (flags & x) --> if ((flags & x) != 0)
if (!(flags & x)) --> if ((flags & x) == 0)
Only done for those lines where "get0_cipher" calls were made.
Reviewed-by: Matt Caswell <matt@openssl.org>
Reviewed-by: Richard Levitte <levitte@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/14193)
2021-02-17 06:51:56 +08:00
|
|
|
*ppmd = EVP_MD_CTX_get0_md(ctx);
|
2015-01-22 11:40:55 +08:00
|
|
|
} else
|
|
|
|
ret = 0;
|
|
|
|
break;
|
|
|
|
case BIO_C_GET_MD_CTX:
|
|
|
|
pctx = ptr;
|
|
|
|
*pctx = ctx;
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO_set_init(b, 1);
|
2015-01-22 11:40:55 +08:00
|
|
|
break;
|
|
|
|
case BIO_C_SET_MD_CTX:
|
2016-03-22 17:21:29 +08:00
|
|
|
if (BIO_get_init(b))
|
|
|
|
BIO_set_data(b, ptr);
|
2015-01-22 11:40:55 +08:00
|
|
|
else
|
|
|
|
ret = 0;
|
|
|
|
break;
|
|
|
|
case BIO_C_DO_STATE_MACHINE:
|
|
|
|
BIO_clear_retry_flags(b);
|
2016-03-22 17:21:29 +08:00
|
|
|
ret = BIO_ctrl(next, cmd, num, ptr);
|
2015-01-22 11:40:55 +08:00
|
|
|
BIO_copy_next_retry(b);
|
|
|
|
break;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2015-01-22 11:40:55 +08:00
|
|
|
case BIO_C_SET_MD:
|
|
|
|
md = ptr;
|
|
|
|
ret = EVP_DigestInit_ex(ctx, md, NULL);
|
|
|
|
if (ret > 0)
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO_set_init(b, 1);
|
2015-01-22 11:40:55 +08:00
|
|
|
break;
|
|
|
|
case BIO_CTRL_DUP:
|
|
|
|
dbio = ptr;
|
2016-03-22 17:21:29 +08:00
|
|
|
dctx = BIO_get_data(dbio);
|
2015-01-22 11:40:55 +08:00
|
|
|
if (!EVP_MD_CTX_copy_ex(dctx, ctx))
|
|
|
|
return 0;
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO_set_init(b, 1);
|
2015-01-22 11:40:55 +08:00
|
|
|
break;
|
|
|
|
default:
|
2016-03-22 17:21:29 +08:00
|
|
|
ret = BIO_ctrl(next, cmd, num, ptr);
|
2015-01-22 11:40:55 +08:00
|
|
|
break;
|
|
|
|
}
|
2017-10-17 22:04:09 +08:00
|
|
|
return ret;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2017-12-16 02:33:48 +08:00
|
|
|
static long md_callback_ctrl(BIO *b, int cmd, BIO_info_cb *fp)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
2016-03-22 17:21:29 +08:00
|
|
|
BIO *next;
|
|
|
|
|
|
|
|
next = BIO_next(b);
|
|
|
|
|
|
|
|
if (next == NULL)
|
|
|
|
return 0;
|
2000-02-21 07:43:02 +08:00
|
|
|
|
2020-02-19 10:38:12 +08:00
|
|
|
return BIO_callback_ctrl(next, cmd, fp);
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|
2000-02-21 07:43:02 +08:00
|
|
|
|
1999-04-20 05:31:43 +08:00
|
|
|
static int md_gets(BIO *bp, char *buf, int size)
|
2015-01-22 11:40:55 +08:00
|
|
|
{
|
|
|
|
EVP_MD_CTX *ctx;
|
|
|
|
unsigned int ret;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2016-03-22 17:21:29 +08:00
|
|
|
ctx = BIO_get_data(bp);
|
|
|
|
|
Rename all getters to use get/get0 in name
For functions that exist in 1.1.1 provide a simple aliases via #define.
Fixes #15236
Functions with OSSL_DECODER_, OSSL_ENCODER_, OSSL_STORE_LOADER_,
EVP_KEYEXCH_, EVP_KEM_, EVP_ASYM_CIPHER_, EVP_SIGNATURE_,
EVP_KEYMGMT_, EVP_RAND_, EVP_MAC_, EVP_KDF_, EVP_PKEY_,
EVP_MD_, and EVP_CIPHER_ prefixes are renamed.
Reviewed-by: Paul Dale <pauli@openssl.org>
(Merged from https://github.com/openssl/openssl/pull/15405)
2021-05-21 22:58:08 +08:00
|
|
|
if (size < EVP_MD_CTX_get_size(ctx))
|
2016-03-22 17:21:29 +08:00
|
|
|
return 0;
|
|
|
|
|
2015-01-22 11:40:55 +08:00
|
|
|
if (EVP_DigestFinal_ex(ctx, (unsigned char *)buf, &ret) <= 0)
|
|
|
|
return -1;
|
1998-12-21 18:52:47 +08:00
|
|
|
|
2017-10-17 22:04:09 +08:00
|
|
|
return (int)ret;
|
2015-01-22 11:40:55 +08:00
|
|
|
}
|