Skip to content

feat(x509): expose ASN.1 parse options and raise the default node limit - #2926

Draft
hacdias wants to merge 1 commit into
mainfrom
feat/expose-x509-parsing-options
Draft

feat(x509): expose ASN.1 parse options and raise the default node limit#2926
hacdias wants to merge 1 commit into
mainfrom
feat/expose-x509-parsing-options

Conversation

@hacdias

@hacdias hacdias commented Sep 7, 2026

Copy link
Copy Markdown
Member

Updates @peculiar/* packages, which enforce the asn1js parse limits. The 10000 node default rejects any CRL over ~3300 entries while fetchCrl downloads up to 10 MB, and an unparseable CRL counts as reachable-but-invalid, so SoftFail does not tolerate it: a CA with a large CRL would hard-fail chain validation in every mode but Disabled.

  • Exposes the limits as X509ParseOptions on the parsing factories, on the X509Service and revocation methods that parse, and as parseOptions on the module.
  • Adds defaultX509ParseOptions with maxNodes at 1500000, sized to that 10 MB cap. On X509ModuleConfig for what resolves through the config, and as a default parameter on the six factories, which mdoc, sd-jwt, dcql and openid4vc call directly.
  • X509Service.parseCertificateSigningRequest now takes an agentContext first, like every other method on it. X509Api is unchanged.
  • Builds CRL distribution points from their DER: @peculiar/asn1-x509 2.9.4 added an exports map and resolves to ESM, @peculiar/x509 declares none and resolves to CommonJS, so the two get separate schema registries and the lookup fails.

Creating large CRLs is still capped, the generators re-parse their own output under the default limits. That is the trusted path, fixed upstream in PeculiarVentures/x509#150 and PeculiarVentures/asn1-schema#156.

Signed-off-by: Henrique Dias <mail@hacdias.com>
@changeset-bot

changeset-bot Bot commented Sep 7, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: c28aed8

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 18 packages
Name Type
@credo-ts/core Patch
@credo-ts/action-menu Patch
@credo-ts/anoncreds Patch
@credo-ts/askar-to-drizzle-storage-migration Patch
@credo-ts/askar Patch
@credo-ts/cheqd Patch
@credo-ts/didcomm Patch
@credo-ts/drizzle-storage Patch
@credo-ts/drpc Patch
@credo-ts/hedera Patch
@credo-ts/indy-vdr Patch
@credo-ts/node Patch
@credo-ts/openid4vc Patch
@credo-ts/question-answer Patch
@credo-ts/react-native Patch
@credo-ts/redis-cache Patch
@credo-ts/tenants Patch
@credo-ts/webvh Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@hacdias

hacdias commented Sep 7, 2026

Copy link
Copy Markdown
Member Author

@TimoGlastra I'm wondering whether or not we should wait for the linked PRs. The last version addresses the case of parsing certificates, CRLs, etc. However, the x509 package also does some back and forth parsing inside the constructors and generators, and doesn't take any parsing options (I would argue that parsing options don't belong on a creator), so the PRs I opened there bypass the restrictions when creating / generating.

This means that with this PR it won't be possible to create CRLs/certificates with more than 10 000 ASN.1 nodes (parser default). I'd rather wait, but I have no idea how long it'll take. The last PRs took longer than 3 months and if we want to wait we need to pin all versions. Another option is to patch the dependency in order to bypass the restrictions for now during the creation/generation code paths, which, in my view, are trusted paths.

// `@peculiar/asn1-x509` instead. Each build keeps its own schema registry, so a value created
// here has no schema over there. Serializing keeps the values and their schema within a single
// instance, as the other extensions below do.
const value = AsnConvert.serialize(new CRLDistributionPoints([distributionPoint]))

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we link to PeculiarVentures/x509#145?

serialNumber: options.serialNumber,
extensions: [new x509.CRLDistributionPointsExtension(distributionPoints)],
// Built from DER rather than `x509.CRLDistributionPointsExtension`, see
// `createCrlDistributionPointsExtension`.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is quite unfortunate and brittle

@TimoGlastra

Copy link
Copy Markdown
Contributor

We could wait a bit and see how quickly the PRs get merged. Patches don't really work for published packages, as all dependants om Credo wouldn't have them.

@hacdias

hacdias commented Sep 7, 2026

Copy link
Copy Markdown
Member Author

Let's wait a bit then.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants