extend unsigned validation to prevent transaction replay

Signed-off-by: Uncle Stinky <uncle.stinky@ghostchain.io>
This commit is contained in:
Uncle Stinky 2026-10-27 19:15:22 +03:00
parent d18b8ba11f
commit d0db73170d
Signed by: st1nky
GPG Key ID: 016064BD97603B40
2 changed files with 79 additions and 16 deletions

View File

@ -1,6 +1,6 @@
[package]
name = "ghost-exodus"
version = "0.1.4"
version = "0.1.5"
description = "Threshold signature generation with DKG included"
license.workspace = true
authors.workspace = true

View File

@ -2769,6 +2769,10 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
if Round0Packages::<T>::contains_key(&network_curve, &authority_index) {
return Err(InvalidTransaction::Stale);
}
let authorities = QualificationAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -2836,6 +2840,10 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
if Round1Packages::<T>::get(&network_curve).contains(authority_index) {
return Err(InvalidTransaction::Stale);
}
let authority = authorities
.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -2915,6 +2923,10 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
if Round2Packages::<T>::get(&network_curve).contains(authority_index) {
return Err(InvalidTransaction::Stale);
}
let authorities = QualificationAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -2985,6 +2997,10 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
if Complaints::<T>::get(&network_curve).contains_key(&authority_index) {
return Err(InvalidTransaction::Stale);
}
let authorities = QualificationAuthorities::<T>::get(&network_curve);
let authority = authorities
.get(authority_index as usize)
@ -3067,6 +3083,10 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
if Justifications::<T>::get(&network_curve).contains_key(&authority_index) {
return Err(InvalidTransaction::Stale);
}
let authorities = QualificationAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -3129,6 +3149,13 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
if VerifyingKeyConsensus::<T>::get(&network_curve, &package_dkg_index)
.state
.participants
.contains(authority_index) {
return Err(InvalidTransaction::Stale);
}
let authorities = QualificationAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -3195,6 +3222,11 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
if VerifyingSharesParticipants::<T>::get(&network_curve, package_dkg_index)
.contains(authority_index) {
return Err(InvalidTransaction::Stale);
}
let authorities = QualificationAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -3263,15 +3295,6 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
let authorities = ActiveAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
let encoded_package = exodus_package.encode();
if !authority.verify(&encoded_package, signature) {
return Err(InvalidTransaction::BadProof);
}
let exodus_request =
ExodusRequests::<T>::get((&network_curve, exodus_context))
.ok_or(InvalidTransaction::BadProof)?;
@ -3282,6 +3305,22 @@ impl<T: Config> Pallet<T> {
None => exodus_request.next_roast_session,
};
if NonceCommitments::<T>::contains_key(
(exodus_context, roast_session),
authority_index
) {
return Err(InvalidTransaction::Stale);
}
let authorities = ActiveAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
let encoded_package = exodus_package.encode();
if !authority.verify(&encoded_package, signature) {
return Err(InvalidTransaction::BadProof);
}
Ok((exodus_request, roast_session))
}
@ -3331,6 +3370,22 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
let roast_session =
RoastSessions::<T>::get(exodus_context, &authority_index)
.ok_or(InvalidTransaction::BadProof)?;
let roast_state = RoastSessionStates::<T>::get(&exodus_context, &roast_session);
let is_nonce_committer = roast_state.nonce_committers.contains(authority_index);
let is_group_committer = roast_state.group_committers.contains(authority_index);
let is_partial_signer = roast_state.partial_signers.contains(authority_index);
let threshold_reached = roast_state.nonce_committers == roast_state.group_committers;
let already_committed = !threshold_reached || is_group_committer;
if !is_nonce_committer || !already_committed || is_partial_signer {
return Err(InvalidTransaction::Stale);
}
let authorities = ActiveAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -3340,8 +3395,7 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::BadProof);
}
RoastSessions::<T>::get(exodus_context, &authority_index)
.ok_or(InvalidTransaction::BadProof)
Ok(roast_session)
}
fn validate_exodus_signature_share_size_and_get_metadata<'a>(
@ -3395,6 +3449,19 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::Stale);
}
let roast_session =
RoastSessions::<T>::get(exodus_context, &authority_index)
.ok_or(InvalidTransaction::BadProof)?;
let roast_state = RoastSessionStates::<T>::get(&exodus_context, &roast_session);
let is_nonce_committer = roast_state.nonce_committers.contains(authority_index);
let is_group_committer = roast_state.group_committers.contains(authority_index);
let is_partial_signer = roast_state.partial_signers.contains(authority_index);
if !is_nonce_committer || !is_group_committer || is_partial_signer {
return Err(InvalidTransaction::Stale);
}
let authorities = ActiveAuthorities::<T>::get(&network_curve);
let authority = authorities.get(authority_index as usize)
.ok_or(InvalidTransaction::BadSigner)?;
@ -3404,10 +3471,6 @@ impl<T: Config> Pallet<T> {
return Err(InvalidTransaction::BadProof);
}
let roast_session =
RoastSessions::<T>::get(exodus_context, &authority_index)
.ok_or(InvalidTransaction::BadProof)?;
Ok((roast_session, active_state.get_dkg_index()))
}