@@ -3206,27 +3206,24 @@ EVP_PKEY* ManagedEVPPKey::get() const {
32063206 return pkey_.get ();
32073207}
32083208
3209- KeyObjectData* KeyObjectData::CreateSecret (v8::Local<v8::ArrayBufferView> abv) {
3209+ std::shared_ptr<KeyObjectData> KeyObjectData::CreateSecret (
3210+ Local<ArrayBufferView> abv) {
32103211 size_t key_len = abv->ByteLength ();
32113212 char * mem = MallocOpenSSL<char >(key_len);
32123213 abv->CopyContents (mem, key_len);
3213- KeyObjectData* data = new KeyObjectData ();
3214- data->key_type_ = kKeyTypeSecret ;
3215- data->symmetric_key_ = std::unique_ptr<char , std::function<void (char *)>>(mem,
3214+ return std::shared_ptr<KeyObjectData>(new KeyObjectData (
3215+ std::unique_ptr<char , std::function<void (char *)>>(mem,
32163216 [key_len](char * p) {
32173217 OPENSSL_clear_free (p, key_len);
3218- });
3219- data->symmetric_key_len_ = key_len;
3220- return data;
3218+ }),
3219+ key_len));
32213220}
32223221
3223- KeyObjectData* KeyObjectData::CreateAsymmetric (KeyType key_type,
3224- const ManagedEVPPKey& pkey) {
3222+ std::shared_ptr<KeyObjectData> KeyObjectData::CreateAsymmetric (
3223+ KeyType key_type,
3224+ const ManagedEVPPKey& pkey) {
32253225 CHECK (pkey);
3226- KeyObjectData* data = new KeyObjectData ();
3227- data->key_type_ = key_type;
3228- data->asymmetric_key_ = pkey;
3229- return data;
3226+ return std::shared_ptr<KeyObjectData>(new KeyObjectData (key_type, pkey));
32303227}
32313228
32323229KeyType KeyObjectData::GetKeyType () const {
@@ -3270,26 +3267,24 @@ Local<Function> KeyObjectHandle::Initialize(Environment* env,
32703267 return function;
32713268}
32723269
3273- MaybeLocal<Object> KeyObjectHandle::Create (Environment* env,
3274- KeyType key_type,
3275- const ManagedEVPPKey& pkey) {
3276- CHECK_NE (key_type, kKeyTypeSecret );
3277- Local<Value> type = Integer::New (env->isolate (), key_type);
3270+ MaybeLocal<Object> KeyObjectHandle::Create (
3271+ Environment* env,
3272+ std::shared_ptr<KeyObjectData> data) {
32783273 Local<Object> obj;
32793274 if (!env->crypto_key_object_handle_constructor ()
3280- ->NewInstance (env->context (), 1 , &type )
3275+ ->NewInstance (env->context (), 0 , nullptr )
32813276 .ToLocal (&obj)) {
32823277 return MaybeLocal<Object>();
32833278 }
32843279
32853280 KeyObjectHandle* key = Unwrap<KeyObjectHandle>(obj);
32863281 CHECK_NOT_NULL (key);
3287- key->data_ . reset ( KeyObjectData::CreateAsymmetric (key_type, pkey)) ;
3282+ key->data_ = data ;
32883283 return obj;
32893284}
32903285
3291- const KeyObjectData* KeyObjectHandle::Data () {
3292- return data_. get () ;
3286+ const std::shared_ptr< KeyObjectData>& KeyObjectHandle::Data () {
3287+ return data_;
32933288}
32943289
32953290void KeyObjectHandle::New (const FunctionCallbackInfo<Value>& args) {
@@ -3319,8 +3314,7 @@ void KeyObjectHandle::Init(const FunctionCallbackInfo<Value>& args) {
33193314 case kKeyTypeSecret :
33203315 CHECK_EQ (args.Length (), 2 );
33213316 CHECK (args[1 ]->IsArrayBufferView ());
3322- key->data_ .reset (
3323- KeyObjectData::CreateSecret (args[1 ].As <ArrayBufferView>()));
3317+ key->data_ = KeyObjectData::CreateSecret (args[1 ].As <ArrayBufferView>());
33243318 break ;
33253319 case kKeyTypePublic :
33263320 CHECK_EQ (args.Length (), 4 );
@@ -3329,7 +3323,7 @@ void KeyObjectHandle::Init(const FunctionCallbackInfo<Value>& args) {
33293323 pkey = GetPublicOrPrivateKeyFromJs (args, &offset);
33303324 if (!pkey)
33313325 return ;
3332- key->data_ . reset ( KeyObjectData::CreateAsymmetric (type, pkey) );
3326+ key->data_ = KeyObjectData::CreateAsymmetric (type, pkey);
33333327 break ;
33343328 case kKeyTypePrivate :
33353329 CHECK_EQ (args.Length (), 5 );
@@ -3338,7 +3332,7 @@ void KeyObjectHandle::Init(const FunctionCallbackInfo<Value>& args) {
33383332 pkey = GetPrivateKeyFromJs (args, &offset, false );
33393333 if (!pkey)
33403334 return ;
3341- key->data_ . reset ( KeyObjectData::CreateAsymmetric (type, pkey) );
3335+ key->data_ = KeyObjectData::CreateAsymmetric (type, pkey);
33423336 break ;
33433337 default :
33443338 CHECK (false );
@@ -3434,7 +3428,50 @@ MaybeLocal<Value> KeyObjectHandle::ExportPrivateKey(
34343428}
34353429
34363430void NativeKeyObject::New (const FunctionCallbackInfo<Value>& args) {
3437- CHECK_EQ (args.Length (), 0 );
3431+ Environment* env = Environment::GetCurrent (args);
3432+ CHECK_EQ (args.Length (), 1 );
3433+ CHECK (args[0 ]->IsObject ());
3434+ KeyObjectHandle* handle = Unwrap<KeyObjectHandle>(args[0 ].As <Object>());
3435+ new NativeKeyObject (env, args.This (), handle->Data ());
3436+ }
3437+
3438+ BaseObjectPtr<BaseObject> NativeKeyObject::KeyObjectTransferData::Deserialize (
3439+ Environment* env,
3440+ Local<Context> context,
3441+ std::unique_ptr<worker::TransferData> self) {
3442+ if (context != env->context ()) {
3443+ THROW_ERR_MESSAGE_TARGET_CONTEXT_UNAVAILABLE (env);
3444+ return {};
3445+ }
3446+
3447+ Local<Value> handle = KeyObjectHandle::Create (env, data_).ToLocalChecked ();
3448+ Local<Function> key_ctor;
3449+ switch (data_->GetKeyType ()) {
3450+ case kKeyTypeSecret :
3451+ key_ctor = env->crypto_key_object_secret_constructor ();
3452+ break ;
3453+ case kKeyTypePublic :
3454+ key_ctor = env->crypto_key_object_public_constructor ();
3455+ break ;
3456+ case kKeyTypePrivate :
3457+ key_ctor = env->crypto_key_object_private_constructor ();
3458+ break ;
3459+ default :
3460+ CHECK (false );
3461+ }
3462+
3463+ Local<Value> key =
3464+ key_ctor->NewInstance (context, 1 , &handle).ToLocalChecked ();
3465+ return BaseObjectPtr<BaseObject>(Unwrap<KeyObjectHandle>(key.As <Object>()));
3466+ }
3467+
3468+ BaseObject::TransferMode NativeKeyObject::GetTransferMode () const {
3469+ return BaseObject::TransferMode::kCloneable ;
3470+ }
3471+
3472+ std::unique_ptr<worker::TransferData> NativeKeyObject::CloneForMessaging ()
3473+ const {
3474+ return std::make_unique<KeyObjectTransferData>(handle_data_);
34383475}
34393476
34403477static void CreateNativeKeyObjectClass (
@@ -3448,13 +3485,23 @@ static void CreateNativeKeyObjectClass(
34483485 Local<FunctionTemplate> t = env->NewFunctionTemplate (NativeKeyObject::New);
34493486 t->InstanceTemplate ()->SetInternalFieldCount (
34503487 KeyObjectHandle::kInternalFieldCount );
3488+ t->Inherit (BaseObject::GetConstructorTemplate (env));
34513489
34523490 Local<Value> ctor = t->GetFunction (env->context ()).ToLocalChecked ();
34533491
34543492 Local<Value> recv = Undefined (env->isolate ());
3455- Local<Value> ret =
3456- callback.As <Function>()->Call (env->context (), recv, 1 , &ctor)
3457- .ToLocalChecked ();
3493+ Local<Value> ret_v;
3494+ if (!callback.As <Function>()->Call (
3495+ env->context (), recv, 1 , &ctor).ToLocal (&ret_v)) {
3496+ return ;
3497+ }
3498+ Local<Array> ret = ret_v.As <Array>();
3499+ if (!ret->Get (env->context (), 1 ).ToLocal (&ctor)) return ;
3500+ env->set_crypto_key_object_secret_constructor (ctor.As <Function>());
3501+ if (!ret->Get (env->context (), 2 ).ToLocal (&ctor)) return ;
3502+ env->set_crypto_key_object_public_constructor (ctor.As <Function>());
3503+ if (!ret->Get (env->context (), 3 ).ToLocal (&ctor)) return ;
3504+ env->set_crypto_key_object_private_constructor (ctor.As <Function>());
34583505 args.GetReturnValue ().Set (ret);
34593506}
34603507
@@ -6318,8 +6365,9 @@ class GenerateKeyPairJob : public CryptoJob {
63186365 if (public_key_encoding_.output_key_object_ ) {
63196366 // Note that this has the downside of containing sensitive data of the
63206367 // private key.
6321- if (!KeyObjectHandle::Create (env (), kKeyTypePublic , pkey_)
6322- .ToLocal (pubkey))
6368+ std::shared_ptr<KeyObjectData> data =
6369+ KeyObjectData::CreateAsymmetric (kKeyTypePublic , pkey_);
6370+ if (!KeyObjectHandle::Create (env (), data).ToLocal (pubkey))
63236371 return false ;
63246372 } else {
63256373 if (!WritePublicKey (env (), pkey_.get (), public_key_encoding_)
@@ -6329,8 +6377,9 @@ class GenerateKeyPairJob : public CryptoJob {
63296377
63306378 // Now do the same for the private key.
63316379 if (private_key_encoding_.output_key_object_ ) {
6332- if (!KeyObjectHandle::Create (env (), kKeyTypePrivate , pkey_)
6333- .ToLocal (privkey))
6380+ std::shared_ptr<KeyObjectData> data =
6381+ KeyObjectData::CreateAsymmetric (kKeyTypePrivate , pkey_);
6382+ if (!KeyObjectHandle::Create (env (), data).ToLocal (privkey))
63346383 return false ;
63356384 } else {
63366385 if (!WritePrivateKey (env (), pkey_.get (), private_key_encoding_)
0 commit comments