wormhole/solana/bridge/program/src/types.rs

409 lines
10 KiB
Rust

use crate::{
api::ForeignAddress,
vaa::{
DeserializeGovernancePayload,
DeserializePayload,
SerializePayload,
},
};
use borsh::{
BorshDeserialize,
BorshSerialize,
};
use byteorder::{
BigEndian,
ReadBytesExt,
};
use primitive_types::U256;
use solana_program::pubkey::Pubkey;
use solitaire::{
processors::seeded::{
AccountOwner,
Owned,
},
SolitaireError,
};
use std::{
io::{
Cursor,
Read,
Write,
},
ops::{
Deref,
DerefMut,
},
str::FromStr,
};
#[derive(Default, BorshSerialize, BorshDeserialize)]
pub struct GuardianSetData {
/// Version number of this guardian set.
pub index: u32,
/// public key hashes of the guardian set
pub keys: Vec<[u8; 20]>,
/// creation time
pub creation_time: u32,
/// expiration time when VAAs issued by this set are no longer valid
pub expiration_time: u32,
}
impl GuardianSetData {
/// Number of guardians in the set
pub fn num_guardians(&self) -> u8 {
self.keys.iter().filter(|v| **v != [0u8; 20]).count() as u8
}
}
impl Owned for GuardianSetData {
fn owner(&self) -> AccountOwner {
AccountOwner::This
}
}
#[derive(Default, BorshSerialize, BorshDeserialize)]
pub struct BridgeConfig {
/// Period for how long a guardian set is valid after it has been replaced by a new one. This
/// guarantees that VAAs issued by that set can still be submitted for a certain period. In
/// this period we still trust the old guardian set.
pub guardian_set_expiration_time: u32,
/// Amount of lamports that needs to be paid to the protocol to post a message
pub fee: u64,
/// Amount of lamports that needs to be paid to the protocol to post a persistent message
pub fee_persistent: u64,
}
#[derive(Default, BorshSerialize, BorshDeserialize)]
pub struct BridgeData {
/// The current guardian set index, used to decide which signature sets to accept.
pub guardian_set_index: u32,
/// Lamports in the collection account
pub last_lamports: u64,
/// Bridge configuration, which is set once upon initialization.
pub config: BridgeConfig,
}
impl Owned for BridgeData {
fn owner(&self) -> AccountOwner {
AccountOwner::This
}
}
#[derive(Default, BorshSerialize, BorshDeserialize)]
pub struct SignatureSet {
/// Signatures of validators
pub signatures: Vec<[u8; 65]>,
/// Hash of the data
pub hash: [u8; 32],
/// Index of the guardian set
pub guardian_set_index: u32,
}
impl Owned for SignatureSet {
fn owner(&self) -> AccountOwner {
AccountOwner::This
}
}
#[repr(transparent)]
pub struct PostedMessage(pub PostedMessageData);
impl BorshSerialize for PostedMessage {
fn serialize<W: Write>(&self, writer: &mut W) -> std::io::Result<()> {
writer.write(b"msg")?;
BorshSerialize::serialize(&self.0, writer)
}
}
impl BorshDeserialize for PostedMessage {
fn deserialize(buf: &mut &[u8]) -> std::io::Result<Self> {
*buf = &buf[3..];
Ok(PostedMessage(
<PostedMessageData as BorshDeserialize>::deserialize(buf)?,
))
}
}
impl Deref for PostedMessage {
type Target = PostedMessageData;
fn deref(&self) -> &Self::Target {
unsafe { std::mem::transmute(&self.0) }
}
}
impl DerefMut for PostedMessage {
fn deref_mut(&mut self) -> &mut Self::Target {
unsafe { std::mem::transmute(&mut self.0) }
}
}
impl Default for PostedMessage {
fn default() -> Self {
PostedMessage(PostedMessageData::default())
}
}
impl Clone for PostedMessage {
fn clone(&self) -> Self {
PostedMessage(self.0.clone())
}
}
#[derive(Default, BorshSerialize, BorshDeserialize, Clone)]
pub struct PostedMessageData {
/// Header of the posted VAA
pub vaa_version: u8,
/// Whether the VAA for this message should be persisted
pub persist: bool,
/// Level of consistency requested by the emitter
pub consistency_level: u8,
/// Time the vaa was submitted
pub vaa_time: u32,
/// Account where signatures are stored
pub vaa_signature_account: Pubkey,
/// Time the posted message was created
pub submission_time: u32,
/// Unique nonce for this message
pub nonce: u32,
/// Sequence number of this message
pub sequence: u64,
/// Emitter of the message
pub emitter_chain: u16,
/// Emitter of the message
pub emitter_address: [u8; 32],
/// Message payload
pub payload: Vec<u8>,
}
impl Owned for PostedMessage {
fn owner(&self) -> AccountOwner {
AccountOwner::Other(
Pubkey::from_str("Bridge1p5gheXUvJ6jGWGeCsgPKgnE3YgdGKRVCMY9o").unwrap(),
)
}
}
#[derive(Default, Clone, Copy, BorshDeserialize, BorshSerialize)]
pub struct SequenceTracker {
pub sequence: u64,
}
impl Owned for SequenceTracker {
fn owner(&self) -> AccountOwner {
AccountOwner::This
}
}
#[derive(Default, Clone, Copy, BorshDeserialize, BorshSerialize)]
pub struct ClaimData {
pub claimed: bool,
}
impl Owned for ClaimData {
fn owner(&self) -> AccountOwner {
AccountOwner::This
}
}
pub struct GovernancePayloadGuardianSetChange {
// New GuardianSetIndex
pub new_guardian_set_index: u32,
// New GuardianSet
pub new_guardian_set: Vec<[u8; 20]>,
}
impl SerializePayload for GovernancePayloadGuardianSetChange {
fn serialize<W: Write>(&self, v: &mut W) -> std::result::Result<(), SolitaireError> {
use byteorder::WriteBytesExt;
v.write_u32::<BigEndian>(self.new_guardian_set_index)?;
v.write_u8(self.new_guardian_set.len() as u8)?;
for key in self.new_guardian_set.iter() {
v.write(key)?;
}
Ok(())
}
}
impl DeserializePayload for GovernancePayloadGuardianSetChange
where
Self: DeserializeGovernancePayload,
{
fn deserialize(buf: &mut &[u8]) -> Result<Self, SolitaireError> {
let mut c = Cursor::new(buf);
Self::check_governance_header(&mut c)?;
let new_index = c.read_u32::<BigEndian>()?;
let keys_len = c.read_u8()?;
let mut keys = Vec::with_capacity(keys_len as usize);
for _ in 0..keys_len {
let mut key: [u8; 20] = [0; 20];
c.read(&mut key)?;
keys.push(key);
}
Ok(GovernancePayloadGuardianSetChange {
new_guardian_set_index: new_index,
new_guardian_set: keys,
})
}
}
impl DeserializeGovernancePayload for GovernancePayloadGuardianSetChange {
const MODULE: &'static str = "Core";
const ACTION: u8 = 1;
}
pub struct GovernancePayloadUpgrade {
// Address of the new Implementation
pub new_contract: Pubkey,
}
impl SerializePayload for GovernancePayloadUpgrade {
fn serialize<W: Write>(&self, v: &mut W) -> std::result::Result<(), SolitaireError> {
v.write(&self.new_contract.to_bytes())?;
Ok(())
}
}
impl DeserializePayload for GovernancePayloadUpgrade
where
Self: DeserializeGovernancePayload,
{
fn deserialize(buf: &mut &[u8]) -> Result<Self, SolitaireError> {
let mut c = Cursor::new(buf);
Self::check_governance_header(&mut c)?;
let mut addr = [0u8; 32];
c.read_exact(&mut addr)?;
Ok(GovernancePayloadUpgrade {
new_contract: Pubkey::new(&addr[..]),
})
}
}
impl DeserializeGovernancePayload for GovernancePayloadUpgrade {
const MODULE: &'static str = "Core";
const ACTION: u8 = 2;
}
pub struct GovernancePayloadSetMessageFee {
// New fee in lamports
pub fee: U256,
// New fee for persisted messages in lamports
pub persisted_fee: U256,
}
impl SerializePayload for GovernancePayloadSetMessageFee {
fn serialize<W: Write>(&self, v: &mut W) -> std::result::Result<(), SolitaireError> {
let mut fee_data = [0u8; 32];
self.fee.to_big_endian(&mut fee_data);
v.write(&fee_data[..])?;
let mut fee_persistent_data = [0u8; 32];
self.persisted_fee.to_big_endian(&mut fee_persistent_data);
v.write(&fee_persistent_data[..])?;
Ok(())
}
}
impl DeserializePayload for GovernancePayloadSetMessageFee
where
Self: DeserializeGovernancePayload,
{
fn deserialize(buf: &mut &[u8]) -> Result<Self, SolitaireError> {
let mut c = Cursor::new(buf);
Self::check_governance_header(&mut c)?;
let mut fee_data: [u8; 32] = [0; 32];
c.read_exact(&mut fee_data)?;
let fee = U256::from_big_endian(&fee_data);
let mut fee_persisted_data: [u8; 32] = [0; 32];
c.read_exact(&mut fee_persisted_data)?;
let fee_persisted = U256::from_big_endian(&fee_persisted_data);
Ok(GovernancePayloadSetMessageFee {
fee,
persisted_fee: fee_persisted,
})
}
}
impl DeserializeGovernancePayload for GovernancePayloadSetMessageFee {
const MODULE: &'static str = "Core";
const ACTION: u8 = 3;
}
pub struct GovernancePayloadTransferFees {
// Amount to be transferred
pub amount: U256,
// Recipient
pub to: ForeignAddress,
}
impl SerializePayload for GovernancePayloadTransferFees {
fn serialize<W: Write>(&self, v: &mut W) -> std::result::Result<(), SolitaireError> {
let mut amount_data = [0u8; 32];
self.amount.to_big_endian(&mut amount_data);
v.write(&amount_data)?;
v.write(&self.to)?;
Ok(())
}
}
impl DeserializePayload for GovernancePayloadTransferFees
where
Self: DeserializeGovernancePayload,
{
fn deserialize(buf: &mut &[u8]) -> Result<Self, SolitaireError> {
let mut c = Cursor::new(buf);
Self::check_governance_header(&mut c)?;
let mut amount_data: [u8; 32] = [0; 32];
c.read_exact(&mut amount_data)?;
let amount = U256::from_big_endian(&amount_data);
let mut to = ForeignAddress::default();
c.read_exact(&mut to)?;
Ok(GovernancePayloadTransferFees { amount, to })
}
}
impl DeserializeGovernancePayload for GovernancePayloadTransferFees {
const MODULE: &'static str = "Core";
const ACTION: u8 = 4;
}
#[repr(u8)]
#[derive(BorshSerialize, BorshDeserialize, Clone)]
pub enum ConsistencyLevel {
Confirmed,
Finalized,
}