Skip to content

Commit 6bc7480

Browse files
davidbenrvagg
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: nodejs#16130 Reviewed-By: Ben Noordhuis <info@bnoordhuis.nl> Reviewed-By: Rod Vagg <rod@vagg.org>
1 parent 2b28d6c commit 6bc7480

2 files changed

Lines changed: 51 additions & 76 deletions

File tree

src/node_crypto.cc

Lines changed: 45 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -4021,6 +4021,38 @@ void Hash::HashDigest(const FunctionCallbackInfo<Value>& args) {
40214021
}
40224022

40234023

4024+
SignBase::~SignBase() {
4025+
EVP_MD_CTX_free(mdctx_);
4026+
}
4027+
4028+
4029+
SignBase::Error SignBase::Init(const char* sign_type) {
4030+
CHECK_EQ(mdctx_, nullptr);
4031+
const EVP_MD* md = EVP_get_digestbyname(sign_type);
4032+
if (md == nullptr)
4033+
return kSignUnknownDigest;
4034+
4035+
mdctx_ = EVP_MD_CTX_new();
4036+
if (mdctx_ == nullptr ||
4037+
!EVP_DigestInit_ex(mdctx_, md, nullptr)) {
4038+
EVP_MD_CTX_free(mdctx_);
4039+
mdctx_ = nullptr;
4040+
return kSignInit;
4041+
}
4042+
4043+
return kSignOk;
4044+
}
4045+
4046+
4047+
SignBase::Error SignBase::Update(const char* data, int len) {
4048+
if (mdctx_ == nullptr)
4049+
return kSignNotInitialised;
4050+
if (!EVP_DigestUpdate(mdctx_, data, len))
4051+
return kSignUpdate;
4052+
return kSignOk;
4053+
}
4054+
4055+
40244056
void SignBase::CheckThrow(SignBase::Error error) {
40254057
HandleScope scope(env()->isolate());
40264058

@@ -4094,36 +4126,12 @@ void Sign::New(const FunctionCallbackInfo<Value>& args) {
40944126
}
40954127

40964128

4097-
SignBase::Error Sign::SignInit(const char* sign_type) {
4098-
CHECK_EQ(initialised_, false);
4099-
const EVP_MD* md = EVP_get_digestbyname(sign_type);
4100-
if (md == nullptr)
4101-
return kSignUnknownDigest;
4102-
4103-
EVP_MD_CTX_init(&mdctx_);
4104-
if (!EVP_DigestInit_ex(&mdctx_, md, nullptr))
4105-
return kSignInit;
4106-
initialised_ = true;
4107-
4108-
return kSignOk;
4109-
}
4110-
4111-
41124129
void Sign::SignInit(const FunctionCallbackInfo<Value>& args) {
41134130
Sign* sign;
41144131
ASSIGN_OR_RETURN_UNWRAP(&sign, args.Holder());
41154132

41164133
const node::Utf8Value sign_type(args.GetIsolate(), args[0]);
4117-
sign->CheckThrow(sign->SignInit(*sign_type));
4118-
}
4119-
4120-
4121-
SignBase::Error Sign::SignUpdate(const char* data, int len) {
4122-
if (!initialised_)
4123-
return kSignNotInitialised;
4124-
if (!EVP_DigestUpdate(&mdctx_, data, len))
4125-
return kSignUpdate;
4126-
return kSignOk;
4134+
sign->CheckThrow(sign->Init(*sign_type));
41274135
}
41284136

41294137

@@ -4134,7 +4142,7 @@ void Sign::SignUpdate(const FunctionCallbackInfo<Value>& args) {
41344142
Error err;
41354143
char* buf = Buffer::Data(args[0]);
41364144
size_t buflen = Buffer::Length(args[0]);
4137-
err = sign->SignUpdate(buf, buflen);
4145+
err = sign->Update(buf, buflen);
41384146

41394147
sign->CheckThrow(err);
41404148
}
@@ -4177,7 +4185,7 @@ SignBase::Error Sign::SignFinal(const char* key_pem,
41774185
unsigned int* sig_len,
41784186
int padding,
41794187
int salt_len) {
4180-
if (!initialised_)
4188+
if (!mdctx_)
41814189
return kSignNotInitialised;
41824190

41834191
BIO* bp = nullptr;
@@ -4222,18 +4230,17 @@ SignBase::Error Sign::SignFinal(const char* key_pem,
42224230
}
42234231
#endif // NODE_FIPS_MODE
42244232

4225-
if (Node_SignFinal(&mdctx_, sig, sig_len, pkey, padding, salt_len))
4233+
if (Node_SignFinal(mdctx_, sig, sig_len, pkey, padding, salt_len))
42264234
fatal = false;
42274235

4228-
initialised_ = false;
4229-
42304236
exit:
42314237
if (pkey != nullptr)
42324238
EVP_PKEY_free(pkey);
42334239
if (bp != nullptr)
42344240
BIO_free_all(bp);
42354241

4236-
EVP_MD_CTX_cleanup(&mdctx_);
4242+
EVP_MD_CTX_free(mdctx_);
4243+
mdctx_ = nullptr;
42374244

42384245
if (fatal)
42394246
return kSignPrivateKey;
@@ -4307,38 +4314,12 @@ void Verify::New(const FunctionCallbackInfo<Value>& args) {
43074314
}
43084315

43094316

4310-
SignBase::Error Verify::VerifyInit(const char* verify_type) {
4311-
CHECK_EQ(initialised_, false);
4312-
const EVP_MD* md = EVP_get_digestbyname(verify_type);
4313-
if (md == nullptr)
4314-
return kSignUnknownDigest;
4315-
4316-
EVP_MD_CTX_init(&mdctx_);
4317-
if (!EVP_DigestInit_ex(&mdctx_, md, nullptr))
4318-
return kSignInit;
4319-
initialised_ = true;
4320-
4321-
return kSignOk;
4322-
}
4323-
4324-
43254317
void Verify::VerifyInit(const FunctionCallbackInfo<Value>& args) {
43264318
Verify* verify;
43274319
ASSIGN_OR_RETURN_UNWRAP(&verify, args.Holder());
43284320

43294321
const node::Utf8Value verify_type(args.GetIsolate(), args[0]);
4330-
verify->CheckThrow(verify->VerifyInit(*verify_type));
4331-
}
4332-
4333-
4334-
SignBase::Error Verify::VerifyUpdate(const char* data, int len) {
4335-
if (!initialised_)
4336-
return kSignNotInitialised;
4337-
4338-
if (!EVP_DigestUpdate(&mdctx_, data, len))
4339-
return kSignUpdate;
4340-
4341-
return kSignOk;
4322+
verify->CheckThrow(verify->Init(*verify_type));
43424323
}
43434324

43444325

@@ -4349,7 +4330,7 @@ void Verify::VerifyUpdate(const FunctionCallbackInfo<Value>& args) {
43494330
Error err;
43504331
char* buf = Buffer::Data(args[0]);
43514332
size_t buflen = Buffer::Length(args[0]);
4352-
err = verify->VerifyUpdate(buf, buflen);
4333+
err = verify->Update(buf, buflen);
43534334

43544335
verify->CheckThrow(err);
43554336
}
@@ -4362,7 +4343,7 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
43624343
int padding,
43634344
int saltlen,
43644345
bool* verify_result) {
4365-
if (!initialised_)
4346+
if (!mdctx_)
43664347
return kSignNotInitialised;
43674348

43684349
EVP_PKEY* pkey = nullptr;
@@ -4407,7 +4388,7 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
44074388
goto exit;
44084389
}
44094390

4410-
if (!EVP_DigestFinal_ex(&mdctx_, m, &m_len)) {
4391+
if (!EVP_DigestFinal_ex(mdctx_, m, &m_len)) {
44114392
goto exit;
44124393
}
44134394

@@ -4420,7 +4401,7 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
44204401
goto err;
44214402
if (!ApplyRSAOptions(pkey, pkctx, padding, saltlen))
44224403
goto err;
4423-
if (EVP_PKEY_CTX_set_signature_md(pkctx, mdctx_.digest) <= 0)
4404+
if (EVP_PKEY_CTX_set_signature_md(pkctx, EVP_MD_CTX_md(mdctx_)) <= 0)
44244405
goto err;
44254406
r = EVP_PKEY_verify(pkctx,
44264407
reinterpret_cast<const unsigned char*>(sig),
@@ -4439,8 +4420,8 @@ SignBase::Error Verify::VerifyFinal(const char* key_pem,
44394420
if (x509 != nullptr)
44404421
X509_free(x509);
44414422

4442-
EVP_MD_CTX_cleanup(&mdctx_);
4443-
initialised_ = false;
4423+
EVP_MD_CTX_free(mdctx_);
4424+
mdctx_ = nullptr;
44444425

44454426
if (fatal)
44464427
return kSignPublicKey;

src/node_crypto.h

Lines changed: 6 additions & 12 deletions
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)