Skip to content

Commit f2ce5c0

Browse files
goffrieConvex, Inc.
authored and
Convex, Inc.
committed
Use AWS-LC (via openssl-rs) to implement SubtleCrypto RSA (#36374)
GitOrigin-RevId: e849cd89bd627d6b7b23920fc89ceb576e69a41e
1 parent f49a18e commit f2ce5c0

File tree

11 files changed

+159
-209
lines changed

11 files changed

+159
-209
lines changed

Cargo.lock

Lines changed: 18 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,6 +99,7 @@ native-tls = "^0.2.10"
9999
num_cpus = "1.16.0"
100100
oauth2 = { version = "5", default-features = false, features = [ "reqwest" ] }
101101
openidconnect = { git = "https://github.com/get-convex/openidconnect-rs", rev = "f21c7999356bd374a683d13378bd2a6c0ebdbf11", default-features = false, features = [ "accept-rfc3339-timestamps", "timing-resistant-secret-traits", "reqwest" ] }
102+
openssl = { version = "0.10.72", features = [ "aws-lc" ] }
102103
parking_lot = { version = "0.12", features = [ "hardware-lock-elision" ] }
103104
paste = { version = "1.0.12" }
104105
phf = { version = "0.11.2", features = [ "macros" ] }

crates/isolate/Cargo.toml

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,11 +50,14 @@ mime = { workspace = true }
5050
model = { path = "../model" }
5151
multer = { workspace = true }
5252
must-let = { workspace = true, optional = true }
53+
openssl = { workspace = true }
5354
p256 = { workspace = true }
5455
p384 = { workspace = true }
5556
parking_lot = { workspace = true }
5657
pb = { path = "../pb" }
5758
phf = { workspace = true }
59+
pkcs1 = "0.7.5"
60+
pkcs8 = "0.10.2"
5861
prometheus = { workspace = true }
5962
proptest = { workspace = true, optional = true }
6063
proptest-derive = { workspace = true, optional = true }
@@ -63,7 +66,6 @@ rand = { workspace = true }
6366
rand_chacha = { workspace = true }
6467
regex = { workspace = true }
6568
ring = { workspace = true }
66-
rsa = { workspace = true }
6769
runtime = { path = "../runtime" }
6870
search = { path = "../search" }
6971
semver = { workspace = true }

crates/isolate/src/environment/crypto_rng.rs

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,9 +13,4 @@ impl CryptoRng {
1313
pub fn ring(&self) -> ring::rand::SystemRandom {
1414
ring::rand::SystemRandom::new()
1515
}
16-
17-
/// Returns an `rsa`-compatible random number generator
18-
pub fn rsa(&self) -> rsa::rand_core::OsRng {
19-
rsa::rand_core::OsRng
20-
}
2116
}

crates/isolate/src/ops/crypto/ed25519.rs

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ use spki::{
1414
Decode,
1515
Encode,
1616
},
17+
AlgorithmIdentifierRef,
1718
SubjectPublicKeyInfo,
1819
};
1920

@@ -104,9 +105,9 @@ impl CryptoOps {
104105

105106
pub fn export_pkcs8_ed25519(pkey: &[u8]) -> Result<ToJsBuffer, AnyError> {
106107
// This should probably use OneAsymmetricKey instead
107-
let pk_info = rsa::pkcs8::PrivateKeyInfo {
108+
let pk_info = PrivateKeyInfo {
108109
public_key: None,
109-
algorithm: rsa::pkcs8::AlgorithmIdentifierRef {
110+
algorithm: AlgorithmIdentifierRef {
110111
// id-Ed25519
111112
oid: ED25519_OID,
112113
parameters: None,

crates/isolate/src/ops/crypto/export_key.rs

Lines changed: 14 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -8,21 +8,20 @@ use const_oid::{
88
use deno_core::ToJsBuffer;
99
use elliptic_curve::sec1::ToEncodedPoint;
1010
use p256::pkcs8::DecodePrivateKey;
11-
use rsa::{
12-
pkcs1::der::Decode,
13-
pkcs8::der::{
14-
asn1::UintRef,
15-
Encode,
16-
},
17-
};
11+
use pkcs1::UintRef;
1812
use serde::{
1913
Deserialize,
2014
Serialize,
2115
};
2216
use spki::{
2317
der::{
24-
asn1,
25-
asn1::BitString,
18+
self,
19+
asn1::{
20+
self,
21+
BitString,
22+
},
23+
Decode as _,
24+
Encode as _,
2625
},
2726
AlgorithmIdentifier,
2827
AlgorithmIdentifierOwned,
@@ -176,16 +175,14 @@ fn export_key_rsa(
176175

177176
// version is 0 when publickey is None
178177

179-
let pk_info = rsa::pkcs8::PrivateKeyInfo {
178+
let pk_info = pkcs8::PrivateKeyInfo {
180179
public_key: None,
181-
algorithm: rsa::pkcs8::AlgorithmIdentifierRef {
180+
algorithm: pkcs8::AlgorithmIdentifierRef {
182181
// rsaEncryption(1)
183-
oid: rsa::pkcs8::ObjectIdentifier::new_unwrap("1.2.840.113549.1.1.1"),
182+
oid: pkcs8::ObjectIdentifier::new_unwrap("1.2.840.113549.1.1.1"),
184183
// parameters field should not be omitted (None).
185184
// It MUST have ASN.1 type NULL as per defined in RFC 3279 Section 2.3.1
186-
parameters: Some(rsa::pkcs8::der::asn1::AnyRef::from(
187-
rsa::pkcs8::der::asn1::Null,
188-
)),
185+
parameters: Some(der::asn1::AnyRef::from(der::asn1::Null)),
189186
},
190187
private_key,
191188
};
@@ -198,7 +195,7 @@ fn export_key_rsa(
198195
},
199196
ExportKeyFormat::JwkPublic => {
200197
let public_key = key_data.as_rsa_public_key()?;
201-
let public_key = rsa::pkcs1::RsaPublicKey::from_der(&public_key).map_err(|_| {
198+
let public_key = pkcs1::RsaPublicKey::from_der(&public_key).map_err(|_| {
202199
custom_error("DOMExceptionOperationError", "failed to decode public key")
203200
})?;
204201

@@ -209,7 +206,7 @@ fn export_key_rsa(
209206
},
210207
ExportKeyFormat::JwkPrivate => {
211208
let private_key = key_data.as_rsa_private_key()?;
212-
let private_key = rsa::pkcs1::RsaPrivateKey::from_der(private_key).map_err(|_| {
209+
let private_key = pkcs1::RsaPrivateKey::from_der(private_key).map_err(|_| {
213210
custom_error("DOMExceptionOperationError", "failed to decode private key")
214211
})?;
215212

crates/isolate/src/ops/crypto/generate_key.rs

Lines changed: 11 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,9 @@
11
use anyhow::Context as _;
22
use deno_core::ToJsBuffer;
3+
use openssl::{
4+
bn::BigNum,
5+
rsa::Rsa,
6+
};
37
use ring::{
48
rand::SecureRandom,
59
signature::{
@@ -8,10 +12,6 @@ use ring::{
812
KeyPair,
913
},
1014
};
11-
use rsa::pkcs1::{
12-
EncodeRsaPrivateKey,
13-
EncodeRsaPublicKey,
14-
};
1515

1616
use super::{
1717
shared::RustRawKeyData,
@@ -35,16 +35,17 @@ impl CryptoOps {
3535
modulus_length,
3636
public_exponent,
3737
} => {
38-
let exp = rsa::BigUint::from_bytes_be(&public_exponent);
39-
let private_key =
40-
rsa::RsaPrivateKey::new_with_exp(&mut rng.rsa(), modulus_length, &exp)?;
41-
let public_key = private_key.to_public_key();
38+
let exp = BigNum::from_slice(&public_exponent)?;
39+
let private_key = Rsa::generate_with_e(
40+
modulus_length.try_into().context("bad modulus length")?,
41+
&exp,
42+
)?;
4243
Ok(GeneratedKeypair {
4344
private_raw_data: GeneratedKey::KeyData(RustRawKeyData::Private(
44-
private_key.to_pkcs1_der()?.as_bytes().to_vec().into(),
45+
private_key.private_key_to_der()?.into(),
4546
)),
4647
public_raw_data: GeneratedKey::KeyData(RustRawKeyData::Public(
47-
public_key.to_pkcs1_der()?.into_vec().into(),
48+
private_key.public_key_to_der_pkcs1()?.into(),
4849
)),
4950
})
5051
},

crates/isolate/src/ops/crypto/import_key.rs

Lines changed: 16 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -5,18 +5,18 @@ use anyhow::Context as _;
55
use deno_core::ToJsBuffer;
66
use elliptic_curve::pkcs8::PrivateKeyInfo;
77
use p256::pkcs8::EncodePrivateKey;
8+
use pkcs1::UintRef;
89
use ring::signature::EcdsaKeyPair;
9-
use rsa::{
10-
pkcs1::UintRef,
11-
pkcs8::der::Decode as RsaDecode,
12-
};
1310
use serde::{
1411
Deserialize,
1512
Serialize,
1613
};
1714
use serde_bytes::ByteBuf;
1815
use spki::{
19-
der::Encode as SpkiEncode,
16+
der::{
17+
Decode as _,
18+
Encode as SpkiEncode,
19+
},
2020
SubjectPublicKeyInfoRef,
2121
};
2222

@@ -142,7 +142,7 @@ fn import_key_rsa_jwk(key_data: KeyData) -> anyhow::Result<ImportKeyResult> {
142142
jwt_b64_int_or_err!(modulus, &n, "invalid modulus");
143143
jwt_b64_int_or_err!(public_exponent, &e, "invalid public exponent");
144144

145-
let public_key = rsa::pkcs1::RsaPublicKey {
145+
let public_key = pkcs1::RsaPublicKey {
146146
modulus,
147147
public_exponent,
148148
};
@@ -179,7 +179,7 @@ fn import_key_rsa_jwk(key_data: KeyData) -> anyhow::Result<ImportKeyResult> {
179179
jwt_b64_int_or_err!(exponent2, &dq, "invalid second CRT exponent");
180180
jwt_b64_int_or_err!(coefficient, &qi, "invalid CRT coefficient");
181181

182-
let private_key = rsa::pkcs1::RsaPrivateKey {
182+
let private_key = pkcs1::RsaPrivateKey {
183183
modulus,
184184
public_exponent,
185185
private_exponent,
@@ -227,9 +227,8 @@ fn import_key_rsassa(key_data: KeyData) -> anyhow::Result<ImportKeyResult> {
227227
}
228228

229229
// 8-9.
230-
let public_key =
231-
rsa::pkcs1::RsaPublicKey::from_der(pk_info.subject_public_key.raw_bytes())
232-
.map_err(|e| data_error(e.to_string()))?;
230+
let public_key = pkcs1::RsaPublicKey::from_der(pk_info.subject_public_key.raw_bytes())
231+
.map_err(|e| data_error(e.to_string()))?;
233232

234233
let bytes_consumed = public_key
235234
.encoded_len()
@@ -264,7 +263,7 @@ fn import_key_rsassa(key_data: KeyData) -> anyhow::Result<ImportKeyResult> {
264263
}
265264

266265
// 8-9.
267-
let private_key = rsa::pkcs1::RsaPrivateKey::from_der(pk_info.private_key)
266+
let private_key = pkcs1::RsaPrivateKey::from_der(pk_info.private_key)
268267
.map_err(|e| data_error(e.to_string()))?;
269268

270269
let bytes_consumed = private_key
@@ -308,9 +307,8 @@ fn import_key_rsapss(key_data: KeyData) -> anyhow::Result<ImportKeyResult> {
308307
}
309308

310309
// 8-9.
311-
let public_key =
312-
rsa::pkcs1::RsaPublicKey::from_der(pk_info.subject_public_key.raw_bytes())
313-
.map_err(|e| data_error(e.to_string()))?;
310+
let public_key = pkcs1::RsaPublicKey::from_der(pk_info.subject_public_key.raw_bytes())
311+
.map_err(|e| data_error(e.to_string()))?;
314312

315313
let bytes_consumed = public_key
316314
.encoded_len()
@@ -345,7 +343,7 @@ fn import_key_rsapss(key_data: KeyData) -> anyhow::Result<ImportKeyResult> {
345343
}
346344

347345
// 8-9.
348-
let private_key = rsa::pkcs1::RsaPrivateKey::from_der(pk_info.private_key)
346+
let private_key = pkcs1::RsaPrivateKey::from_der(pk_info.private_key)
349347
.map_err(|e| data_error(e.to_string()))?;
350348

351349
let bytes_consumed = private_key
@@ -389,9 +387,8 @@ fn import_key_rsaoaep(key_data: KeyData) -> Result<ImportKeyResult, anyhow::Erro
389387
}
390388

391389
// 8-9.
392-
let public_key =
393-
rsa::pkcs1::RsaPublicKey::from_der(pk_info.subject_public_key.raw_bytes())
394-
.map_err(|e| data_error(e.to_string()))?;
390+
let public_key = pkcs1::RsaPublicKey::from_der(pk_info.subject_public_key.raw_bytes())
391+
.map_err(|e| data_error(e.to_string()))?;
395392

396393
let bytes_consumed = public_key
397394
.encoded_len()
@@ -426,7 +423,7 @@ fn import_key_rsaoaep(key_data: KeyData) -> Result<ImportKeyResult, anyhow::Erro
426423
}
427424

428425
// 8-9.
429-
let private_key = rsa::pkcs1::RsaPrivateKey::from_der(pk_info.private_key)
426+
let private_key = pkcs1::RsaPrivateKey::from_der(pk_info.private_key)
430427
.map_err(|e| data_error(e.to_string()))?;
431428

432429
let bytes_consumed = private_key

0 commit comments

Comments
 (0)