Skip to content

Commit

Permalink
fix(dart/catalyst_cardano_serialization): x509 distinguished name str…
Browse files Browse the repository at this point in the history
…ucture (#1290)

* fix: x509 distinguished name structure

Signed-off-by: bkioshn <bkioshn@gmail.com>

* fix: format

Signed-off-by: bkioshn <bkioshn@gmail.com>

* feat: make it possible to override ASN1 tag for subject alt name in the x509 cert

* fix: static analysis issue

---------

Signed-off-by: bkioshn <bkioshn@gmail.com>
Co-authored-by: Dominik Toton <166132265+dtscalac@users.noreply.github.com>
Co-authored-by: Dominik Toton <dominik.toton@iohk.io>
  • Loading branch information
3 people authored Dec 2, 2024
1 parent c189dd5 commit b5935f4
Show file tree
Hide file tree
Showing 4 changed files with 86 additions and 30 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -157,7 +157,10 @@ final class RegistrationTransactionBuilder {
subject: issuer,
extensions: X509CertificateExtensions(
subjectAltName: [
'web+cardano://addr/${_stakeAddress.toBech32()}',
X509String(
'web+cardano://addr/${_stakeAddress.toBech32()}',
tag: X509String.uriTag,
),
],
),
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -212,11 +212,14 @@ Future<X509Certificate> generateX509Certificate({
subject: issuer,
extensions: X509CertificateExtensions(
subjectAltName: [
'mydomain.com',
'www.mydomain.com',
'example.com',
'www.example.com',
'web+cardano://addr/${stakeAddress.toBech32()}',
const X509String('mydomain.com', tag: X509String.domainNameTag),
const X509String('www.mydomain.com', tag: X509String.domainNameTag),
const X509String('example.com', tag: X509String.domainNameTag),
const X509String('www.example.com', tag: X509String.domainNameTag),
X509String(
'web+cardano://addr/${stakeAddress.toBech32()}',
tag: X509String.uriTag,
),
],
),
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -245,54 +245,72 @@ class X509DistinguishedName with EquatableMixin {
final countryName = this.countryName;
if (countryName != null) {
sequence.add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('c'))
..add(ASN1PrintableString(countryName)),
ASN1Set()
..add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('c'))
..add(ASN1PrintableString(countryName)),
),
);
}

final stateOrProvinceName = this.stateOrProvinceName;
if (stateOrProvinceName != null) {
sequence.add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('st'))
..add(ASN1PrintableString(stateOrProvinceName)),
ASN1Set()
..add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('st'))
..add(ASN1PrintableString(stateOrProvinceName)),
),
);
}

final localityName = this.localityName;
if (localityName != null) {
sequence.add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('l'))
..add(ASN1PrintableString(localityName)),
ASN1Set()
..add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('l'))
..add(ASN1PrintableString(localityName)),
),
);
}

final organizationName = this.organizationName;
if (organizationName != null) {
sequence.add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('o'))
..add(ASN1PrintableString(organizationName)),
ASN1Set()
..add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('o'))
..add(ASN1PrintableString(organizationName)),
),
);
}

final organizationalUnitName = this.organizationalUnitName;
if (organizationalUnitName != null) {
sequence.add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('ou'))
..add(ASN1PrintableString(organizationalUnitName)),
ASN1Set()
..add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('ou'))
..add(ASN1PrintableString(organizationalUnitName)),
),
);
}

final commonName = this.commonName;
if (commonName != null) {
sequence.add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('cn'))
..add(ASN1PrintableString(commonName)),
ASN1Set()
..add(
ASN1Sequence()
..add(ASN1ObjectIdentifier.fromName('cn'))
..add(ASN1PrintableString(commonName)),
),
);
}

Expand All @@ -313,7 +331,7 @@ class X509DistinguishedName with EquatableMixin {
/// Extra extensions of the certificate.
class X509CertificateExtensions with EquatableMixin {
/// List of alternative subject names.
final List<String>? subjectAltName;
final List<X509String>? subjectAltName;

/// The default constructor for the [X509CertificateExtensions].
const X509CertificateExtensions({this.subjectAltName});
Expand All @@ -330,7 +348,7 @@ class X509CertificateExtensions with EquatableMixin {
if (subjectAltName != null) {
final subjectAltNameSequence = ASN1Sequence();
for (final name in subjectAltName) {
subjectAltNameSequence.add(ASN1OctetString(name));
subjectAltNameSequence.add(name.toASN1());
}

extensionsSequence.add(
Expand All @@ -350,3 +368,35 @@ class X509CertificateExtensions with EquatableMixin {
@override
List<Object?> get props => [subjectAltName];
}

/// Represents an ASN1 encodable string
/// that can be optionally tagged with [tag].
class X509String with EquatableMixin {
/// An ASN1 tag for the uris.
static const int uriTag = 0x86;

/// An ASN1 tag for domain names.
static const int domainNameTag = 0x82;

/// The string value.
final String value;

/// The optional ASN1 tag.
final int tag;

/// The default constructor for the [X509String].
const X509String(
this.value, {
this.tag = OCTET_STRING_TYPE,
});

/// Encodes the data in ASN1 format.
ASN1Object toASN1() {
_ensureASN1FrequentNamesRegistered();

return ASN1OctetString(value, tag: tag);
}

@override
List<Object?> get props => [value, tag];
}
Original file line number Diff line number Diff line change
Expand Up @@ -29,10 +29,10 @@ void main() {
subject: issuer,
extensions: const X509CertificateExtensions(
subjectAltName: [
'mydomain.com',
'www.mydomain.com',
'example.com',
'www.example.com',
X509String('mydomain.com', tag: X509String.domainNameTag),
X509String('www.mydomain.com', tag: X509String.domainNameTag),
X509String('example.com', tag: X509String.domainNameTag),
X509String('www.example.com', tag: X509String.domainNameTag),
],
),
);
Expand Down

0 comments on commit b5935f4

Please sign in to comment.