Skip to content

Commit fa1fc16

Browse files
davidbenevanlucas
authored andcommitted
crypto: make SignBase compatible with OpenSSL 1.1.0
1.1.0 requires EVP_MD_CTX be heap-allocated. In doing so, move the Init and Update hooks to shared code because they are the same between Verify and Sign. PR-URL: #16130 Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl> Reviewed-By: Rod Vagg <rod@vagg.org>
1 parent abe3dc4 commit fa1fc16

File tree

2 files changed

+51
-76
lines changed

2 files changed

+51
-76
lines changed

src/node_crypto.cc

+45-64
Original file line numberDiff line numberDiff line change
@@ -4052,6 +4052,38 @@ void Hash::HashDigest(const FunctionCallbackInfo<Value>& args) {
40524052
}
40534053

40544054

4055+
SignBase::~SignBase() {
4056+
EVP_MD_CTX_free(mdctx_);
4057+
}
4058+
4059+
4060+
SignBase::Error SignBase::Init(const char* sign_type) {
4061+
CHECK_EQ(mdctx_, nullptr);
4062+
const EVP_MD* md = EVP_get_digestbyname(sign_type);
4063+
if (md == nullptr)
4064+
return kSignUnknownDigest;
4065+
4066+
mdctx_ = EVP_MD_CTX_new();
4067+
if (mdctx_ == nullptr ||
4068+
!EVP_DigestInit_ex(mdctx_, md, nullptr)) {
4069+
EVP_MD_CTX_free(mdctx_);
4070+
mdctx_ = nullptr;
4071+
return kSignInit;
4072+
}
4073+
4074+
return kSignOk;
4075+
}
4076+
4077+
4078+
SignBase::Error SignBase::Update(const char* data, int len) {
4079+
if (mdctx_ == nullptr)
4080+
return kSignNotInitialised;
4081+
if (!EVP_DigestUpdate(mdctx_, data, len))
4082+
return kSignUpdate;
4083+
return kSignOk;
4084+
}
4085+
4086+
40554087
void SignBase::CheckThrow(SignBase::Error error) {
40564088
HandleScope scope(env()->isolate());
40574089

@@ -4125,36 +4157,12 @@ void Sign::New(const FunctionCallbackInfo<Value>& args) {
41254157
}
41264158

41274159

4128-
SignBase::Error Sign::SignInit(const char* sign_type) {
4129-
CHECK_EQ(initialised_, false);
4130-
const EVP_MD* md = EVP_get_digestbyname(sign_type);
4131-
if (md == nullptr)
4132-
return kSignUnknownDigest;
4133-
4134-
EVP_MD_CTX_init(&mdctx_);
4135-
if (!EVP_DigestInit_ex(&mdctx_, md, nullptr))
4136-
return kSignInit;
4137-
initialised_ = true;
4138-
4139-
return kSignOk;
4140-
}
4141-
4142-
41434160
void Sign::SignInit(const FunctionCallbackInfo<Value>& args) {
41444161
Sign* sign;
41454162
ASSIGN_OR_RETURN_UNWRAP(&sign, args.Holder());
41464163

41474164
const node::Utf8Value sign_type(args.GetIsolate(), args[0]);
4148-
sign->CheckThrow(sign->SignInit(*sign_type));
4149-
}
4150-
4151-
4152-
SignBase::Error Sign::SignUpdate(const char* data, int len) {
4153-
if (!initialised_)
4154-
return kSignNotInitialised;
4155-
if (!EVP_DigestUpdate(&mdctx_, data, len))
4156-
return kSignUpdate;
4157-
return kSignOk;
4165+
sign->CheckThrow(sign->Init(*sign_type));
41584166
}
41594167

41604168

@@ -4165,7 +4173,7 @@ void Sign::SignUpdate(const FunctionCallbackInfo<Value>& args) {
41654173
Error err;
41664174
char* buf = Buffer::Data(args[0]);
41674175
size_t buflen = Buffer::Length(args[0]);
4168-
err = sign->SignUpdate(buf, buflen);
4176+
err = sign->Update(buf, buflen);
41694177

41704178
sign->CheckThrow(err);
41714179
}
@@ -4208,7 +4216,7 @@ SignBase::Error Sign::SignFinal(const char* key_pem,
42084216
unsigned int* sig_len,
42094217
int padding,
42104218
int salt_len) {
4211-
if (!initialised_)
4219+
if (!mdctx_)
42124220
return kSignNotInitialised;
42134221

42144222
BIO* bp = nullptr;
@@ -4253,18 +4261,17 @@ SignBase::Error Sign::SignFinal(const char* key_pem,
42534261
}
42544262
#endif // NODE_FIPS_MODE
42554263

4256-
if (Node_SignFinal(&mdctx_, sig, sig_len, pkey, padding, salt_len))
4264+
if (Node_SignFinal(mdctx_, sig, sig_len, pkey, padding, salt_len))
42574265
fatal = false;
42584266

4259-
initialised_ = false;
4260-
42614267
exit:
42624268
if (pkey != nullptr)
42634269
EVP_PKEY_free(pkey);
42644270
if (bp != nullptr)
42654271
BIO_free_all(bp);
42664272

4267-
EVP_MD_CTX_cleanup(&mdctx_);
4273+
EVP_MD_CTX_free(mdctx_);
4274+
mdctx_ = nullptr;
42684275

42694276
if (fatal)
42704277
return kSignPrivateKey;
@@ -4338,38 +4345,12 @@ void Verify::New(const FunctionCallbackInfo<Value>& args) {
43384345
}
43394346

43404347

4341-
SignBase::Error Verify::VerifyInit(const char* verify_type) {
4342-
CHECK_EQ(initialised_, false);
4343-
const EVP_MD* md = EVP_get_digestbyname(verify_type);
4344-
if (md == nullptr)
4345-
return kSignUnknownDigest;
4346-
4347-
EVP_MD_CTX_init(&mdctx_);
4348-
if (!EVP_DigestInit_ex(&mdctx_, md, nullptr))
4349-
return kSignInit;
4350-
initialised_ = true;
4351-
4352-
return kSignOk;
4353-
}
4354-
4355-
43564348
void Verify::VerifyInit(const FunctionCallbackInfo<Value>& args) {
43574349
Verify* verify;
43584350
ASSIGN_OR_RETURN_UNWRAP(&verify, args.Holder());
43594351

43604352
const node::Utf8Value verify_type(args.GetIsolate(), args[0]);
4361-
verify->CheckThrow(verify->VerifyInit(*verify_type));
4362-
}
4363-
4364-
4365-
SignBase::Error Verify::VerifyUpdate(const char* data, int len) {
4366-
if (!initialised_)
4367-
return kSignNotInitialised;
4368-
4369-
if (!EVP_DigestUpdate(&mdctx_, data, len))
4370-
return kSignUpdate;
4371-
4372-
return kSignOk;
4353+
verify->CheckThrow(verify->Init(*verify_type));
43734354
}
43744355

43754356

@@ -4380,7 +4361,7 @@ void Verify::VerifyUpdate(const FunctionCallbackInfo<Value>& args) {
43804361
Error err;
43814362
char* buf = Buffer::Data(args[0]);
43824363
size_t buflen = Buffer::Length(args[0]);
4383-
err = verify->VerifyUpdate(buf, buflen);
4364+
err = verify->Update(buf, buflen);
43844365

43854366
verify->CheckThrow(err);
43864367
}
@@ -4393,7 +4374,7 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
43934374
int padding,
43944375
int saltlen,
43954376
bool* verify_result) {
4396-
if (!initialised_)
4377+
if (!mdctx_)
43974378
return kSignNotInitialised;
43984379

43994380
EVP_PKEY* pkey = nullptr;
@@ -4438,7 +4419,7 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
44384419
goto exit;
44394420
}
44404421

4441-
if (!EVP_DigestFinal_ex(&mdctx_, m, &m_len)) {
4422+
if (!EVP_DigestFinal_ex(mdctx_, m, &m_len)) {
44424423
goto exit;
44434424
}
44444425

@@ -4451,7 +4432,7 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
44514432
goto err;
44524433
if (!ApplyRSAOptions(pkey, pkctx, padding, saltlen))
44534434
goto err;
4454-
if (EVP_PKEY_CTX_set_signature_md(pkctx, mdctx_.digest) <= 0)
4435+
if (EVP_PKEY_CTX_set_signature_md(pkctx, EVP_MD_CTX_md(mdctx_)) <= 0)
44554436
goto err;
44564437
r = EVP_PKEY_verify(pkctx,
44574438
reinterpret_cast<const unsigned char*>(sig),
@@ -4470,8 +4451,8 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
44704451
if (x509 != nullptr)
44714452
X509_free(x509);
44724453

4473-
EVP_MD_CTX_cleanup(&mdctx_);
4474-
initialised_ = false;
4454+
EVP_MD_CTX_free(mdctx_);
4455+
mdctx_ = nullptr;
44754456

44764457
if (fatal)
44774458
return kSignPublicKey;

src/node_crypto.h

+6-12
Original file line numberDiff line numberDiff line change
@@ -562,28 +562,24 @@ class SignBase : public BaseObject {
562562

563563
SignBase(Environment* env, v8::Local<v8::Object> wrap)
564564
: BaseObject(env, wrap),
565-
initialised_(false) {
565+
mdctx_(nullptr) {
566566
}
567567

568-
~SignBase() override {
569-
if (!initialised_)
570-
return;
571-
EVP_MD_CTX_cleanup(&mdctx_);
572-
}
568+
~SignBase() override;
569+
570+
Error Init(const char* sign_type);
571+
Error Update(const char* data, int len);
573572

574573
protected:
575574
void CheckThrow(Error error);
576575

577-
EVP_MD_CTX mdctx_; /* coverity[member_decl] */
578-
bool initialised_;
576+
EVP_MD_CTX* mdctx_;
579577
};
580578

581579
class Sign : public SignBase {
582580
public:
583581
static void Initialize(Environment* env, v8::Local<v8::Object> target);
584582

585-
Error SignInit(const char* sign_type);
586-
Error SignUpdate(const char* data, int len);
587583
Error SignFinal(const char* key_pem,
588584
int key_pem_len,
589585
const char* passphrase,
@@ -607,8 +603,6 @@ class Verify : public SignBase {
607603
public:
608604
static void Initialize(Environment* env, v8::Local<v8::Object> target);
609605

610-
Error VerifyInit(const char* verify_type);
611-
Error VerifyUpdate(const char* data, int len);
612606
Error VerifyFinal(const char* key_pem,
613607
int key_pem_len,
614608
const char* sig,

0 commit comments

Comments
 (0)