Skip to content

Commit 4433852

Browse files
RaisinTentargos
authored andcommitted
src,crypto: remove AllocatedBuffer from crypto_cipher.cc
Signed-off-by: Darshan Sen <[email protected]> PR-URL: #40400 Reviewed-By: Anna Henningsen <[email protected]>
1 parent 814126c commit 4433852

File tree

2 files changed

+59
-35
lines changed

2 files changed

+59
-35
lines changed

src/crypto/crypto_cipher.cc

+55-31
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@
1212
namespace node {
1313

1414
using v8::Array;
15+
using v8::ArrayBuffer;
16+
using v8::BackingStore;
1517
using v8::FunctionCallbackInfo;
1618
using v8::FunctionTemplate;
1719
using v8::HandleScope;
@@ -752,7 +754,7 @@ void CipherBase::SetAAD(const FunctionCallbackInfo<Value>& args) {
752754
CipherBase::UpdateResult CipherBase::Update(
753755
const char* data,
754756
size_t len,
755-
AllocatedBuffer* out) {
757+
std::unique_ptr<BackingStore>* out) {
756758
if (!ctx_ || len > INT_MAX)
757759
return kErrorState;
758760
MarkPopErrorOnReturn mark_pop_error_on_return;
@@ -779,15 +781,22 @@ CipherBase::UpdateResult CipherBase::Update(
779781
return kErrorState;
780782
}
781783

782-
*out = AllocatedBuffer::AllocateManaged(env(), buf_len);
784+
{
785+
NoArrayBufferZeroFillScope no_zero_fill_scope(env()->isolate_data());
786+
*out = ArrayBuffer::NewBackingStore(env()->isolate(), buf_len);
787+
}
788+
783789
int r = EVP_CipherUpdate(ctx_.get(),
784-
reinterpret_cast<unsigned char*>(out->data()),
790+
static_cast<unsigned char*>((*out)->Data()),
785791
&buf_len,
786792
reinterpret_cast<const unsigned char*>(data),
787793
len);
788794

789-
CHECK_LE(static_cast<size_t>(buf_len), out->size());
790-
out->Resize(buf_len);
795+
CHECK_LE(static_cast<size_t>(buf_len), (*out)->ByteLength());
796+
if (buf_len == 0)
797+
*out = ArrayBuffer::NewBackingStore(env()->isolate(), 0);
798+
else
799+
*out = BackingStore::Reallocate(env()->isolate(), std::move(*out), buf_len);
791800

792801
// When in CCM mode, EVP_CipherUpdate will fail if the authentication tag is
793802
// invalid. In that case, remember the error and throw in final().
@@ -802,7 +811,7 @@ void CipherBase::Update(const FunctionCallbackInfo<Value>& args) {
802811
Decode<CipherBase>(args, [](CipherBase* cipher,
803812
const FunctionCallbackInfo<Value>& args,
804813
const char* data, size_t size) {
805-
AllocatedBuffer out;
814+
std::unique_ptr<BackingStore> out;
806815
Environment* env = Environment::GetCurrent(args);
807816

808817
if (UNLIKELY(size > INT_MAX))
@@ -818,8 +827,9 @@ void CipherBase::Update(const FunctionCallbackInfo<Value>& args) {
818827
return;
819828
}
820829

821-
CHECK(out.data() != nullptr || out.size() == 0);
822-
args.GetReturnValue().Set(out.ToBuffer().FromMaybe(Local<Value>()));
830+
Local<ArrayBuffer> ab = ArrayBuffer::New(env->isolate(), std::move(out));
831+
args.GetReturnValue().Set(
832+
Buffer::New(env, ab, 0, ab->ByteLength()).FromMaybe(Local<Value>()));
823833
});
824834
}
825835

@@ -838,36 +848,40 @@ void CipherBase::SetAutoPadding(const FunctionCallbackInfo<Value>& args) {
838848
args.GetReturnValue().Set(b); // Possibly report invalid state failure
839849
}
840850

841-
bool CipherBase::Final(AllocatedBuffer* out) {
851+
bool CipherBase::Final(std::unique_ptr<BackingStore>* out) {
842852
if (!ctx_)
843853
return false;
844854

845855
const int mode = EVP_CIPHER_CTX_mode(ctx_.get());
846856

847-
*out = AllocatedBuffer::AllocateManaged(
848-
env(),
849-
static_cast<size_t>(EVP_CIPHER_CTX_block_size(ctx_.get())));
857+
{
858+
NoArrayBufferZeroFillScope no_zero_fill_scope(env()->isolate_data());
859+
*out = ArrayBuffer::NewBackingStore(env()->isolate(),
860+
static_cast<size_t>(EVP_CIPHER_CTX_block_size(ctx_.get())));
861+
}
850862

851-
if (kind_ == kDecipher && IsSupportedAuthenticatedMode(ctx_.get())) {
863+
if (kind_ == kDecipher && IsSupportedAuthenticatedMode(ctx_.get()))
852864
MaybePassAuthTagToOpenSSL();
853-
}
854865

855866
// In CCM mode, final() only checks whether authentication failed in update().
856867
// EVP_CipherFinal_ex must not be called and will fail.
857868
bool ok;
858869
if (kind_ == kDecipher && mode == EVP_CIPH_CCM_MODE) {
859870
ok = !pending_auth_failed_;
860-
*out = AllocatedBuffer::AllocateManaged(env(), 0); // Empty buffer.
871+
*out = ArrayBuffer::NewBackingStore(env()->isolate(), 0);
861872
} else {
862-
int out_len = out->size();
873+
int out_len = (*out)->ByteLength();
863874
ok = EVP_CipherFinal_ex(ctx_.get(),
864-
reinterpret_cast<unsigned char*>(out->data()),
875+
static_cast<unsigned char*>((*out)->Data()),
865876
&out_len) == 1;
866877

867-
if (out_len >= 0)
868-
out->Resize(out_len);
869-
else
870-
*out = AllocatedBuffer(); // *out will not be used.
878+
CHECK_LE(static_cast<size_t>(out_len), (*out)->ByteLength());
879+
if (out_len > 0) {
880+
*out =
881+
BackingStore::Reallocate(env()->isolate(), std::move(*out), out_len);
882+
} else {
883+
*out = ArrayBuffer::NewBackingStore(env()->isolate(), 0);
884+
}
871885

872886
if (ok && kind_ == kCipher && IsAuthenticatedMode()) {
873887
// In GCM mode, the authentication tag length can be specified in advance,
@@ -896,7 +910,7 @@ void CipherBase::Final(const FunctionCallbackInfo<Value>& args) {
896910
if (cipher->ctx_ == nullptr)
897911
return THROW_ERR_CRYPTO_INVALID_STATE(env);
898912

899-
AllocatedBuffer out;
913+
std::unique_ptr<BackingStore> out;
900914

901915
// Check IsAuthenticatedMode() first, Final() destroys the EVP_CIPHER_CTX.
902916
const bool is_auth_mode = cipher->IsAuthenticatedMode();
@@ -910,7 +924,9 @@ void CipherBase::Final(const FunctionCallbackInfo<Value>& args) {
910924
return ThrowCryptoError(env, ERR_get_error(), msg);
911925
}
912926

913-
args.GetReturnValue().Set(out.ToBuffer().FromMaybe(Local<Value>()));
927+
Local<ArrayBuffer> ab = ArrayBuffer::New(env->isolate(), std::move(out));
928+
args.GetReturnValue().Set(
929+
Buffer::New(env, ab, 0, ab->ByteLength()).FromMaybe(Local<Value>()));
914930
}
915931

916932
template <PublicKeyCipher::Operation operation,
@@ -923,7 +939,7 @@ bool PublicKeyCipher::Cipher(
923939
const EVP_MD* digest,
924940
const ArrayBufferOrViewContents<unsigned char>& oaep_label,
925941
const ArrayBufferOrViewContents<unsigned char>& data,
926-
AllocatedBuffer* out) {
942+
std::unique_ptr<BackingStore>* out) {
927943
EVPKeyCtxPointer ctx(EVP_PKEY_CTX_new(pkey.get(), nullptr));
928944
if (!ctx)
929945
return false;
@@ -959,18 +975,26 @@ bool PublicKeyCipher::Cipher(
959975
return false;
960976
}
961977

962-
*out = AllocatedBuffer::AllocateManaged(env, out_len);
978+
{
979+
NoArrayBufferZeroFillScope no_zero_fill_scope(env->isolate_data());
980+
*out = ArrayBuffer::NewBackingStore(env->isolate(), out_len);
981+
}
963982

964983
if (EVP_PKEY_cipher(
965984
ctx.get(),
966-
reinterpret_cast<unsigned char*>(out->data()),
985+
static_cast<unsigned char*>((*out)->Data()),
967986
&out_len,
968987
data.data(),
969988
data.size()) <= 0) {
970989
return false;
971990
}
972991

973-
out->Resize(out_len);
992+
CHECK_LE(out_len, (*out)->ByteLength());
993+
if (out_len > 0)
994+
*out = BackingStore::Reallocate(env->isolate(), std::move(*out), out_len);
995+
else
996+
*out = ArrayBuffer::NewBackingStore(env->isolate(), 0);
997+
974998
return true;
975999
}
9761000

@@ -1009,15 +1033,15 @@ void PublicKeyCipher::Cipher(const FunctionCallbackInfo<Value>& args) {
10091033
return THROW_ERR_OUT_OF_RANGE(env, "oaep_label is too big");
10101034
}
10111035

1012-
AllocatedBuffer out;
1036+
std::unique_ptr<BackingStore> out;
10131037
if (!Cipher<operation, EVP_PKEY_cipher_init, EVP_PKEY_cipher>(
10141038
env, pkey, padding, digest, oaep_label, buf, &out)) {
10151039
return ThrowCryptoError(env, ERR_get_error());
10161040
}
10171041

1018-
Local<Value> result;
1019-
if (out.ToBuffer().ToLocal(&result))
1020-
args.GetReturnValue().Set(result);
1042+
Local<ArrayBuffer> ab = ArrayBuffer::New(env->isolate(), std::move(out));
1043+
args.GetReturnValue().Set(
1044+
Buffer::New(env, ab, 0, ab->ByteLength()).FromMaybe(Local<Value>()));
10211045
}
10221046

10231047
} // namespace crypto

src/crypto/crypto_cipher.h

+4-4
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,6 @@
55

66
#include "crypto/crypto_keys.h"
77
#include "crypto/crypto_util.h"
8-
#include "allocated_buffer-inl.h"
98
#include "base_object.h"
109
#include "env.h"
1110
#include "memory_tracker.h"
@@ -61,8 +60,9 @@ class CipherBase : public BaseObject {
6160
bool InitAuthenticated(const char* cipher_type, int iv_len,
6261
unsigned int auth_tag_len);
6362
bool CheckCCMMessageLength(int message_len);
64-
UpdateResult Update(const char* data, size_t len, AllocatedBuffer* out);
65-
bool Final(AllocatedBuffer* out);
63+
UpdateResult Update(const char* data, size_t len,
64+
std::unique_ptr<v8::BackingStore>* out);
65+
bool Final(std::unique_ptr<v8::BackingStore>* out);
6666
bool SetAutoPadding(bool auto_padding);
6767

6868
bool IsAuthenticatedMode() const;
@@ -115,7 +115,7 @@ class PublicKeyCipher {
115115
const EVP_MD* digest,
116116
const ArrayBufferOrViewContents<unsigned char>& oaep_label,
117117
const ArrayBufferOrViewContents<unsigned char>& data,
118-
AllocatedBuffer* out);
118+
std::unique_ptr<v8::BackingStore>* out);
119119

120120
template <Operation operation,
121121
EVP_PKEY_cipher_init_t EVP_PKEY_cipher_init,

0 commit comments

Comments
 (0)