Skip to content

Commit

Permalink
fix(dart/catalyst_cardano_serialization): remove key reference from R…
Browse files Browse the repository at this point in the history
…BAC, use local key ref instead (#1292)

* fix(dart/catalyst_cardano_serialization): remove key reference from RBAC, use local key ref

* fix: update RBAC issuer properties, catalyst users don't have any of these identifiable

* fix: payment key should refer to the first transaction output which is the change address

* chore: rename keyOffset to offset
  • Loading branch information
dtscalac authored Nov 28, 2024
1 parent 4446448 commit b443449
Show file tree
Hide file tree
Showing 4 changed files with 40 additions and 103 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -83,16 +83,13 @@ final class RegistrationTransactionBuilder {
// they should be registered here
RoleData(
roleNumber: AccountRole.root.roleNumber,
roleSigningKey: KeyReference(
localRef: const LocalKeyReference(
keyType: LocalKeyReferenceType.x509Certs,
keyOffset: 0,
),
roleSigningKey: const LocalKeyReference(
keyType: LocalKeyReferenceType.x509Certs,
offset: 0,
),
roleEncryptionKey: KeyReference(
hash: CertificateHash.fromX509DerCertificate(derCert),
),
paymentKey: 0,
// Refer to first key in transaction outputs,
// in our case it's the change address (which the user controls).
paymentKey: -1,
),
},
),
Expand Down Expand Up @@ -143,12 +140,12 @@ final class RegistrationTransactionBuilder {

/* cSpell:disable */
const issuer = X509DistinguishedName(
countryName: 'US',
stateOrProvinceName: 'California',
localityName: 'San Francisco',
organizationName: 'MyCompany',
organizationalUnitName: 'MyDepartment',
commonName: 'mydomain.com',
countryName: '',
stateOrProvinceName: '',
localityName: '',
organizationName: '',
organizationalUnitName: '',
commonName: '',
);

final tbs = X509TBSCertificate(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -107,16 +107,11 @@ Future<X509MetadataEnvelope<RegistrationData>> _buildMetadataEnvelope({
roleDataSet: {
RoleData(
roleNumber: 0,
roleSigningKey: KeyReference(
localRef: const LocalKeyReference(
keyType: LocalKeyReferenceType.x509Certs,
keyOffset: 0,
),
roleSigningKey: const LocalKeyReference(
keyType: LocalKeyReferenceType.x509Certs,
offset: 0,
),
roleEncryptionKey: KeyReference(
hash: CertificateHash.fromX509DerCertificate(derCert),
),
paymentKey: 0,
paymentKey: -1,
roleSpecificData: {
10: CborString('Test'),
},
Expand Down Expand Up @@ -200,12 +195,12 @@ Future<X509Certificate> generateX509Certificate({

/* cSpell:disable */
const issuer = X509DistinguishedName(
countryName: 'US',
stateOrProvinceName: 'California',
localityName: 'San Francisco',
organizationName: 'MyCompany',
organizationalUnitName: 'MyDepartment',
commonName: 'mydomain.com',
countryName: '',
stateOrProvinceName: '',
localityName: '',
organizationName: '',
organizationalUnitName: '',
commonName: '',
);

final tbs = X509TBSCertificate(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@ class RoleData extends Equatable implements CborEncodable {
///
/// If the certificate is revoked, the role is unusable for signing unless
/// and until a new signing certificate is registered for the role.
final KeyReference? roleSigningKey;
final LocalKeyReference? roleSigningKey;

/// A Role may require the ability to transfer encrypted data.
/// The registration can include the Public key use by the role to encrypt
Expand All @@ -155,7 +155,7 @@ class RoleData extends Equatable implements CborEncodable {
/// key encryption, and not just a signing key.
/// If the key referenced does not support public key encryption,
/// the registration is invalid.
final KeyReference? roleEncryptionKey;
final LocalKeyReference? roleEncryptionKey;

/// Reference to a transaction input/output as the payment key to use for a role.
/// Payment key (n) >= 0 = Use Transaction Input Key offset (n)
Expand Down Expand Up @@ -207,10 +207,11 @@ class RoleData extends Equatable implements CborEncodable {

return RoleData(
roleNumber: roleNumber.value,
roleSigningKey:
roleSigningKey != null ? KeyReference.fromCbor(roleSigningKey) : null,
roleSigningKey: roleSigningKey != null
? LocalKeyReference.fromCbor(roleSigningKey)
: null,
roleEncryptionKey: roleEncryptionKey != null
? KeyReference.fromCbor(roleEncryptionKey)
? LocalKeyReference.fromCbor(roleEncryptionKey)
: null,
paymentKey: paymentKey?.value,
roleSpecificData: roleSpecificData.isNotEmpty
Expand Down Expand Up @@ -246,61 +247,6 @@ class RoleData extends Equatable implements CborEncodable {
];
}

/// References a local key in this registration or
/// a given key in an earlier registration.
///
/// Either [localRef] or [hash] must be set, but not both and not none.
class KeyReference extends Equatable implements CborEncodable {
/// Offset reference to a key defined in this registration.
/// More efficient than a key hash.
final LocalKeyReference? localRef;

/// Reference to a key defined in an earlier registration.
final CertificateHash? hash;

/// The default constructor for [KeyReference].
KeyReference({this.localRef, this.hash}) {
if (!((localRef == null) ^ (hash == null))) {
throw ArgumentError(
'Either localRef or hash must be set, but not both and not none.',
);
}
}

/// Deserializes the type from cbor.
factory KeyReference.fromCbor(CborValue value) {
return KeyReference(
localRef: _tryParseLocalRef(value),
hash: _tryParseHash(value),
);
}

static LocalKeyReference? _tryParseLocalRef(CborValue value) {
try {
return LocalKeyReference.fromCbor(value);
} catch (ignored) {
return null;
}
}

static CertificateHash? _tryParseHash(CborValue value) {
try {
return CertificateHash.fromCbor(value);
} catch (ignored) {
return null;
}
}

/// Serializes the type as cbor.
@override
CborValue toCbor() {
return localRef?.toCbor() ?? hash!.toCbor();
}

@override
List<Object?> get props => [localRef, hash];
}

/// Offset reference to a key defined in this registration.
///
/// More efficient than a key hash.
Expand All @@ -309,23 +255,23 @@ class LocalKeyReference extends Equatable implements CborEncodable {
final LocalKeyReferenceType keyType;

/// Offset of the key in the specified set. 0 = first entry.
final int keyOffset;
final int offset;

/// The default constructor for [LocalKeyReference].
const LocalKeyReference({
required this.keyType,
required this.keyOffset,
required this.offset,
});

/// Deserializes the type from cbor.
factory LocalKeyReference.fromCbor(CborValue value) {
final list = value as CborList;
final keyType = list[0] as CborSmallInt;
final keyOffset = list[1] as CborSmallInt;
final offset = list[1] as CborSmallInt;

return LocalKeyReference(
keyType: LocalKeyReferenceType.fromTag(keyType.value),
keyOffset: keyOffset.value,
offset: offset.value,
);
}

Expand All @@ -334,12 +280,12 @@ class LocalKeyReference extends Equatable implements CborEncodable {
CborValue toCbor() {
return CborList([
CborSmallInt(keyType.tag),
CborSmallInt(keyOffset),
CborSmallInt(offset),
]);
}

@override
List<Object?> get props => [keyType, keyOffset];
List<Object?> get props => [keyType, offset];
}

/// Defines the type of the referenced local key.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,14 +22,13 @@ void main() {
roleDataSet: {
RoleData(
roleNumber: 0,
roleSigningKey: KeyReference(
localRef: const LocalKeyReference(
keyType: LocalKeyReferenceType.x509Certs,
keyOffset: 0,
),
roleSigningKey: const LocalKeyReference(
keyType: LocalKeyReferenceType.x509Certs,
offset: 0,
),
roleEncryptionKey: KeyReference(
hash: CertificateHash.fromX509DerCertificate(derCert),
roleEncryptionKey: const LocalKeyReference(
keyType: LocalKeyReferenceType.x509Certs,
offset: 0,
),
paymentKey: 0,
roleSpecificData: {
Expand Down

0 comments on commit b443449

Please sign in to comment.