Add command line arguments

Replace the hard-coded addresses with clap arguments: --bind <IP> and one or more --peer <IP>. Peers must match the address family of the bind address. Also updates Cargo.lock.
This commit is contained in:
ktims committed 2026-10-22 15:41:08 -07:00
1 parent 0bb1f437ae
commit c7a6ed16e4
3 files changed
+368 -373

No files matched your search

+35 -12
View File
@@ -1,8 +1,8 @@
use clap::Parser;
use futures::future;
use rust_bfd::events::{EventMessageSink, ScriptHookSink, StateChangeEvent};
use rust_bfd::{set_ttl_or_hop_limit, BfdSessionStats};
use rust_bfd::{bfd::*, events::EventMessage};
use std::net::Ipv6Addr;
use rust_bfd::{set_ttl_or_hop_limit, BfdSessionStats};
use std::{
collections::HashMap,
error::Error,
@@ -10,7 +10,6 @@ use std::{
io::ErrorKind,
mem::swap,
net::{IpAddr, SocketAddr},
str::FromStr,
sync::{atomic::Ordering, Arc},
time::{Duration, Instant},
};
@@ -36,6 +35,18 @@ use atomic::Atomic;
const CONTROL_PORT: u16 = 3784;
const ECHO_PORT: u16 = 3785;
#[derive(Parser, Debug)]
#[command(version, about = "BFD (RFC 5880) daemon")]
struct Args {
/// Local IP address to bind to and use as the source of BFD control packets
#[arg(short, long, value_name = "IP")]
bind: IpAddr,
/// Peer IP address to establish a session with (repeatable; must match the bind address family)
#[arg(short, long = "peer", value_name = "IP", required = true)]
peers: Vec<IpAddr>,
}
const ORDERING: Ordering = Ordering::Relaxed;
#[derive(Debug)]
@@ -923,14 +934,24 @@ struct Bfdd {
}
impl Bfdd {
async fn new() -> Result<Self, Box<dyn Error>> {
// let local = SocketAddr::from_str("192.168.255.2:3784").unwrap();
let local = SocketAddr::new(Ipv6Addr::from_str("2001:db8::2").unwrap().into(), 3784);
let peers = vec![
// SocketAddr::from_str("192.168.122.132:3784").unwrap(),
// SocketAddr::from_str("192.168.255.1:3784").unwrap(),
SocketAddr::new(Ipv6Addr::from_str("2001:db8::1").unwrap().into(), 3784),
];
async fn new(args: Args) -> Result<Self, Box<dyn Error>> {
let local = SocketAddr::new(args.bind, CONTROL_PORT);
if let Some(peer) = args
.peers
.iter()
.find(|p| p.is_ipv4() != args.bind.is_ipv4())
{
return Err(format!(
"peer {peer} is not the same address family as bind address {}",
args.bind
)
.into());
}
let peers = args
.peers
.into_iter()
.map(|ip| SocketAddr::new(ip, CONTROL_PORT))
.collect();
let sessions_by_ip = HashMap::new();
let sessions_by_discr = HashMap::new();
@@ -1075,11 +1096,13 @@ impl Bfdd {
#[tokio::main]
async fn main() -> io::Result<()> {
let args = Args::parse();
env_logger::Builder::from_env(Env::default().default_filter_or("info"))
.format_timestamp_micros()
.init();
match Bfdd::new().await {
match Bfdd::new(args).await {
Ok(bfdd) => bfdd.run().await,
Err(e) => Err(std::io::Error::new(ErrorKind::Other, e.to_string())),
}