forked from Deuxfleurs/diplonat
parse private_ip earlier
This commit is contained in:
parent
b3f76f272a
commit
f410230240
5 changed files with 25 additions and 24 deletions
|
@ -26,7 +26,7 @@ fn all_valid_options() -> HashMap<String, String> {
|
||||||
);
|
);
|
||||||
opts.insert(
|
opts.insert(
|
||||||
"DIPLONAT_PRIVATE_IP".to_string(),
|
"DIPLONAT_PRIVATE_IP".to_string(),
|
||||||
"172.123.43.555".to_string(),
|
"172.123.43.55".to_string(),
|
||||||
);
|
);
|
||||||
opts.insert("DIPLONAT_REFRESH_TIME".to_string(), "10".to_string());
|
opts.insert("DIPLONAT_REFRESH_TIME".to_string(), "10".to_string());
|
||||||
opts.insert(
|
opts.insert(
|
||||||
|
@ -118,7 +118,7 @@ fn ok_from_iter_all_valid_options() {
|
||||||
);
|
);
|
||||||
assert_eq!(rt_config.firewall.refresh_time, refresh_time);
|
assert_eq!(rt_config.firewall.refresh_time, refresh_time);
|
||||||
assert_eq!(
|
assert_eq!(
|
||||||
&rt_config.igd.private_ip.unwrap(),
|
&rt_config.igd.private_ip.unwrap().to_string(),
|
||||||
opts.get(&"DIPLONAT_PRIVATE_IP".to_string()).unwrap()
|
opts.get(&"DIPLONAT_PRIVATE_IP".to_string()).unwrap()
|
||||||
);
|
);
|
||||||
assert_eq!(rt_config.igd.expiration_time, expiration_time);
|
assert_eq!(rt_config.igd.expiration_time, expiration_time);
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
use std::fs::File;
|
use std::fs::File;
|
||||||
use std::io::Read;
|
use std::io::Read;
|
||||||
use std::net::{SocketAddr, ToSocketAddrs};
|
use std::net::{Ipv4Addr, SocketAddr, ToSocketAddrs};
|
||||||
use std::time::Duration;
|
use std::time::Duration;
|
||||||
|
|
||||||
use anyhow::{anyhow, bail, Result};
|
use anyhow::{anyhow, bail, Context, Result};
|
||||||
|
|
||||||
use crate::config::{ConfigOpts, ConfigOptsAcme, ConfigOptsBase, ConfigOptsConsul};
|
use crate::config::{ConfigOpts, ConfigOptsAcme, ConfigOptsBase, ConfigOptsConsul};
|
||||||
|
|
||||||
|
@ -31,7 +31,7 @@ pub struct RuntimeConfigFirewall {
|
||||||
|
|
||||||
#[derive(Debug)]
|
#[derive(Debug)]
|
||||||
pub struct RuntimeConfigIgd {
|
pub struct RuntimeConfigIgd {
|
||||||
pub private_ip: Option<String>,
|
pub private_ip: Option<Ipv4Addr>,
|
||||||
pub expiration_time: Duration,
|
pub expiration_time: Duration,
|
||||||
pub refresh_time: Duration,
|
pub refresh_time: Duration,
|
||||||
}
|
}
|
||||||
|
@ -137,7 +137,12 @@ impl RuntimeConfigFirewall {
|
||||||
|
|
||||||
impl RuntimeConfigIgd {
|
impl RuntimeConfigIgd {
|
||||||
pub(super) fn new(opts: &ConfigOptsBase) -> Result<Self> {
|
pub(super) fn new(opts: &ConfigOptsBase) -> Result<Self> {
|
||||||
let private_ip = opts.private_ip.clone();
|
let private_ip = opts
|
||||||
|
.private_ip
|
||||||
|
.as_ref()
|
||||||
|
.map(|x| x.parse())
|
||||||
|
.transpose()
|
||||||
|
.context("parse private_ip")?;
|
||||||
let expiration_time = Duration::from_secs(
|
let expiration_time = Duration::from_secs(
|
||||||
opts.expiration_time
|
opts.expiration_time
|
||||||
.unwrap_or(super::EXPIRATION_TIME)
|
.unwrap_or(super::EXPIRATION_TIME)
|
||||||
|
|
|
@ -23,7 +23,7 @@ impl Diplonat {
|
||||||
let fw = FirewallActor::new(rt_cfg.firewall.refresh_time, &ca.rx_open_ports).await?;
|
let fw = FirewallActor::new(rt_cfg.firewall.refresh_time, &ca.rx_open_ports).await?;
|
||||||
|
|
||||||
let ia = IgdActor::new(
|
let ia = IgdActor::new(
|
||||||
rt_cfg.igd.private_ip.as_ref().map(String::as_str),
|
rt_cfg.igd.private_ip,
|
||||||
rt_cfg.igd.refresh_time,
|
rt_cfg.igd.refresh_time,
|
||||||
rt_cfg.igd.expiration_time,
|
rt_cfg.igd.expiration_time,
|
||||||
&ca.rx_open_ports,
|
&ca.rx_open_ports,
|
||||||
|
|
|
@ -11,7 +11,7 @@ pub fn setup(ipt: &iptables::IPTables) -> Result<()> {
|
||||||
// ensure we start from a clean state without any rule already set
|
// ensure we start from a clean state without any rule already set
|
||||||
cleanup(ipt)?;
|
cleanup(ipt)?;
|
||||||
|
|
||||||
info!("{}: creating DIPLONAT chain using", ipt.cmd);
|
info!("{}: creating DIPLONAT chain", ipt.cmd);
|
||||||
ipt.new_chain("filter", "DIPLONAT")
|
ipt.new_chain("filter", "DIPLONAT")
|
||||||
.context("Failed to create new chain")?;
|
.context("Failed to create new chain")?;
|
||||||
ipt.insert_unique("filter", "INPUT", "-j DIPLONAT", 1)
|
ipt.insert_unique("filter", "INPUT", "-j DIPLONAT", 1)
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
use std::net::SocketAddrV4;
|
use std::net::{Ipv4Addr, SocketAddrV4};
|
||||||
|
|
||||||
use anyhow::{Context, Result};
|
use anyhow::{Context, Result};
|
||||||
use igd::{aio::*, PortMappingProtocol};
|
use igd::{aio::*, PortMappingProtocol};
|
||||||
|
@ -17,12 +17,12 @@ pub struct IgdActor {
|
||||||
gateway: Gateway,
|
gateway: Gateway,
|
||||||
refresh: Duration,
|
refresh: Duration,
|
||||||
expire: Duration,
|
expire: Duration,
|
||||||
private_ip: String,
|
private_ip: Ipv4Addr,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl IgdActor {
|
impl IgdActor {
|
||||||
pub async fn new(
|
pub async fn new(
|
||||||
priv_ip: Option<&str>,
|
priv_ip: Option<Ipv4Addr>,
|
||||||
refresh: Duration,
|
refresh: Duration,
|
||||||
expire: Duration,
|
expire: Duration,
|
||||||
rxp: &watch::Receiver<messages::PublicExposedPorts>,
|
rxp: &watch::Receiver<messages::PublicExposedPorts>,
|
||||||
|
@ -34,7 +34,7 @@ impl IgdActor {
|
||||||
|
|
||||||
let private_ip = if let Some(ip) = priv_ip {
|
let private_ip = if let Some(ip) = priv_ip {
|
||||||
info!("Using private IP from config: {}", ip);
|
info!("Using private IP from config: {}", ip);
|
||||||
ip.to_string()
|
ip
|
||||||
} else {
|
} else {
|
||||||
info!("Trying to automatically detect private IP");
|
info!("Trying to automatically detect private IP");
|
||||||
let gwa = gw.addr.ip().octets();
|
let gwa = gw.addr.ip().octets();
|
||||||
|
@ -47,18 +47,17 @@ impl IgdActor {
|
||||||
),
|
),
|
||||||
};
|
};
|
||||||
#[allow(unused_parens)]
|
#[allow(unused_parens)]
|
||||||
let public_ip = get_if_addrs::get_if_addrs()?
|
let private_ip = get_if_addrs::get_if_addrs()?
|
||||||
.into_iter()
|
.into_iter()
|
||||||
.map(|i| i.addr.ip())
|
.map(|i| i.addr.ip())
|
||||||
.filter(|a| match a {
|
.filter_map(|a| match a {
|
||||||
std::net::IpAddr::V4(a4) => (a4.octets()[..cmplen] == gwa[..cmplen]),
|
std::net::IpAddr::V4(a4) if a4.octets()[..cmplen] == gwa[..cmplen] => Some(a4),
|
||||||
_ => false,
|
_ => None,
|
||||||
})
|
})
|
||||||
.next()
|
.next()
|
||||||
.expect("No interface has an IP on same subnet as gateway")
|
.expect("No interface has an IP on same subnet as gateway");
|
||||||
.to_string();
|
info!("Autodetected private IP: {}", private_ip);
|
||||||
info!("Found private IP: {}", public_ip);
|
private_ip
|
||||||
public_ip
|
|
||||||
};
|
};
|
||||||
|
|
||||||
let ctx = Self {
|
let ctx = Self {
|
||||||
|
@ -104,10 +103,7 @@ impl IgdActor {
|
||||||
|
|
||||||
for (proto, list) in actions.iter() {
|
for (proto, list) in actions.iter() {
|
||||||
for port in *list {
|
for port in *list {
|
||||||
let service_str = format!("{}:{}", self.private_ip, port);
|
let service = SocketAddrV4::new(self.private_ip, *port);
|
||||||
let service = service_str
|
|
||||||
.parse::<SocketAddrV4>()
|
|
||||||
.context("Invalid socket address")?;
|
|
||||||
self.gateway
|
self.gateway
|
||||||
.add_port(
|
.add_port(
|
||||||
*proto,
|
*proto,
|
||||||
|
|
Loading…
Reference in a new issue