morpheus_network/mainloop/
runner.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
//! Main loop runner.
//!
//! # Reference
//! NETWORK_IMPL_GUIDE.md ยง6.2

use super::phases::{phase1_rx_refill, phase5_tx_completions, TX_BUDGET};
use crate::driver::NetworkDriver;

/// Main loop configuration.
pub struct MainLoopConfig {
    /// TSC frequency (ticks per second).
    pub tsc_freq: u64,
    /// Warning threshold for iteration timing (ticks).
    pub timing_warning_ticks: u64,
}

impl MainLoopConfig {
    /// Create from TSC frequency.
    pub fn new(tsc_freq: u64) -> Self {
        Self {
            tsc_freq,
            // 5ms warning threshold
            timing_warning_ticks: tsc_freq / 200,
        }
    }

    /// Convert TSC ticks to milliseconds.
    pub fn ticks_to_ms(&self, ticks: u64) -> u64 {
        ticks * 1000 / self.tsc_freq
    }
}

/// Single iteration result.
#[derive(Debug, Clone, Copy, PartialEq, Eq)]
pub enum IterationResult {
    /// Continue running.
    Continue,
    /// Application completed successfully.
    Done,
    /// Application failed.
    Failed,
    /// Application timed out.
    Timeout,
}

/// Run a single main loop iteration.
///
/// This is a building block - the full main loop calls this repeatedly.
/// Useful for testing and integration.
///
/// # Arguments
/// - `device`: Network device
/// - `config`: Loop configuration
///
/// # Returns
/// Whether to continue looping.
#[cfg(target_arch = "x86_64")]
pub fn run_iteration<D: NetworkDriver>(
    device: &mut D,
    _config: &MainLoopConfig,
) -> IterationResult {
    // Phase 1: Refill RX queue
    phase1_rx_refill(device);

    // Phase 2: Would call smoltcp poll here
    // (requires smoltcp integration - handled by caller)

    // Phase 3: TX drain
    // (handled by smoltcp adapter)

    // Phase 4: App state machine step
    // (handled by caller)

    // Phase 5: Collect TX completions
    phase5_tx_completions(device);

    IterationResult::Continue
}

#[cfg(not(target_arch = "x86_64"))]
pub fn run_iteration<D: NetworkDriver>(
    _device: &mut D,
    _config: &MainLoopConfig,
) -> IterationResult {
    IterationResult::Continue
}

/// Get current TSC value.
#[cfg(target_arch = "x86_64")]
pub fn get_tsc() -> u64 {
    crate::asm::core::tsc::read_tsc()
}

#[cfg(not(target_arch = "x86_64"))]
pub fn get_tsc() -> u64 {
    0
}