Skip to main content

df_hyperliquid_core/client/evm/precompiles/
outcomes.rs

1//! HIP-4 outcomes: an outcome's status, the only HIP-4 read on HyperEVM.
2
3use crate::client::evm::precompiles::fields::{Fields, tokens};
4use crate::client::evm::precompiles::read::{Arg, Read, read};
5use crate::utils::Dec;
6
7/// A HIP-4 outcome as the chain sees it, the only HIP-4 read on HyperEVM.
8#[derive(Debug, Clone, Copy, PartialEq, Eq)]
9pub struct OutcomeStatus {
10    pub status: u8,
11    /// 1e8 is 1.0; meaningful once settled.
12    pub settled_value: u64,
13    /// `u32::MAX` when the outcome stands alone or its question is unknown.
14    pub question: u32,
15}
16
17/// What [`OutcomeStatus::status`] says.
18#[derive(Debug, Clone, Copy, PartialEq, Eq)]
19pub enum OutcomeState {
20    NeverExisted,
21    Active,
22    /// Settled, its value readable.
23    Settled,
24    /// Settled and pruned: its value is gone.
25    Pruned,
26    Other(u8),
27}
28
29/// The places [`OutcomeStatus::settled_value`] is counted in.
30pub const SETTLED_DECIMALS: u32 = 8;
31
32impl OutcomeStatus {
33    #[must_use]
34    pub const fn state(&self) -> OutcomeState {
35        match self.status {
36            0 => OutcomeState::NeverExisted,
37            1 => OutcomeState::Active,
38            2 => OutcomeState::Settled,
39            3 => OutcomeState::Pruned,
40            other => OutcomeState::Other(other),
41        }
42    }
43
44    /// The question the outcome belongs to, if any.
45    #[must_use]
46    pub const fn in_question(&self) -> Option<u32> {
47        match self.question {
48            u32::MAX => None,
49            question => Some(question),
50        }
51    }
52
53    /// The settlement, 0 to 1, once settled and not pruned.
54    #[must_use]
55    pub fn settled(&self) -> Option<Dec> {
56        match self.state() {
57            OutcomeState::Settled => Dec::new(i128::from(self.settled_value), SETTLED_DECIMALS),
58            _ => None,
59        }
60    }
61}
62
63/// `0x814`: an outcome's status.
64#[must_use]
65pub fn outcome_status(outcome: u32) -> Read<OutcomeStatus> {
66    read(0x814, &[Arg::Uint(u64::from(outcome))], |answer| {
67        let tokens = tokens(0x814, answer)?;
68        let mut fields = Fields::of("outcomeStatus", &tokens)?;
69        Ok(OutcomeStatus { status: fields.u8()?, settled_value: fields.u64()?, question: fields.u32()? })
70    })
71}
72
73#[cfg(test)]
74#[path = "tests/outcomes.rs"]
75mod tests;