Skip to content

Commit

Permalink
register service: apply interface selection for auto IP addr (#262)
Browse files Browse the repository at this point in the history
* Error log: log the actual invalid hostname
  • Loading branch information
keepsimple1 authored Oct 11, 2024
1 parent 0381e30 commit f902cf2
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 11 deletions.
12 changes: 11 additions & 1 deletion examples/register.rs
Original file line number Diff line number Diff line change
Expand Up @@ -10,8 +10,9 @@
//!
//! Options:
//! "--unregister": automatically unregister after 2 seconds.
//! "--disable-ipv6": not to use IPv6 interfaces.

use mdns_sd::{DaemonEvent, ServiceDaemon, ServiceInfo};
use mdns_sd::{DaemonEvent, IfKind, ServiceDaemon, ServiceInfo};
use std::{env, thread, time::Duration};

fn main() {
Expand All @@ -20,14 +21,23 @@ fn main() {
// Simple command line options.
let args: Vec<String> = env::args().collect();
let mut should_unreg = false;
let mut disable_ipv6 = false;

for arg in args.iter() {
if arg.as_str() == "--unregister" {
should_unreg = true
} else if arg.as_str() == "--disable-ipv6" {
disable_ipv6 = true
}
}

// Create a new mDNS daemon.
let mdns = ServiceDaemon::new().expect("Could not create service daemon");

if disable_ipv6 {
mdns.disable_interface(IfKind::IPv6).unwrap();
}

let service_type = match args.get(1) {
Some(arg) => format!("{}.local.", arg),
None => {
Expand Down
47 changes: 37 additions & 10 deletions src/service_daemon.rs
Original file line number Diff line number Diff line change
Expand Up @@ -285,16 +285,10 @@ impl ServiceDaemon {
///
/// To re-announce a service with an updated `service_info`, just call
/// this `register` function again. No need to call `unregister` first.
pub fn register(&self, mut service_info: ServiceInfo) -> Result<()> {
pub fn register(&self, service_info: ServiceInfo) -> Result<()> {
check_service_name(service_info.get_fullname())?;
check_hostname(service_info.get_hostname())?;

if service_info.is_addr_auto() {
for iface in my_ip_interfaces() {
service_info.insert_ipaddr(iface.ip());
}
}

self.send_cmd(Command::Register(service_info))
}

Expand Down Expand Up @@ -624,7 +618,6 @@ impl ServiceDaemon {
}

Command::Register(service_info) => {
debug!("register service {:?}", &service_info);
zc.register_service(service_info);
zc.increase_counter(Counter::Register, 1);
}
Expand Down Expand Up @@ -1081,6 +1074,31 @@ impl Zeroconf {
self.timers.pop().map(|Reverse(v)| v)
}

/// Apply all selections to `interfaces` and return the selected addresses.
fn selected_addrs(&self, interfaces: Vec<Interface>) -> HashSet<IpAddr> {
let intf_count = interfaces.len();
let mut intf_selections = vec![true; intf_count];

// apply if_selections
for selection in self.if_selections.iter() {
// Mark the interfaces for this selection.
for i in 0..intf_count {
if selection.if_kind.matches(&interfaces[i]) {
intf_selections[i] = selection.selected;
}
}
}

let mut selected_addrs = HashSet::new();
for i in 0..intf_count {
if intf_selections[i] {
selected_addrs.insert(interfaces[i].addr.ip());
}
}

selected_addrs
}

/// Apply all selections to `interfaces`.
///
/// For any interface, add it if selected but not bound yet,
Expand Down Expand Up @@ -1192,14 +1210,23 @@ impl Zeroconf {
/// Section, all of its newly registered resource records
///
/// Zeroconf will then respond to requests for information about this service.
fn register_service(&mut self, info: ServiceInfo) {
fn register_service(&mut self, mut info: ServiceInfo) {
// Check the service name length.
if let Err(e) = check_service_name_length(info.get_type(), self.service_name_len_max) {
error!("check_service_name_length: {}", &e);
self.notify_monitors(DaemonEvent::Error(e));
return;
}

if info.is_addr_auto() {
let selected_addrs = self.selected_addrs(my_ip_interfaces());
for addr in selected_addrs {
info.insert_ipaddr(addr);
}
}

debug!("register service {:?}", &info);

let outgoing_addrs = self.send_unsolicited_response(&info);
if !outgoing_addrs.is_empty() {
self.notify_monitors(DaemonEvent::Announce(
Expand Down Expand Up @@ -2483,7 +2510,7 @@ fn check_service_name(fullname: &str) -> Result<()> {
/// Validate a hostname.
fn check_hostname(hostname: &str) -> Result<()> {
if !hostname.ends_with(".local.") {
return Err(e_fmt!("Hostname must end with '.local.'"));
return Err(e_fmt!("Hostname must end with '.local.': {hostname}"));
}

if hostname == ".local." {
Expand Down

0 comments on commit f902cf2

Please sign in to comment.