forked from osmosis-labs/mesh-security
-
Notifications
You must be signed in to change notification settings - Fork 0
/
packet.rs
191 lines (174 loc) · 7.66 KB
/
packet.rs
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
use std::error::Error;
use cosmwasm_schema::cw_serde;
use cosmwasm_std::{to_json_binary, Binary, Coin, Decimal, StdResult, Timestamp};
use crate::converter_api::{RewardInfo, ValidatorSlashInfo};
/// These are messages sent from provider -> consumer
/// ibc_packet_receive in converter must handle them all.
/// Each one has a different ack to be used in the reply.
#[cw_serde]
pub enum ProviderPacket {
/// This should be called when we lock more tokens to virtually stake on a given validator
Stake {
validator: String,
/// This is the local (provider-side) denom that is held in the vault.
/// It will be converted to the consumer-side staking token in the converter with help
/// of the price feed.
stake: Coin,
/// This is local to the sending side to track the transaction, should be passed through opaquely on the consumer
tx_id: u64,
},
/// This should be called when we begin the unbonding period of some more tokens previously virtually staked
Unstake {
validator: String,
/// This is the local (provider-side) denom that is held in the vault.
/// It will be converted to the consumer-side staking token in the converter with help
/// of the price feed.
unstake: Coin,
/// This is local to the sending side to track the transaction, should be passed through opaquely on the consumer
tx_id: u64,
},
/// This should be called when we burn tokens from the given validators, because of slashing
/// propagation / vault invariants keeping.
/// If there is more than one validator, the burn amount will be split evenly between them.
/// This is non-transactional, as if it fails we cannot do much about it, besides logging the failure.
Burn {
validators: Vec<String>,
/// This is the local (provider-side) denom that is being burned in the vault.
/// It will be converted to the consumer-side staking token in the converter with help
/// of the price feed.
burn: Coin,
},
/// This is part of the rewards protocol
TransferRewards {
/// Amount previously received by ConsumerPacket::Distribute
rewards: Coin,
/// A valid address on the consumer chain to receive these rewards
recipient: String,
/// This is local to the sending side to track the transaction, should be passed through opaquely on the consumer
tx_id: u64,
},
}
/// Ack sent for ProviderPacket::Stake
#[cw_serde]
pub struct StakeAck {}
/// Ack sent for ProviderPacket::Unstake
#[cw_serde]
pub struct UnstakeAck {}
/// Ack sent for ProviderPacket::TransferRewards
#[cw_serde]
pub struct TransferRewardsAck {}
/// These are messages sent from consumer -> provider
/// ibc_packet_receive in external-staking must handle them all.
#[cw_serde]
pub enum ConsumerPacket {
ValsetUpdate {
/// This is the height of the validator set update event.
/// It is used to index the validator update events on the Provider.
/// It can be used to detect slashing conditions, e.g. which header heights are punishable.
height: u64,
/// This is the timestamp of the update event.
/// It may be used for unbonding_period issues, maybe just for informational purposes.
/// Stored as unix seconds.
time: u64,
/// This is sent when a new validator registers and is available to receive delegations.
/// One such packet is sent right after the channel is opened to sync initial state.
/// If the validator already exists, or is tombstoned, this is a no-op for that validator.
additions: Vec<AddValidator>,
/// This is sent when a validator is removed from the active set because it doesn't have
/// enough stake to be part of it.
/// If the validator doesn't exist or is tombstoned, this is a no-op for that validator.
removals: Vec<String>,
/// This is sent sent when a validator changes pubkey. It will not change the validator's state.
/// If the validator doesn't exist or is tombstoned, this is a no-op for that validator.
updated: Vec<AddValidator>,
/// This is sent when a validator is removed from the active set because it's being jailed for
/// misbehaviour.
/// The validator will be slashed for being offline as well.
/// If the validator doesn't exist or is tombstoned, this is a no-op for that validator.
jailed: Vec<String>,
/// This is sent when a validator is a candidate to be added to the active set again.
/// If the validator is also in the `removals` list, it will be marked as inactive /
/// unbonded instead.
/// If the validator doesn't exist or is tombstoned, this is a no-op for that validator.
unjailed: Vec<String>,
/// This is sent when a validator is tombstoned. Not just leaving the active state,
/// but when it is no longer a valid target to delegate to.
/// The validator will be slashed for double signing as well.
/// If the validator doesn't exist or is already tombstoned, this is a no-op for that validator.
/// This has precedence over all other events in the same packet
tombstoned: Vec<String>,
/// This is sent when a validator is slashed.
/// If the validator doesn't exist or is inactive at the infraction height, this is a no-op
/// for that validator.
/// This has precedence over all other events in the same packet.
slashed: Vec<ValidatorSlashInfo>,
},
/// This is part of the rewards protocol
Distribute {
/// The validator whose stakers should receive these rewards
validator: String,
/// The amount of rewards held on the consumer side to be released later
rewards: Coin,
},
/// This is part of the rewards protocol
DistributeBatch {
/// Per-validator reward amounts
rewards: Vec<RewardInfo>,
/// Rewards denom
denom: String,
},
}
#[cw_serde]
pub struct AddValidator {
/// This is the validator operator (valoper) address used for delegations and rewards
pub valoper: String,
// TODO: is there a better type for this? what encoding is used
/// This is the *Tendermint* public key, used for signing blocks.
/// This is needed to detect slashing conditions
pub pub_key: String,
}
impl AddValidator {
pub fn mock(valoper: &str) -> Self {
Self {
valoper: valoper.to_string(),
pub_key: "mock-pubkey".to_string(),
}
}
}
/// Ack sent for ConsumerPacket::ValsetUpdate
#[cw_serde]
pub struct ValsetUpdateAck {}
/// Ack sent for ConsumerPacket::Distribute and ConsumerPacket::DistributeBatch
#[cw_serde]
pub struct DistributeAck {}
/// This is a generic ICS acknowledgement format.
/// Protobuf defined here: https://github.com/cosmos/cosmos-sdk/blob/v0.42.0/proto/ibc/core/channel/v1/channel.proto#L141-L147
/// This is compatible with the JSON serialization.
/// Wasmd uses this same wrapper for unhandled errors.
#[cw_serde]
pub enum AckWrapper {
Result(Binary),
Error(String),
}
// create a serialized success message
pub fn ack_success<T: serde::Serialize>(data: &T) -> StdResult<Binary> {
let res = AckWrapper::Result(to_json_binary(data)?);
to_json_binary(&res)
}
// create a serialized error message
pub fn ack_fail<E: Error>(err: E) -> StdResult<Binary> {
let res = AckWrapper::Error(err.to_string());
to_json_binary(&res)
}
#[cw_serde]
pub enum PriceFeedProviderAck {
Update { time: Timestamp, twap: Decimal },
}
#[cw_serde]
pub enum RemotePriceFeedPacket {
QueryTwap {
pool_id: u64,
base_asset: String,
quote_asset: String,
},
}