net: add support for dhcp hostname option.
This commit is contained in:
parent
f30fc949ff
commit
534eb960e9
3 changed files with 46 additions and 1 deletions
2
ci.sh
2
ci.sh
|
@ -36,7 +36,7 @@ cargo batch \
|
||||||
--- build --release --manifest-path embassy-time/Cargo.toml --target thumbv6m-none-eabi --features nightly,defmt,defmt-timestamp-uptime,tick-hz-32_768,generic-queue-8 \
|
--- build --release --manifest-path embassy-time/Cargo.toml --target thumbv6m-none-eabi --features nightly,defmt,defmt-timestamp-uptime,tick-hz-32_768,generic-queue-8 \
|
||||||
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv4,medium-ethernet \
|
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv4,medium-ethernet \
|
||||||
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,dhcpv4,medium-ethernet \
|
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,dhcpv4,medium-ethernet \
|
||||||
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,dhcpv4,medium-ethernet,nightly \
|
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,dhcpv4,medium-ethernet,nightly,dhcpv4-hostname \
|
||||||
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv6,medium-ethernet \
|
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv6,medium-ethernet \
|
||||||
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv6,medium-ieee802154 \
|
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv6,medium-ieee802154 \
|
||||||
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv6,medium-ethernet,medium-ieee802154 \
|
--- build --release --manifest-path embassy-net/Cargo.toml --target thumbv7em-none-eabi --features defmt,tcp,udp,dns,proto-ipv6,medium-ethernet,medium-ieee802154 \
|
||||||
|
|
|
@ -33,6 +33,7 @@ udp = ["smoltcp/socket-udp"]
|
||||||
tcp = ["smoltcp/socket-tcp"]
|
tcp = ["smoltcp/socket-tcp"]
|
||||||
dns = ["smoltcp/socket-dns", "smoltcp/proto-dns"]
|
dns = ["smoltcp/socket-dns", "smoltcp/proto-dns"]
|
||||||
dhcpv4 = ["proto-ipv4", "medium-ethernet", "smoltcp/socket-dhcpv4"]
|
dhcpv4 = ["proto-ipv4", "medium-ethernet", "smoltcp/socket-dhcpv4"]
|
||||||
|
dhcpv4-hostname = ["dhcpv4"]
|
||||||
proto-ipv4 = ["smoltcp/proto-ipv4"]
|
proto-ipv4 = ["smoltcp/proto-ipv4"]
|
||||||
proto-ipv6 = ["smoltcp/proto-ipv6"]
|
proto-ipv6 = ["smoltcp/proto-ipv6"]
|
||||||
medium-ethernet = ["smoltcp/medium-ethernet"]
|
medium-ethernet = ["smoltcp/medium-ethernet"]
|
||||||
|
|
|
@ -56,12 +56,22 @@ const LOCAL_PORT_MIN: u16 = 1025;
|
||||||
const LOCAL_PORT_MAX: u16 = 65535;
|
const LOCAL_PORT_MAX: u16 = 65535;
|
||||||
#[cfg(feature = "dns")]
|
#[cfg(feature = "dns")]
|
||||||
const MAX_QUERIES: usize = 4;
|
const MAX_QUERIES: usize = 4;
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
const MAX_HOSTNAME_LEN: usize = 32;
|
||||||
|
|
||||||
/// Memory resources needed for a network stack.
|
/// Memory resources needed for a network stack.
|
||||||
pub struct StackResources<const SOCK: usize> {
|
pub struct StackResources<const SOCK: usize> {
|
||||||
sockets: [SocketStorage<'static>; SOCK],
|
sockets: [SocketStorage<'static>; SOCK],
|
||||||
#[cfg(feature = "dns")]
|
#[cfg(feature = "dns")]
|
||||||
queries: [Option<dns::DnsQuery>; MAX_QUERIES],
|
queries: [Option<dns::DnsQuery>; MAX_QUERIES],
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
hostname: core::cell::UnsafeCell<HostnameResources>,
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
struct HostnameResources {
|
||||||
|
option: smoltcp::wire::DhcpOption<'static>,
|
||||||
|
data: [u8; MAX_HOSTNAME_LEN],
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<const SOCK: usize> StackResources<SOCK> {
|
impl<const SOCK: usize> StackResources<SOCK> {
|
||||||
|
@ -73,6 +83,11 @@ impl<const SOCK: usize> StackResources<SOCK> {
|
||||||
sockets: [SocketStorage::EMPTY; SOCK],
|
sockets: [SocketStorage::EMPTY; SOCK],
|
||||||
#[cfg(feature = "dns")]
|
#[cfg(feature = "dns")]
|
||||||
queries: [INIT; MAX_QUERIES],
|
queries: [INIT; MAX_QUERIES],
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
hostname: core::cell::UnsafeCell::new(HostnameResources {
|
||||||
|
option: smoltcp::wire::DhcpOption { kind: 0, data: &[] },
|
||||||
|
data: [0; MAX_HOSTNAME_LEN],
|
||||||
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -104,6 +119,7 @@ pub struct StaticConfigV6 {
|
||||||
/// DHCP configuration.
|
/// DHCP configuration.
|
||||||
#[cfg(feature = "dhcpv4")]
|
#[cfg(feature = "dhcpv4")]
|
||||||
#[derive(Debug, Clone, PartialEq, Eq)]
|
#[derive(Debug, Clone, PartialEq, Eq)]
|
||||||
|
#[non_exhaustive]
|
||||||
pub struct DhcpConfig {
|
pub struct DhcpConfig {
|
||||||
/// Maximum lease duration.
|
/// Maximum lease duration.
|
||||||
///
|
///
|
||||||
|
@ -120,6 +136,9 @@ pub struct DhcpConfig {
|
||||||
pub server_port: u16,
|
pub server_port: u16,
|
||||||
/// Client port. This is almost always 68. Do not change unless you know what you're doing.
|
/// Client port. This is almost always 68. Do not change unless you know what you're doing.
|
||||||
pub client_port: u16,
|
pub client_port: u16,
|
||||||
|
/// Our hostname. This will be sent to the DHCP server as Option 12.
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
pub hostname: Option<heapless::String<MAX_HOSTNAME_LEN>>,
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(feature = "dhcpv4")]
|
#[cfg(feature = "dhcpv4")]
|
||||||
|
@ -131,6 +150,8 @@ impl Default for DhcpConfig {
|
||||||
ignore_naks: Default::default(),
|
ignore_naks: Default::default(),
|
||||||
server_port: smoltcp::wire::DHCP_SERVER_PORT,
|
server_port: smoltcp::wire::DHCP_SERVER_PORT,
|
||||||
client_port: smoltcp::wire::DHCP_CLIENT_PORT,
|
client_port: smoltcp::wire::DHCP_CLIENT_PORT,
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
hostname: None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -232,6 +253,8 @@ struct Inner<D: Driver> {
|
||||||
dns_socket: SocketHandle,
|
dns_socket: SocketHandle,
|
||||||
#[cfg(feature = "dns")]
|
#[cfg(feature = "dns")]
|
||||||
dns_waker: WakerRegistration,
|
dns_waker: WakerRegistration,
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
hostname: &'static mut core::cell::UnsafeCell<HostnameResources>,
|
||||||
}
|
}
|
||||||
|
|
||||||
pub(crate) struct SocketStack {
|
pub(crate) struct SocketStack {
|
||||||
|
@ -307,6 +330,8 @@ impl<D: Driver> Stack<D> {
|
||||||
)),
|
)),
|
||||||
#[cfg(feature = "dns")]
|
#[cfg(feature = "dns")]
|
||||||
dns_waker: WakerRegistration::new(),
|
dns_waker: WakerRegistration::new(),
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
hostname: &mut resources.hostname,
|
||||||
};
|
};
|
||||||
|
|
||||||
#[cfg(feature = "proto-ipv4")]
|
#[cfg(feature = "proto-ipv4")]
|
||||||
|
@ -673,6 +698,25 @@ impl<D: Driver> Inner<D> {
|
||||||
socket.set_max_lease_duration(c.max_lease_duration.map(crate::time::duration_to_smoltcp));
|
socket.set_max_lease_duration(c.max_lease_duration.map(crate::time::duration_to_smoltcp));
|
||||||
socket.set_ports(c.server_port, c.client_port);
|
socket.set_ports(c.server_port, c.client_port);
|
||||||
socket.set_retry_config(c.retry_config);
|
socket.set_retry_config(c.retry_config);
|
||||||
|
|
||||||
|
socket.set_outgoing_options(&[]);
|
||||||
|
#[cfg(feature = "dhcpv4-hostname")]
|
||||||
|
if let Some(h) = c.hostname {
|
||||||
|
// safety: we just did set_outgoing_options([]) so we know the socket is no longer holding a reference.
|
||||||
|
let hostname = unsafe { &mut *self.hostname.get() };
|
||||||
|
|
||||||
|
// create data
|
||||||
|
// safety: we know the buffer lives forever, new borrows the StackResources for 'static.
|
||||||
|
// also we won't modify it until next call to this function.
|
||||||
|
hostname.data[..h.len()].copy_from_slice(h.as_bytes());
|
||||||
|
let data: &[u8] = &hostname.data[..h.len()];
|
||||||
|
let data: &'static [u8] = unsafe { core::mem::transmute(data) };
|
||||||
|
|
||||||
|
// set the option.
|
||||||
|
hostname.option = smoltcp::wire::DhcpOption { data, kind: 12 };
|
||||||
|
socket.set_outgoing_options(core::slice::from_ref(&hostname.option));
|
||||||
|
}
|
||||||
|
|
||||||
socket.reset();
|
socket.reset();
|
||||||
}
|
}
|
||||||
_ => {
|
_ => {
|
||||||
|
|
Loading…
Reference in a new issue