Skip to content

Commit 6d52775

Browse files
committed
wip
1 parent 91a9a8c commit 6d52775

File tree

3 files changed

+86
-51
lines changed

3 files changed

+86
-51
lines changed

rust/rbac-registration/src/cardano/cip509/utils/cip134_uri_set.rs

Lines changed: 40 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -39,6 +39,8 @@ struct Cip0134UriSetInner {
3939
x_uris: UrisMap,
4040
/// URIs from c509 certificates.
4141
c_uris: UrisMap,
42+
/// URIs which are taken by another certificates.
43+
taken_uris: HashSet<Cip0134Uri>,
4244
}
4345

4446
impl Cip0134UriSet {
@@ -51,7 +53,12 @@ impl Cip0134UriSet {
5153
) -> Self {
5254
let x_uris = extract_x509_uris(x509_certs, report);
5355
let c_uris = extract_c509_uris(c509_certs, report);
54-
Self(Arc::new(Cip0134UriSetInner { x_uris, c_uris }))
56+
let taken_uris = HashSet::new();
57+
Self(Arc::new(Cip0134UriSetInner {
58+
x_uris,
59+
c_uris,
60+
taken_uris,
61+
}))
5562
}
5663

5764
/// Returns a mapping from the x509 certificate index to URIs contained within.
@@ -67,7 +74,7 @@ impl Cip0134UriSet {
6774
}
6875

6976
/// Returns an iterator over of `Cip0134Uri`.
70-
pub fn values(&self) -> impl Iterator<Item = &Cip0134Uri> {
77+
pub(crate) fn values(&self) -> impl Iterator<Item = &Cip0134Uri> {
7178
self.x_uris()
7279
.values()
7380
.chain(self.c_uris().values())
@@ -159,6 +166,7 @@ impl Cip0134UriSet {
159166
let Cip0134UriSetInner {
160167
mut x_uris,
161168
mut c_uris,
169+
mut taken_uris,
162170
} = Arc::unwrap_or_clone(self.0);
163171

164172
for (index, cert) in metadata.x509_certs.iter().enumerate() {
@@ -171,6 +179,7 @@ impl Cip0134UriSet {
171179
},
172180
X509DerCert::X509Cert(_) => {
173181
if let Some(uris) = metadata.certificate_uris.x_uris().get(&index) {
182+
taken_uris.remove(&uris);
174183
x_uris.insert(index, uris.clone());
175184
}
176185
},
@@ -190,13 +199,41 @@ impl Cip0134UriSet {
190199
},
191200
C509Cert::C509Certificate(_) => {
192201
if let Some(uris) = metadata.certificate_uris.c_uris().get(&index) {
202+
taken_uris.remove(&uris);
193203
c_uris.insert(index, uris.clone());
194204
}
195205
},
196206
}
197207
}
198208

199-
Self(Arc::new(Cip0134UriSetInner { x_uris, c_uris }))
209+
Self(Arc::new(Cip0134UriSetInner {
210+
x_uris,
211+
c_uris,
212+
taken_uris,
213+
}))
214+
}
215+
216+
/// Return the updated URIs set where the provided URIs were taken by other
217+
/// registration chains.
218+
///
219+
/// Updates the current URI set by removing the taken URIs from it.
220+
#[must_use]
221+
pub fn update_taken_uris(
222+
self,
223+
metadata: &Cip509RbacMetadata,
224+
) -> Self {
225+
let taken_uri_set = metadata.certificate_uris.values().collect::<HashSet<_>>();
226+
let current_uris_set = self.values().collect::<HashSet<_>>();
227+
let taken_uris = current_uris_set.intersection(&taken_uri_set);
228+
229+
let Cip0134UriSetInner { x_uris, c_uris, .. } = Arc::unwrap_or_clone(self.0);
230+
let taken_uris = taken_uris.cloned().cloned().collect();
231+
232+
Self(Arc::new(Cip0134UriSetInner {
233+
x_uris,
234+
c_uris,
235+
taken_uris,
236+
}))
200237
}
201238
}
202239

rust/rbac-registration/src/cardano/cip509/validation.rs

Lines changed: 2 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -157,10 +157,7 @@ fn extract_stake_addresses(uris: Option<&Cip0134UriSet>) -> Vec<(VKeyHash, Strin
157157
return Vec::new();
158158
};
159159

160-
uris.x_uris()
161-
.iter()
162-
.chain(uris.c_uris())
163-
.flat_map(|(_index, uris)| uris.iter())
160+
uris.values()
164161
.filter_map(|uri| {
165162
if let Address::Stake(a) = uri.address() {
166163
let bech32 = uri.address().to_string();
@@ -185,10 +182,7 @@ fn extract_payment_addresses(uris: Option<&Cip0134UriSet>) -> Vec<(VKeyHash, Str
185182
return Vec::new();
186183
};
187184

188-
uris.x_uris()
189-
.iter()
190-
.chain(uris.c_uris())
191-
.flat_map(|(_index, uris)| uris.iter())
185+
uris.values()
192186
.filter_map(|uri| {
193187
if let Address::Shelley(a) = uri.address() {
194188
match a.payment() {

rust/rbac-registration/src/registration/cardano/mod.rs

Lines changed: 44 additions & 40 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,7 @@ use std::{
99

1010
use anyhow::Context;
1111
use c509_certificate::c509::C509;
12-
use cardano_blockchain_types::{
13-
hashes::TransactionId, pallas_addresses::Address, Cip0134Uri, Point, StakeAddress, TxnIndex,
14-
};
12+
use cardano_blockchain_types::{hashes::TransactionId, Point, StakeAddress, TxnIndex};
1513
use catalyst_types::{
1614
catalyst_id::{key_rotation::KeyRotation, role_index::RoleId, CatalystId},
1715
conversion::zero_out_last_n_bytes,
@@ -26,8 +24,8 @@ use x509_cert::certificate::Certificate as X509Certificate;
2624

2725
use crate::{
2826
cardano::cip509::{
29-
CertKeyHash, CertOrPk, Cip0134UriSet, Cip509, PaymentHistory, PointData, RoleData,
30-
RoleDataRecord, ValidationSignature,
27+
CertKeyHash, CertOrPk, Cip0134UriSet, Cip509, PaymentHistory, PointData, PointTxnIdx,
28+
RoleData, RoleDataRecord, ValidationSignature,
3129
},
3230
providers::RbacRegistrationProvider,
3331
};
@@ -349,26 +347,13 @@ impl RegistrationChain {
349347
/// Returns all stake addresses associated to this chain.
350348
#[must_use]
351349
pub fn stake_addresses(&self) -> HashSet<StakeAddress> {
352-
let stolen_stake_addresses = self
353-
.inner
354-
.stolen_uris
355-
.iter()
356-
.flat_map(|v| {
357-
v.data().iter().filter_map(|uri| {
358-
match uri.address() {
359-
Address::Stake(a) => Some(a.clone().into()),
360-
_ => None,
361-
}
362-
})
363-
})
364-
.collect();
350+
self.inner.certificate_uris.stake_addresses();
351+
}
365352

366-
self.inner
367-
.certificate_uris
368-
.stake_addresses()
369-
.difference(&stolen_stake_addresses)
370-
.cloned()
371-
.collect()
353+
/// Returns the latest know applied registration's `PointTxnIdx`.
354+
#[must_use]
355+
pub fn latest_applied(&self) -> PointTxnIdx {
356+
self.inner.latest_applied()
372357
}
373358
}
374359

@@ -379,6 +364,9 @@ struct RegistrationChainInner {
379364
catalyst_id: CatalystId,
380365
/// The current transaction ID hash (32 bytes)
381366
current_tx_id_hash: PointData<TransactionId>,
367+
/// The latest `PointTxnIdx` of the stolen taken URIs by another registration chains.
368+
latest_taken_uris_point: Option<PointTxnIdx>,
369+
382370
/// List of purpose for this registration chain
383371
purpose: Vec<UuidV4>,
384372

@@ -397,9 +385,6 @@ struct RegistrationChainInner {
397385
/// List of point + transaction index, and certificate key hash.
398386
revocations: Vec<PointData<CertKeyHash>>,
399387

400-
/// URIs which are stolen by another registration chains.
401-
stolen_uris: Vec<PointData<Box<[Cip0134Uri]>>>,
402-
403388
// Role
404389
/// Map of role number to list point + transaction index, and role data.
405390
/// Record history of the whole role data in point in time.
@@ -516,9 +501,9 @@ impl RegistrationChainInner {
516501
x509_certs,
517502
c509_certs,
518503
certificate_uris,
504+
latest_taken_uris_point: None,
519505
simple_keys,
520506
revocations,
521-
stolen_uris: vec![],
522507
role_data_history,
523508
role_data_record,
524509
payment_history,
@@ -536,6 +521,18 @@ impl RegistrationChainInner {
536521
signing_pk: VerifyingKey,
537522
) -> Option<Self> {
538523
let context = "Registration Chain update";
524+
if self.latest_applied().point() >= cip509.origin().point() {
525+
cip509.report().functional_validation(
526+
&format!(
527+
"The provided registration is earlier {} than the current one {}",
528+
cip509.origin().point(),
529+
self.current_tx_id_hash.point()
530+
),
531+
"Provided registrations must be applied in the correct order.",
532+
);
533+
return None;
534+
}
535+
539536
let mut new_inner = self.clone();
540537

541538
let Some(prv_tx_id) = cip509.previous_transaction() else {
@@ -654,19 +651,12 @@ impl RegistrationChainInner {
654651
fn update_cause_another_chain(
655652
mut self,
656653
cip509: &Cip509,
657-
) -> Option<Self> {
658-
if let Some(uri_set) = cip509.certificate_uris() {
659-
let origin = cip509.origin().clone();
660-
self.stolen_uris.push(PointData::new(
661-
origin,
662-
uri_set
663-
.values()
664-
.cloned()
665-
.collect::<Vec<_>>()
666-
.into_boxed_slice(),
667-
));
654+
) -> Self {
655+
if let Some(reg) = cip509.metadata() {
656+
self.certificate_uris = self.certificate_uris.update_taken_uris(reg);
668657
}
669-
Some(self)
658+
self.latest_taken_uris_point = Some(cip509.origin().clone());
659+
self
670660
}
671661

672662
/// Get the latest signing public key for a role.
@@ -700,6 +690,20 @@ impl RegistrationChainInner {
700690
})
701691
})
702692
}
693+
694+
/// Returns the latest know applied registration's `PointTxnIdx`.
695+
#[must_use]
696+
fn latest_applied(&self) -> PointTxnIdx {
697+
if let Some(latest_taken_uris_point) = &self.latest_taken_uris_point {
698+
if latest_taken_uris_point.point() > self.current_tx_id_hash.point() {
699+
return latest_taken_uris_point.clone();
700+
}
701+
}
702+
PointTxnIdx::new(
703+
self.current_tx_id_hash.point().clone(),
704+
self.current_tx_id_hash.txn_index(),
705+
)
706+
}
703707
}
704708

705709
/// Perform a check on the validation signature.

0 commit comments

Comments
 (0)