pub struct EventLoop { /* private fields */ }
Expand description
The main event loop structure for registering I/O sources and handling events.
EventLoop
is the primary interface for Mill-IO, providing a simple API for:
- Registering I/O sources (sockets, files, etc.) with event handlers
- Starting and stopping the event loop
- Managing the underlying reactor and thread pool
The event loop uses a reactor pattern internally, where I/O events are detected by the polling mechanism and dispatched to registered handlers via a thread pool.
§Examples
Basic usage with default configuration:
use mill_io::{EventLoop, EventHandler};
use mio::{net::TcpListener, Interest, Token};
use std::net::SocketAddr;
struct MyHandler;
impl EventHandler for MyHandler {
fn handle_event(&self, event: &mio::event::Event) {
println!("Event received: {:?}", event);
}
}
let event_loop = EventLoop::default();
let addr: SocketAddr = "127.0.0.1:0".parse()?;
let mut listener = TcpListener::bind(addr)?;
event_loop.register(&mut listener, Token(0), Interest::READABLE, MyHandler)?;
event_loop.run()?; // Blocks until stopped
Custom configuration:
use mill_io::EventLoop;
let event_loop = EventLoop::new(
4, // 4 worker threads
512, // Buffer for 512 events per poll
50 // 50ms poll timeout
)?;
Implementations§
Source§impl EventLoop
impl EventLoop
Sourcepub fn new(
workers: usize,
events_capacity: usize,
poll_timeout_ms: u64,
) -> Result<Self>
pub fn new( workers: usize, events_capacity: usize, poll_timeout_ms: u64, ) -> Result<Self>
Creates a new EventLoop
with custom configuration.
§Arguments
workers
- Number of worker threads in the thread pool (recommended: num_cpus)events_capacity
- Maximum number of events to poll per iteration (typical: 512-4096)poll_timeout_ms
- Poll timeout in milliseconds (balance between latency and CPU usage)
§Errors
Returns an error if:
- The reactor cannot be initialized
- The thread pool cannot be created
- The polling mechanism fails to initialize
§Examples
use mill_io::EventLoop;
// High-throughput configuration
let event_loop = EventLoop::new(8, 2048, 50)?;
// Low-latency configuration
let event_loop = EventLoop::new(2, 256, 10)?;
Sourcepub fn register<H, S>(
&self,
source: &mut S,
token: Token,
interests: Interest,
handler: H,
) -> Result<()>
pub fn register<H, S>( &self, source: &mut S, token: Token, interests: Interest, handler: H, ) -> Result<()>
Registers an I/O source with the event loop and associates it with a handler.
This method registers an I/O source (such as a TCP listener or socket) with the event loop. When events occur on the source, the provided handler will be invoked on a worker thread.
§Arguments
source
- The I/O source to register (e.g.,mio::net::TcpListener
)token
- Unique token for identifying events from this sourceinterests
- I/O events to listen for (mio::Interest::READABLE
,mio::Interest::WRITABLE
)handler
- Event handler that will process events from this source
§Errors
Returns an error if:
- The token is already in use
- The source cannot be registered with the underlying poll mechanism
- The handler registry is full
§Examples
use mill_io::{EventLoop, EventHandler};
use mio::{net::TcpListener, Interest, Token};
use std::net::SocketAddr;
struct ConnectionHandler;
impl EventHandler for ConnectionHandler {
fn handle_event(&self, event: &mio::event::Event) {
// Handle new connections
}
}
let event_loop = EventLoop::default();
let addr: SocketAddr = "0.0.0.0:8080".parse()?;
let mut listener = TcpListener::bind(addr)?;
event_loop.register(
&mut listener,
Token(0),
Interest::READABLE,
ConnectionHandler
)?;
Sourcepub fn deregister<S>(&self, source: &mut S, token: Token) -> Result<()>
pub fn deregister<S>(&self, source: &mut S, token: Token) -> Result<()>
Deregisters an I/O source from the event loop.
Removes the source from the polling mechanism and clears its associated handler. After deregistration, no more events will be delivered for this source.
§Arguments
source
- The I/O source to deregistertoken
- Token associated with the source during registration
§Errors
Returns an error if:
- The source is not currently registered
- The deregistration fails at the OS level
- The token is invalid
§Examples
use mill_io::{EventLoop, EventHandler};
use mio::{net::TcpListener, Interest, Token};
use std::net::SocketAddr;
struct Handler;
impl EventHandler for Handler {
fn handle_event(&self, _: &mio::event::Event) {}
}
let event_loop = EventLoop::default();
let addr: SocketAddr = "127.0.0.1:0".parse()?;
let mut listener = TcpListener::bind(addr)?;
let token = Token(0);
// Register
event_loop.register(&mut listener, token, Interest::READABLE, Handler)?;
// Later, deregister
event_loop.deregister(&mut listener, token)?;
Sourcepub fn run(&self) -> Result<()>
pub fn run(&self) -> Result<()>
Runs the event loop, blocking the current thread and dispatching events.
This method starts the reactor’s main loop, which will:
- Poll for I/O events using the configured timeout
- Dispatch events to registered handlers via the thread pool
- Continue until
stop()
is called or an error occurs
The method blocks the calling thread and will only return when the event loop is stopped or encounters a fatal error.
§Errors
Returns an error if:
- The polling mechanism fails
- The thread pool encounters a fatal error
- System resources are exhausted
§Ok::<(), Box>(())
Sourcepub fn stop(&self)
pub fn stop(&self)
Signals the event loop to stop gracefully.
This method initiates a graceful shutdown of the event loop. It sends a shutdown signal to the reactor, which will cause the main loop to exit after finishing the current polling cycle.
This method is non-blocking and returns immediately. The actual shutdown happens
asynchronously, and run()
will return once the shutdown is complete.
§Thread Safety
This method is thread-safe and can be called from any thread, making it suitable for use in signal handlers or from other threads.
§Examples
use mill_io::EventLoop;
use std::thread;
use std::sync::Arc;
let event_loop = Arc::new(EventLoop::default());
let event_loop_clone = Arc::clone(&event_loop);
// Start event loop in background thread
let handle = thread::spawn(move || {
// In a real application, you would handle the result properly
let _ = event_loop_clone.run();
});
// Stop after some time
thread::sleep(std::time::Duration::from_secs(1));
event_loop.stop();
// Wait for shutdown
let _ = handle.join();
Trait Implementations§
Source§impl Default for EventLoop
impl Default for EventLoop
Source§fn default() -> Self
fn default() -> Self
Creates a new EventLoop
with default configuration.
The default configuration uses:
- 4 worker threads (
DEFAULT_POOL_CAPACITY
) - 1024 events capacity (
DEFAULT_EVENTS_CAPACITY
) - 100ms poll timeout (
DEFAULT_POLL_TIMEOUT_MS
)
§Panics
Panics if the reactor cannot be initialized with default settings.