It ran. It did something. Yay.

This commit is contained in:
Adam Ierymenko 2022-06-16 17:53:52 -04:00
parent 564df37c1d
commit fd00642ec1
No known key found for this signature in database
GPG key ID: C8877CF2D7A5D7F3
9 changed files with 27 additions and 24 deletions

View file

@ -15,5 +15,3 @@ mod networkhypervisor;
pub use event::Event; pub use event::Event;
pub use networkhypervisor::{Interface, NetworkHypervisor}; pub use networkhypervisor::{Interface, NetworkHypervisor};
pub use vl1::protocol::{PacketBuffer, PooledPacketBuffer}; pub use vl1::protocol::{PacketBuffer, PooledPacketBuffer};
pub use async_trait::async_trait;

View file

@ -216,9 +216,7 @@ impl Identity {
/// ///
/// This is somewhat time consuming due to the memory-intensive work algorithm. /// This is somewhat time consuming due to the memory-intensive work algorithm.
pub fn validate_identity(&self) -> bool { pub fn validate_identity(&self) -> bool {
if self.p384.is_some() { if let Some(p384) = self.p384.as_ref() {
let p384 = self.p384.as_ref().unwrap();
let mut self_sign_buf: Vec<u8> = Vec::with_capacity(ADDRESS_SIZE + 4 + C25519_PUBLIC_KEY_SIZE + ED25519_PUBLIC_KEY_SIZE + P384_PUBLIC_KEY_SIZE + P384_PUBLIC_KEY_SIZE); let mut self_sign_buf: Vec<u8> = Vec::with_capacity(ADDRESS_SIZE + 4 + C25519_PUBLIC_KEY_SIZE + ED25519_PUBLIC_KEY_SIZE + P384_PUBLIC_KEY_SIZE + P384_PUBLIC_KEY_SIZE);
let _ = self_sign_buf.write_all(&self.address.to_bytes()); let _ = self_sign_buf.write_all(&self.address.to_bytes());
let _ = self_sign_buf.write_all(&self.c25519); let _ = self_sign_buf.write_all(&self.c25519);
@ -260,7 +258,7 @@ impl Identity {
/// Nothing actually uses a 512-bit secret directly, but if the base secret is 512 bits then /// Nothing actually uses a 512-bit secret directly, but if the base secret is 512 bits then
/// no entropy is lost when deriving smaller secrets with a KDF. /// no entropy is lost when deriving smaller secrets with a KDF.
pub fn agree(&self, other: &Identity) -> Option<Secret<64>> { pub fn agree(&self, other: &Identity) -> Option<Secret<64>> {
self.secret.as_ref().and_then(|secret| { if let Some(secret) = self.secret.as_ref() {
let c25519_secret = Secret(SHA512::hash(&secret.c25519.agree(&other.c25519).0)); let c25519_secret = Secret(SHA512::hash(&secret.c25519.agree(&other.c25519).0));
// FIPS note: FIPS-compliant exchange algorithms must be the last algorithms in any HKDF chain // FIPS note: FIPS-compliant exchange algorithms must be the last algorithms in any HKDF chain
@ -271,7 +269,9 @@ impl Identity {
} else { } else {
Some(c25519_secret) Some(c25519_secret)
} }
}) } else {
None
}
} }
/// Sign a message with this identity. /// Sign a message with this identity.
@ -281,8 +281,7 @@ impl Identity {
/// ///
/// A return of None happens if we don't have our secret key(s) or some other error occurs. /// A return of None happens if we don't have our secret key(s) or some other error occurs.
pub fn sign(&self, msg: &[u8], legacy_ed25519_only: bool) -> Option<Vec<u8>> { pub fn sign(&self, msg: &[u8], legacy_ed25519_only: bool) -> Option<Vec<u8>> {
if self.secret.is_some() { if let Some(secret) = self.secret.as_ref() {
let secret = self.secret.as_ref().unwrap();
if legacy_ed25519_only { if legacy_ed25519_only {
Some(secret.ed25519.sign_zt(msg).to_vec()) Some(secret.ed25519.sign_zt(msg).to_vec())
} else if let Some(p384s) = secret.p384.as_ref() { } else if let Some(p384s) = secret.p384.as_ref() {

View file

@ -438,11 +438,11 @@ impl<SI: SystemInterface> Peer<SI> {
pub(crate) async fn send_hello(&self, si: &SI, node: &Node<SI>, explicit_endpoint: Option<&Endpoint>) -> bool { pub(crate) async fn send_hello(&self, si: &SI, node: &Node<SI>, explicit_endpoint: Option<&Endpoint>) -> bool {
let mut path = None; let mut path = None;
let destination = if let Some(explicit_endpoint) = explicit_endpoint { let destination = if let Some(explicit_endpoint) = explicit_endpoint {
explicit_endpoint.clone() explicit_endpoint
} else { } else {
if let Some(p) = self.path(node) { if let Some(p) = self.path(node) {
let _ = path.insert(p); let _ = path.insert(p);
path.as_ref().unwrap().endpoint.clone() &path.as_ref().unwrap().endpoint
} else { } else {
return false; return false;
} }
@ -534,15 +534,15 @@ impl<SI: SystemInterface> Peer<SI> {
debug_event!(si, "HELLO -> {} @ {} ({} bytes)", self.identity.address.to_string(), destination.to_string(), packet.len()); debug_event!(si, "HELLO -> {} @ {} ({} bytes)", self.identity.address.to_string(), destination.to_string(), packet.len());
} }
if let Some(p) = path { if let Some(p) = path.as_ref() {
if self.internal_send(si, &destination, Some(&p.local_socket), Some(&p.local_interface), max_fragment_size, &packet).await { if self.internal_send(si, destination, Some(&p.local_socket), Some(&p.local_interface), max_fragment_size, &packet).await {
p.log_send_anything(time_ticks); p.log_send_anything(time_ticks);
true true
} else { } else {
false false
} }
} else { } else {
self.internal_send(si, &destination, None, None, max_fragment_size, &packet).await self.internal_send(si, destination, None, None, max_fragment_size, &packet).await
} }
} }

View file

@ -176,7 +176,7 @@ impl RootSet {
/// All current members must sign whether they are disabled (witnessing) or active. The verify() /// All current members must sign whether they are disabled (witnessing) or active. The verify()
/// method will return true when signing is complete. /// method will return true when signing is complete.
pub fn sign(&mut self, member_identity: &Identity) -> bool { pub fn sign(&mut self, member_identity: &Identity) -> bool {
let signature = member_identity.sign(self.marshal_for_signing().as_bytes(), Identity::ALGORITHM_ALL, false); let signature = member_identity.sign(self.marshal_for_signing().as_bytes(), false);
let unsigned_entry = self.members.iter().find_map(|m| if m.identity.eq(member_identity) { Some(m.clone()) } else { None }); let unsigned_entry = self.members.iter().find_map(|m| if m.identity.eq(member_identity) { Some(m.clone()) } else { None });
if unsigned_entry.is_some() && signature.is_some() { if unsigned_entry.is_some() && signature.is_some() {
let unsigned_entry = unsigned_entry.unwrap(); let unsigned_entry = unsigned_entry.unwrap();

View file

@ -1056,6 +1056,7 @@ dependencies = [
name = "zerotier-system-service" name = "zerotier-system-service"
version = "0.1.0" version = "0.1.0"
dependencies = [ dependencies = [
"async-trait",
"clap", "clap",
"lazy_static", "lazy_static",
"libc", "libc",

View file

@ -14,6 +14,7 @@ panic = 'abort'
[dependencies] [dependencies]
zerotier-network-hypervisor = { path = "../zerotier-network-hypervisor" } zerotier-network-hypervisor = { path = "../zerotier-network-hypervisor" }
zerotier-core-crypto = { path = "../zerotier-core-crypto" } zerotier-core-crypto = { path = "../zerotier-core-crypto" }
async-trait = "^0"
num-traits = "^0" num-traits = "^0"
tokio = { version = "^1", features = ["full"], default-features = false } tokio = { version = "^1", features = ["full"], default-features = false }
serde = { version = "^1", features = ["derive"], default-features = false } serde = { version = "^1", features = ["derive"], default-features = false }

View file

@ -6,7 +6,8 @@ use std::path::Path;
use std::sync::atomic::{AtomicUsize, Ordering}; use std::sync::atomic::{AtomicUsize, Ordering};
use std::sync::Arc; use std::sync::Arc;
use zerotier_network_hypervisor::async_trait; use async_trait::async_trait;
use zerotier_network_hypervisor::vl1::*; use zerotier_network_hypervisor::vl1::*;
use zerotier_network_hypervisor::vl2::*; use zerotier_network_hypervisor::vl2::*;
use zerotier_network_hypervisor::*; use zerotier_network_hypervisor::*;

View file

@ -39,7 +39,8 @@ pub fn get_l2_multicast_subscriptions(dev: &str) -> HashSet<MAC> {
let la: &libc::sockaddr_dl = &*((*i).ifma_addr.cast()); let la: &libc::sockaddr_dl = &*((*i).ifma_addr.cast());
if la.sdl_alen == 6 && in_.sdl_nlen <= dev.len().as_() && libc::memcmp(dev.as_ptr().cast(), in_.sdl_data.as_ptr().cast(), in_.sdl_nlen.as_()) == 0 { if la.sdl_alen == 6 && in_.sdl_nlen <= dev.len().as_() && libc::memcmp(dev.as_ptr().cast(), in_.sdl_data.as_ptr().cast(), in_.sdl_nlen.as_()) == 0 {
let mi = la.sdl_nlen as usize; let mi = la.sdl_nlen as usize;
MAC::from_u64((la.sdl_data[mi] as u64) << 40 | (la.sdl_data[mi + 1] as u64) << 32 | (la.sdl_data[mi + 2] as u64) << 24 | (la.sdl_data[mi + 3] as u64) << 16 | (la.sdl_data[mi + 4] as u64) << 8 | la.sdl_data[mi + 5] as u64).map(|mac| groups.insert(mac)); MAC::from_u64((la.sdl_data[mi] as u64) << 40 | (la.sdl_data[mi + 1] as u64) << 32 | (la.sdl_data[mi + 2] as u64) << 24 | (la.sdl_data[mi + 3] as u64) << 16 | (la.sdl_data[mi + 4] as u64) << 8 | la.sdl_data[mi + 5] as u64)
.map(|mac| groups.insert(mac));
} }
} }
i = (*i).ifma_next; i = (*i).ifma_next;
@ -53,6 +54,5 @@ pub fn get_l2_multicast_subscriptions(dev: &str) -> HashSet<MAC> {
/// Linux stores this stuff in /proc and it needs to be fetched from there. /// Linux stores this stuff in /proc and it needs to be fetched from there.
#[cfg(target_os = "linux")] #[cfg(target_os = "linux")]
pub fn get_l2_multicast_subscriptions(dev: &str) -> HashSet<MAC> { pub fn get_l2_multicast_subscriptions(dev: &str) -> HashSet<MAC> {
let mut groups: HashSet<MAC> = HashSet::new(); todo!()
groups
} }

View file

@ -1,19 +1,22 @@
// (c) 2020-2022 ZeroTier, Inc. -- currently propritery pending actual release and licensing. See LICENSE.md. // (c) 2020-2022 ZeroTier, Inc. -- currently propritery pending actual release and licensing. See LICENSE.md.
use async_trait::async_trait;
use zerotier_network_hypervisor::vl1::{InetAddress, MAC}; use zerotier_network_hypervisor::vl1::{InetAddress, MAC};
use zerotier_network_hypervisor::vl2::MulticastGroup; use zerotier_network_hypervisor::vl2::MulticastGroup;
/// Virtual network interface /// Virtual network interface
#[async_trait]
pub trait VNIC { pub trait VNIC {
/// Add a new IPv4 or IPv6 address to this interface, returning true on success. /// Add a new IPv4 or IPv6 address to this interface, returning true on success.
fn add_ip(&self, ip: &InetAddress) -> bool; async fn add_ip(&self, ip: &InetAddress) -> bool;
/// Remove an IPv4 or IPv6 address, returning true on success. /// Remove an IPv4 or IPv6 address, returning true on success.
/// Nothing happens if the address is not found. /// Nothing happens if the address is not found.
fn remove_ip(&self, ip: &InetAddress) -> bool; async fn remove_ip(&self, ip: &InetAddress) -> bool;
/// Enumerate all IPs on this interface including ones assigned outside ZeroTier. /// Enumerate all IPs on this interface including ones assigned outside ZeroTier.
fn ips(&self) -> Vec<InetAddress>; async fn ips(&self) -> Vec<InetAddress>;
/// Get the OS-specific device name for this interface, e.g. zt## or tap##. /// Get the OS-specific device name for this interface, e.g. zt## or tap##.
fn device_name(&self) -> String; fn device_name(&self) -> String;
@ -22,8 +25,8 @@ pub trait VNIC {
/// This doesn't do any IGMP snooping. It just reports the groups the port /// This doesn't do any IGMP snooping. It just reports the groups the port
/// knows about. On some OSes this may not be supported in which case it /// knows about. On some OSes this may not be supported in which case it
/// will return an empty set. /// will return an empty set.
fn get_multicast_groups(&self) -> std::collections::BTreeSet<MulticastGroup>; async fn get_multicast_groups(&self) -> std::collections::BTreeSet<MulticastGroup>;
/// Inject an Ethernet frame into this port. /// Inject an Ethernet frame into this port.
fn put(&self, source_mac: &MAC, dest_mac: &MAC, ethertype: u16, vlan_id: u16, data: *const u8, len: usize) -> bool; async fn put(&self, source_mac: &MAC, dest_mac: &MAC, ethertype: u16, vlan_id: u16, data: &[u8]) -> bool;
} }