// Copyright 2019-2023 Parity Technologies (UK) Ltd. // This file is part of Parity Bridges Common. // Parity Bridges Common is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by // the Free Software Foundation, either version 3 of the License, or // (at your option) any later version. // Parity Bridges Common is distributed in the hope that it will be useful, // but WITHOUT ANY WARRANTY; without even the implied warranty of // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the // GNU General Public License for more details. // You should have received a copy of the GNU General Public License // along with Parity Bridges Common. If not, see . //! Types and functions intended to ease adding of new Substrate -> Substrate //! equivocation detection pipelines. mod source; mod target; use crate::finality_base::{engine::Engine, SubstrateFinalityPipeline, SubstrateFinalityProof}; use async_trait::async_trait; use bp_runtime::{AccountIdOf, BlockNumberOf, HashOf}; use equivocation_detector::EquivocationDetectionPipeline; use finality_relay::FinalityPipeline; use pallet_grandpa::{Call as GrandpaCall, Config as GrandpaConfig}; use relay_substrate_client::{AccountKeyPairOf, CallOf, Chain, ChainWithTransactions}; use sp_core::Pair; use sp_runtime::traits::{Block, Header}; use std::marker::PhantomData; /// Convenience trait that adds bounds to `SubstrateEquivocationDetectionPipeline`. pub trait BaseSubstrateEquivocationDetectionPipeline: SubstrateFinalityPipeline { /// Bounded `SubstrateFinalityPipeline::SourceChain`. type BoundedSourceChain: ChainWithTransactions; /// Bounded `AccountIdOf`. type BoundedSourceChainAccountId: From< as Pair>::Public> + Send; } impl BaseSubstrateEquivocationDetectionPipeline for T where T: SubstrateFinalityPipeline, T::SourceChain: ChainWithTransactions, AccountIdOf: From< as Pair>::Public>, { type BoundedSourceChain = T::SourceChain; type BoundedSourceChainAccountId = AccountIdOf; } /// Substrate -> Substrate equivocation detection pipeline. #[async_trait] pub trait SubstrateEquivocationDetectionPipeline: BaseSubstrateEquivocationDetectionPipeline { /// How the `report_equivocation` call is built ? type ReportEquivocationCallBuilder: ReportEquivocationCallBuilder; } type FinalityProoffOf

= <

::FinalityEngine as Engine<

::SourceChain, >>::FinalityProof; type FinalityVerificationContextfOf

= <

::FinalityEngine as Engine<

::SourceChain, >>::FinalityVerificationContext; type EquivocationProofOf

= <

::FinalityEngine as Engine<

::SourceChain, >>::EquivocationProof; type EquivocationsFinderOf

= <

::FinalityEngine as Engine<

::SourceChain, >>::EquivocationsFinder; type KeyOwnerProofOf

= <

::FinalityEngine as Engine<

::SourceChain, >>::KeyOwnerProof; /// Adapter that allows a `SubstrateEquivocationDetectionPipeline` to act as an /// `EquivocationDetectionPipeline`. #[derive(Clone, Debug)] pub struct EquivocationDetectionPipelineAdapter { _phantom: PhantomData

, } impl FinalityPipeline for EquivocationDetectionPipelineAdapter

{ const SOURCE_NAME: &'static str = P::SourceChain::NAME; const TARGET_NAME: &'static str = P::TargetChain::NAME; type Hash = HashOf; type Number = BlockNumberOf; type FinalityProof = SubstrateFinalityProof

; } impl EquivocationDetectionPipeline for EquivocationDetectionPipelineAdapter

{ type TargetNumber = BlockNumberOf; type FinalityVerificationContext = FinalityVerificationContextfOf

; type EquivocationProof = EquivocationProofOf

; type EquivocationsFinder = EquivocationsFinderOf

; } /// Different ways of building `report_equivocation` calls. pub trait ReportEquivocationCallBuilder { /// Build a `report_equivocation` call to be executed on the source chain. fn build_report_equivocation_call( equivocation_proof: EquivocationProofOf

, key_owner_proof: KeyOwnerProofOf

, ) -> CallOf; } /// Building the `report_equivocation` call when having direct access to the target chain runtime. pub struct DirectReportGrandpaEquivocationCallBuilder { _phantom: PhantomData<(P, R)>, } impl ReportEquivocationCallBuilder

for DirectReportGrandpaEquivocationCallBuilder where P: SubstrateEquivocationDetectionPipeline, P::FinalityEngine: Engine< P::SourceChain, EquivocationProof = sp_consensus_grandpa::EquivocationProof< HashOf, BlockNumberOf, >, >, R: frame_system::Config> + GrandpaConfig>, ::Header: Header>, CallOf: From>, { fn build_report_equivocation_call( equivocation_proof: EquivocationProofOf

, key_owner_proof: KeyOwnerProofOf

, ) -> CallOf { GrandpaCall::::report_equivocation { equivocation_proof: Box::new(equivocation_proof), key_owner_proof, } .into() } }