| FazBrowse GitHub Viewer | Trending | | Home |
| Tools: [Download Repo ZIP] [Original HTTPS Page] |
1 parent be48760 commit 039ac19
6 files changed
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -8,7 +8,9 @@ | |||
| 8 | 8 | #include <openssl/rand.h> | |
| 9 | 9 | #include <openssl/x509v3.h> | |
| 10 | 10 | #include <algorithm> | |
| 11 | + #include <array> | ||
| 11 | 12 | #include <cstring> | |
| 13 | + #include <string_view> | ||
| 12 | 14 | #if OPENSSL_VERSION_MAJOR >= 3 | |
| 13 | 15 | #include <openssl/core_names.h> | |
| 14 | 16 | #include <openssl/params.h> | |
@@ -1094,6 +1096,29 @@ BIOPointer X509View::getValidTo() const { | |||
| 1094 | 1096 | return bio; | |
| 1095 | 1097 | } | |
| 1096 | 1098 | ||
| 1099 | + std::optional<std::string_view> X509View::getSignatureAlgorithm() const { | ||
| 1100 | + if (cert_ == nullptr) return std::nullopt; | ||
| 1101 | + int nid = X509_get_signature_nid(cert_); | ||
| 1102 | + if (nid == NID_undef) return std::nullopt; | ||
| 1103 | + const char* ln = OBJ_nid2ln(nid); | ||
| 1104 | + if (ln == nullptr) return std::nullopt; | ||
| 1105 | + return std::string_view(ln); | ||
| 1106 | + } | ||
| 1107 | + | ||
| 1108 | + std::optional<std::string> X509View::getSignatureAlgorithmOID() const { | ||
| 1109 | + if (cert_ == nullptr) return std::nullopt; | ||
| 1110 | + const X509_ALGOR* alg = nullptr; | ||
| 1111 | + X509_get0_signature(nullptr, &alg, cert_); | ||
| 1112 | + if (alg == nullptr) return std::nullopt; | ||
| 1113 | + const ASN1_OBJECT* obj = nullptr; | ||
| 1114 | + X509_ALGOR_get0(&obj, nullptr, nullptr, alg); | ||
| 1115 | + if (obj == nullptr) return std::nullopt; | ||
| 1116 | + std::array<char, 128> buf{}; | ||
| 1117 | + int len = OBJ_obj2txt(buf.data(), buf.size(), obj, 1); | ||
| 1118 | + if (len < 0 || static_cast<size_t>(len) >= buf.size()) return std::nullopt; | ||
| 1119 | + return std::string(buf.data(), static_cast<size_t>(len)); | ||
| 1120 | + } | ||
| 1121 | + | ||
| 1097 | 1122 | int64_t X509View::getValidToTime() const { | |
| 1098 | 1123 | #ifdef OPENSSL_IS_BORINGSSL | |
| 1099 | 1124 | // Boringssl does not implement ASN1_TIME_to_tm in a public way, | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -1191,6 +1191,8 @@ class X509View final { | |||
| 1191 | 1191 | BIOPointer getInfoAccess() const; | |
| 1192 | 1192 | BIOPointer getValidFrom() const; | |
| 1193 | 1193 | BIOPointer getValidTo() const; | |
| 1194 | + std::optional<std::string_view> getSignatureAlgorithm() const; | ||
| 1195 | + std::optional<std::string> getSignatureAlgorithmOID() const; | ||
| 1194 | 1196 | int64_t getValidFromTime() const; | |
| 1195 | 1197 | int64_t getValidToTime() const; | |
| 1196 | 1198 | DataPointer getSerialNumber() const; | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -2971,6 +2971,26 @@ added: | |||
| 2971 | 2971 | ||
| 2972 | 2972 | The date/time until which this certificate is valid, encapsulated in a `Date` object. | |
| 2973 | 2973 | ||
| 2974 | + ### `x509.signatureAlgorithm` | ||
| 2975 | + | ||
| 2976 | + <!-- YAML | ||
| 2977 | + added: REPLACEME | ||
| 2978 | + --> | ||
| 2979 | + | ||
| 2980 | + * Type: {string|undefined} | ||
| 2981 | + | ||
| 2982 | + The algorithm used to sign the certificate or `undefined` if the signature algorithm is unknown by OpenSSL. | ||
| 2983 | + | ||
| 2984 | + ### `x509.signatureAlgorithmOid` | ||
| 2985 | + | ||
| 2986 | + <!-- YAML | ||
| 2987 | + added: REPLACEME | ||
| 2988 | + --> | ||
| 2989 | + | ||
| 2990 | + * Type: {string} | ||
| 2991 | + | ||
| 2992 | + The OID of the algorithm used to sign the certificate. | ||
| 2993 | + | ||
| 2974 | 2994 | ### `x509.verify(publicKey)` | |
| 2975 | 2995 | ||
| 2976 | 2996 | <!-- YAML | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -142,6 +142,8 @@ class X509Certificate { | |||
| 142 | 142 | fingerprint512: this.fingerprint512, | |
| 143 | 143 | keyUsage: this.keyUsage, | |
| 144 | 144 | serialNumber: this.serialNumber, | |
| 145 | + signatureAlgorithm: this.signatureAlgorithm, | ||
| 146 | + signatureAlgorithmOid: this.signatureAlgorithmOid, | ||
| 145 | 147 | }, opts)}`; | |
| 146 | 148 | } | |
| 147 | 149 | ||
@@ -285,6 +287,24 @@ class X509Certificate { | |||
| 285 | 287 | return value; | |
| 286 | 288 | } | |
| 287 | 289 | ||
| 290 | + get signatureAlgorithm() { | ||
| 291 | + let value = this[kInternalState].get('signatureAlgorithm'); | ||
| 292 | + if (value === undefined) { | ||
| 293 | + value = this[kHandle].signatureAlgorithm(); | ||
| 294 | + this[kInternalState].set('signatureAlgorithm', value); | ||
| 295 | + } | ||
| 296 | + return value; | ||
| 297 | + } | ||
| 298 | + | ||
| 299 | + get signatureAlgorithmOid() { | ||
| 300 | + let value = this[kInternalState].get('signatureAlgorithmOid'); | ||
| 301 | + if (value === undefined) { | ||
| 302 | + value = this[kHandle].signatureAlgorithmOid(); | ||
| 303 | + this[kInternalState].set('signatureAlgorithmOid', value); | ||
| 304 | + } | ||
| 305 | + return value; | ||
| 306 | + } | ||
| 307 | + | ||
| 288 | 308 | get raw() { | |
| 289 | 309 | let value = this[kInternalState].get('raw'); | |
| 290 | 310 | if (value === undefined) { | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -225,6 +225,30 @@ MaybeLocal<Value> GetValidToDate(Environment* env, const X509View& view) { | |||
| 225 | 225 | return Date::New(env->context(), validToTime * 1000.); | |
| 226 | 226 | } | |
| 227 | 227 | ||
| 228 | + MaybeLocal<Value> GetSignatureAlgorithm(Environment* env, | ||
| 229 | + const X509View& view) { | ||
| 230 | + auto algo = view.getSignatureAlgorithm(); | ||
| 231 | + if (!algo.has_value()) [[unlikely]] | ||
| 232 | + return Undefined(env->isolate()); | ||
| 233 | + Local<Value> ret; | ||
| 234 | + if (!ToV8Value(env, algo.value()).ToLocal(&ret)) { | ||
| 235 | + return {}; | ||
| 236 | + } | ||
| 237 | + return ret; | ||
| 238 | + } | ||
| 239 | + | ||
| 240 | + MaybeLocal<Value> GetSignatureAlgorithmOID(Environment* env, | ||
| 241 | + const X509View& view) { | ||
| 242 | + auto oid = view.getSignatureAlgorithmOID(); | ||
| 243 | + if (!oid.has_value()) [[unlikely]] | ||
| 244 | + return Undefined(env->isolate()); | ||
| 245 | + Local<Value> ret; | ||
| 246 | + if (!ToV8Value(env, oid.value()).ToLocal(&ret)) { | ||
| 247 | + return {}; | ||
| 248 | + } | ||
| 249 | + return ret; | ||
| 250 | + } | ||
| 251 | + | ||
| 228 | 252 | MaybeLocal<Value> GetSerialNumber(Environment* env, const X509View& view) { | |
| 229 | 253 | if (auto serial = view.getSerialNumber()) { | |
| 230 | 254 | return OneByteString(env->isolate(), | |
@@ -342,6 +366,26 @@ void ValidToDate(const FunctionCallbackInfo<Value>& args) { | |||
| 342 | 366 | } | |
| 343 | 367 | } | |
| 344 | 368 | ||
| 369 | + void SignatureAlgorithm(const FunctionCallbackInfo<Value>& args) { | ||
| 370 | + Environment* env = Environment::GetCurrent(args); | ||
| 371 | + X509Certificate* cert; | ||
| 372 | + ASSIGN_OR_RETURN_UNWRAP(&cert, args.This()); | ||
| 373 | + Local<Value> ret; | ||
| 374 | + if (GetSignatureAlgorithm(env, cert->view()).ToLocal(&ret)) { | ||
| 375 | + args.GetReturnValue().Set(ret); | ||
| 376 | + } | ||
| 377 | + } | ||
| 378 | + | ||
| 379 | + void SignatureAlgorithmOID(const FunctionCallbackInfo<Value>& args) { | ||
| 380 | + Environment* env = Environment::GetCurrent(args); | ||
| 381 | + X509Certificate* cert; | ||
| 382 | + ASSIGN_OR_RETURN_UNWRAP(&cert, args.This()); | ||
| 383 | + Local<Value> ret; | ||
| 384 | + if (GetSignatureAlgorithmOID(env, cert->view()).ToLocal(&ret)) { | ||
| 385 | + args.GetReturnValue().Set(ret); | ||
| 386 | + } | ||
| 387 | + } | ||
| 388 | + | ||
| 345 | 389 | void SerialNumber(const FunctionCallbackInfo<Value>& args) { | |
| 346 | 390 | Environment* env = Environment::GetCurrent(args); | |
| 347 | 391 | X509Certificate* cert; | |
@@ -822,6 +866,10 @@ Local<FunctionTemplate> X509Certificate::GetConstructorTemplate( | |||
| 822 | 866 | SetProtoMethodNoSideEffect(isolate, tmpl, "validFrom", ValidFrom); | |
| 823 | 867 | SetProtoMethodNoSideEffect(isolate, tmpl, "validToDate", ValidToDate); | |
| 824 | 868 | SetProtoMethodNoSideEffect(isolate, tmpl, "validFromDate", ValidFromDate); | |
| 869 | + SetProtoMethodNoSideEffect( | ||
| 870 | + isolate, tmpl, "signatureAlgorithm", SignatureAlgorithm); | ||
| 871 | + SetProtoMethodNoSideEffect( | ||
| 872 | + isolate, tmpl, "signatureAlgorithmOid", SignatureAlgorithmOID); | ||
| 825 | 873 | SetProtoMethodNoSideEffect( | |
| 826 | 874 | isolate, tmpl, "fingerprint", Fingerprint<Digest::SHA1>); | |
| 827 | 875 | SetProtoMethodNoSideEffect( | |
@@ -996,6 +1044,8 @@ void X509Certificate::RegisterExternalReferences( | |||
| 996 | 1044 | registry->Register(ValidFrom); | |
| 997 | 1045 | registry->Register(ValidToDate); | |
| 998 | 1046 | registry->Register(ValidFromDate); | |
| 1047 | + registry->Register(SignatureAlgorithm); | ||
| 1048 | + registry->Register(SignatureAlgorithmOID); | ||
| 999 | 1049 | registry->Register(Fingerprint<Digest::SHA1>); | |
| 1000 | 1050 | registry->Register(Fingerprint<Digest::SHA256>); | |
| 1001 | 1051 | registry->Register(Fingerprint<Digest::SHA512>); | |
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
@@ -114,6 +114,9 @@ const der = Buffer.from( | |||
| 114 | 114 | assert.strictEqual(x509.keyUsage, undefined); | |
| 115 | 115 | assert.strictEqual(x509.serialNumber.toUpperCase(), '147D36C1C2F74206DE9FAB5F2226D78ADB00A426'); | |
| 116 | 116 | ||
| 117 | + assert.strictEqual(x509.signatureAlgorithm, 'sha256WithRSAEncryption'); | ||
| 118 | + assert.strictEqual(x509.signatureAlgorithmOid, '1.2.840.113549.1.1.11'); | ||
| 119 | + | ||
| 117 | 120 | assert.deepStrictEqual(x509.raw, der); | |
| 118 | 121 | ||
| 119 | 122 | if (!process.features.openssl_is_boringssl) { | |
@@ -448,3 +451,17 @@ CWwQO8JZjJqFtqtuzy2n+gLCvqePgG/gmSqHOPm2ZbLW | |||
| 448 | 451 | assert.deepStrictEqual(c2.validToDate, new Date('2050-01-02T00:00:01Z')); | |
| 449 | 452 | } | |
| 450 | 453 | } | |
| 454 | + | ||
| 455 | + { | ||
| 456 | + const certPem = `-----BEGIN CERTIFICATE----- | ||
| 457 | + MIGXMHugAwIBAgIBATANBgkrBgEEAYaNHwEFADASMRAwDgYDVQQDEwdVbmtub3du | ||
| 458 | + MB4XDTI0MDEwMTAwMDAwMFoXDTM0MDEwMTAwMDAwMFowEjEQMA4GA1UEAxMHVW5r | ||
| 459 | + bm93bjAaMA0GCSqGSIb3DQEBAQUAAwkAAAAAAAAAAAAwDQYJKwYBBAGGjR8BBQAD | ||
| 460 | + CQAAAAAAAAAAAA== | ||
| 461 | + -----END CERTIFICATE-----`; | ||
| 462 | + | ||
| 463 | + const cert = new X509Certificate(certPem); | ||
| 464 | + | ||
| 465 | + assert.strictEqual(cert.signatureAlgorithm, undefined); | ||
| 466 | + assert.strictEqual(cert.signatureAlgorithmOid, '1.3.6.1.4.1.99999.1'); | ||
| 467 | + } | ||
| Back | FazBrowse Home | New Git URL |
0 commit comments