diff --git a/.github/ansible/redeploy-derper.yml b/.github/ansible/redeploy-relay.yml similarity index 75% rename from .github/ansible/redeploy-derper.yml rename to .github/ansible/redeploy-relay.yml index 0c3f5dc79b..8863aa9c7c 100644 --- a/.github/ansible/redeploy-derper.yml +++ b/.github/ansible/redeploy-relay.yml @@ -1,10 +1,10 @@ --- -- name: Update derper node +- name: Update iroh-relay node hosts: derper become: yes tasks: - - name: Fetch derper binary + - name: Fetch iroh-relay binary get_url: url: https://vorc.s3.us-east-2.amazonaws.com/derper-linux-amd64-{{ derper_version }} mode: '0755' @@ -13,8 +13,8 @@ - name: Allow ports shell: cmd: sudo setcap CAP_NET_BIND_SERVICE=+eip /usr/local/bin/derper - - name: Make sure derper is started + - name: Make sure iroh-relay is started ansible.builtin.systemd: state: restarted enabled: yes - name: derper \ No newline at end of file + name: derper diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 129f5c95c7..5c5e7aa231 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -192,7 +192,7 @@ jobs: - name: Copy binaries to right location run: | cp target/release/iroh ../chuck/netsim/bins/iroh - cp target/release/derper ../chuck/netsim/bins/derper + cp target/release/iroh-relay ../chuck/netsim/bins/derper cp ../chuck/target/release/chuck ../chuck/netsim/bins/chuck - name: Run tests diff --git a/.github/workflows/netsim.yml b/.github/workflows/netsim.yml index cab1dbdc15..3e7d660443 100644 --- a/.github/workflows/netsim.yml +++ b/.github/workflows/netsim.yml @@ -97,7 +97,7 @@ jobs: - name: Copy binaries to right location run: | cp target/optimized-release/iroh ../chuck/netsim/bins/iroh - cp target/optimized-release/derper ../chuck/netsim/bins/derper + cp target/optimized-release/iroh-relay ../chuck/netsim/bins/derper cp ../chuck/target/release/chuck ../chuck/netsim/bins/chuck - name: Detect comment commands diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 07c6351121..f6ac856dde 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -127,10 +127,10 @@ jobs: if: matrix.os != 'windows-latest' run: | aws s3 cp ./target/optimized-release/iroh s3://vorc/iroh-${RELEASE_OS}-${RELEASE_ARCH}-${GITHUB_SHA::7} --no-progress - aws s3 cp ./target/optimized-release/derper s3://vorc/derper-${RELEASE_OS}-${RELEASE_ARCH}-${GITHUB_SHA::7} --no-progress + aws s3 cp ./target/optimized-release/iroh-relay s3://vorc/derper-${RELEASE_OS}-${RELEASE_ARCH}-${GITHUB_SHA::7} --no-progress - name: push release latest if: matrix.os != 'windows-latest' run: | aws s3 cp ./target/optimized-release/iroh s3://vorc/iroh-${RELEASE_OS}-${RELEASE_ARCH}-latest --no-progress - aws s3 cp ./target/optimized-release/derper s3://vorc/derper-${RELEASE_OS}-${RELEASE_ARCH}-latest --no-progress + aws s3 cp ./target/optimized-release/iroh-relay s3://vorc/derper-${RELEASE_OS}-${RELEASE_ARCH}-latest --no-progress diff --git a/.github/workflows/test_derper.yml b/.github/workflows/test_relay_server.yml similarity index 83% rename from .github/workflows/test_derper.yml rename to .github/workflows/test_relay_server.yml index 31c27a0807..257fc9a300 100644 --- a/.github/workflows/test_derper.yml +++ b/.github/workflows/test_relay_server.yml @@ -1,4 +1,4 @@ -name: Deploy Test Derper +name: Deploy Test Relay Server on: workflow_dispatch: @@ -6,7 +6,7 @@ on: - cron: '0 4 * * *' concurrency: - group: derper-${{ github.workflow }}-${{ github.ref }} + group: relay-${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true env: @@ -17,7 +17,7 @@ env: SCCACHE_CACHE_SIZE: "50G" jobs: - build_derper: + build_relay_server: runs-on: [self-hosted, linux, X64] if: github.ref_name=='main' env: @@ -35,7 +35,7 @@ jobs: - name: build release run: | - cargo build --release --all-features --bin derper + cargo build --release --all-features --bin iroh-relay - name: Setup awscli on linux run: | @@ -50,24 +50,24 @@ jobs: - name: push release run: | - aws s3 cp ./target/release/derper s3://vorc/derper-linux-amd64-${GITHUB_SHA::7} --no-progress + aws s3 cp ./target/release/iroh-relay s3://vorc/derper-linux-amd64-${GITHUB_SHA::7} --no-progress - - name: Set derper tag + - name: Set iroh-relay tag id: set_tag run: | echo ::set-output name=tag::${GITHUB_SHA::7} - deploy_derper: + deploy_iroh-relay: runs-on: ubuntu-latest if: github.ref_name=='main' - needs: build_derper + needs: build_relay_server steps: - uses: actions/checkout@v4 - name: Run Staging Deploy Playbook uses: arqu/action-ansible-playbook@master with: - playbook: redeploy-derper.yml + playbook: redeploy-relay.yml directory: .github/ansible key: ${{ secrets.TEST_DERPER_SSH_PKEY }} inventory: ${{ secrets.TEST_DERPER_INVENTORY }} diff --git a/iroh-base/src/node_addr.rs b/iroh-base/src/node_addr.rs index c696bd86c6..bf54e1293e 100644 --- a/iroh-base/src/node_addr.rs +++ b/iroh-base/src/node_addr.rs @@ -24,9 +24,9 @@ impl NodeAddr { } } - /// Add a derp url to the peer's [`AddrInfo`]. - pub fn with_derp_url(mut self, derp_url: DerpUrl) -> Self { - self.info.derp_url = Some(derp_url); + /// Add a relay url to the peer's [`AddrInfo`]. + pub fn with_relay_url(mut self, relay_url: RelayUrl) -> Self { + self.info.relay_url = Some(relay_url); self } @@ -44,19 +44,19 @@ impl NodeAddr { self.info.direct_addresses.iter() } - /// Get the derp url of this peer. - pub fn derp_url(&self) -> Option<&DerpUrl> { - self.info.derp_url.as_ref() + /// Get the relay url of this peer. + pub fn relay_url(&self) -> Option<&RelayUrl> { + self.info.relay_url.as_ref() } } -impl From<(PublicKey, Option, &[SocketAddr])> for NodeAddr { - fn from(value: (PublicKey, Option, &[SocketAddr])) -> Self { - let (node_id, derp_url, direct_addresses_iter) = value; +impl From<(PublicKey, Option, &[SocketAddr])> for NodeAddr { + fn from(value: (PublicKey, Option, &[SocketAddr])) -> Self { + let (node_id, relay_url, direct_addresses_iter) = value; NodeAddr { node_id, info: AddrInfo { - derp_url, + relay_url, direct_addresses: direct_addresses_iter.iter().copied().collect(), }, } @@ -66,8 +66,8 @@ impl From<(PublicKey, Option, &[SocketAddr])> for NodeAddr { /// Addressing information to connect to a peer. #[derive(Debug, Clone, Serialize, Deserialize, PartialEq, Eq, Default)] pub struct AddrInfo { - /// The peer's home DERP url. - pub derp_url: Option, + /// The peer's home relay url. + pub relay_url: Option, /// Socket addresses where the peer might be reached directly. pub direct_addresses: BTreeSet, } @@ -75,7 +75,7 @@ pub struct AddrInfo { impl AddrInfo { /// Return whether this addressing information is empty. pub fn is_empty(&self) -> bool { - self.derp_url.is_none() && self.direct_addresses.is_empty() + self.relay_url.is_none() && self.direct_addresses.is_empty() } } @@ -83,43 +83,43 @@ impl NodeAddr { /// Create a new [`NodeAddr`] from its parts. pub fn from_parts( node_id: PublicKey, - derp_url: Option, + relay_url: Option, direct_addresses: Vec, ) -> Self { Self { node_id, info: AddrInfo { - derp_url, + relay_url, direct_addresses: direct_addresses.into_iter().collect(), }, } } } -/// A URL identifying a DERP server. +/// A URL identifying a relay server. /// /// This is but a wrapper around [`Url`], with a few custom tweaks: /// -/// - A DERP URL is never a relative URL, so an implicit `.` is added at the end of the +/// - A relay URL is never a relative URL, so an implicit `.` is added at the end of the /// domain name if missing. /// /// - [`fmt::Debug`] is implemented so it prints the URL rather than the URL struct fields. -/// Useful when logging e.g. `Option`. +/// Useful when logging e.g. `Option`. /// -/// To create a [`DerpUrl`] use the `From` implementation. +/// To create a [`RelayUrl`] use the `From` implementation. #[derive( Clone, derive_more::Display, PartialEq, Eq, PartialOrd, Ord, Hash, Serialize, Deserialize, )] -pub struct DerpUrl(Url); +pub struct RelayUrl(Url); -impl From for DerpUrl { +impl From for RelayUrl { fn from(mut url: Url) -> Self { if let Some(domain) = url.domain() { if !domain.ends_with('.') { let domain = String::from(domain) + "."; // This can fail, though it is unlikely the resulting URL is usable as a - // DERP URL, probably it has the wrong scheme or is not a base URL or the + // relay URL, probably it has the wrong scheme or is not a base URL or the // like. We don't do full URL validation however, so just silently leave // this bad URL in place. Something will fail later. url.set_host(Some(&domain)).ok(); @@ -131,14 +131,14 @@ impl From for DerpUrl { /// This is a convenience only to directly parse strings. /// -/// If you need more control over the error first create a [`Url`] and use [`DerpUrl::from`] +/// If you need more control over the error first create a [`Url`] and use [`RelayUrl::from`] /// instead. -impl FromStr for DerpUrl { +impl FromStr for RelayUrl { type Err = anyhow::Error; fn from_str(s: &str) -> Result { let inner = Url::from_str(s).context("invalid URL")?; - Ok(DerpUrl::from(inner)) + Ok(RelayUrl::from(inner)) } } @@ -148,7 +148,7 @@ impl FromStr for DerpUrl { /// to change the inner later. /// /// [`DerefMut`]: std::ops::DerefMut -impl Deref for DerpUrl { +impl Deref for RelayUrl { type Target = Url; fn deref(&self) -> &Self::Target { @@ -156,9 +156,9 @@ impl Deref for DerpUrl { } } -impl fmt::Debug for DerpUrl { +impl fmt::Debug for RelayUrl { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { - f.debug_tuple("DerpUrl") + f.debug_tuple("RelayUrl") .field(&DbgStr(self.0.as_str())) .finish() } @@ -182,27 +182,27 @@ mod tests { use super::*; #[test] - fn test_derp_url_debug_display() { - let url = DerpUrl::from(Url::parse("https://example.com").unwrap()); + fn test_relay_url_debug_display() { + let url = RelayUrl::from(Url::parse("https://example.com").unwrap()); - assert_eq!(format!("{url:?}"), r#"DerpUrl("https://example.com./")"#); + assert_eq!(format!("{url:?}"), r#"RelayUrl("https://example.com./")"#); assert_eq!(format!("{url}"), "https://example.com./"); } #[test] - fn test_derp_url_absolute() { - let url = DerpUrl::from(Url::parse("https://example.com").unwrap()); + fn test_relay_url_absolute() { + let url = RelayUrl::from(Url::parse("https://example.com").unwrap()); assert_eq!(url.domain(), Some("example.com.")); - let url1 = DerpUrl::from(Url::parse("https://example.com.").unwrap()); + let url1 = RelayUrl::from(Url::parse("https://example.com.").unwrap()); assert_eq!(url, url1); - let url2 = DerpUrl::from(Url::parse("https://example.com./").unwrap()); + let url2 = RelayUrl::from(Url::parse("https://example.com./").unwrap()); assert_eq!(url, url2); - let url3 = DerpUrl::from(Url::parse("https://example.com/").unwrap()); + let url3 = RelayUrl::from(Url::parse("https://example.com/").unwrap()); assert_eq!(url, url3); } } diff --git a/iroh-base/src/ticket/blob.rs b/iroh-base/src/ticket/blob.rs index 3a7356f90b..ecdc23ddc4 100644 --- a/iroh-base/src/ticket/blob.rs +++ b/iroh-base/src/ticket/blob.rs @@ -132,10 +132,10 @@ mod tests { let hash = Hash::new(b"hi there"); let peer = SecretKey::generate().public(); let addr = SocketAddr::from_str("127.0.0.1:1234").unwrap(); - let derp_url = None; + let relay_url = None; BlobTicket { hash, - node: NodeAddr::from_parts(peer, derp_url, vec![addr]), + node: NodeAddr::from_parts(peer, relay_url, vec![addr]), format: BlobFormat::HashSeq, } } @@ -174,7 +174,7 @@ mod tests { let expected = parse_hexdump(" 00 # discriminator for variant 0 ae58ff8833241ac82d6ff7611046ed67b5072d142c588d0063e942d9a75502b6 # node id, 32 bytes, see above - 00 # derp url + 00 # relay url 00 # number of addresses (0) 00 # format (raw) 0b84d358e4c8be6c38626b2182ff575818ba6bd3f4b90464994be14cb354a072 # hash, 32 bytes, see above diff --git a/iroh-base/src/ticket/node.rs b/iroh-base/src/ticket/node.rs index 27b04963c5..bc8d9b9eaa 100644 --- a/iroh-base/src/ticket/node.rs +++ b/iroh-base/src/ticket/node.rs @@ -101,9 +101,9 @@ mod tests { fn make_ticket() -> NodeTicket { let peer = SecretKey::generate().public(); let addr = SocketAddr::from((Ipv4Addr::LOCALHOST, 1234)); - let derp_url = None; + let relay_url = None; NodeTicket { - node: NodeAddr::from_parts(peer, derp_url, vec![addr]), + node: NodeAddr::from_parts(peer, relay_url, vec![addr]), } } @@ -140,8 +140,8 @@ mod tests { let expected = parse_hexdump(" 00 # variant ae58ff8833241ac82d6ff7611046ed67b5072d142c588d0063e942d9a75502b6 # node id, 32 bytes, see above - 01 # derp url present - 10 687474703a2f2f646572702e6d652e2f # derp url, 16 bytes, see above + 01 # relay url present + 10 687474703a2f2f646572702e6d652e2f # relay url, 16 bytes, see above 01 # one direct address 00 # ipv4 7f000001 8008 # address, see above diff --git a/iroh-bytes/src/store/bao_file.rs b/iroh-bytes/src/store/bao_file.rs index 5a2bccddee..f3578cd1c2 100644 --- a/iroh-bytes/src/store/bao_file.rs +++ b/iroh-bytes/src/store/bao_file.rs @@ -134,6 +134,7 @@ fn create_read_write(path: impl AsRef) -> io::Result { .read(true) .write(true) .create(true) + .truncate(false) .open(path) } diff --git a/iroh-bytes/src/store/file/util.rs b/iroh-bytes/src/store/file/util.rs index 4d6fd8ca2b..39dcd43ce9 100644 --- a/iroh-bytes/src/store/file/util.rs +++ b/iroh-bytes/src/store/file/util.rs @@ -49,7 +49,11 @@ pub fn overwrite_and_sync(path: &Path, data: &[u8]) -> io::Result // std::fs::create_dir_all(path.parent().unwrap()).unwrap(); // tracing::error!("{}", path.parent().unwrap().display()); // tracing::error!("{}", path.parent().unwrap().metadata().unwrap().is_dir()); - let mut file = OpenOptions::new().write(true).create(true).open(path)?; + let mut file = OpenOptions::new() + .write(true) + .create(true) + .truncate(false) + .open(path)?; file.write_all(data)?; // todo: figure out if it is safe to not sync here file.sync_all()?; diff --git a/iroh-cli/src/commands.rs b/iroh-cli/src/commands.rs index 447598005d..eba273bb37 100644 --- a/iroh-cli/src/commands.rs +++ b/iroh-cli/src/commands.rs @@ -75,7 +75,7 @@ pub(crate) enum Commands { #[clap(flatten)] Rpc(#[clap(subcommand)] RpcCommands), - /// Diagnostic commands for the derp relay protocol. + /// Diagnostic commands for the relay protocol. Doctor { /// Commands for doctor - defined in the mod #[clap(subcommand)] diff --git a/iroh-cli/src/commands/blob.rs b/iroh-cli/src/commands/blob.rs index 9f850357e6..d68e7525a8 100644 --- a/iroh-cli/src/commands/blob.rs +++ b/iroh-cli/src/commands/blob.rs @@ -19,7 +19,7 @@ use iroh::bytes::{ store::{ValidateLevel, ValidateProgress}, BlobFormat, Hash, HashAndFormat, Tag, }; -use iroh::net::{derp::DerpUrl, key::PublicKey, NodeAddr}; +use iroh::net::{key::PublicKey, relay::RelayUrl, NodeAddr}; use iroh::{ client::{BlobStatus, Iroh, ShareTicketOptions}, rpc_protocol::{ @@ -55,9 +55,9 @@ pub enum BlobCommands { /// Additional socket address to use to contact the node. Can be used multiple times. #[clap(long)] address: Vec, - /// Override the Derp URL to use to contact the node. + /// Override the relay URL to use to contact the node. #[clap(long)] - derp_url: Option, + relay_url: Option, /// Override to treat the blob as a raw blob or a hash sequence. #[clap(long)] recursive: Option, @@ -106,7 +106,7 @@ pub enum BlobCommands { /// Hash of the blob to share. hash: Hash, /// Options to configure the generated ticket. - #[clap(long, default_value_t = ShareTicketOptions::DerpAndAddresses)] + #[clap(long, default_value_t = ShareTicketOptions::RelayAndAddresses)] ticket_options: ShareTicketOptions, /// If the blob is a collection, the requester will also fetch the listed blobs. #[clap(long, default_value_t = false)] @@ -146,7 +146,7 @@ impl BlobCommands { Self::Get { ticket, mut address, - derp_url, + relay_url, recursive, override_addresses, node, @@ -171,9 +171,9 @@ impl BlobCommands { }; // prefer direct arg over ticket - let derp_url = derp_url.or(info.derp_url); + let relay_url = relay_url.or(info.relay_url); - NodeAddr::from_parts(node_id, derp_url, addresses) + NodeAddr::from_parts(node_id, relay_url, addresses) }; // check if the blob format has an override @@ -197,7 +197,7 @@ impl BlobCommands { bail!("missing NodeId"); }; - let node_addr = NodeAddr::from_parts(node, derp_url, address); + let node_addr = NodeAddr::from_parts(node, relay_url, address); (node_addr, hash, blob_format) } }; @@ -208,7 +208,7 @@ impl BlobCommands { if node_addr.info.is_empty() { return Err(anyhow::anyhow!( - "no Derp url provided and no direct addresses provided" + "no relay url provided and no direct addresses provided" )); } let tag = match tag { diff --git a/iroh-cli/src/commands/doctor.rs b/iroh-cli/src/commands/doctor.rs index 1c6f23d37c..99208a2125 100644 --- a/iroh-cli/src/commands/doctor.rs +++ b/iroh-cli/src/commands/doctor.rs @@ -20,12 +20,12 @@ use iroh::{ base::ticket::Ticket, bytes::store::ReadableStore, net::{ - defaults::DEFAULT_DERP_STUN_PORT, - derp::{DerpMap, DerpMode, DerpUrl}, + defaults::DEFAULT_RELAY_STUN_PORT, key::{PublicKey, SecretKey}, magic_endpoint, magicsock::EndpointInfo, netcheck, portmapper, + relay::{RelayMap, RelayMode, RelayUrl}, util::AbortingJoinHandle, MagicEndpoint, NodeAddr, NodeId, }, @@ -69,11 +69,11 @@ pub enum Commands { /// Report on the current network environment, using either an explicitly provided stun host /// or the settings from the config file. Report { - /// Explicitly provided stun host. If provided, this will disable derp and just do stun. + /// Explicitly provided stun host. If provided, this will disable relay and just do stun. #[clap(long)] stun_host: Option, /// The port of the STUN server. - #[clap(long, default_value_t = DEFAULT_DERP_STUN_PORT)] + #[clap(long, default_value_t = DEFAULT_RELAY_STUN_PORT)] stun_port: u16, }, /// Wait for incoming requests from iroh doctor connect @@ -90,9 +90,9 @@ pub enum Commands { #[clap(long)] iterations: Option, - /// Use a local derp relay + /// Use a local relay #[clap(long)] - local_derper: bool, + local_relay_server: bool, }, /// Connect to an iroh doctor accept node. Connect { @@ -107,21 +107,21 @@ pub enum Commands { #[clap(long, default_value_t = SecretKeyOption::Random)] secret_key: SecretKeyOption, - /// Use a local derp relay + /// Use a local relay /// - /// Overrides the `derp_url` field. + /// Overrides the `relay_url` field. #[clap(long)] - local_derper: bool, + local_relay_server: bool, - /// The DERP url the peer you are dialing can be found on. + /// The relay url the peer you are dialing can be found on. /// - /// If `local_derper` is true, this field is ignored. + /// If `local_relay_server` is true, this field is ignored. /// /// When `None`, or if attempting to dial an unknown url, no hole punching can occur. /// /// Default is `None`. #[clap(long)] - derp_url: Option, + relay_url: Option, }, /// Probe the port mapping protocols. PortMapProbe { @@ -145,11 +145,11 @@ pub enum Commands { #[clap(long, default_value_t = 10)] timeout_secs: u64, }, - /// Get the latencies of the different DERP url + /// Get the latencies of the different relay url /// - /// Tests the latencies of the default DERP url and nodes. To test custom urls or nodes, + /// Tests the latencies of the default relay url and nodes. To test custom urls or nodes, /// adjust the `Config`. - DerpUrls { + RelayUrls { /// How often to execute. #[clap(long, default_value_t = 5)] count: usize, @@ -280,12 +280,12 @@ async fn report( let dm = match stun_host { Some(host_name) => { let url = host_name.parse()?; - // creating a derp map from host name and stun port - DerpMap::default_from_node(url, stun_port) + // creating a relay map from host name and stun port + RelayMap::default_from_node(url, stun_port) } - None => config.derp_map()?.unwrap_or_else(DerpMap::empty), + None => config.relay_map()?.unwrap_or_else(RelayMap::empty), }; - println!("getting report using derp map {dm:#?}"); + println!("getting report using relay map {dm:#?}"); let r = client.get_report(dm, None, None).await?; println!("{r:#?}"); @@ -354,13 +354,13 @@ impl Gui { }; let msg = match endpoint.connection_info(*node_id) { Some(EndpointInfo { - derp_url, + relay_url, conn_type, latency, addrs, .. }) => { - let derp_url = derp_url + let relay_url = relay_url .map(|x| x.to_string()) .unwrap_or_else(|| "unknown".to_string()); let latency = format_latency(latency); @@ -372,8 +372,8 @@ impl Gui { .collect::>() .join("; "); format!( - "derp url: {}, latency: {}, connection type: {}, addrs: [{}]", - derp_url, latency, conn_type, addrs + "relay url: {}, latency: {}, connection type: {}, addrs: [{}]", + relay_url, latency, conn_type, addrs ) } None => "connection info unavailable".to_string(), @@ -387,16 +387,16 @@ impl Gui { tracing::error!("metrics enabled"); let send_ipv4 = HumanBytes(metrics.send_ipv4.get()); let send_ipv6 = HumanBytes(metrics.send_ipv6.get()); - let send_derp = HumanBytes(metrics.send_derp.get()); - let recv_data_derp = HumanBytes(metrics.recv_data_derp.get()); + let send_relay = HumanBytes(metrics.send_relay.get()); + let recv_data_relay = HumanBytes(metrics.recv_data_relay.get()); let recv_data_ipv4 = HumanBytes(metrics.recv_data_ipv4.get()); let recv_data_ipv6 = HumanBytes(metrics.recv_data_ipv6.get()); let text = format!( r#"Counters -Derp: - send: {send_derp} - recv: {recv_data_derp} +Relay: + send: {send_relay} + recv: {recv_data_relay} Ipv4: send: {send_ipv4} recv: {recv_data_ipv4} @@ -565,23 +565,23 @@ async fn passive_side( } } -fn configure_local_derp_map() -> DerpMap { - let stun_port = DEFAULT_DERP_STUN_PORT; +fn configure_local_relay_map() -> RelayMap { + let stun_port = DEFAULT_RELAY_STUN_PORT; let url = "http://localhost:3340".parse().unwrap(); - DerpMap::default_from_node(url, stun_port) + RelayMap::default_from_node(url, stun_port) } -const DR_DERP_ALPN: [u8; 11] = *b"n0/drderp/1"; +const DR_RELAY_ALPN: [u8; 11] = *b"n0/drderp/1"; async fn make_endpoint( secret_key: SecretKey, - derp_map: Option, + relay_map: Option, ) -> anyhow::Result { tracing::info!( "public key: {}", hex::encode(secret_key.public().as_bytes()) ); - tracing::info!("derp map {:#?}", derp_map); + tracing::info!("relay map {:#?}", relay_map); let mut transport_config = quinn::TransportConfig::default(); transport_config.keep_alive_interval(Some(Duration::from_secs(5))); @@ -589,18 +589,18 @@ async fn make_endpoint( let endpoint = MagicEndpoint::builder() .secret_key(secret_key) - .alpns(vec![DR_DERP_ALPN.to_vec()]) + .alpns(vec![DR_RELAY_ALPN.to_vec()]) .transport_config(transport_config); - let endpoint = match derp_map { - Some(derp_map) => endpoint.derp_mode(DerpMode::Custom(derp_map)), + let endpoint = match relay_map { + Some(relay_map) => endpoint.relay_mode(RelayMode::Custom(relay_map)), None => endpoint, }; let endpoint = endpoint.bind(0).await?; tokio::time::timeout(Duration::from_secs(10), endpoint.local_endpoints().next()) .await - .context("wait for derp connection")? + .context("wait for relay connection")? .context("no endpoints")?; Ok(endpoint) @@ -610,14 +610,14 @@ async fn connect( node_id: NodeId, secret_key: SecretKey, direct_addresses: Vec, - derp_url: Option, - derp_map: Option, + relay_url: Option, + relay_map: Option, ) -> anyhow::Result<()> { - let endpoint = make_endpoint(secret_key, derp_map).await?; + let endpoint = make_endpoint(secret_key, relay_map).await?; tracing::info!("dialing {:?}", node_id); - let node_addr = NodeAddr::from_parts(node_id, derp_url, direct_addresses); - let conn = endpoint.connect(node_addr, &DR_DERP_ALPN).await; + let node_addr = NodeAddr::from_parts(node_id, relay_url, direct_addresses); + let conn = endpoint.connect(node_addr, &DR_RELAY_ALPN).await; match conn { Ok(connection) => { if let Err(cause) = passive_side(endpoint.clone(), connection).await { @@ -644,9 +644,9 @@ fn format_addr(addr: SocketAddr) -> String { async fn accept( secret_key: SecretKey, config: TestConfig, - derp_map: Option, + relay_map: Option, ) -> anyhow::Result<()> { - let endpoint = make_endpoint(secret_key.clone(), derp_map).await?; + let endpoint = make_endpoint(secret_key.clone(), relay_map).await?; let endpoints = endpoint .local_endpoints() .next() @@ -657,17 +657,17 @@ async fn accept( .map(|endpoint| format!("--remote-endpoint {}", format_addr(endpoint.addr))) .collect::>() .join(" "); - println!("Connect to this node using one of the following commands to connect either directly by address or indirectly by derp url:"); + println!("Connect to this node using one of the following commands to connect either directly by address or indirectly by relay url:"); println!( "iroh doctor connect {} {}", secret_key.public(), remote_addrs, ); - if let Some(derp_url) = endpoint.my_derp() { + if let Some(relay_url) = endpoint.my_relay() { println!( - "iroh doctor connect {} --derp-url {}", + "iroh doctor connect {} --relay-url {}", secret_key.public(), - derp_url, + relay_url, ); } let connections = Arc::new(AtomicU64::default()); @@ -755,16 +755,16 @@ async fn port_map_probe(config: portmapper::Config) -> anyhow::Result<()> { Ok(()) } -async fn derp_urls(count: usize, config: NodeConfig) -> anyhow::Result<()> { +async fn relay_urls(count: usize, config: NodeConfig) -> anyhow::Result<()> { let key = SecretKey::generate(); - if config.derp_nodes.is_empty() { - println!("No DERP nodes specified in the config file."); + if config.relay_nodes.is_empty() { + println!("No relay nodes specified in the config file."); } let mut clients = HashMap::new(); - for node in &config.derp_nodes { + for node in &config.relay_nodes { let secret_key = key.clone(); - let client = iroh::net::derp::http::ClientBuilder::new(node.url.clone()).build(secret_key); + let client = iroh::net::relay::http::ClientBuilder::new(node.url.clone()).build(secret_key); clients.insert(node.url.clone(), client); } @@ -774,8 +774,8 @@ async fn derp_urls(count: usize, config: NodeConfig) -> anyhow::Result<()> { for i in 0..count { println!("Round {}/{count}", i + 1); - let derp_nodes = config.derp_nodes.clone(); - for node in derp_nodes.into_iter() { + let relay_nodes = config.relay_nodes.clone(); + for node in relay_nodes.into_iter() { let mut node_details = NodeDetails { connect: None, latency: None, @@ -824,7 +824,7 @@ async fn derp_urls(count: usize, config: NodeConfig) -> anyhow::Result<()> { // success.sort_by_key(|d| d.latency); if !success.is_empty() { - println!("DERP Node Latencies:"); + println!("Relay Node Latencies:"); println!(); } for node in success { @@ -846,7 +846,7 @@ async fn derp_urls(count: usize, config: NodeConfig) -> anyhow::Result<()> { struct NodeDetails { connect: Option, latency: Option, - host: DerpUrl, + host: RelayUrl, error: Option, } @@ -921,34 +921,34 @@ pub async fn run(command: Commands, config: &NodeConfig) -> anyhow::Result<()> { Commands::Connect { dial, secret_key, - local_derper, - derp_url, + local_relay_server, + relay_url, remote_endpoint, } => { - let (derp_map, derp_url) = if local_derper { - let dm = configure_local_derp_map(); + let (relay_map, relay_url) = if local_relay_server { + let dm = configure_local_relay_map(); let url = dm.urls().next().unwrap().clone(); (Some(dm), Some(url)) } else { - (config.derp_map()?, derp_url) + (config.relay_map()?, relay_url) }; let secret_key = create_secret_key(secret_key)?; - connect(dial, secret_key, remote_endpoint, derp_url, derp_map).await + connect(dial, secret_key, remote_endpoint, relay_url, relay_map).await } Commands::Accept { secret_key, - local_derper, + local_relay_server, size, iterations, } => { - let derp_map = if local_derper { - Some(configure_local_derp_map()) + let relay_map = if local_relay_server { + Some(configure_local_relay_map()) } else { - config.derp_map()? + config.relay_map()? }; let secret_key = create_secret_key(secret_key)?; let config = TestConfig { size, iterations }; - accept(secret_key, config, derp_map).await + accept(secret_key, config, relay_map).await } Commands::PortMap { protocol, @@ -968,9 +968,9 @@ pub async fn run(command: Commands, config: &NodeConfig) -> anyhow::Result<()> { port_map_probe(config).await } - Commands::DerpUrls { count } => { + Commands::RelayUrls { count } => { let config = NodeConfig::from_env(None)?; - derp_urls(count, config).await + relay_urls(count, config).await } Commands::TicketInspect { ticket } => inspect_ticket(&ticket), Commands::ValidateBlobStore { path, repair } => { diff --git a/iroh-cli/src/commands/node.rs b/iroh-cli/src/commands/node.rs index e4865d6676..695e3e8dcc 100644 --- a/iroh-cli/src/commands/node.rs +++ b/iroh-cli/src/commands/node.rs @@ -88,14 +88,14 @@ async fn fmt_connections( ) -> String { let mut table = Table::new(); table.load_preset(NOTHING).set_header( - ["node id", "derp", "conn type", "latency", "last used"] + ["node id", "relay", "conn type", "latency", "last used"] .into_iter() .map(bold_cell), ); while let Some(Ok(conn_info)) = infos.next().await { let node_id: Cell = conn_info.node_id.to_string().into(); - let derp_url = conn_info - .derp_url + let relay_url = conn_info + .relay_url .map_or(String::new(), |url| url.to_string()) .into(); let conn_type = conn_info.conn_type.to_string().into(); @@ -109,7 +109,7 @@ async fn fmt_connections( .map(fmt_how_long_ago) .map(Cell::new) .unwrap_or_else(never); - table.add_row([node_id, derp_url, conn_type, latency, last_used]); + table.add_row([node_id, relay_url, conn_type, latency, last_used]); } table.to_string() } @@ -118,7 +118,7 @@ fn fmt_connection(info: ConnectionInfo) -> String { let ConnectionInfo { id: _, node_id, - derp_url, + relay_url, addrs, conn_type, latency, @@ -131,10 +131,10 @@ fn fmt_connection(info: ConnectionInfo) -> String { table.load_preset(NOTHING); table.add_row([bold_cell("current time"), timestamp.into()]); table.add_row([bold_cell("node id"), node_id.to_string().into()]); - let derp_url = derp_url + let relay_url = relay_url .map(|r| r.to_string()) .unwrap_or_else(|| String::from("unknown")); - table.add_row([bold_cell("derp url"), derp_url.into()]); + table.add_row([bold_cell("relay url"), relay_url.into()]); table.add_row([bold_cell("connection type"), conn_type.to_string().into()]); table.add_row([bold_cell("latency"), fmt_latency(latency).into()]); table.add_row([ diff --git a/iroh-cli/src/commands/start.rs b/iroh-cli/src/commands/start.rs index 9dc6fea59f..507ee4c7bb 100644 --- a/iroh-cli/src/commands/start.rs +++ b/iroh-cli/src/commands/start.rs @@ -7,7 +7,7 @@ use futures::Future; use indicatif::{ProgressBar, ProgressDrawTarget, ProgressStyle}; use iroh::node::Node; use iroh::{ - net::derp::{DerpMap, DerpMode}, + net::relay::{RelayMap, RelayMode}, node::RpcStatus, }; use tracing::{info_span, Instrument}; @@ -71,10 +71,10 @@ where F: FnOnce(iroh::client::mem::Iroh) -> T + Send + 'static, T: Future> + 'static, { - let derp_map = config.derp_map()?; + let relay_map = config.relay_map()?; let spinner = create_spinner("Iroh booting..."); - let node = start_node(iroh_data_root, derp_map).await?; + let node = start_node(iroh_data_root, relay_map).await?; drop(spinner); eprintln!("{}", welcome_message(&node)?); @@ -123,7 +123,7 @@ where pub(crate) async fn start_node( iroh_data_root: &Path, - derp_map: Option, + relay_map: Option, ) -> Result> { let rpc_status = RpcStatus::load(iroh_data_root).await?; match rpc_status { @@ -135,14 +135,14 @@ pub(crate) async fn start_node( } } - let derp_mode = match derp_map { - None => DerpMode::Default, - Some(derp_map) => DerpMode::Custom(derp_map), + let relay_mode = match relay_map { + None => RelayMode::Default, + Some(relay_map) => RelayMode::Custom(relay_map), }; Node::persistent(iroh_data_root) .await? - .derp_mode(derp_mode) + .relay_mode(relay_mode) .enable_rpc() .await? .spawn() diff --git a/iroh-cli/src/config.rs b/iroh-cli/src/config.rs index 68a556cebe..b0d13c83af 100644 --- a/iroh-cli/src/config.rs +++ b/iroh-cli/src/config.rs @@ -12,8 +12,8 @@ use std::{ use anyhow::{anyhow, bail, ensure, Context, Result}; use config::{Environment, File, Value}; use iroh::net::{ - defaults::{default_eu_derp_node, default_na_derp_node}, - derp::{DerpMap, DerpNode}, + defaults::{default_eu_relay_node, default_na_relay_node}, + relay::{RelayMap, RelayNode}, }; use iroh::node::GcPolicy; use iroh::sync::{AuthorId, NamespaceId}; @@ -85,8 +85,8 @@ impl ConsolePaths { #[derive(PartialEq, Eq, Debug, Deserialize, Serialize, Clone)] #[serde(default)] pub(crate) struct NodeConfig { - /// The nodes for DERP to use. - pub(crate) derp_nodes: Vec, + /// The nodes for relay to use. + pub(crate) relay_nodes: Vec, /// How often to run garbage collection. pub(crate) gc_policy: GcPolicy, /// Bind address on which to serve Prometheus metrics @@ -96,8 +96,8 @@ pub(crate) struct NodeConfig { impl Default for NodeConfig { fn default() -> Self { Self { - // TODO(ramfox): this should probably just be a derp map - derp_nodes: [default_na_derp_node(), default_eu_derp_node()].into(), + // TODO(ramfox): this should probably just be a relay map + relay_nodes: [default_na_relay_node(), default_eu_relay_node()].into(), gc_policy: GcPolicy::Disabled, metrics_addr: None, } @@ -178,12 +178,12 @@ impl NodeConfig { Ok(cfg) } - /// Constructs a `DerpMap` based on the current configuration. - pub(crate) fn derp_map(&self) -> Result> { - if self.derp_nodes.is_empty() { + /// Constructs a `RelayMap` based on the current configuration. + pub(crate) fn relay_map(&self) -> Result> { + if self.relay_nodes.is_empty() { return Ok(None); } - Some(DerpMap::from_nodes(self.derp_nodes.iter().cloned())).transpose() + Some(RelayMap::from_nodes(self.relay_nodes.iter().cloned())).transpose() } } @@ -426,6 +426,6 @@ mod tests { fn test_default_settings() { let config = NodeConfig::load(&[][..], "__FOO", HashMap::::new()).unwrap(); - assert_eq!(config.derp_nodes.len(), 2); + assert_eq!(config.relay_nodes.len(), 2); } } diff --git a/iroh-cli/tests/cli.rs b/iroh-cli/tests/cli.rs index df804c6013..491f015e69 100644 --- a/iroh-cli/tests/cli.rs +++ b/iroh-cli/tests/cli.rs @@ -785,10 +785,10 @@ fn test_provide_get_loop_single(input: Input, output: Output, hash: Hash) -> Res .map(|x| x.to_string()) .collect::>(); let node = ticket.node_addr().node_id.to_string(); - let derp_url = ticket + let relay_url = ticket .node_addr() - .derp_url() - .context("should have derp url in ticket")? + .relay_url() + .context("should have relay url in ticket")? .to_string(); // create a `get-ticket` cmd & optionally provide out path @@ -800,8 +800,8 @@ fn test_provide_get_loop_single(input: Input, output: Output, hash: Hash) -> Res args.push("--out"); args.push(&out); - args.push("--derp-url"); - args.push(&derp_url); + args.push("--relay-url"); + args.push(&relay_url); let hash_str = hash.to_string(); args.push(&hash_str); let get_iroh_data_dir = dir.join("get-iroh-data-dir"); diff --git a/iroh-gossip/examples/chat.rs b/iroh-gossip/examples/chat.rs index 102e3660fe..6a596b1bec 100644 --- a/iroh-gossip/examples/chat.rs +++ b/iroh-gossip/examples/chat.rs @@ -10,9 +10,9 @@ use iroh_gossip::{ proto::{Event, TopicId}, }; use iroh_net::{ - derp::{DerpMap, DerpMode, DerpUrl}, key::{PublicKey, SecretKey}, magic_endpoint::accept_conn, + relay::{RelayMap, RelayMode, RelayUrl}, MagicEndpoint, NodeAddr, }; use serde::{Deserialize, Serialize}; @@ -25,20 +25,20 @@ use serde::{Deserialize, Serialize}; /// By default a new node id is created when starting the example. To reuse your identity, /// set the `--secret-key` flag with the secret key printed on a previous invocation. /// -/// By default, the DERP server run by n0 is used. To use a local DERP server, run -/// cargo run --bin derper --features derper -- --dev +/// By default, the relay server run by n0 is used. To use a local relay server, run +/// cargo run --bin iroh-relay --features iroh-relay -- --dev /// in another terminal and then set the `-d http://localhost:3340` flag on this example. #[derive(Parser, Debug)] struct Args { /// secret key to derive our node id from. #[clap(long)] secret_key: Option, - /// Set a custom DERP server. By default, the DERP server hosted by n0 will be used. + /// Set a custom relay server. By default, the relay server hosted by n0 will be used. #[clap(short, long)] - derp: Option, - /// Disable DERP completely. + relay: Option, + /// Disable relay completely. #[clap(long)] - no_derp: bool, + no_relay: bool, /// Set your nickname. #[clap(short, long)] name: Option, @@ -91,20 +91,20 @@ async fn main() -> anyhow::Result<()> { }; println!("> our secret key: {}", base32::fmt(secret_key.to_bytes())); - // configure our derp map - let derp_mode = match (args.no_derp, args.derp) { - (false, None) => DerpMode::Default, - (false, Some(url)) => DerpMode::Custom(DerpMap::from_url(url)), - (true, None) => DerpMode::Disabled, - (true, Some(_)) => bail!("You cannot set --no-derp and --derp at the same time"), + // confgure our relay map + let relay_mode = match (args.no_relay, args.relay) { + (false, None) => RelayMode::Default, + (false, Some(url)) => RelayMode::Custom(RelayMap::from_url(url)), + (true, None) => RelayMode::Disabled, + (true, Some(_)) => bail!("You cannot set --no-relay and --relay at the same time"), }; - println!("> using DERP servers: {}", fmt_derp_mode(&derp_mode)); + println!("> using relay servers: {}", fmt_relay_mode(&relay_mode)); // build our magic endpoint let endpoint = MagicEndpoint::builder() .secret_key(secret_key) .alpns(vec![GOSSIP_ALPN.to_vec()]) - .derp_mode(derp_mode) + .relay_mode(relay_mode) .bind(args.bind_port) .await?; println!("> our node id: {}", endpoint.node_id()); @@ -299,11 +299,11 @@ fn parse_secret_key(secret: &str) -> anyhow::Result { Ok(SecretKey::from(bytes)) } -fn fmt_derp_mode(derp_mode: &DerpMode) -> String { - match derp_mode { - DerpMode::Disabled => "None".to_string(), - DerpMode::Default => "Default Derp servers".to_string(), - DerpMode::Custom(map) => map +fn fmt_relay_mode(relay_mode: &RelayMode) -> String { + match relay_mode { + RelayMode::Disabled => "None".to_string(), + RelayMode::Default => "Default Relay servers".to_string(), + RelayMode::Custom(map) => map .urls() .map(|url| url.to_string()) .collect::>() diff --git a/iroh-gossip/src/net.rs b/iroh-gossip/src/net.rs index fde0010386..071eb6c7a8 100644 --- a/iroh-gossip/src/net.rs +++ b/iroh-gossip/src/net.rs @@ -655,7 +655,7 @@ mod test { use iroh_net::NodeAddr; use iroh_net::{ - derp::{DerpMap, DerpMode}, + relay::{RelayMap, RelayMode}, MagicEndpoint, }; use tokio::spawn; @@ -665,10 +665,10 @@ mod test { use super::*; - async fn create_endpoint(derp_map: DerpMap) -> anyhow::Result { + async fn create_endpoint(relay_map: RelayMap) -> anyhow::Result { MagicEndpoint::builder() .alpns(vec![GOSSIP_ALPN.to_vec()]) - .derp_mode(DerpMode::Custom(derp_map)) + .relay_mode(RelayMode::Custom(relay_map)) .bind(0) .await } @@ -695,23 +695,23 @@ mod test { #[ignore = "flaky"] async fn gossip_net_smoke() { let _guard = iroh_test::logging::setup(); - let (derp_map, derp_url, cleanup) = util::run_derp_and_stun([127, 0, 0, 1].into()) + let (relay_map, relay_url, cleanup) = util::run_relay_and_stun([127, 0, 0, 1].into()) .await .unwrap(); - let ep1 = create_endpoint(derp_map.clone()).await.unwrap(); - let ep2 = create_endpoint(derp_map.clone()).await.unwrap(); - let ep3 = create_endpoint(derp_map.clone()).await.unwrap(); + let ep1 = create_endpoint(relay_map.clone()).await.unwrap(); + let ep2 = create_endpoint(relay_map.clone()).await.unwrap(); + let ep3 = create_endpoint(relay_map.clone()).await.unwrap(); let addr1 = AddrInfo { - derp_url: Some(derp_url.clone()), + relay_url: Some(relay_url.clone()), direct_addresses: Default::default(), }; let addr2 = AddrInfo { - derp_url: Some(derp_url.clone()), + relay_url: Some(relay_url.clone()), direct_addresses: Default::default(), }; let addr3 = AddrInfo { - derp_url: Some(derp_url.clone()), + relay_url: Some(relay_url.clone()), direct_addresses: Default::default(), }; @@ -732,8 +732,8 @@ mod test { debug!("----- adding peers ----- "); let topic: TopicId = blake3::hash(b"foobar").into(); - // share info that pi1 is on the same derp_node - let addr1 = NodeAddr::new(pi1).with_derp_url(derp_url); + // share info that pi1 is on the same relay_node + let addr1 = NodeAddr::new(pi1).with_relay_url(relay_url); ep2.add_node_addr(addr1.clone()).unwrap(); ep3.add_node_addr(addr1).unwrap(); @@ -828,8 +828,8 @@ mod test { use anyhow::Result; use iroh_net::{ - derp::{DerpMap, DerpUrl}, key::SecretKey, + relay::{RelayMap, RelayUrl}, stun::{is, parse_binding_request, response}, }; use tokio::sync::oneshot; @@ -845,30 +845,30 @@ mod test { #[allow(dead_code)] pub(crate) struct CleanupDropGuard(pub(crate) oneshot::Sender<()>); - /// Runs a DERP server with STUN enabled suitable for tests. + /// Runs a relay server with STUN enabled suitable for tests. /// - /// The returned `Url` is the url of the DERP server in the returned [`DerpMap`], it + /// The returned `Url` is the url of the relay server in the returned [`RelayMap`], it /// is always `Some` as that is how the [`MagicEndpoint::connect`] API expects it. /// /// [`MagicEndpoint::connect`]: crate::magic_endpoint::MagicEndpoint - pub(crate) async fn run_derp_and_stun( + pub(crate) async fn run_relay_and_stun( stun_ip: IpAddr, - ) -> Result<(DerpMap, DerpUrl, CleanupDropGuard)> { + ) -> Result<(RelayMap, RelayUrl, CleanupDropGuard)> { let server_key = SecretKey::generate(); - let server = iroh_net::derp::http::ServerBuilder::new("127.0.0.1:0".parse().unwrap()) + let server = iroh_net::relay::http::ServerBuilder::new("127.0.0.1:0".parse().unwrap()) .secret_key(Some(server_key)) .tls_config(None) .spawn() .await?; let http_addr = server.addr(); - info!("DERP listening on {:?}", http_addr); + info!("relay listening on {:?}", http_addr); let (stun_addr, stun_drop_guard) = serve(stun_ip).await?; - let derp_url: DerpUrl = format!("http://localhost:{}", http_addr.port()) + let relay_url: RelayUrl = format!("http://localhost:{}", http_addr.port()) .parse() .unwrap(); - let m = DerpMap::default_from_node(derp_url.clone(), stun_addr.port()); + let m = RelayMap::default_from_node(relay_url.clone(), stun_addr.port()); let (tx, rx) = oneshot::channel(); tokio::spawn(async move { @@ -879,7 +879,7 @@ mod test { server.shutdown().await; }); - Ok((m, derp_url, CleanupDropGuard(tx))) + Ok((m, relay_url, CleanupDropGuard(tx))) } /// Sets up a simple STUN server. diff --git a/iroh-net/Cargo.toml b/iroh-net/Cargo.toml index d4edebf594..80dd2f0c0f 100644 --- a/iroh-net/Cargo.toml +++ b/iroh-net/Cargo.toml @@ -72,7 +72,7 @@ webpki = { package = "rustls-webpki", version = "0.101.4", features = ["std"] } webpki-roots = "0.25" x509-parser = "0.15" -# derper +# iroh-relay clap = { version = "4", features = ["derive"], optional = true } regex = { version = "1.7.1", optional = true } rustls-pemfile = { version = "1.0.2", optional = true } @@ -116,12 +116,12 @@ duct = "0.13.6" [features] default = ["metrics"] -derper = ["clap", "toml", "rustls-pemfile", "regex", "serde_with", "tracing-subscriber"] +iroh-relay = ["clap", "toml", "rustls-pemfile", "regex", "serde_with", "tracing-subscriber"] metrics = ["iroh-metrics/metrics"] [[bin]] -name = "derper" -required-features = ["derper"] +name = "iroh-relay" +required-features = ["iroh-relay"] [[example]] name = "listen" diff --git a/iroh-net/README.md b/iroh-net/README.md index f8cf3a25f3..0ad1fb9f48 100644 --- a/iroh-net/README.md +++ b/iroh-net/README.md @@ -2,11 +2,11 @@ This crate contains the networking support for iroh. Iroh networking is built on direct peer-to-peer [QUIC](https://en.wikipedia.org/wiki/QUIC) connections that use relays and holepunching. The main structure for connection is the `MagicEndpoint` entrypoint. -Peer to peer connectivity is established with the help of a _DERP server_ or _derper_. The DERP server provides Session Traversal Utilities for NAT [(STUN)](https://en.wikipedia.org/wiki/STUN) for the peers and connection coordination using the [DERP protocol](https://pkg.go.dev/tailscale.com/derp) (Designated Relay for Encrypted Packets protocol). If no direct connection can be established, the connection is relayed via the DERP server. +Peer to peer connectivity is established with the help of a _relay server_. The relay server provides Session Traversal Utilities for NAT [(STUN)](https://en.wikipedia.org/wiki/STUN) for the peers and connection coordination using the [DERP protocol](https://pkg.go.dev/tailscale.com/derp) (Designated Relay for Encrypted Packets protocol). If no direct connection can be established, the connection is relayed via the server. -Peers must know and do verify the PeerID of each other before they can connect. When using a DERP server to aid the connection establishment they will register with a home DERP server using their PublicKey. Other peers which can not establish a direct connection can then establish connection via this DERP server. This will try to assist establishing a direct connection using STUN and holepunching but continue relaying if not possible. +Peers must know and do verify the PeerID of each other before they can connect. When using a relay server to aid the connection establishment they will register with a home relay server using their PublicKey. Other peers which can not establish a direct connection can then establish connection via this relay server. This will try to assist establishing a direct connection using STUN and holepunching but continue relaying if not possible. -Peers can also connect directly without using a DERP server. For this, however the listening peer must be directly reachable by the connecting peer via one of it's addresses. +Peers can also connect directly without using a relay server. For this, however the listening peer must be directly reachable by the connecting peer via one of it's addresses. ## Examples diff --git a/iroh-net/bench/src/lib.rs b/iroh-net/bench/src/lib.rs index 3ef082400a..8009dccad1 100644 --- a/iroh-net/bench/src/lib.rs +++ b/iroh-net/bench/src/lib.rs @@ -3,7 +3,7 @@ use std::{convert::TryInto, net::SocketAddr, num::ParseIntError, str::FromStr}; use anyhow::{Context, Result}; use bytes::Bytes; use clap::Parser; -use iroh_net::{derp::DerpMode, MagicEndpoint, NodeAddr}; +use iroh_net::{relay::RelayMode, MagicEndpoint, NodeAddr}; use tokio::runtime::{Builder, Runtime}; use tracing::trace; @@ -26,7 +26,7 @@ pub fn server_endpoint(rt: &tokio::runtime::Runtime, opt: &Opt) -> (NodeAddr, Ma rt.block_on(async move { let ep = MagicEndpoint::builder() .alpns(vec![ALPN.to_vec()]) - .derp_mode(DerpMode::Disabled) + .relay_mode(RelayMode::Disabled) .transport_config(transport_config(opt)) .bind(0) .await @@ -45,7 +45,7 @@ pub async fn connect_client( ) -> Result<(MagicEndpoint, quinn::Connection)> { let endpoint = MagicEndpoint::builder() .alpns(vec![ALPN.to_vec()]) - .derp_mode(DerpMode::Disabled) + .relay_mode(RelayMode::Disabled) .transport_config(transport_config(&opt)) .bind(0) .await diff --git a/iroh-net/docs/derp_nodes.md b/iroh-net/docs/derp_nodes.md deleted file mode 100644 index 1b3db6d444..0000000000 --- a/iroh-net/docs/derp_nodes.md +++ /dev/null @@ -1,32 +0,0 @@ -# DERP nodes, or DERPers - -When an Iroh node starts up, it does a latency test to see which known DERP node it is “closest to”. That DERPer (as we sometimes call a DERP node) is considered the Iroh node's home DERPer. - -A node may be connected to multiple DERPers, but it will advertise its home DERP node as the one best used to hole-punch or relay packets through. - -You do not need to know a node's DERPer in order to connect to them directly, if there are no firewalls or NATs between the two nodes trying to connect. However, to have any hole punching, you must know at least one DERPer to which that node is connected. - -We currently run 2 DERP nodes. -## North America - -```rust -DerpNode { - url: format!("https://derp.iroh.network") - .parse() - .unwrap(), - stun_only: false, - stun_port: 3478, -} -``` - -## Europe - -```rust -DerpNode { - url: format!("https://eu1.derp.iroh.network") - .parse() - .unwrap(), - stun_only: false, - stun_port: 3478, -} -``` diff --git a/iroh-net/docs/local_derper.md b/iroh-net/docs/local_derper.md deleted file mode 100644 index 77e633147f..0000000000 --- a/iroh-net/docs/local_derper.md +++ /dev/null @@ -1,41 +0,0 @@ -# Using a local derper - -It's easy to set up a derper that runs locally on your machine. - -Using cargo: - -```shell -$ cargo run --bin derper --features="derper" -- --dev -``` - -This will bind the derper to `[::]3340` and run it over HTTP. - -To connect to this derper when doing your normal iroh commands, adjust the iroh configuration file to read: - -```toml -# iroh.config.toml: -[[derp_nodes]] -url = "http://localhost:3340" -stun_only = false -stun_port = 3478 -``` - -If you want to give a specific port for the derper to bind to, you can create a derper config file and pass that file in using the `--config_path` flag. You need to retain a `secret_key`, so it is recommended to run `derper --config-path [PATH]` once to generate a secret key and save it to the config file before doing further edits to the file. - -To change the port you want to listen on, change the port in the `addr` field: - -``` -# derper.toml - -secret_key = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX" -addr = "[::]:12345" -stun_port = 3478 -hostname = "my.derp.network" -enable_stun = true -enable_derp = true -``` - -Check [the derper file's](../src/bin/derper.rs) `Config` struct for documentation on each configuration field. - -If you change the local derper's configuration, however, be sure to adjust the associated fields in your iroh config as well. - diff --git a/iroh-net/docs/local_relay_node.md b/iroh-net/docs/local_relay_node.md new file mode 100644 index 0000000000..cb6736478f --- /dev/null +++ b/iroh-net/docs/local_relay_node.md @@ -0,0 +1,41 @@ +# Using a local iroh-relay + +It's easy to set up a iroh-relay that runs locally on your machine. + +Using cargo: + +```shell +$ cargo run --bin iroh-relay --features="iroh-relay" -- --dev +``` + +This will bind the iroh-relay to `[::]3340` and run it over HTTP. + +To connect to this iroh-relay when doing your normal iroh commands, adjust the iroh configuration file to read: + +```toml +# iroh.config.toml: +[[relay_nodes]] +url = "http://localhost:3340" +stun_only = false +stun_port = 3478 +``` + +If you want to give a specific port for the iroh-relay to bind to, you can create a iroh-relay config file and pass that file in using the `--config_path` flag. You need to retain a `secret_key`, so it is recommended to run `iroh-relay --config-path [PATH]` once to generate a secret key and save it to the config file before doing further edits to the file. + +To change the port you want to listen on, change the port in the `addr` field: + +``` +# iroh-relay.toml + +secret_key = "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX" +addr = "[::]:12345" +stun_port = 3478 +hostname = "my.relay.network" +enable_stun = true +enable_relay = true +``` + +Check [the iroh-relay file's](../src/bin/iroh-relay.rs) `Config` struct for documentation on each configuration field. + +If you change the local iroh-relay server's configuration, however, be sure to adjust the associated fields in your iroh config as well. + diff --git a/iroh-net/docs/relay_nodes.md b/iroh-net/docs/relay_nodes.md new file mode 100644 index 0000000000..12dbee03b0 --- /dev/null +++ b/iroh-net/docs/relay_nodes.md @@ -0,0 +1,32 @@ +# Relay nodes + +When an Iroh node starts up, it does a latency test to see which known relay node it is “closest to”. That relay server is considered the Iroh node's home relay server. + +A node may be connected to multiple relay servers, but it will advertise its home relay node as the one best used to hole-punch or relay packets through. + +You do not need to know a node's relay server in order to connect to them directly, if there are no firewalls or NATs between the two nodes trying to connect. However, to have any hole punching, you must know at least one relay server to which that node is connected. + +We currently run 2 relay nodes. +## North America + +```rust +RelayNode { + url: format!("https://derp.iroh.network") + .parse() + .unwrap(), + stun_only: false, + stun_port: 3478, +} +``` + +## Europe + +```rust +RelayNode { + url: format!("https://eu1.derp.iroh.network") + .parse() + .unwrap(), + stun_only: false, + stun_port: 3478, +} +``` diff --git a/iroh-net/examples/connect-unreliable.rs b/iroh-net/examples/connect-unreliable.rs index 7061075cd1..fc4ebd1315 100644 --- a/iroh-net/examples/connect-unreliable.rs +++ b/iroh-net/examples/connect-unreliable.rs @@ -1,8 +1,8 @@ //! The smallest example showing how to use iroh-net and `MagicEndpoint` to connect to a remote node and pass bytes using unreliable datagrams. //! -//! We use the node ID (the PublicKey of the remote node), the direct UDP addresses, and the DERP url to achieve a connection. +//! We use the node ID (the PublicKey of the remote node), the direct UDP addresses, and the relay url to achieve a connection. //! -//! This example uses the default DERP servers to attempt to holepunch, and will use that DERP server to relay packets if the two devices cannot establish a direct UDP connection. +//! This example uses the default relay servers to attempt to holepunch, and will use that relay server to relay packets if the two devices cannot establish a direct UDP connection. //! //! Run the `listen-unreliable` example first (`iroh-net/examples/listen-unreliable.rs`), which will give you instructions on how to run this example to watch two nodes connect and exchange bytes. use std::net::SocketAddr; @@ -12,8 +12,8 @@ use clap::Parser; use futures::StreamExt; use iroh_base::base32; use iroh_net::{ - derp::{DerpMode, DerpUrl}, key::SecretKey, + relay::{RelayMode, RelayUrl}, MagicEndpoint, NodeAddr, }; use tracing::info; @@ -29,9 +29,9 @@ struct Cli { /// The list of direct UDP addresses for the remote node. #[clap(long, value_parser, num_args = 1.., value_delimiter = ' ')] addrs: Vec, - /// The url of the DERP server the remote node can also be reached at. + /// The url of the relay server the remote node can also be reached at. #[clap(long)] - derp_url: DerpUrl, + relay_url: RelayUrl, } #[tokio::main] @@ -42,17 +42,17 @@ async fn main() -> anyhow::Result<()> { let secret_key = SecretKey::generate(); println!("secret key: {}", base32::fmt(secret_key.to_bytes())); - // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the DERP protocol and DERP servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the DERP servers. + // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the relay protocol and relay servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the relay servers. let endpoint = MagicEndpoint::builder() // The secret key is used to authenticate with other nodes. The PublicKey portion of this secret key is how we identify nodes, often referred to as the `node_id` in our codebase. .secret_key(secret_key) // Set the ALPN protocols this endpoint will accept on incoming connections .alpns(vec![EXAMPLE_ALPN.to_vec()]) - // `DerpMode::Default` means that we will use the default DERP servers to holepunch and relay. - // Use `DerpMode::Custom` to pass in a `DerpMap` with custom DERP urls. - // Use `DerpMode::Disable` to disable holepunching and relaying over HTTPS - // If you want to experiment with relaying using your own DERP server, you must pass in the same custom DERP url to both the `listen` code AND the `connect` code - .derp_mode(DerpMode::Default) + // `RelayMode::Default` means that we will use the default relay servers to holepunch and relay. + // Use `RelayMode::Custom` to pass in a `RelayMap` with custom relay urls. + // Use `RelayMode::Disable` to disable holepunching and relaying over HTTPS + // If you want to experiment with relaying using your own relay server, you must pass in the same custom relay url to both the `listen` code AND the `connect` code + .relay_mode(RelayMode::Default) // You can choose a port to bind to, but passing in `0` will bind the socket to a random available port .bind(0) .await?; @@ -69,12 +69,12 @@ async fn main() -> anyhow::Result<()> { println!("\t{}", local_endpoint.addr) } - let derp_url = endpoint - .my_derp() - .expect("should be connected to a DERP server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected DERP server"); - println!("node DERP server url: {derp_url}\n"); - // Build a `NodeAddr` from the node_id, DERP url, and UDP addresses. - let addr = NodeAddr::from_parts(args.node_id, Some(args.derp_url), args.addrs); + let relay_url = endpoint + .my_relay() + .expect("should be connected to a relay server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected relay server"); + println!("node relay server url: {relay_url}\n"); + // Build a `NodeAddr` from the node_id, relay url, and UDP addresses. + let addr = NodeAddr::from_parts(args.node_id, Some(args.relay_url), args.addrs); // Attempt to connect, over the given ALPN. // Returns a QUIC connection. diff --git a/iroh-net/examples/connect.rs b/iroh-net/examples/connect.rs index 18749bd310..2ec735cbca 100644 --- a/iroh-net/examples/connect.rs +++ b/iroh-net/examples/connect.rs @@ -1,8 +1,8 @@ //! The smallest example showing how to use iroh-net and `MagicEndpoint` to connect to a remote node. //! -//! We use the node ID (the PublicKey of the remote node), the direct UDP addresses, and the DERP url to achieve a connection. +//! We use the node ID (the PublicKey of the remote node), the direct UDP addresses, and the relay url to achieve a connection. //! -//! This example uses the default DERP servers to attempt to holepunch, and will use that DERP server to relay packets if the two devices cannot establish a direct UDP connection. +//! This example uses the default relay servers to attempt to holepunch, and will use that relay server to relay packets if the two devices cannot establish a direct UDP connection. //! //! Run the `listen` example first (`iroh-net/examples/listen.rs`), which will give you instructions on how to run this example to watch two nodes connect and exchange bytes. use std::net::SocketAddr; @@ -11,8 +11,8 @@ use anyhow::Context; use clap::Parser; use futures::StreamExt; use iroh_base::base32; -use iroh_net::derp::DerpUrl; -use iroh_net::{derp::DerpMode, key::SecretKey, MagicEndpoint, NodeAddr}; +use iroh_net::relay::RelayUrl; +use iroh_net::{key::SecretKey, relay::RelayMode, MagicEndpoint, NodeAddr}; use tracing::info; // An example ALPN that we are using to communicate over the `MagicEndpoint` @@ -26,9 +26,9 @@ struct Cli { /// The list of direct UDP addresses for the remote node. #[clap(long, value_parser, num_args = 1.., value_delimiter = ' ')] addrs: Vec, - /// The url of the DERP server the remote node can also be reached at. + /// The url of the relay server the remote node can also be reached at. #[clap(long)] - derp_url: DerpUrl, + relay_url: RelayUrl, } #[tokio::main] @@ -39,17 +39,17 @@ async fn main() -> anyhow::Result<()> { let secret_key = SecretKey::generate(); println!("secret key: {}", base32::fmt(secret_key.to_bytes())); - // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the DERP protocol and DERP servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the DERP servers. + // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the relay protocol and relay servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the relay servers. let endpoint = MagicEndpoint::builder() // The secret key is used to authenticate with other nodes. The PublicKey portion of this secret key is how we identify nodes, often referred to as the `node_id` in our codebase. .secret_key(secret_key) // Set the ALPN protocols this endpoint will accept on incoming connections .alpns(vec![EXAMPLE_ALPN.to_vec()]) - // `DerpMode::Default` means that we will use the default DERP servers to holepunch and relay. - // Use `DerpMode::Custom` to pass in a `DerpMap` with custom DERP urls. - // Use `DerpMode::Disable` to disable holepunching and relaying over HTTPS - // If you want to experiment with relaying using your own DERP server, you must pass in the same custom DERP url to both the `listen` code AND the `connect` code - .derp_mode(DerpMode::Default) + // `RelayMode::Default` means that we will use the default relay servers to holepunch and relay. + // Use `RelayMode::Custom` to pass in a `RelayMap` with custom relay urls. + // Use `RelayMode::Disable` to disable holepunching and relaying over HTTPS + // If you want to experiment with relaying using your own relay server, you must pass in the same custom relay url to both the `listen` code AND the `connect` code + .relay_mode(RelayMode::Default) // You can choose a port to bind to, but passing in `0` will bind the socket to a random available port .bind(0) .await?; @@ -66,12 +66,12 @@ async fn main() -> anyhow::Result<()> { println!("\t{}", local_endpoint.addr) } - let derp_url = endpoint - .my_derp() - .expect("should be connected to a DERP server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected DERP server"); - println!("node DERP server url: {derp_url}\n"); - // Build a `NodeAddr` from the node_id, DERP url, and UDP addresses. - let addr = NodeAddr::from_parts(args.node_id, Some(args.derp_url), args.addrs); + let relay_url = endpoint + .my_relay() + .expect("should be connected to a relay server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected relay server"); + println!("node relay server url: {relay_url}\n"); + // Build a `NodeAddr` from the node_id, relay url, and UDP addresses. + let addr = NodeAddr::from_parts(args.node_id, Some(args.relay_url), args.addrs); // Attempt to connect, over the given ALPN. // Returns a Quinn connection. diff --git a/iroh-net/examples/listen-unreliable.rs b/iroh-net/examples/listen-unreliable.rs index 4636ade2f2..4ed651ff1a 100644 --- a/iroh-net/examples/listen-unreliable.rs +++ b/iroh-net/examples/listen-unreliable.rs @@ -1,12 +1,12 @@ //! The smallest example showing how to use iroh-net and `MagicEndpoint` to connect two devices and pass bytes using unreliable datagrams. //! -//! This example uses the default DERP servers to attempt to holepunch, and will use that DERP server to relay packets if the two devices cannot establish a direct UDP connection. +//! This example uses the default relay servers to attempt to holepunch, and will use that relay server to relay packets if the two devices cannot establish a direct UDP connection. //! run this example from the project root: //! $ cargo run --example listen-unreliable use anyhow::Context; use futures::StreamExt; use iroh_base::base32; -use iroh_net::{derp::DerpMode, key::SecretKey, MagicEndpoint}; +use iroh_net::{key::SecretKey, relay::RelayMode, MagicEndpoint}; use tracing::info; // An example ALPN that we are using to communicate over the `MagicEndpoint` @@ -19,17 +19,17 @@ async fn main() -> anyhow::Result<()> { let secret_key = SecretKey::generate(); println!("secret key: {}", base32::fmt(secret_key.to_bytes())); - // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the DERP protocol and DERP servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the DERP servers. + // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the relay servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the relay servers. let endpoint = MagicEndpoint::builder() // The secret key is used to authenticate with other nodes. The PublicKey portion of this secret key is how we identify nodes, often referred to as the `node_id` in our codebase. .secret_key(secret_key) // set the ALPN protocols this endpoint will accept on incoming connections .alpns(vec![EXAMPLE_ALPN.to_vec()]) - // `DerpMode::Default` means that we will use the default DERP servers to holepunch and relay. - // Use `DerpMode::Custom` to pass in a `DerpMap` with custom DERP urls. - // Use `DerpMode::Disable` to disable holepunching and relaying over HTTPS - // If you want to experiment with relaying using your own DERP server, you must pass in the same custom DERP url to both the `listen` code AND the `connect` code - .derp_mode(DerpMode::Default) + // `RelayMode::Default` means that we will use the default relay servers to holepunch and relay. + // Use `RelayMode::Custom` to pass in a `RelayMap` with custom relay urls. + // Use `RelayMode::Disable` to disable holepunching and relaying over HTTPS + // If you want to experiment with relaying using your own relay server, you must pass in the same custom relay url to both the `listen` code AND the `connect` code + .relay_mode(RelayMode::Default) // you can choose a port to bind to, but passing in `0` will bind the socket to a random available port .bind(0) .await?; @@ -52,14 +52,14 @@ async fn main() -> anyhow::Result<()> { .collect::>() .join(" "); - let derp_url = endpoint - .my_derp() - .expect("should be connected to a DERP server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected DERP server"); - println!("node DERP server url: {derp_url}"); + let relay_url = endpoint + .my_relay() + .expect("should be connected to a relay server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected relay server"); + println!("node relay server url: {relay_url}"); println!("\nin a separate terminal run:"); println!( - "\tcargo run --example connect-unreliable -- --node-id {me} --addrs \"{local_addrs}\" --derp-url {derp_url}\n" + "\tcargo run --example connect-unreliable -- --node-id {me} --addrs \"{local_addrs}\" --relay-url {relay_url}\n" ); // accept incoming connections, returns a normal QUIC connection diff --git a/iroh-net/examples/listen.rs b/iroh-net/examples/listen.rs index ff977a6853..5049ac4343 100644 --- a/iroh-net/examples/listen.rs +++ b/iroh-net/examples/listen.rs @@ -1,12 +1,12 @@ //! The smallest example showing how to use iroh-net and `MagicEndpoint` to connect two devices. //! -//! This example uses the default DERP servers to attempt to holepunch, and will use that DERP server to relay packets if the two devices cannot establish a direct UDP connection. +//! This example uses the default relay servers to attempt to holepunch, and will use that relay server to relay packets if the two devices cannot establish a direct UDP connection. //! run this example from the project root: //! $ cargo run --example listen use anyhow::Context; use futures::StreamExt; use iroh_base::base32; -use iroh_net::{derp::DerpMode, key::SecretKey, MagicEndpoint}; +use iroh_net::{key::SecretKey, relay::RelayMode, MagicEndpoint}; use tracing::{debug, info}; // An example ALPN that we are using to communicate over the `MagicEndpoint` @@ -19,17 +19,17 @@ async fn main() -> anyhow::Result<()> { let secret_key = SecretKey::generate(); println!("secret key: {}", base32::fmt(secret_key.to_bytes())); - // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the DERP protocol and DERP servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the DERP servers. + // Build a `MagicEndpoint`, which uses PublicKeys as node identifiers, uses QUIC for directly connecting to other nodes, and uses the relay protocol and relay servers to holepunch direct connections between nodes when there are NATs or firewalls preventing direct connections. If no direct connection can be made, packets are relayed over the relay servers. let endpoint = MagicEndpoint::builder() // The secret key is used to authenticate with other nodes. The PublicKey portion of this secret key is how we identify nodes, often referred to as the `node_id` in our codebase. .secret_key(secret_key) // set the ALPN protocols this endpoint will accept on incoming connections .alpns(vec![EXAMPLE_ALPN.to_vec()]) - // `DerpMode::Default` means that we will use the default DERP servers to holepunch and relay. - // Use `DerpMode::Custom` to pass in a `DerpMap` with custom DERP urls. - // Use `DerpMode::Disable` to disable holepunching and relaying over HTTPS - // If you want to experiment with relaying using your own DERP server, you must pass in the same custom DERP url to both the `listen` code AND the `connect` code - .derp_mode(DerpMode::Default) + // `RelayMode::Default` means that we will use the default relay servers to holepunch and relay. + // Use `RelayMode::Custom` to pass in a `RelayMap` with custom relay urls. + // Use `RelayMode::Disable` to disable holepunching and relaying over HTTPS + // If you want to experiment with relaying using your own relay server, you must pass in the same custom relay url to both the `listen` code AND the `connect` code + .relay_mode(RelayMode::Default) // you can choose a port to bind to, but passing in `0` will bind the socket to a random available port .bind(0) .await?; @@ -52,14 +52,14 @@ async fn main() -> anyhow::Result<()> { .collect::>() .join(" "); - let derp_url = endpoint - .my_derp() - .expect("should be connected to a DERP server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected DERP server"); - println!("node DERP server url: {derp_url}"); + let relay_url = endpoint + .my_relay() + .expect("should be connected to a relay server, try calling `endpoint.local_endpoints()` or `endpoint.connect()` first, to ensure the endpoint has actually attempted a connection before checking for the connected relay server"); + println!("node relay server url: {relay_url}"); println!("\nin a separate terminal run:"); println!( - "\tcargo run --example connect -- --node-id {me} --addrs \"{local_addrs}\" --derp-url {derp_url}\n" + "\tcargo run --example connect -- --node-id {me} --addrs \"{local_addrs}\" --relay-url {relay_url}\n" ); // accept incoming connections, returns a normal QUIC connection while let Some(conn) = endpoint.accept().await { diff --git a/iroh-net/src/bin/derper.rs b/iroh-net/src/bin/iroh-relay.rs similarity index 90% rename from iroh-net/src/bin/derper.rs rename to iroh-net/src/bin/iroh-relay.rs index 045a2537e3..7fe65649e4 100644 --- a/iroh-net/src/bin/derper.rs +++ b/iroh-net/src/bin/iroh-relay.rs @@ -1,4 +1,4 @@ -//! A simple DERP server. +//! A simple relay server. //! //! Based on /tailscale/cmd/derper @@ -17,12 +17,12 @@ use http::{response::Builder as ResponseBuilder, HeaderMap}; use hyper::body::Incoming; use hyper::{Method, Request, Response, StatusCode}; use iroh_metrics::inc; -use iroh_net::defaults::{DEFAULT_DERP_STUN_PORT, NA_DERP_HOSTNAME}; -use iroh_net::derp::http::{ - ServerBuilder as DerpServerBuilder, TlsAcceptor, TlsConfig as DerpTlsConfig, -}; -use iroh_net::derp::{self}; +use iroh_net::defaults::{DEFAULT_RELAY_STUN_PORT, NA_RELAY_HOSTNAME}; use iroh_net::key::SecretKey; +use iroh_net::relay::http::{ + ServerBuilder as RelayServerBuilder, TlsAcceptor, TlsConfig as RelayTlsConfig, +}; +use iroh_net::relay::{self}; use iroh_net::stun; use serde::{Deserialize, Serialize}; use serde_with::{serde_as, DisplayFromStr}; @@ -42,13 +42,13 @@ fn body_empty() -> BytesBody { http_body_util::Full::new(hyper::body::Bytes::new()) } -/// A simple DERP server. +/// A simple relay server. #[derive(Parser, Debug, Clone)] #[clap(version, about, long_about = None)] struct Cli { /// Run in localhost development mode over plain HTTP. /// - /// Defaults to running the derper on port 3340. + /// Defaults to running the relay server on port 3340. /// /// Running in dev mode will ignore any config file fields pertaining to TLS. #[clap(long, default_value_t = false)] @@ -166,7 +166,7 @@ fn load_secret_key(filename: impl AsRef) -> Result { #[serde_as] #[derive(Serialize, Deserialize)] struct Config { - /// [`SecretKey`] for this Derper. + /// [`SecretKey`] for this relay server. #[serde_as(as = "DisplayFromStr")] #[serde(default = "SecretKey::generate")] secret_key: SecretKey, @@ -174,24 +174,24 @@ struct Config { /// /// Defaults to `[::]:443`. /// - /// If the port address is 443, the derper will issue a warning if it is started + /// If the port address is 443, the relay server will issue a warning if it is started /// without a `tls` config. addr: SocketAddr, /// The UDP port on which to serve STUN. The listener is bound to the same IP (if any) as - /// specified in the `addr` field. Defaults to [`DEFAULT_DERP_STUN_PORT`]. + /// specified in the `addr` field. Defaults to [`DEFAULT_RELAY_STUN_PORT`]. stun_port: u16, - /// Certificate hostname. Defaults to [`NA_DERP_HOSTNAME`]. + /// Certificate hostname. Defaults to [`NA_RELAY_HOSTNAME`]. hostname: String, /// Whether to run a STUN server. It will bind to the same IP as the `addr` field. /// /// Defaults to `true`. enable_stun: bool, - /// Whether to run a DERP server. The only reason to set this false is if you're decommissioning a + /// Whether to run a relay server. The only reason to set this false is if you're decommissioning a /// server but want to keep its bootstrap DNS functionality still running. /// /// Defaults to `true` - enable_derp: bool, + enable_relay: bool, /// TLS specific configuration tls: Option, /// Rate limiting configuration @@ -224,7 +224,7 @@ struct TlsConfig { /// The port on which to serve a response for the captive portal probe over HTTP. /// /// The listener is bound to the same IP as specified in the `addr` field. Defaults to 80. - /// This field is only read in we are serving the derper over HTTPS. In that case, we must listen for requests for the `/generate_204` over a non-TLS connection. + /// This field is only read in we are serving the relay server over HTTPS. In that case, we must listen for requests for the `/generate_204` over a non-TLS connection. captive_portal_port: Option, } @@ -241,10 +241,10 @@ impl Default for Config { Self { secret_key: SecretKey::generate(), addr: (Ipv6Addr::UNSPECIFIED, 443).into(), - stun_port: DEFAULT_DERP_STUN_PORT, - hostname: NA_DERP_HOSTNAME.into(), + stun_port: DEFAULT_RELAY_STUN_PORT, + hostname: NA_RELAY_HOSTNAME.into(), enable_stun: true, - enable_derp: true, + enable_relay: true, tls: None, limits: None, #[cfg(feature = "metrics")] @@ -317,7 +317,7 @@ pub fn init_metrics_collection( // doesn't start the server if the address is None if let Some(metrics_addr) = metrics_addr { iroh_metrics::core::Core::init(|reg, metrics| { - metrics.insert(iroh_net::metrics::DerpMetrics::new(reg)); + metrics.insert(iroh_net::metrics::RelayMetrics::new(reg)); metrics.insert(StunMetrics::new(reg)); }); @@ -386,11 +386,11 @@ async fn run( } } else if addr.port() == 443 { // no tls config, but the port is 443 - warn!("The address port is 443, which is typically the expected tls port, but you have not supplied any tls configuration.\nIf you meant to run the derper with tls enabled, adjust the config file to include tls configuration."); + warn!("The address port is 443, which is typically the expected tls port, but you have not supplied any tls configuration.\nIf you meant to run the relay server with tls enabled, adjust the config file to include tls configuration."); } - // set up derp configuration details - let secret_key = if cfg.enable_derp { + // set up relay configuration details + let secret_key = if cfg.enable_relay { Some(cfg.secret_key) } else { None @@ -423,7 +423,7 @@ async fn run( headers.insert(*name, value.parse()?); } ( - Some(DerpTlsConfig { config, acceptor }), + Some(RelayTlsConfig { config, acceptor }), headers, tls_config .captive_portal_port @@ -433,11 +433,11 @@ async fn run( (None, HeaderMap::new(), 0) }; - let mut builder = DerpServerBuilder::new(addr) + let mut builder = RelayServerBuilder::new(addr) .secret_key(secret_key.map(Into::into)) .headers(headers) .tls_config(tls_config.clone()) - .derp_override(Box::new(derp_disabled_handler)) + .relay_override(Box::new(relay_disabled_handler)) .request_handler(Method::GET, "/", Box::new(root_handler)) .request_handler(Method::GET, "/index.html", Box::new(root_handler)) .request_handler(Method::GET, "/derp/probe", Box::new(probe_handler)) @@ -451,7 +451,7 @@ async fn run( Box::new(serve_no_content_handler), ); } - let derp_server = builder.spawn().await?; + let relay_server = builder.spawn().await?; // captive portal detections must be served over HTTP let captive_portal_task = if tls_config.is_some() { @@ -463,7 +463,7 @@ async fn run( }; if let Some(addr_sender) = addr_sender { - if let Err(e) = addr_sender.send(derp_server.addr()) { + if let Err(e) = addr_sender.send(relay_server.addr()) { bail!("Unable to send the local SocketAddr, the Sender was dropped - {e:?}"); } } @@ -476,7 +476,7 @@ async fn run( if let Some(task) = captive_portal_task { task.abort() } - derp_server.shutdown().await; + relay_server.shutdown().await; Ok(()) } @@ -485,13 +485,13 @@ const NO_CONTENT_CHALLENGE_HEADER: &str = "X-Tailscale-Challenge"; const NO_CONTENT_RESPONSE_HEADER: &str = "X-Tailscale-Response"; const NOTFOUND: &[u8] = b"Not Found"; -const DERP_DISABLED: &[u8] = b"derp server disabled"; +const RELAY_DISABLED: &[u8] = b"relay server disabled"; const ROBOTS_TXT: &[u8] = b"User-agent: *\nDisallow: /\n"; const INDEX: &[u8] = br#" -

DERP

+

RELAY

This is an - Iroh DERP + Iroh Relay server.

"#; @@ -520,7 +520,7 @@ async fn serve_captive_portal_service(addr: SocketAddr) -> Result> for CaptivePortalService { } } -fn derp_disabled_handler( +fn relay_disabled_handler( _r: Request, response: ResponseBuilder, ) -> HyperResult> { response .status(StatusCode::NOT_FOUND) - .body(DERP_DISABLED.into()) + .body(RELAY_DISABLED.into()) .map_err(|err| Box::new(err) as HyperError) } @@ -663,7 +663,10 @@ async fn serve_stun(host: IpAddr, port: u16) { .await; } Err(err) => { - error!("failed to open STUN listener: {:#?}", err); + error!( + "failed to open STUN listener at host {host} and port {port}: {:#?}", + err + ); } } } @@ -736,7 +739,7 @@ async fn server_stun_listener(sock: UdpSocket) { } } -// var validProdHostname = regexp.MustCompile(`^derp([^.]*)\.tailscale\.com\.?$`) +// var validProdHostname = regexp.MustCompile(`^relay([^.]*)\.tailscale\.com\.?$`) // func prodAutocertHostPolicy(_ context.Context, host string) error { // if validProdHostname.MatchString(host) { @@ -811,7 +814,7 @@ mod metrics { struct_iterable::Iterable, }; - /// StunMetrics tracked for the DERPER + /// StunMetrics tracked for the relay server #[allow(missing_docs)] #[derive(Debug, Clone, Iterable)] pub struct StunMetrics { @@ -863,10 +866,11 @@ mod tests { use anyhow::Result; use bytes::Bytes; use http_body_util::BodyExt; - use iroh_base::node_addr::DerpUrl; - use iroh_net::derp::http::ClientBuilder; - use iroh_net::derp::ReceivedMessage; + use iroh_base::node_addr::RelayUrl; use iroh_net::key::SecretKey; + use iroh_net::relay::http::ClientBuilder; + use iroh_net::relay::ReceivedMessage; + use tokio::task::JoinHandle; #[tokio::test] async fn test_serve_no_content_handler() { @@ -903,8 +907,18 @@ mod tests { ); } + struct DropServer { + server_task: JoinHandle<()>, + } + + impl Drop for DropServer { + fn drop(&mut self) { + self.server_task.abort(); + } + } + #[tokio::test] - async fn test_derper_basic() -> Result<()> { + async fn test_relay_server_basic() -> Result<()> { tracing_subscriber::registry() .with(tracing_subscriber::fmt::layer().with_writer(std::io::stderr)) .with(EnvFilter::from_default_env()) @@ -913,41 +927,44 @@ mod tests { // Binding to LOCALHOST to satisfy issues when binding to UNSPECIFIED in Windows for tests // Binding to Ipv4 because, when binding to `IPv6::UNSPECIFIED`, it will also listen for // IPv4 connections, but will not automatically do the same for `LOCALHOST`. In order to - // test STUN, which only listens on Ipv4, we must bind the whole derper to Ipv4::LOCALHOST. + // test STUN, which only listens on Ipv4, we must bind the whole relay server to Ipv4::LOCALHOST. let cfg = Config { addr: SocketAddr::new(IpAddr::V4(Ipv4Addr::LOCALHOST), 0), ..Default::default() }; let (addr_send, addr_recv) = tokio::sync::oneshot::channel(); - let derper_task = tokio::spawn( + let relay_server_task = tokio::spawn( async move { // dev mode will bind to IPv6::UNSPECIFIED, so setting it `false` let res = run(false, cfg, Some(addr_send)).await; if let Err(e) = res { - eprintln!("error starting derp server {e}"); + eprintln!("error starting relay server {e}"); } } - .instrument(debug_span!("derper")), + .instrument(debug_span!("relay server")), ); + let _drop_server = DropServer { + server_task: relay_server_task, + }; - let derper_addr = addr_recv.await?; - let derper_str_url = format!("http://{}", derper_addr); - let derper_url: DerpUrl = derper_str_url.parse().unwrap(); + let relay_server_addr = addr_recv.await?; + let relay_server_str_url = format!("http://{}", relay_server_addr); + let relay_server_url: RelayUrl = relay_server_str_url.parse().unwrap(); // set up clients let a_secret_key = SecretKey::generate(); let a_key = a_secret_key.public(); let (client_a, mut client_a_receiver) = - ClientBuilder::new(derper_url.clone()).build(a_secret_key); + ClientBuilder::new(relay_server_url.clone()).build(a_secret_key); let connect_client = client_a.clone(); - // give the derper some time to set up + // give the relay server some time to set up if let Err(e) = tokio::time::timeout(Duration::from_secs(10), async move { loop { match connect_client.connect().await { Ok(_) => break, Err(e) => { - tracing::warn!("client a unable to connect to derper: {e:?}. Attempting to dial again in 10ms"); + tracing::warn!("client a unable to connect to relay server: {e:?}. Attempting to dial again in 10ms"); tokio::time::sleep(Duration::from_millis(100)).await } } @@ -955,13 +972,13 @@ mod tests { }) .await { - bail!("error connecting client a to derper: {e:?}"); + bail!("error connecting client a to relay server: {e:?}"); } let b_secret_key = SecretKey::generate(); let b_key = b_secret_key.public(); let (client_b, mut client_b_receiver) = - ClientBuilder::new(derper_url.clone()).build(b_secret_key); + ClientBuilder::new(relay_server_url.clone()).build(b_secret_key); client_b.connect().await?; let msg = Bytes::from("hello, b"); @@ -1015,14 +1032,14 @@ mod tests { // get 200 home page response tracing::info!("send request for homepage"); - let res = reqwest::get(derper_str_url).await?; + let res = reqwest::get(relay_server_str_url).await?; assert!(res.status().is_success()); tracing::info!("got OK"); // test captive portal tracing::info!("test captive portal response"); - let url = derper_url.join("/generate_204")?; + let url = relay_server_url.join("/generate_204")?; let challenge = "123az__."; let client = reqwest::Client::new(); let res = client @@ -1038,7 +1055,6 @@ mod tests { tracing::info!("got successful captive portal response"); - derper_task.abort(); Ok(()) } } diff --git a/iroh-net/src/config.rs b/iroh-net/src/config.rs index 34b168d2b5..8c98749810 100644 --- a/iroh-net/src/config.rs +++ b/iroh-net/src/config.rs @@ -2,7 +2,7 @@ use std::{collections::BTreeMap, fmt::Display, net::SocketAddr}; -use crate::derp::DerpUrl; +use crate::relay::RelayUrl; use super::portmapper; @@ -75,24 +75,24 @@ pub struct NetInfo { /// Probe indicating the presence of port mapping protocols on the LAN. pub portmap_probe: Option, - /// This node's preferred DERP server for incoming traffic. The node might be be temporarily - /// connected to multiple DERP servers (to send to other nodes) - /// but PreferredDERP is the instance number that the node + /// This node's preferred relay server for incoming traffic. The node might be be temporarily + /// connected to multiple relay servers (to send to other nodes) + /// but PreferredRelay is the instance number that the node /// subscribes to traffic at. Zero means disconnected or unknown. - pub preferred_derp: Option, + pub preferred_relay: Option, /// LinkType is the current link type, if known. pub link_type: Option, - /// The fastest recent time to reach various DERP STUN servers, in seconds. + /// The fastest recent time to reach various relay STUN servers, in seconds. /// /// This should only be updated rarely, or when there's a /// material change, as any change here also gets uploaded to the control plane. - pub derp_latency: BTreeMap, + pub relay_latency: BTreeMap, } impl NetInfo { - /// reports whether `self` and `other` are basically equal, ignoring changes in DERP ServerLatency & DerpLatency. + /// reports whether `self` and `other` are basically equal, ignoring changes in relay ServerLatency & RelayLatency. pub fn basically_equal(&self, other: &Self) -> bool { let eq_icmp_v4 = match (self.working_icmp_v4, other.working_icmp_v4) { (Some(slf), Some(other)) => slf == other, @@ -111,7 +111,7 @@ impl NetInfo { && eq_icmp_v6 && self.have_port_map == other.have_port_map && self.portmap_probe == other.portmap_probe - && self.preferred_derp == other.preferred_derp + && self.preferred_relay == other.preferred_relay && self.link_type == other.link_type } } diff --git a/iroh-net/src/defaults.rs b/iroh-net/src/defaults.rs index 251b85dd10..002100d659 100644 --- a/iroh-net/src/defaults.rs +++ b/iroh-net/src/defaults.rs @@ -2,44 +2,44 @@ use url::Url; -use crate::derp::{DerpMap, DerpNode}; +use crate::relay::{RelayMap, RelayNode}; -/// Hostname of the default NA Derp. -pub const NA_DERP_HOSTNAME: &str = "use1-1.derp.iroh.network."; -/// Hostname of the default EU Derp. -pub const EU_DERP_HOSTNAME: &str = "euw1-1.derp.iroh.network."; +/// Hostname of the default NA relay. +pub const NA_RELAY_HOSTNAME: &str = "use1-1.derp.iroh.network."; +/// Hostname of the default EU relay. +pub const EU_RELAY_HOSTNAME: &str = "euw1-1.derp.iroh.network."; /// STUN port as defined by [RFC 8489]() -pub const DEFAULT_DERP_STUN_PORT: u16 = 3478; +pub const DEFAULT_RELAY_STUN_PORT: u16 = 3478; -/// Get the default [`DerpMap`]. -pub fn default_derp_map() -> DerpMap { - DerpMap::from_nodes([default_na_derp_node(), default_eu_derp_node()]) +/// Get the default [`RelayMap`]. +pub fn default_relay_map() -> RelayMap { + RelayMap::from_nodes([default_na_relay_node(), default_eu_relay_node()]) .expect("default nodes invalid") } -/// Get the default [`DerpNode`] for NA. -pub fn default_na_derp_node() -> DerpNode { - // The default NA derper run by number0. - let url: Url = format!("https://{NA_DERP_HOSTNAME}") +/// Get the default [`RelayNode`] for NA. +pub fn default_na_relay_node() -> RelayNode { + // The default NA relay server run by number0. + let url: Url = format!("https://{NA_RELAY_HOSTNAME}") .parse() .expect("default url"); - DerpNode { + RelayNode { url: url.into(), stun_only: false, - stun_port: DEFAULT_DERP_STUN_PORT, + stun_port: DEFAULT_RELAY_STUN_PORT, } } -/// Get the default [`DerpNode`] for EU. -pub fn default_eu_derp_node() -> DerpNode { - // The default EU derper run by number0. - let url: Url = format!("https://{EU_DERP_HOSTNAME}") +/// Get the default [`RelayNode`] for EU. +pub fn default_eu_relay_node() -> RelayNode { + // The default EU relay server run by number0. + let url: Url = format!("https://{EU_RELAY_HOSTNAME}") .parse() .expect("default_url"); - DerpNode { + RelayNode { url: url.into(), stun_only: false, - stun_port: DEFAULT_DERP_STUN_PORT, + stun_port: DEFAULT_RELAY_STUN_PORT, } } diff --git a/iroh-net/src/derp.rs b/iroh-net/src/derp.rs deleted file mode 100644 index b9d5def89d..0000000000 --- a/iroh-net/src/derp.rs +++ /dev/null @@ -1,29 +0,0 @@ -//! Package derp implements the Designated Encrypted Relay for Packets (DERP) -//! protocol written by Tailscale. -// -//! DERP routes packets to clients using curve25519 keys as addresses. -// -//! DERP is used by proxy encrypted QUIC packets through the DERP servers when -//! a direct path cannot be found or opened. DERP is a last resort. Both side -//! between very aggressive NATs, firewalls, no IPv6, etc? Well, DERP. -//! Based on tailscale/derp/derp.go - -#![deny(missing_docs, rustdoc::broken_intra_doc_links)] - -pub(crate) mod client; -pub(crate) mod client_conn; -pub(crate) mod clients; -mod codec; -pub mod http; -mod map; -mod metrics; -pub(crate) mod server; -pub(crate) mod types; - -pub use self::client::{Client as DerpClient, ReceivedMessage}; -pub use self::codec::MAX_PACKET_SIZE; -pub use self::http::Client as HttpClient; -pub use self::map::{DerpMap, DerpMode, DerpNode}; -pub use self::metrics::Metrics; -pub use self::server::{ClientConnHandler, MaybeTlsStream as MaybeTlsStreamServer, Server}; -pub use iroh_base::node_addr::DerpUrl; diff --git a/iroh-net/src/dialer.rs b/iroh-net/src/dialer.rs index daf4dc3f4f..1cd5854a38 100644 --- a/iroh-net/src/dialer.rs +++ b/iroh-net/src/dialer.rs @@ -32,7 +32,7 @@ impl Dialer { /// Start to dial a node. /// - /// Note that the node's addresses and/or derp url must be added to the endpoint's + /// Note that the node's addresses and/or relay url must be added to the endpoint's /// addressbook for a dial to succeed, see [`MagicEndpoint::add_node_addr`]. pub fn queue_dial(&mut self, node_id: NodeId, alpn: &'static [u8]) { if self.is_pending(&node_id) { diff --git a/iroh-net/src/disco.rs b/iroh-net/src/disco.rs index dfd4b42dee..e218e469da 100644 --- a/iroh-net/src/disco.rs +++ b/iroh-net/src/disco.rs @@ -26,7 +26,7 @@ use std::{ use anyhow::{anyhow, bail, ensure, Context, Result}; use url::Url; -use crate::{derp::DerpUrl, key, net::ip::to_canonical}; +use crate::{key, net::ip::to_canonical, relay::RelayUrl}; use super::{key::PublicKey, stun}; @@ -132,25 +132,25 @@ pub struct Pong { pub src: SendAddr, } -/// Addresses to which we can send. This is either a UDP or a derp address. +/// Addresses to which we can send. This is either a UDP or a relay address. #[derive(Debug, Clone, PartialEq, Eq, Hash)] pub enum SendAddr { /// UDP, the ip addr. Udp(SocketAddr), - /// Derp Url. - Derp(DerpUrl), + /// Relay Url. + Relay(RelayUrl), } impl SendAddr { - /// Returns if this is a `derp` addr. - pub fn is_derp(&self) -> bool { - matches!(self, Self::Derp(_)) + /// Returns if this is a `relay` addr. + pub fn is_relay(&self) -> bool { + matches!(self, Self::Relay(_)) } - /// Returns the `Some(Url)` if it is a derp addr. - pub fn derp_url(&self) -> Option { + /// Returns the `Some(Url)` if it is a relay addr. + pub fn relay_url(&self) -> Option { match self { - Self::Derp(url) => Some(url.clone()), + Self::Relay(url) => Some(url.clone()), Self::Udp(_) => None, } } @@ -159,7 +159,7 @@ impl SendAddr { impl PartialEq for SendAddr { fn eq(&self, other: &SocketAddr) -> bool { match self { - Self::Derp(_) => false, + Self::Relay(_) => false, Self::Udp(addr) => addr.eq(other), } } @@ -168,13 +168,13 @@ impl PartialEq for SendAddr { impl Display for SendAddr { fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result { match self { - SendAddr::Derp(id) => write!(f, "Derp({})", id), + SendAddr::Relay(id) => write!(f, "Relay({})", id), SendAddr::Udp(addr) => write!(f, "UDP({})", addr), } } } -/// Message sent only over DERP to request that the recipient try +/// Message sent only over the relay to request that the recipient try /// to open up a magicsock path back to the sender. /// /// The sender should've already sent UDP packets to the peer to open @@ -224,7 +224,7 @@ fn send_addr_from_bytes(p: &[u8]) -> Result { 1u8 => { let s = std::str::from_utf8(&p[1..])?; let u: Url = s.parse()?; - Ok(SendAddr::Derp(u.into())) + Ok(SendAddr::Relay(u.into())) } _ => { bail!("invalid addr type {}", p[0]); @@ -234,7 +234,7 @@ fn send_addr_from_bytes(p: &[u8]) -> Result { fn send_addr_to_vec(addr: &SendAddr) -> Vec { match addr { - SendAddr::Derp(url) => { + SendAddr::Relay(url) => { let mut out = vec![1u8]; out.extend_from_slice(url.to_string().as_bytes()); out diff --git a/iroh-net/src/discovery.rs b/iroh-net/src/discovery.rs index 3a5b87152c..0bb3791fad 100644 --- a/iroh-net/src/discovery.rs +++ b/iroh-net/src/discovery.rs @@ -13,7 +13,7 @@ use crate::{AddrInfo, MagicEndpoint, NodeId}; /// Node discovery for [`super::MagicEndpoint`]. /// /// The purpose of this trait is to hook up a node discovery mechanism that -/// allows finding information such as the Derp URL and direct addresses +/// allows finding information such as the relay URL and direct addresses /// of a node given its [`NodeId`]. /// /// To allow for discovery, the [`super::MagicEndpoint`] will call `publish` whenever @@ -272,7 +272,7 @@ mod tests { use parking_lot::Mutex; use rand::Rng; - use crate::{derp::DerpMode, key::SecretKey, NodeAddr}; + use crate::{key::SecretKey, relay::RelayMode, NodeAddr}; use super::*; @@ -335,7 +335,7 @@ mod tests { // "240.0.0.0/4" is reserved and unreachable let addr: SocketAddr = format!("240.0.0.1:{port}").parse().unwrap(); let addr_info = AddrInfo { - derp_url: None, + relay_url: None, direct_addresses: BTreeSet::from([addr]), }; Some((addr_info, ts)) @@ -506,7 +506,7 @@ mod tests { let ep1_wrong_addr = NodeAddr { node_id: ep1.node_id(), info: AddrInfo { - derp_url: None, + relay_url: None, direct_addresses: BTreeSet::from(["240.0.0.1:1000".parse().unwrap()]), }, }; @@ -518,7 +518,7 @@ mod tests { MagicEndpoint::builder() .secret_key(secret) .discovery(Box::new(disco)) - .derp_mode(DerpMode::Disabled) + .relay_mode(RelayMode::Disabled) .alpns(vec![TEST_ALPN.to_vec()]) .bind(0) .await diff --git a/iroh-net/src/dns.rs b/iroh-net/src/dns.rs index 80e0abbecb..094feffb2e 100644 --- a/iroh-net/src/dns.rs +++ b/iroh-net/src/dns.rs @@ -126,7 +126,7 @@ pub(crate) async fn lookup_ipv4_ipv6( #[cfg(test)] mod tests { - use crate::defaults::NA_DERP_HOSTNAME; + use crate::defaults::NA_RELAY_HOSTNAME; use super::*; @@ -134,7 +134,7 @@ mod tests { #[cfg_attr(target_os = "windows", ignore = "flaky")] async fn test_dns_lookup_basic() { let _logging = iroh_test::logging::setup(); - let res = DNS_RESOLVER.lookup_ip(NA_DERP_HOSTNAME).await.unwrap(); + let res = DNS_RESOLVER.lookup_ip(NA_RELAY_HOSTNAME).await.unwrap(); let res: Vec<_> = res.iter().collect(); assert!(!res.is_empty()); dbg!(res); @@ -144,7 +144,7 @@ mod tests { #[cfg_attr(target_os = "windows", ignore = "flaky")] async fn test_dns_lookup_ipv4_ipv6() { let _logging = iroh_test::logging::setup(); - let res = lookup_ipv4_ipv6(NA_DERP_HOSTNAME, Duration::from_secs(5)) + let res = lookup_ipv4_ipv6(NA_RELAY_HOSTNAME, Duration::from_secs(5)) .await .unwrap(); assert!(!res.is_empty()); diff --git a/iroh-net/src/lib.rs b/iroh-net/src/lib.rs index 95362a2ca1..128ab42a39 100644 --- a/iroh-net/src/lib.rs +++ b/iroh-net/src/lib.rs @@ -4,7 +4,7 @@ //! the high level [`MagicEndpoint`] is used to establish a QUIC connection with //! authenticated peers, relaying and holepunching support. //! -//! The "derp-only" feature forces all traffic to send over the derp relays. We still +//! The "relay-only" feature forces all traffic to send over the relays. We still //! receive traffic over udp and relay. This feature should only be used for testing. #![recursion_limit = "256"] @@ -12,7 +12,6 @@ pub mod config; pub mod defaults; -pub mod derp; pub mod dialer; mod disco; pub mod discovery; @@ -24,6 +23,7 @@ pub mod net; pub mod netcheck; pub mod ping; pub mod portmapper; +pub mod relay; pub mod stun; pub mod ticket; pub mod tls; diff --git a/iroh-net/src/magic_endpoint.rs b/iroh-net/src/magic_endpoint.rs index f1d765f2ac..816773d153 100644 --- a/iroh-net/src/magic_endpoint.rs +++ b/iroh-net/src/magic_endpoint.rs @@ -11,11 +11,11 @@ use tracing::{debug, trace}; use crate::{ config, - defaults::default_derp_map, - derp::{DerpMap, DerpMode, DerpUrl}, + defaults::default_relay_map, discovery::{Discovery, DiscoveryTask}, key::{PublicKey, SecretKey}, magicsock::{self, MagicSock}, + relay::{RelayMap, RelayMode, RelayUrl}, tls, NodeId, }; @@ -31,7 +31,7 @@ const DISCOVERY_WAIT_PERIOD: Duration = Duration::from_millis(500); #[derive(Debug)] pub struct MagicEndpointBuilder { secret_key: Option, - derp_mode: DerpMode, + relay_mode: RelayMode, alpn_protocols: Vec>, transport_config: Option, concurrent_connections: Option, @@ -45,7 +45,7 @@ impl Default for MagicEndpointBuilder { fn default() -> Self { Self { secret_key: Default::default(), - derp_mode: DerpMode::Default, + relay_mode: RelayMode::Default, alpn_protocols: Default::default(), transport_config: Default::default(), concurrent_connections: Default::default(), @@ -81,19 +81,19 @@ impl MagicEndpointBuilder { self } - /// Sets the DERP servers to assist in establishing connectivity. + /// Sets the relay servers to assist in establishing connectivity. /// - /// DERP servers are used to discover other peers by [`PublicKey`] and also help + /// relay servers are used to discover other peers by [`PublicKey`] and also help /// establish connections between peers by being an initial relay for traffic while /// assisting in holepunching to establish a direct connection between peers. /// - /// When using [DerpMode::Custom], the provided `derp_map` must contain at least one - /// configured derp node. If an invalid [`DerpMap`] is provided [`bind`] + /// When using [RelayMode::Custom], the provided `relay_map` must contain at least one + /// configured relay node. If an invalid [`RelayMap`] is provided [`bind`] /// will result in an error. /// /// [`bind`]: MagicEndpointBuilder::bind - pub fn derp_mode(mut self, derp_mode: DerpMode) -> Self { - self.derp_mode = derp_mode; + pub fn relay_mode(mut self, relay_mode: RelayMode) -> Self { + self.relay_mode = relay_mode; self } @@ -133,7 +133,7 @@ impl MagicEndpointBuilder { /// [`crate::discovery::ConcurrentDiscovery`]. /// /// If no discovery service is set, connecting to a node without providing its - /// direct addresses or Derp URLs will fail. + /// direct addresses or relay URLs will fail. /// /// See the documentation of the [`Discovery`] trait for details. pub fn discovery(mut self, discovery: Box) -> Self { @@ -148,12 +148,12 @@ impl MagicEndpointBuilder { /// You can pass `0` to let the operating system choose a free port for you. /// NOTE: This will be improved soon to add support for binding on specific addresses. pub async fn bind(self, bind_port: u16) -> Result { - let derp_map = match self.derp_mode { - DerpMode::Disabled => DerpMap::empty(), - DerpMode::Default => default_derp_map(), - DerpMode::Custom(derp_map) => { - ensure!(!derp_map.is_empty(), "Empty custom Derp server map",); - derp_map + let relay_map = match self.relay_mode { + RelayMode::Disabled => RelayMap::empty(), + RelayMode::Default => default_relay_map(), + RelayMode::Custom(relay_map) => { + ensure!(!relay_map.is_empty(), "Empty custom relay server map",); + relay_map } }; let secret_key = self.secret_key.unwrap_or_else(SecretKey::generate); @@ -169,7 +169,7 @@ impl MagicEndpointBuilder { let msock_opts = magicsock::Options { port: bind_port, secret_key, - derp_map, + relay_map, nodes_path: self.peers_path, discovery: self.discovery, }; @@ -305,11 +305,11 @@ impl MagicEndpoint { self.msock.local_endpoints() } - /// Get the DERP url we are connected to with the lowest latency. + /// Get the relay url we are connected to with the lowest latency. /// - /// Returns `None` if we are not connected to any DERPer. - pub fn my_derp(&self) -> Option { - self.msock.my_derp() + /// Returns `None` if we are not connected to any relayer. + pub fn my_relay(&self) -> Option { + self.msock.my_relay() } /// Get the [`NodeAddr`] for this endpoint. @@ -319,23 +319,23 @@ impl MagicEndpoint { .next() .await .ok_or(anyhow!("No endpoints found"))?; - let derp = self.my_derp(); + let relay = self.my_relay(); let addrs = addrs.into_iter().map(|x| x.addr).collect(); - Ok(NodeAddr::from_parts(self.node_id(), derp, addrs)) + Ok(NodeAddr::from_parts(self.node_id(), relay, addrs)) } /// Get the [`NodeAddr`] for this endpoint, while providing the endpoints. pub fn my_addr_with_endpoints(&self, eps: Vec) -> Result { - let derp = self.my_derp(); + let relay = self.my_relay(); let addrs = eps.into_iter().map(|x| x.addr).collect(); - Ok(NodeAddr::from_parts(self.node_id(), derp, addrs)) + Ok(NodeAddr::from_parts(self.node_id(), relay, addrs)) } /// Get information on all the nodes we have connection information about. /// - /// Includes the node's [`PublicKey`], potential DERP Url, its addresses with any known + /// Includes the node's [`PublicKey`], potential relay Url, its addresses with any known /// latency, and its [`crate::magicsock::ConnectionType`], which let's us know if we are - /// currently communicating with that node over a `Direct` (UDP) or `Relay` (DERP) connection. + /// currently communicating with that node over a `Direct` (UDP) or `Relay` (relay) connection. /// /// Connections are currently only pruned on user action (when we explicitly add a new address /// to the internal addressbook through [`MagicEndpoint::add_node_addr`]), so these connections @@ -346,9 +346,9 @@ impl MagicEndpoint { /// Get connection information about a specific node. /// - /// Includes the node's [`PublicKey`], potential DERP Url, its addresses with any known + /// Includes the node's [`PublicKey`], potential relay Url, its addresses with any known /// latency, and its [`crate::magicsock::ConnectionType`], which let's us know if we are - /// currently communicating with that node over a `Direct` (UDP) or `Relay` (DERP) connection. + /// currently communicating with that node over a `Direct` (UDP) or `Relay` (relay) connection. pub fn connection_info(&self, node_id: PublicKey) -> Option { self.msock.tracked_endpoint(node_id) } @@ -370,19 +370,19 @@ impl MagicEndpoint { /// Connect to a remote endpoint. /// /// A [`NodeAddr`] is required. It must contain the [`NodeId`] to dial and may also contain a - /// Derp URL and direct addresses. If direct addresses are provided, they will be used to - /// try and establish a direct connection without involving a Derp server. + /// relay URL and direct addresses. If direct addresses are provided, they will be used to + /// try and establish a direct connection without involving a relay server. /// /// The `alpn`, or application-level protocol identifier, is also required. The remote endpoint /// must support this `alpn`, otherwise the connection attempt will fail with an error. /// - /// If the [`NodeAddr`] contains only [`NodeId`] and no direct addresses and no Derp servers, + /// If the [`NodeAddr`] contains only [`NodeId`] and no direct addresses and no relay servers, /// a discovery service will be invoked, if configured, to try and discover the node's /// addressing information. The discovery services must be configured globally per [`MagicEndpoint`] /// with [`MagicEndpointBuilder::discovery`]. The discovery service will also be invoked if /// none of the existing or provided direct addresses are reachable. /// - /// If addresses or Derp servers are neither provided nor can be discovered, the connection + /// If addresses or relay servers are neither provided nor can be discovered, the connection /// attempt will fail with an error. pub async fn connect(&self, node_addr: NodeAddr, alpn: &[u8]) -> Result { if !node_addr.info.is_empty() { @@ -411,7 +411,7 @@ impl MagicEndpoint { None => { // We have not spoken to this endpoint before, and the user provided no direct - // addresses or Derp URLs. Thus, we start a discovery task and wait for the first + // addresses or relay URLs. Thus, we start a discovery task and wait for the first // result to arrive, and only then continue, because otherwise we wouldn't have any // path to the remote endpoint. let mut discovery = DiscoveryTask::start(self.clone(), node_id)?; @@ -472,13 +472,13 @@ impl MagicEndpoint { /// Inform the magic socket about addresses of the peer. /// /// This updates the magic socket's *netmap* with these addresses, which are used as candidates - /// when connecting to this peer (in addition to addresses obtained from a derp server). + /// when connecting to this peer (in addition to addresses obtained from a relay server). /// /// Note: updating the magic socket's *netmap* will also prune any connections that are *not* /// present in the netmap. /// - /// If no UDP addresses are added, and `derp_url` is `None`, it will error. - /// If no UDP addresses are added, and the given `derp_url` cannot be dialed, it will error. + /// If no UDP addresses are added, and `relay_url` is `None`, it will error. + /// If no UDP addresses are added, and the given `relay_url` cannot be dialed, it will error. // TODO: This is infallible, stop returning a result. pub fn add_node_addr(&self, node_addr: NodeAddr) -> Result<()> { self.msock.add_node_addr(node_addr); @@ -580,7 +580,7 @@ mod tests { use rand_core::SeedableRng; use tracing::{error_span, info, info_span, Instrument}; - use crate::test_utils::run_derper; + use crate::test_utils::run_relay_server; use super::*; @@ -589,32 +589,32 @@ mod tests { #[test] fn test_addr_info_debug() { let info = AddrInfo { - derp_url: Some("https://derp.example.com".parse().unwrap()), + relay_url: Some("https://relay.example.com".parse().unwrap()), direct_addresses: vec![SocketAddr::from(([1, 2, 3, 4], 1234))] .into_iter() .collect(), }; assert_eq!( format!("{:?}", info), - r#"AddrInfo { derp_url: Some(DerpUrl("https://derp.example.com./")), direct_addresses: {1.2.3.4:1234} }"# + r#"AddrInfo { relay_url: Some(RelayUrl("https://relay.example.com./")), direct_addresses: {1.2.3.4:1234} }"# ); } #[tokio::test] async fn magic_endpoint_connect_close() { let _guard = iroh_test::logging::setup(); - let (derp_map, derp_url, _guard) = run_derper().await.unwrap(); + let (relay_map, relay_url, _guard) = run_relay_server().await.unwrap(); let server_secret_key = SecretKey::generate(); let server_peer_id = server_secret_key.public(); let server = { - let derp_map = derp_map.clone(); + let relay_map = relay_map.clone(); tokio::spawn( async move { let ep = MagicEndpoint::builder() .secret_key(server_secret_key) .alpns(vec![TEST_ALPN.to_vec()]) - .derp_mode(DerpMode::Custom(derp_map)) + .relay_mode(RelayMode::Custom(relay_map)) .bind(0) .await .unwrap(); @@ -648,12 +648,12 @@ mod tests { async move { let ep = MagicEndpoint::builder() .alpns(vec![TEST_ALPN.to_vec()]) - .derp_mode(DerpMode::Custom(derp_map)) + .relay_mode(RelayMode::Custom(relay_map)) .bind(0) .await .unwrap(); info!("client connecting"); - let node_addr = NodeAddr::new(server_peer_id).with_derp_url(derp_url); + let node_addr = NodeAddr::new(server_peer_id).with_relay_url(relay_url); let conn = ep.connect(node_addr, TEST_ALPN).await.unwrap(); let mut stream = conn.open_uni().await.unwrap(); @@ -741,26 +741,26 @@ mod tests { } #[tokio::test] - async fn magic_endpoint_derp_connect_loop() { + async fn magic_endpoint_relay_connect_loop() { let _logging_guard = iroh_test::logging::setup(); let start = Instant::now(); let n_clients = 5; let n_chunks_per_client = 2; let chunk_size = 10; let mut rng = rand_chacha::ChaCha8Rng::seed_from_u64(42); - let (derp_map, derp_url, _derp_guard) = run_derper().await.unwrap(); + let (relay_map, relay_url, _relay_guard) = run_relay_server().await.unwrap(); let server_secret_key = SecretKey::generate_with_rng(&mut rng); let server_node_id = server_secret_key.public(); // The server accepts the connections of the clients sequentially. let server = { - let derp_map = derp_map.clone(); + let relay_map = relay_map.clone(); tokio::spawn( async move { let ep = MagicEndpoint::builder() .secret_key(server_secret_key) .alpns(vec![TEST_ALPN.to_vec()]) - .derp_mode(DerpMode::Custom(derp_map)) + .relay_mode(RelayMode::Custom(relay_map)) .bind(0) .await .unwrap(); @@ -795,21 +795,21 @@ mod tests { for i in 0..n_clients { let now = Instant::now(); println!("[client] round {}", i + 1); - let derp_map = derp_map.clone(); + let relay_map = relay_map.clone(); let client_secret_key = SecretKey::generate_with_rng(&mut rng); - let derp_url = derp_url.clone(); + let relay_url = relay_url.clone(); async { info!("client binding"); let ep = MagicEndpoint::builder() .alpns(vec![TEST_ALPN.to_vec()]) - .derp_mode(DerpMode::Custom(derp_map)) + .relay_mode(RelayMode::Custom(relay_map)) .secret_key(client_secret_key) .bind(0) .await .unwrap(); let eps = ep.local_addr().unwrap(); info!(me = %ep.node_id().fmt_short(), ipv4=%eps.0, ipv6=?eps.1, "client bound"); - let node_addr = NodeAddr::new(server_node_id).with_derp_url(derp_url); + let node_addr = NodeAddr::new(server_node_id).with_relay_url(relay_url); info!(to = ?node_addr, "client connecting"); let conn = ep.connect(node_addr, TEST_ALPN).await.unwrap(); info!("client connected"); @@ -847,13 +847,13 @@ mod tests { let _logging_guard = iroh_test::logging::setup(); let ep1 = MagicEndpoint::builder() .alpns(vec![TEST_ALPN.to_vec()]) - .derp_mode(DerpMode::Disabled) + .relay_mode(RelayMode::Disabled) .bind(0) .await .unwrap(); let ep2 = MagicEndpoint::builder() .alpns(vec![TEST_ALPN.to_vec()]) - .derp_mode(DerpMode::Disabled) + .relay_mode(RelayMode::Disabled) .bind(0) .await .unwrap(); diff --git a/iroh-net/src/magicsock.rs b/iroh-net/src/magicsock.rs index 67f6b79cfd..717b5657dc 100644 --- a/iroh-net/src/magicsock.rs +++ b/iroh-net/src/magicsock.rs @@ -2,12 +2,12 @@ //! //! Based on tailscale/wgengine/magicsock //! -//! ### `DEV_DERP_ONLY` env var: +//! ### `DEV_RELAY_ONLY` env var: //! When present at *compile time*, this env var will force all packets -//! to be sent over the DERP relay connection, regardless of whether or +//! to be sent over the relay connection, regardless of whether or //! not we have a direct UDP address for the given node. //! -//! The intended use is for testing the DERP protocol inside the MagicSock +//! The intended use is for testing the relay protocol inside the MagicSock //! to ensure that we can rely on the relay to send packets when two nodes //! are unable to find direct UDP connections to each other. //! @@ -53,26 +53,27 @@ use watchable::Watchable; use crate::{ config, - derp::{DerpMap, DerpUrl}, disco::{self, SendAddr}, discovery::Discovery, dns::DNS_RESOLVER, key::{PublicKey, SecretKey, SharedSecret}, magic_endpoint::NodeAddr, net::{interfaces, ip::LocalAddresses, netmon, IpFamily}, - netcheck, portmapper, stun, AddrInfo, + netcheck, portmapper, + relay::{RelayMap, RelayUrl}, + stun, AddrInfo, }; use self::{ - derp_actor::{DerpActor, DerpActorMessage, DerpReadResult}, metrics::Metrics as MagicsockMetrics, node_map::{NodeMap, PingAction, PingRole, SendPing}, + relay_actor::{RelayActor, RelayActorMessage, RelayReadResult}, udp_conn::UdpConn, }; -mod derp_actor; mod metrics; mod node_map; +mod relay_actor; mod timer; mod udp_conn; @@ -104,8 +105,8 @@ pub struct Options { /// Secret key for this node. pub secret_key: SecretKey, - /// The [`DerpMap`] to use, leave empty to not use a DERP server. - pub derp_map: DerpMap, + /// The [`RelayMap`] to use, leave empty to not use a relay server. + pub relay_map: RelayMap, /// Path to store known nodes. pub nodes_path: Option, @@ -119,21 +120,21 @@ impl Default for Options { Options { port: 0, secret_key: SecretKey::generate(), - derp_map: DerpMap::empty(), + relay_map: RelayMap::empty(), nodes_path: None, discovery: None, } } } -/// Contents of a DERP message. Use a SmallVec to avoid allocations for the very +/// Contents of a relay message. Use a SmallVec to avoid allocations for the very /// common case of a single packet. -pub(crate) type DerpContents = SmallVec<[Bytes; 1]>; +pub(crate) type RelayContents = SmallVec<[Bytes; 1]>; /// Iroh connectivity layer. /// /// This is responsible for routing packets to nodes based on node IDs, it will initially -/// route packets via a derper relay and transparently try and establish a node-to-node +/// route packets via a relay and transparently try and establish a node-to-node /// connection and upgrade to it. It will also keep looking for better connections as the /// network details of both endpoints change. /// @@ -151,12 +152,12 @@ pub struct MagicSock { #[derive(derive_more::Debug)] struct Inner { actor_sender: mpsc::Sender, - derp_actor_sender: mpsc::Sender, + relay_actor_sender: mpsc::Sender, /// String representation of the node_id of this node. me: String, - /// Used for receiving DERP messages. - derp_recv_receiver: flume::Receiver, - /// Stores wakers, to be called when derp_recv_ch receives new data. + /// Used for receiving relay messages. + relay_recv_receiver: flume::Receiver, + /// Stores wakers, to be called when relay_recv_ch receives new data. network_recv_wakers: parking_lot::Mutex>, network_send_wakers: parking_lot::Mutex>, @@ -176,10 +177,10 @@ struct Inner { /// If the last netcheck report, reports IPv6 to be available. ipv6_reported: Arc, - /// None (or zero nodes) means DERP is disabled. - derp_map: DerpMap, - /// Nearest DERP node ID; 0 means none/unknown. - my_derp: std::sync::RwLock>, + /// None (or zero nodes) means relay is disabled. + relay_map: RelayMap, + /// Nearest relay node ID; 0 means none/unknown. + my_relay: std::sync::RwLock>, /// Tracks the networkmap node entity for each node discovery key. node_map: NodeMap, /// UDP IPv4 socket @@ -205,25 +206,25 @@ struct Inner { /// List of CallMeMaybe disco messages that should be sent out after the next endpoint update /// completes - pending_call_me_maybes: parking_lot::Mutex>, + pending_call_me_maybes: parking_lot::Mutex>, /// Indicates the update endpoint state. endpoints_update_state: EndpointUpdateState, } impl Inner { - /// Returns the derp node we are connected to, that has the best latency. + /// Returns the relay node we are connected to, that has the best latency. /// - /// If `None`, then we are not connected to any derp region. - fn my_derp(&self) -> Option { - self.my_derp.read().expect("not poisoned").clone() + /// If `None`, then we are not connected to any relay nodes. + fn my_relay(&self) -> Option { + self.my_relay.read().expect("not poisoned").clone() } - /// Sets the derp node with the best latency. + /// Sets the relay node with the best latency. /// - /// If we are not connected to any derp nodes, set this to `None`. - fn set_my_derp(&self, my_derp: Option) { - *self.my_derp.write().expect("not poisoned") = my_derp; + /// If we are not connected to any relay nodes, set this to `None`. + fn set_my_relay(&self, my_relay: Option) { + *self.my_relay.write().expect("not poisoned") = my_relay; } fn is_closing(&self) -> bool { @@ -314,7 +315,7 @@ impl Inner { .node_map .get_send_addrs_for_quic_mapped_addr(&dest, self.ipv6_reported.load(Ordering::Relaxed)) { - Some((public_key, udp_addr, derp_url, mut msgs)) => { + Some((public_key, udp_addr, relay_url, mut msgs)) => { let mut pings_sent = false; // If we have pings to send, we *have* to send them out first. if !msgs.is_empty() { @@ -325,10 +326,10 @@ impl Inner { } let mut udp_sent = false; - let mut derp_sent = false; + let mut relay_sent = false; let mut udp_error = None; let mut udp_pending = false; - let mut derp_pending = false; + let mut relay_pending = false; // send udp if let Some(addr) = udp_addr { @@ -340,7 +341,7 @@ impl Inner { Poll::Ready(Ok(n)) => { trace!(node = %public_key.fmt_short(), dst = %addr, transmit_count=n, "sent transmits over UDP"); // truncate the transmits vec to `n`. these transmits will be sent to - // Derp further below. We only want to send those transmits to Derp that were + // the relay further below. We only want to send those transmits to the relay that were // sent to UDP, because the next transmits will be sent on the next // call to poll_send, which will happen immediately after, because we // are always returning Poll::Ready if poll_send_udp returned @@ -360,30 +361,30 @@ impl Inner { } } - // send derp - if let Some(ref derp_url) = derp_url { - match self.poll_send_derp(derp_url, public_key, split_packets(&transmits)) { + // send relay + if let Some(ref relay_url) = relay_url { + match self.poll_send_relay(relay_url, public_key, split_packets(&transmits)) { Poll::Ready(sent) => { - derp_sent = sent; + relay_sent = sent; transmits_sent = transmits.len(); } Poll::Pending => { self.network_send_wakers.lock().replace(cx.waker().clone()); - derp_pending = true; + relay_pending = true; } } } - if udp_addr.is_none() && derp_url.is_none() { + if udp_addr.is_none() && relay_url.is_none() { // Handle no addresses being available - warn!(node = %public_key.fmt_short(), "failed to send: no UDP or DERP addr"); + warn!(node = %public_key.fmt_short(), "failed to send: no UDP or relay addr"); return Poll::Ready(Err(io::Error::new( io::ErrorKind::NotConnected, - "no UDP or Derp address available for node", + "no UDP or relay address available for node", ))); } - if (udp_addr.is_none() || udp_pending) && (derp_url.is_none() || derp_pending) { + if (udp_addr.is_none() || udp_pending) && (relay_url.is_none() || relay_pending) { // Handle backpressure // The explicit choice here is to only return pending, iff all available paths returned // pending. @@ -392,12 +393,12 @@ impl Inner { return Poll::Pending; } - if !derp_sent && !udp_sent && !pings_sent { - warn!(node = %public_key.fmt_short(), "failed to send: no UDP or DERP addr"); + if !relay_sent && !udp_sent && !pings_sent { + warn!(node = %public_key.fmt_short(), "failed to send: no UDP or relay addr"); let err = udp_error.unwrap_or_else(|| { io::Error::new( io::ErrorKind::NotConnected, - "no UDP or Derp address available for node", + "no UDP or relay address available for node", ) }); return Poll::Ready(Err(err)); @@ -407,7 +408,7 @@ impl Inner { node = %public_key.fmt_short(), transmit_count = %transmits_sent, send_udp = ?udp_addr, - send_derp = ?derp_url, + send_relay = ?relay_url, "sent transmits" ); Poll::Ready(Ok(transmits_sent)) @@ -470,17 +471,17 @@ impl Inner { ))); } - // order of polling is: UDPv4, UDPv6, Derp + // order of polling is: UDPv4, UDPv6, relay let msgs = match self.pconn4.poll_recv(cx, bufs, metas)? { Poll::Pending | Poll::Ready(0) => match &self.pconn6 { Some(conn) => match conn.poll_recv(cx, bufs, metas)? { Poll::Pending | Poll::Ready(0) => { - return self.poll_recv_derp(cx, bufs, metas); + return self.poll_recv_relay(cx, bufs, metas); } Poll::Ready(n) => n, }, None => { - return self.poll_recv_derp(cx, bufs, metas); + return self.poll_recv_relay(cx, bufs, metas); } }, Poll::Ready(n) => n, @@ -565,7 +566,7 @@ impl Inner { } #[instrument(skip_all, fields(name = %self.me))] - fn poll_recv_derp( + fn poll_recv_relay( &self, cx: &mut Context, bufs: &mut [io::IoSliceMut<'_>], @@ -576,7 +577,7 @@ impl Inner { if self.is_closed() { break; } - match self.derp_recv_receiver.try_recv() { + match self.relay_recv_receiver.try_recv() { Err(flume::TryRecvError::Empty) => { self.network_recv_wakers.lock().replace(cx.waker().clone()); break; @@ -589,8 +590,8 @@ impl Inner { } Ok(Err(err)) => return Poll::Ready(Err(err)), Ok(Ok((node_id, meta, bytes))) => { - inc_by!(MagicsockMetrics, recv_data_derp, bytes.len() as _); - trace!(src = %meta.addr, node = %node_id.fmt_short(), count = meta.len / meta.stride, len = meta.len, "recv quic packets from derp"); + inc_by!(MagicsockMetrics, recv_data_relay, bytes.len() as _); + trace!(src = %meta.addr, node = %node_id.fmt_short(), count = meta.len / meta.stride, len = meta.len, "recv quic packets from relay"); buf_out[..bytes.len()].copy_from_slice(&bytes); *meta_out = meta; num_msgs += 1; @@ -641,8 +642,8 @@ impl Inner { } }; - if src.is_derp() { - inc!(MagicsockMetrics, recv_disco_derp); + if src.is_relay() { + inc!(MagicsockMetrics, recv_disco_relay); } else { inc!(MagicsockMetrics, recv_disco_udp); } @@ -661,8 +662,8 @@ impl Inner { } disco::Message::CallMeMaybe(cm) => { inc!(MagicsockMetrics, recv_disco_call_me_maybe); - if !matches!(src, DiscoMessageSource::Derp { .. }) { - warn!("call-me-maybe packets should only come via DERP"); + if !matches!(src, DiscoMessageSource::Relay { .. }) { + warn!("call-me-maybe packets should only come via relay"); return; }; let ping_actions = self.node_map.handle_call_me_maybe(sender, cm); @@ -745,7 +746,7 @@ impl Inner { .udp_disco_sender .try_send((addr, dst_node, msg)) .is_ok(), - SendAddr::Derp(ref url) => self.send_disco_message_derp(url, dst_node, msg), + SendAddr::Relay(ref url) => self.send_disco_message_relay(url, dst_node, msg), }; if sent { let msg_sender = self.actor_sender.clone(); @@ -779,7 +780,7 @@ impl Inner { /// Send a disco message. UDP messages will be queued. /// - /// If `dst` is [`SendAddr::Derp`], the message will be pushed into the derp client channel. + /// If `dst` is [`SendAddr::Relay`], the message will be pushed into the relay client channel. /// If `dst` is [`SendAddr::Udp`], the message will be pushed into the udp disco send channel. /// /// Returns true if the channel had capacity for the message, and false if the message was @@ -792,7 +793,7 @@ impl Inner { ) -> bool { match dst { SendAddr::Udp(addr) => self.udp_disco_sender.try_send((addr, dst_key, msg)).is_ok(), - SendAddr::Derp(ref url) => self.send_disco_message_derp(url, dst_key, msg), + SendAddr::Relay(ref url) => self.send_disco_message_relay(url, dst_key, msg), } } @@ -808,25 +809,25 @@ impl Inner { SendAddr::Udp(addr) => { ready!(self.poll_send_disco_message_udp(addr, dst_key, &msg, cx))?; } - SendAddr::Derp(ref url) => { - self.send_disco_message_derp(url, dst_key, msg); + SendAddr::Relay(ref url) => { + self.send_disco_message_relay(url, dst_key, msg); } } Poll::Ready(Ok(())) } - fn send_disco_message_derp( + fn send_disco_message_relay( &self, - url: &DerpUrl, + url: &RelayUrl, dst_key: PublicKey, msg: disco::Message, ) -> bool { - debug!(node = %dst_key.fmt_short(), %url, %msg, "send disco message (derp)"); + debug!(node = %dst_key.fmt_short(), %url, %msg, "send disco message (relay)"); let pkt = self.encode_disco_message(dst_key, &msg); - inc!(MagicsockMetrics, send_disco_derp); - match self.poll_send_derp(url, dst_key, smallvec![pkt]) { + inc!(MagicsockMetrics, send_disco_relay); + match self.poll_send_relay(url, dst_key, smallvec![pkt]) { Poll::Ready(true) => { - inc!(MagicsockMetrics, sent_disco_derp); + inc!(MagicsockMetrics, sent_disco_relay); disco_message_sent(&msg); true } @@ -919,10 +920,10 @@ impl Inner { } match *msg { PingAction::SendCallMeMaybe { - ref derp_url, + ref relay_url, dst_node, } => { - self.send_or_queue_call_me_maybe(derp_url, dst_node); + self.send_or_queue_call_me_maybe(relay_url, dst_node); } PingAction::SendPing(ref ping) => { ready!(self.poll_send_ping(ping, cx))?; @@ -931,24 +932,29 @@ impl Inner { Poll::Ready(Ok(())) } - fn poll_send_derp(&self, url: &DerpUrl, node: PublicKey, contents: DerpContents) -> Poll { - trace!(node = %node.fmt_short(), derp_url = %url, count = contents.len(), len = contents.iter().map(|c| c.len()).sum::(), "send derp"); - let msg = DerpActorMessage::Send { + fn poll_send_relay( + &self, + url: &RelayUrl, + node: PublicKey, + contents: RelayContents, + ) -> Poll { + trace!(node = %node.fmt_short(), relay_url = %url, count = contents.len(), len = contents.iter().map(|c| c.len()).sum::(), "send relay"); + let msg = RelayActorMessage::Send { url: url.clone(), contents, peer: node, }; - match self.derp_actor_sender.try_send(msg) { + match self.relay_actor_sender.try_send(msg) { Ok(_) => { - trace!(node = %node.fmt_short(), derp_url = %url, "send derp: message queued"); + trace!(node = %node.fmt_short(), relay_url = %url, "send relay: message queued"); Poll::Ready(true) } Err(mpsc::error::TrySendError::Closed(_)) => { - warn!(node = %node.fmt_short(), derp_url = %url, "send derp: message dropped, channel to actor is closed"); + warn!(node = %node.fmt_short(), relay_url = %url, "send relay: message dropped, channel to actor is closed"); Poll::Ready(false) } Err(mpsc::error::TrySendError::Full(_)) => { - warn!(node = %node.fmt_short(), derp_url = %url, "send derp: message dropped, channel to actor is full"); + warn!(node = %node.fmt_short(), relay_url = %url, "send relay: message dropped, channel to actor is full"); Poll::Pending } } @@ -958,22 +964,22 @@ impl Inner { let msg = self.endpoints.read().to_call_me_maybe_message(); let msg = disco::Message::CallMeMaybe(msg); for (public_key, url) in self.pending_call_me_maybes.lock().drain() { - if !self.send_disco_message_derp(&url, public_key, msg.clone()) { - warn!(node = %public_key.fmt_short(), "derp channel full, dropping call-me-maybe"); + if !self.send_disco_message_relay(&url, public_key, msg.clone()) { + warn!(node = %public_key.fmt_short(), "relay channel full, dropping call-me-maybe"); } } } - fn send_or_queue_call_me_maybe(&self, url: &DerpUrl, dst_key: PublicKey) { + fn send_or_queue_call_me_maybe(&self, url: &RelayUrl, dst_key: PublicKey) { let endpoints = self.endpoints.read(); if endpoints.fresh_enough() { let msg = endpoints.to_call_me_maybe_message(); let msg = disco::Message::CallMeMaybe(msg); - if !self.send_disco_message_derp(url, dst_key, msg) { - warn!(dstkey = %dst_key.fmt_short(), derpurl = ?url, - "derp channel full, dropping call-me-maybe"); + if !self.send_disco_message_relay(url, dst_key, msg) { + warn!(dstkey = %dst_key.fmt_short(), relayurl = ?url, + "relay channel full, dropping call-me-maybe"); } else { - debug!(dstkey = %dst_key.fmt_short(), derpurl = ?url, "call-me-maybe sent"); + debug!(dstkey = %dst_key.fmt_short(), relayurl = ?url, "call-me-maybe sent"); } } else { self.pending_call_me_maybes @@ -996,14 +1002,14 @@ impl Inner { /// Publishes our address to a discovery service, if configured. /// - /// Called whenever our addresses or home derper changes. + /// Called whenever our addresses or home relay node changes. fn publish_my_addr(&self) { if let Some(ref discovery) = self.discovery { let eps = self.endpoints.read(); - let derp_url = self.my_derp(); + let relay_url = self.my_relay(); let direct_addresses = eps.iter().map(|ep| ep.addr).collect(); let info = AddrInfo { - derp_url, + relay_url, direct_addresses, }; discovery.publish(&info); @@ -1014,14 +1020,14 @@ impl Inner { #[derive(Clone, Debug)] enum DiscoMessageSource { Udp(SocketAddr), - Derp { url: DerpUrl, key: PublicKey }, + Relay { url: RelayUrl, key: PublicKey }, } impl Display for DiscoMessageSource { fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { match self { Self::Udp(addr) => write!(f, "Udp({addr})"), - Self::Derp { ref url, key } => write!(f, "Derp({url}, {})", key.fmt_short()), + Self::Relay { ref url, key } => write!(f, "Relay({url}, {})", key.fmt_short()), } } } @@ -1030,7 +1036,7 @@ impl From for SendAddr { fn from(value: DiscoMessageSource) -> Self { match value { DiscoMessageSource::Udp(addr) => SendAddr::Udp(addr), - DiscoMessageSource::Derp { url, .. } => SendAddr::Derp(url), + DiscoMessageSource::Relay { url, .. } => SendAddr::Relay(url), } } } @@ -1039,14 +1045,14 @@ impl From<&DiscoMessageSource> for SendAddr { fn from(value: &DiscoMessageSource) -> Self { match value { DiscoMessageSource::Udp(addr) => SendAddr::Udp(*addr), - DiscoMessageSource::Derp { url, .. } => SendAddr::Derp(url.clone()), + DiscoMessageSource::Relay { url, .. } => SendAddr::Relay(url.clone()), } } } impl DiscoMessageSource { - fn is_derp(&self) -> bool { - matches!(self, DiscoMessageSource::Derp { .. }) + fn is_relay(&self) -> bool { + matches!(self, DiscoMessageSource::Relay { .. }) } } @@ -1109,8 +1115,10 @@ impl MagicSock { /// Creates a magic `MagicSock` listening on `opts.port`. pub async fn new(opts: Options) -> Result { let me = opts.secret_key.public().fmt_short(); - if crate::util::derp_only_mode() { - warn!("creating a MagicSock that will only send packets over a DERP relay connection."); + if crate::util::relay_only_mode() { + warn!( + "creating a MagicSock that will only send packets over a relay relay connection." + ); } Self::with_name(me.clone(), opts) @@ -1124,7 +1132,7 @@ impl MagicSock { let Options { port, secret_key, - derp_map, + relay_map, discovery, nodes_path, } = opts; @@ -1141,7 +1149,7 @@ impl MagicSock { None => None, }; - let (derp_recv_sender, derp_recv_receiver) = flume::bounded(128); + let (relay_recv_sender, relay_recv_receiver) = flume::bounded(128); let (pconn4, pconn6) = bind(port)?; let port = pconn4.port(); @@ -1159,7 +1167,7 @@ impl MagicSock { let net_checker = netcheck::Client::new(Some(port_mapper.clone()))?; let (actor_sender, actor_receiver) = mpsc::channel(256); - let (derp_actor_sender, derp_actor_receiver) = mpsc::channel(256); + let (relay_actor_sender, relay_actor_receiver) = mpsc::channel(256); let (udp_disco_sender, mut udp_disco_receiver) = mpsc::channel(256); // load the node data @@ -1186,19 +1194,19 @@ impl MagicSock { local_addrs: std::sync::RwLock::new((ipv4_addr, ipv6_addr)), closing: AtomicBool::new(false), closed: AtomicBool::new(false), - derp_recv_receiver, + relay_recv_receiver, network_recv_wakers: parking_lot::Mutex::new(None), network_send_wakers: parking_lot::Mutex::new(None), actor_sender: actor_sender.clone(), ipv6_reported: Arc::new(AtomicBool::new(false)), - derp_map, - my_derp: Default::default(), + relay_map, + my_relay: Default::default(), pconn4: pconn4.clone(), pconn6: pconn6.clone(), net_checker: net_checker.clone(), disco_secrets: DiscoSecrets::default(), node_map, - derp_actor_sender: derp_actor_sender.clone(), + relay_actor_sender: relay_actor_sender.clone(), udp_state, send_buffer: Default::default(), udp_disco_sender, @@ -1210,13 +1218,13 @@ impl MagicSock { let mut actor_tasks = JoinSet::default(); - let derp_actor = DerpActor::new(inner.clone(), actor_sender.clone()); - let derp_actor_cancel_token = derp_actor.cancel_token(); + let relay_actor = RelayActor::new(inner.clone(), actor_sender.clone()); + let relay_actor_cancel_token = relay_actor.cancel_token(); actor_tasks.spawn( async move { - derp_actor.run(derp_actor_receiver).await; + relay_actor.run(relay_actor_receiver).await; } - .instrument(info_span!("derp-actor")), + .instrument(info_span!("relay-actor")), ); let inner2 = inner.clone(); @@ -1235,10 +1243,10 @@ impl MagicSock { let actor = Actor { msg_receiver: actor_receiver, msg_sender: actor_sender, - derp_actor_sender, - derp_actor_cancel_token, + relay_actor_sender, + relay_actor_cancel_token, inner: inner2, - derp_recv_sender, + relay_recv_sender, periodic_re_stun_timer: new_re_stun_timer(false), net_info_last: None, nodes_path, @@ -1251,7 +1259,7 @@ impl MagicSock { }; if let Err(err) = actor.run().await { - warn!("derp handler errored: {:?}", err); + warn!("relay handler errored: {:?}", err); } } .instrument(info_span!("actor")), @@ -1329,11 +1337,11 @@ impl MagicSock { .map(|a| a.0) } - /// Returns the DERP node with the best latency. + /// Returns the relay node with the best latency. /// - /// If `None`, then we currently have no verified connection to a DERP node. - pub fn my_derp(&self) -> Option { - self.inner.my_derp() + /// If `None`, then we currently have no verified connection to a relay node. + pub fn my_relay(&self) -> Option { + self.inner.my_relay() } #[instrument(skip_all, fields(me = %self.inner.me))] @@ -1490,7 +1498,7 @@ enum DiscoBoxError { Parse(anyhow::Error), } -type DerpRecvResult = Result<(PublicKey, quinn_udp::RecvMeta, Bytes), io::Error>; +type RelayRecvResult = Result<(PublicKey, quinn_udp::RecvMeta, Bytes), io::Error>; /// Reports whether x and y represent the same set of endpoints. The order doesn't matter. fn endpoint_sets_equal(xs: &[config::Endpoint], ys: &[config::Endpoint]) -> bool { @@ -1558,7 +1566,7 @@ impl AsyncUdpSocket for MagicSock { #[derive(Debug)] enum ActorMessage { Shutdown, - ReceiveDerp(DerpReadResult), + ReceiveRelay(RelayReadResult), EndpointPingExpired(usize, stun::TransactionId), NetcheckReport(Result>>, &'static str), NetworkChange, @@ -1570,10 +1578,10 @@ struct Actor { inner: Arc, msg_receiver: mpsc::Receiver, msg_sender: mpsc::Sender, - derp_actor_sender: mpsc::Sender, - derp_actor_cancel_token: CancellationToken, - /// Channel to send received derp messages on, for processing. - derp_recv_sender: flume::Sender, + relay_actor_sender: mpsc::Sender, + relay_actor_cancel_token: CancellationToken, + /// Channel to send received relay messages on, for processing. + relay_recv_sender: flume::Sender, /// When set, is an AfterFunc timer that will call MagicSock::do_periodic_stun. periodic_re_stun_timer: time::Interval, /// The `NetInfo` provided in the last call to `net_info_func`. It's used to deduplicate calls to netInfoFunc. @@ -1593,7 +1601,7 @@ struct Actor { /// (as can happen on darwin after a network link status change). no_v4_send: bool, - /// The prober that discovers local network conditions, including the closest DERP relay and NAT mappings. + /// The prober that discovers local network conditions, including the closest relay relay and NAT mappings. net_checker: netcheck::Client, network_monitor: netmon::Monitor, @@ -1690,7 +1698,7 @@ impl Actor { if is_major { DNS_RESOLVER.clear_cache(); self.inner.re_stun("link-change-major"); - self.close_stale_derp_connections().await; + self.close_stale_relay_connections().await; self.reset_endpoint_states(); } else { self.inner.re_stun("link-change-minor"); @@ -1726,7 +1734,7 @@ impl Actor { } } self.port_mapper.deactivate(); - self.derp_actor_cancel_token.cancel(); + self.relay_actor_cancel_token.cancel(); // Ignore errors from pconnN // They will frequently have been closed already by a call to connBind.Close. @@ -1739,10 +1747,10 @@ impl Actor { debug!("shutdown complete"); return true; } - ActorMessage::ReceiveDerp(read_result) => { - let passthroughs = self.process_derp_read_result(read_result); + ActorMessage::ReceiveRelay(read_result) => { + let passthroughs = self.process_relay_read_result(read_result); for passthrough in passthroughs { - self.derp_recv_sender + self.relay_recv_sender .send_async(passthrough) .await .expect("missing recv sender"); @@ -1798,17 +1806,17 @@ impl Actor { (ipv4_addr, ipv6_addr) } - fn process_derp_read_result(&mut self, dm: DerpReadResult) -> Vec { - trace!("process_derp_read {} bytes", dm.buf.len()); + fn process_relay_read_result(&mut self, dm: RelayReadResult) -> Vec { + trace!("process_relay_read {} bytes", dm.buf.len()); if dm.buf.is_empty() { - warn!("received empty derp packet"); + warn!("received empty relay packet"); return Vec::new(); } let url = &dm.url; - let quic_mapped_addr = self.inner.node_map.receive_derp(url, dm.src); + let quic_mapped_addr = self.inner.node_map.receive_relay(url, dm.src); - // the derp packet is made up of multiple udp packets, prefixed by a u16 be length prefix + // the relay packet is made up of multiple udp packets, prefixed by a u16 be length prefix // // split the packet into these parts let parts = PacketSplitIter::new(dm.buf); @@ -1819,7 +1827,7 @@ impl Actor { for part in parts { match part { Ok(part) => { - if self.handle_derp_disco_message(&part, url, dm.src) { + if self.handle_relay_disco_message(&part, url, dm.src) { // Message was internal, do not bubble up. continue; } @@ -2065,8 +2073,8 @@ impl Actor { /// allow this easy mistake to be made. #[instrument(level = "debug", skip_all)] async fn update_net_info(&mut self, why: &'static str) { - if self.inner.derp_map.is_empty() { - debug!("skipping netcheck, empty DerpMap"); + if self.inner.relay_map.is_empty() { + debug!("skipping netcheck, empty RelayMap"); self.msg_sender .send(ActorMessage::NetcheckReport(Ok(None), why)) .await @@ -2074,14 +2082,14 @@ impl Actor { return; } - let derp_map = self.inner.derp_map.clone(); + let relay_map = self.inner.relay_map.clone(); let pconn4 = Some(self.pconn4.as_socket()); let pconn6 = self.pconn6.as_ref().map(|p| p.as_socket()); debug!("requesting netcheck report"); match self .net_checker - .get_report_channel(derp_map, pconn4, pconn6) + .get_report_channel(relay_map, pconn4, pconn6) .await { Ok(rx) => { @@ -2124,7 +2132,7 @@ impl Actor { let have_port_map = self.port_mapper.watch_external_address().borrow().is_some(); let mut ni = config::NetInfo { - derp_latency: Default::default(), + relay_latency: Default::default(), mapping_varies_by_dest_ip: r.mapping_varies_by_dest_ip, hair_pinning: r.hair_pinning, portmap_probe: r.portmap_probe.clone(), @@ -2134,23 +2142,25 @@ impl Actor { working_udp: Some(r.udp), working_icmp_v4: r.icmpv4, working_icmp_v6: r.icmpv6, - preferred_derp: r.preferred_derp.clone(), + preferred_relay: r.preferred_relay.clone(), link_type: None, }; - for (rid, d) in r.derp_v4_latency.iter() { - ni.derp_latency.insert(format!("{rid}-v4"), d.as_secs_f64()); + for (rid, d) in r.relay_v4_latency.iter() { + ni.relay_latency + .insert(format!("{rid}-v4"), d.as_secs_f64()); } - for (rid, d) in r.derp_v6_latency.iter() { - ni.derp_latency.insert(format!("{rid}-v6"), d.as_secs_f64()); + for (rid, d) in r.relay_v6_latency.iter() { + ni.relay_latency + .insert(format!("{rid}-v6"), d.as_secs_f64()); } - if ni.preferred_derp.is_none() { + if ni.preferred_relay.is_none() { // Perhaps UDP is blocked. Pick a deterministic but arbitrary one. - ni.preferred_derp = self.pick_derp_fallback(); + ni.preferred_relay = self.pick_relay_fallback(); } - if !self.set_nearest_derp(ni.preferred_derp.clone()) { - ni.preferred_derp = None; + if !self.set_nearest_relay(ni.preferred_relay.clone()) { + ni.preferred_relay = None; } // TODO: set link type @@ -2159,25 +2169,25 @@ impl Actor { self.store_endpoints_update(report).await; } - fn set_nearest_derp(&mut self, derp_url: Option) -> bool { - let my_derp = self.inner.my_derp(); - if derp_url == my_derp { + fn set_nearest_relay(&mut self, relay_url: Option) -> bool { + let my_relay = self.inner.my_relay(); + if relay_url == my_relay { // No change. return true; } - self.inner.set_my_derp(derp_url.clone()); + self.inner.set_my_relay(relay_url.clone()); - if let Some(ref derp_url) = derp_url { - inc!(MagicsockMetrics, derp_home_change); + if let Some(ref relay_url) = relay_url { + inc!(MagicsockMetrics, relay_home_change); - // On change, notify all currently connected DERP servers and - // start connecting to our home DERP if we are not already. - info!("home is now derp {}", derp_url); + // On change, notify all currently connected relay servers and + // start connecting to our home relay if we are not already. + info!("home is now relay {}", relay_url); self.inner.publish_my_addr(); - self.send_derp_actor(DerpActorMessage::NotePreferred(derp_url.clone())); - self.send_derp_actor(DerpActorMessage::Connect { - url: derp_url.clone(), + self.send_relay_actor(RelayActorMessage::NotePreferred(relay_url.clone())); + self.send_relay_actor(RelayActorMessage::Connect { + url: relay_url.clone(), peer: None, }); } @@ -2185,28 +2195,28 @@ impl Actor { true } - /// Returns a deterministic DERP node to connect to. This is only used if netcheck + /// Returns a deterministic relay node to connect to. This is only used if netcheck /// couldn't find the nearest one, for instance, if UDP is blocked and thus STUN /// latency checks aren't working. /// - /// If no the [`DerpMap`] is empty, returns `0`. - fn pick_derp_fallback(&self) -> Option { - // TODO: figure out which DERP node most of our nodes are using, + /// If no the [`RelayMap`] is empty, returns `0`. + fn pick_relay_fallback(&self) -> Option { + // TODO: figure out which relay node most of our nodes are using, // and use that region as our fallback. // // If we already had selected something in the past and it has any // nodes, we want to stay on it. If there are no nodes at all, - // stay on whatever DERP we previously picked. If we need to pick + // stay on whatever relay we previously picked. If we need to pick // one and have no node info, pick a node randomly. // // We used to do the above for legacy clients, but never updated it for disco. - let my_derp = self.inner.my_derp(); - if my_derp.is_some() { - return my_derp; + let my_relay = self.inner.my_relay(); + if my_relay.is_some() { + return my_relay; } - let ids = self.inner.derp_map.urls().collect::>(); + let ids = self.inner.relay_map.urls().collect::>(); let mut rng = rand::rngs::StdRng::seed_from_u64(0); ids.choose(&mut rng).map(|c| (*c).clone()) } @@ -2218,12 +2228,12 @@ impl Actor { self.inner.node_map.reset_endpoint_states() } - /// Tells the derp actor to close stale derp connections. + /// Tells the relay actor to close stale relay connections. /// - /// The derp connections who's local endpoints no longer exist after a network change + /// The relay connections who's local endpoints no longer exist after a network change /// will error out soon enough. Closing them eagerly speeds this up however and allows - /// re-establishing a derp connection faster. - async fn close_stale_derp_connections(&self) { + /// re-establishing a relay connection faster. + async fn close_stale_relay_connections(&self) { let ifs = interfaces::State::new().await; let local_ips = ifs .interfaces @@ -2231,39 +2241,39 @@ impl Actor { .flat_map(|netif| netif.addrs()) .map(|ipnet| ipnet.addr()) .collect(); - self.send_derp_actor(DerpActorMessage::MaybeCloseDerpsOnRebind(local_ips)); + self.send_relay_actor(RelayActorMessage::MaybeCloseRelaysOnRebind(local_ips)); } - fn send_derp_actor(&self, msg: DerpActorMessage) { - match self.derp_actor_sender.try_send(msg) { + fn send_relay_actor(&self, msg: RelayActorMessage) { + match self.relay_actor_sender.try_send(msg) { Ok(_) => {} Err(mpsc::error::TrySendError::Closed(_)) => { - warn!("unable to send to derp actor, already closed"); + warn!("unable to send to relay actor, already closed"); } Err(mpsc::error::TrySendError::Full(_)) => { - warn!("dropping message for derp actor, channel is full"); + warn!("dropping message for relay actor, channel is full"); } } } - fn handle_derp_disco_message( + fn handle_relay_disco_message( &mut self, msg: &[u8], - url: &DerpUrl, - derp_node_src: PublicKey, + url: &RelayUrl, + relay_node_src: PublicKey, ) -> bool { match disco::source_and_box(msg) { Some((source, sealed_box)) => { - if derp_node_src != source { + if relay_node_src != source { // TODO: return here? - warn!("Received Derp disco message from connection for {}, but with message from {}", derp_node_src.fmt_short(), source.fmt_short()); + warn!("Received relay disco message from connection for {}, but with message from {}", relay_node_src.fmt_short(), source.fmt_short()); } self.inner.handle_disco_message( source, sealed_box, - DiscoMessageSource::Derp { + DiscoMessageSource::Relay { url: url.clone(), - key: derp_node_src, + key: relay_node_src, }, ); true @@ -2374,7 +2384,7 @@ impl DiscoveredEndpoints { /// For each transmit, if it has a segment size, it will be split into /// multiple packets according to that segment size. If it does not have a /// segment size, the contents will be sent as a single packet. -fn split_packets(transmits: &[quinn_udp::Transmit]) -> DerpContents { +fn split_packets(transmits: &[quinn_udp::Transmit]) -> RelayContents { let mut res = SmallVec::with_capacity(transmits.len()); for transmit in transmits { let contents = &transmit.contents; @@ -2438,8 +2448,8 @@ impl Iterator for PacketSplitIter { /// You can consider this as nothing more than a lookup key for a node the [`MagicSock`] knows /// about. /// -/// [`MagicSock`] can reach a node by several real socket addresses, or maybe even via the derper -/// relay. The QUIC layer however needs to address a node by a stable [`SocketAddr`] so +/// [`MagicSock`] can reach a node by several real socket addresses, or maybe even via the relay +/// node. The QUIC layer however needs to address a node by a stable [`SocketAddr`] so /// that normal socket APIs can function. Thus when a new node is introduced to a [`MagicSock`] /// it is given a new fake address. This is the type of that address. /// @@ -2503,7 +2513,7 @@ pub(crate) mod tests { use rand::RngCore; use tokio::task::JoinSet; - use crate::{derp::DerpMode, test_utils::run_derper, tls, MagicEndpoint}; + use crate::{relay::RelayMode, test_utils::run_relay_server, tls, MagicEndpoint}; use super::*; @@ -2517,7 +2527,7 @@ pub(crate) mod tests { const ALPN: &[u8] = b"n0/test/1"; impl MagicStack { - async fn new(derp_map: DerpMap) -> Result { + async fn new(relay_map: RelayMap) -> Result { let secret_key = SecretKey::generate(); let mut transport_config = quinn::TransportConfig::default(); @@ -2526,7 +2536,7 @@ pub(crate) mod tests { let endpoint = MagicEndpoint::builder() .secret_key(secret_key.clone()) .transport_config(transport_config) - .derp_mode(DerpMode::Custom(derp_map)) + .relay_mode(RelayMode::Custom(relay_map)) .alpns(vec![ALPN.to_vec()]) .bind(0) .await?; @@ -2558,13 +2568,13 @@ pub(crate) mod tests { /// first time before returning. /// /// When the returned drop guard is dropped, the tasks doing this updating are stopped. - async fn mesh_stacks(stacks: Vec, derp_url: DerpUrl) -> Result { + async fn mesh_stacks(stacks: Vec, relay_url: RelayUrl) -> Result { /// Registers endpoint addresses of a node to all other nodes. fn update_eps( stacks: &[MagicStack], my_idx: usize, new_eps: Vec, - derp_url: DerpUrl, + relay_url: RelayUrl, ) { let me = &stacks[my_idx]; @@ -2576,7 +2586,7 @@ pub(crate) mod tests { let addr = NodeAddr { node_id: me.public(), info: crate::AddrInfo { - derp_url: Some(derp_url.clone()), + relay_url: Some(relay_url.clone()), direct_addresses: new_eps.iter().map(|ep| ep.addr).collect(), }, }; @@ -2590,13 +2600,13 @@ pub(crate) mod tests { for (my_idx, m) in stacks.iter().enumerate() { let m = m.clone(); let stacks = stacks.clone(); - let derp_url = derp_url.clone(); + let relay_url = relay_url.clone(); tasks.spawn(async move { let me = m.endpoint.node_id().fmt_short(); let mut stream = m.endpoint.local_endpoints(); while let Some(new_eps) = stream.next().await { info!(%me, "conn{} endpoints update: {:?}", my_idx + 1, new_eps); - update_eps(&stacks, my_idx, new_eps, derp_url.clone()); + update_eps(&stacks, my_idx, new_eps, relay_url.clone()); } }); } @@ -2678,11 +2688,11 @@ pub(crate) mod tests { async fn echo_sender( ep: MagicStack, dest_id: PublicKey, - derp_url: DerpUrl, + relay_url: RelayUrl, msg: &[u8], ) -> Result<()> { info!("connecting to {}", dest_id.fmt_short()); - let dest = NodeAddr::new(dest_id).with_derp_url(derp_url); + let dest = NodeAddr::new(dest_id).with_relay_url(relay_url); let conn = ep .endpoint .connect(dest, ALPN) @@ -2726,7 +2736,7 @@ pub(crate) mod tests { async fn run_roundtrip( sender: MagicStack, receiver: MagicStack, - derp_url: DerpUrl, + relay_url: RelayUrl, payload: &[u8], ) { let send_node_id = sender.endpoint.node_id(); @@ -2734,7 +2744,7 @@ pub(crate) mod tests { info!("\nroundtrip: {send_node_id:#} -> {recv_node_id:#}"); let receiver_task = tokio::spawn(echo_receiver(receiver)); - let sender_res = echo_sender(sender, recv_node_id, derp_url, payload).await; + let sender_res = echo_sender(sender, recv_node_id, relay_url, payload).await; let sender_is_err = match sender_res { Ok(()) => false, Err(err) => { @@ -2765,23 +2775,23 @@ pub(crate) mod tests { #[tokio::test(flavor = "multi_thread")] async fn test_two_devices_roundtrip_quinn_magic() -> Result<()> { iroh_test::logging::setup_multithreaded(); - let (derp_map, derp_url, _cleanup_guard) = run_derper().await?; + let (relay_map, relay_url, _cleanup_guard) = run_relay_server().await?; - let m1 = MagicStack::new(derp_map.clone()).await?; - let m2 = MagicStack::new(derp_map.clone()).await?; + let m1 = MagicStack::new(relay_map.clone()).await?; + let m2 = MagicStack::new(relay_map.clone()).await?; - let _guard = mesh_stacks(vec![m1.clone(), m2.clone()], derp_url.clone()).await?; + let _guard = mesh_stacks(vec![m1.clone(), m2.clone()], relay_url.clone()).await?; for i in 0..5 { info!("\n-- round {i}"); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), b"hello m1").await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), b"hello m2").await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), b"hello m1").await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), b"hello m2").await; info!("\n-- larger data"); let mut data = vec![0u8; 10 * 1024]; rand::thread_rng().fill_bytes(&mut data); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), &data).await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), &data).await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), &data).await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), &data).await; } Ok(()) @@ -2801,12 +2811,12 @@ pub(crate) mod tests { /// with (simulated) network changes. async fn test_two_devices_roundtrip_network_change_impl() -> Result<()> { iroh_test::logging::setup_multithreaded(); - let (derp_map, derp_url, _cleanup) = run_derper().await?; + let (relay_map, relay_url, _cleanup) = run_relay_server().await?; - let m1 = MagicStack::new(derp_map.clone()).await?; - let m2 = MagicStack::new(derp_map.clone()).await?; + let m1 = MagicStack::new(relay_map.clone()).await?; + let m2 = MagicStack::new(relay_map.clone()).await?; - let _guard = mesh_stacks(vec![m1.clone(), m2.clone()], derp_url.clone()).await?; + let _guard = mesh_stacks(vec![m1.clone(), m2.clone()], relay_url.clone()).await?; let offset = || { let delay = rand::thread_rng().gen_range(10..=500); @@ -2831,14 +2841,14 @@ pub(crate) mod tests { for i in 0..rounds { println!("-- [m1 changes] round {}", i + 1); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), b"hello m1").await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), b"hello m2").await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), b"hello m1").await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), b"hello m2").await; println!("-- [m1 changes] larger data"); let mut data = vec![0u8; 10 * 1024]; rand::thread_rng().fill_bytes(&mut data); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), &data).await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), &data).await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), &data).await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), &data).await; } std::mem::drop(m1_network_change_guard); @@ -2860,14 +2870,14 @@ pub(crate) mod tests { for i in 0..rounds { println!("-- [m2 changes] round {}", i + 1); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), b"hello m1").await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), b"hello m2").await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), b"hello m1").await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), b"hello m2").await; println!("-- [m2 changes] larger data"); let mut data = vec![0u8; 10 * 1024]; rand::thread_rng().fill_bytes(&mut data); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), &data).await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), &data).await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), &data).await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), &data).await; } std::mem::drop(m2_network_change_guard); @@ -2890,14 +2900,14 @@ pub(crate) mod tests { for i in 0..rounds { println!("-- [m1 & m2 changes] round {}", i + 1); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), b"hello m1").await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), b"hello m2").await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), b"hello m1").await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), b"hello m2").await; println!("-- [m1 & m2 changes] larger data"); let mut data = vec![0u8; 10 * 1024]; rand::thread_rng().fill_bytes(&mut data); - run_roundtrip(m1.clone(), m2.clone(), derp_url.clone(), &data).await; - run_roundtrip(m2.clone(), m1.clone(), derp_url.clone(), &data).await; + run_roundtrip(m1.clone(), m2.clone(), relay_url.clone(), &data).await; + run_roundtrip(m2.clone(), m1.clone(), relay_url.clone(), &data).await; } std::mem::drop(m1_m2_network_change_guard); @@ -2909,10 +2919,10 @@ pub(crate) mod tests { iroh_test::logging::setup_multithreaded(); for i in 0..10 { println!("-- round {i}"); - let (derp_map, url, _cleanup) = run_derper().await?; + let (relay_map, url, _cleanup) = run_relay_server().await?; println!("setting up magic stack"); - let m1 = MagicStack::new(derp_map.clone()).await?; - let m2 = MagicStack::new(derp_map.clone()).await?; + let m1 = MagicStack::new(relay_map.clone()).await?; + let m2 = MagicStack::new(relay_map.clone()).await?; let _guard = mesh_stacks(vec![m1.clone(), m2.clone()], url.clone()).await?; @@ -3228,7 +3238,7 @@ pub(crate) mod tests { src_ip: None, } } - fn mk_expected(parts: impl IntoIterator) -> DerpContents { + fn mk_expected(parts: impl IntoIterator) -> RelayContents { parts .into_iter() .map(|p| p.as_bytes().to_vec().into()) diff --git a/iroh-net/src/magicsock/metrics.rs b/iroh-net/src/magicsock/metrics.rs index 925568d74f..4c48e83cd4 100644 --- a/iroh-net/src/magicsock/metrics.rs +++ b/iroh-net/src/magicsock/metrics.rs @@ -7,29 +7,26 @@ use iroh_metrics::{ #[allow(missing_docs)] #[derive(Debug, Clone, Iterable)] pub struct Metrics { - pub num_derp_conns_added: Counter, - pub num_derp_conns_removed: Counter, - pub rebind_calls: Counter, pub re_stun_calls: Counter, pub update_endpoints: Counter, // Sends (data or disco) - pub send_derp_queued: Counter, - pub send_derp_error_chan: Counter, - pub send_derp_error_closed: Counter, - pub send_derp_error_queue: Counter, + pub send_relay_queued: Counter, + pub send_relay_error_chan: Counter, + pub send_relay_error_closed: Counter, + pub send_relay_error_queue: Counter, pub send_ipv4: Counter, pub send_ipv4_error: Counter, pub send_ipv6: Counter, pub send_ipv6_error: Counter, - pub send_derp: Counter, - pub send_derp_error: Counter, + pub send_relay: Counter, + pub send_relay_error: Counter, // Data packets (non-disco) pub send_data: Counter, pub send_data_network_down: Counter, - pub recv_data_derp: Counter, + pub recv_data_relay: Counter, pub recv_data_ipv4: Counter, pub recv_data_ipv6: Counter, /// Number of QUIC datagrams received. @@ -37,9 +34,9 @@ pub struct Metrics { // Disco packets pub send_disco_udp: Counter, - pub send_disco_derp: Counter, + pub send_disco_relay: Counter, pub sent_disco_udp: Counter, - pub sent_disco_derp: Counter, + pub sent_disco_relay: Counter, pub sent_disco_ping: Counter, pub sent_disco_pong: Counter, pub sent_disco_call_me_maybe: Counter, @@ -48,15 +45,15 @@ pub struct Metrics { pub recv_disco_bad_parse: Counter, pub recv_disco_udp: Counter, - pub recv_disco_derp: Counter, + pub recv_disco_relay: Counter, pub recv_disco_ping: Counter, pub recv_disco_pong: Counter, pub recv_disco_call_me_maybe: Counter, pub recv_disco_call_me_maybe_bad_node: Counter, pub recv_disco_call_me_maybe_bad_disco: Counter, - // How many times our DERP home node DI has changed from non-zero to a different non-zero. - pub derp_home_change: Counter, + // How many times our relay home node DI has changed from non-zero to a different non-zero. + pub relay_home_change: Counter, /* * Connection Metrics @@ -74,38 +71,38 @@ pub struct Metrics { impl Default for Metrics { fn default() -> Self { Self { - num_derp_conns_added: Counter::new("num_derp_conns added"), - num_derp_conns_removed: Counter::new("num_derp_conns removed"), + num_relay_conns_added: Counter::new("num_relay_conns added"), + num_relay_conns_removed: Counter::new("num_relay_conns removed"), rebind_calls: Counter::new("rebind_calls"), re_stun_calls: Counter::new("restun_calls"), update_endpoints: Counter::new("update_endpoints"), // Sends (data or disco) - send_derp_queued: Counter::new("send_derp_queued"), - send_derp_error_chan: Counter::new("send_derp_error_chan"), - send_derp_error_closed: Counter::new("send_derp_error_closed"), - send_derp_error_queue: Counter::new("send_derp_error_queue"), + send_relay_queued: Counter::new("send_relay_queued"), + send_relay_error_chan: Counter::new("send_relay_error_chan"), + send_relay_error_closed: Counter::new("send_relay_error_closed"), + send_relay_error_queue: Counter::new("send_relay_error_queue"), send_ipv4: Counter::new("send_ipv4"), send_ipv4_error: Counter::new("send_ipv4_error"), send_ipv6: Counter::new("send_ipv6"), send_ipv6_error: Counter::new("send_ipv6_error"), - send_derp: Counter::new("send_derp"), - send_derp_error: Counter::new("send_derp_error"), + send_relay: Counter::new("send_relay"), + send_relay_error: Counter::new("send_relay_error"), // Data packets (non-disco) send_data: Counter::new("send_data"), send_data_network_down: Counter::new("send_data_network_down"), - recv_data_derp: Counter::new("recv_data_derp"), + recv_data_relay: Counter::new("recv_data_relay"), recv_data_ipv4: Counter::new("recv_data_ipv4"), recv_data_ipv6: Counter::new("recv_data_ipv6"), recv_datagrams: Counter::new("recv_datagrams"), // Disco packets send_disco_udp: Counter::new("disco_send_udp"), - send_disco_derp: Counter::new("disco_send_derp"), + send_disco_relay: Counter::new("disco_send_relay"), sent_disco_udp: Counter::new("disco_sent_udp"), - sent_disco_derp: Counter::new("disco_sent_derp"), + sent_disco_relay: Counter::new("disco_sent_relay"), sent_disco_ping: Counter::new("disco_sent_ping"), sent_disco_pong: Counter::new("disco_sent_pong"), sent_disco_call_me_maybe: Counter::new("disco_sent_callmemaybe"), @@ -114,15 +111,15 @@ impl Default for Metrics { recv_disco_bad_parse: Counter::new("disco_recv_bad_parse"), recv_disco_udp: Counter::new("disco_recv_udp"), - recv_disco_derp: Counter::new("disco_recv_derp"), + recv_disco_relay: Counter::new("disco_recv_relay"), recv_disco_ping: Counter::new("disco_recv_ping"), recv_disco_pong: Counter::new("disco_recv_pong"), recv_disco_call_me_maybe: Counter::new("disco_recv_callmemaybe"), recv_disco_call_me_maybe_bad_node: Counter::new("disco_recv_callmemaybe_bad_node"), recv_disco_call_me_maybe_bad_disco: Counter::new("disco_recv_callmemaybe_bad_disco"), - // How many times our DERP home node DI has changed from non-zero to a different non-zero. - derp_home_change: Counter::new("derp_home_change"), + // How many times our relay home node DI has changed from non-zero to a different non-zero. + relay_home_change: Counter::new("relay_home_change"), num_direct_conns_added: Counter::new( "number of direct connections to a peer we have added", @@ -130,10 +127,6 @@ impl Default for Metrics { num_direct_conns_removed: Counter::new( "number of direct connections to a peer we have removed", ), - num_relay_conns_added: Counter::new("number of relay connections to a peer we rely on"), - num_relay_conns_removed: Counter::new( - "number of relay connections to a peer we no longer rely on", - ), } } } diff --git a/iroh-net/src/magicsock/node_map.rs b/iroh-net/src/magicsock/node_map.rs index 542b76ce4b..90c214b67e 100644 --- a/iroh-net/src/magicsock/node_map.rs +++ b/iroh-net/src/magicsock/node_map.rs @@ -18,9 +18,9 @@ use super::{ metrics::Metrics as MagicsockMetrics, ActorMessage, DiscoMessageSource, QuicMappedAddr, }; use crate::{ - derp::DerpUrl, disco::{CallMeMaybe, Pong, SendAddr}, key::PublicKey, + relay::RelayUrl, stun, NodeAddr, }; @@ -110,8 +110,8 @@ impl NodeMap { self.inner.lock().receive_udp(udp_addr) } - pub fn receive_derp(&self, derp_url: &DerpUrl, src: PublicKey) -> QuicMappedAddr { - self.inner.lock().receive_derp(derp_url, &src) + pub fn receive_relay(&self, relay_url: &RelayUrl, src: PublicKey) -> QuicMappedAddr { + self.inner.lock().receive_relay(relay_url, &src) } pub fn notify_ping_sent( @@ -171,14 +171,14 @@ impl NodeMap { ) -> Option<( PublicKey, Option, - Option, + Option, Vec, )> { let mut inner = self.inner.lock(); let ep = inner.get_mut(EndpointId::QuicMappedAddr(addr))?; let public_key = *ep.public_key(); - let (udp_addr, derp_url, msgs) = ep.get_send_addrs(have_ipv6); - Some((public_key, udp_addr, derp_url, msgs)) + let (udp_addr, relay_url, msgs) = ep.get_send_addrs(have_ipv6); + Some((public_key, udp_addr, relay_url, msgs)) } pub fn notify_shutdown(&self) { @@ -304,7 +304,7 @@ impl NodeMapInner { let endpoint = self.get_or_insert_with(EndpointId::NodeKey(&node_id), || Options { public_key: node_id, - derp_url: info.derp_url.clone(), + relay_url: info.relay_url.clone(), active: false, }); @@ -357,16 +357,16 @@ impl NodeMapInner { } #[instrument(skip_all, fields(src = %src.fmt_short()))] - fn receive_derp(&mut self, derp_url: &DerpUrl, src: &PublicKey) -> QuicMappedAddr { + fn receive_relay(&mut self, relay_url: &RelayUrl, src: &PublicKey) -> QuicMappedAddr { let endpoint = self.get_or_insert_with(EndpointId::NodeKey(src), || { trace!("packets from unknown node, insert into node map"); Options { public_key: *src, - derp_url: Some(derp_url.clone()), + relay_url: Some(relay_url.clone()), active: true, } }); - endpoint.receive_derp(derp_url, src, Instant::now()); + endpoint.receive_relay(relay_url, src, Instant::now()); *endpoint.quic_mapped_addr() } @@ -434,7 +434,7 @@ impl NodeMapInner { debug!("received ping: node unknown, add to node map"); Options { public_key: sender, - derp_url: src.derp_url(), + relay_url: src.relay_url(), active: true, } }); @@ -452,7 +452,7 @@ impl NodeMapInner { fn insert_endpoint(&mut self, options: Options) -> &mut Endpoint { info!( node = %options.public_key.fmt_short(), - derp_url = ?options.derp_url, + relay_url = ?options.relay_url, "inserting new node endpoint in NodeMap", ); let id = self.next_id; @@ -592,8 +592,8 @@ mod tests { let node_c = SecretKey::generate().public(); let node_d = SecretKey::generate().public(); - let derp_x: DerpUrl = "https://my-derp-1.com".parse().unwrap(); - let derp_y: DerpUrl = "https://my-derp-2.com".parse().unwrap(); + let relay_x: RelayUrl = "https://my-relay-1.com".parse().unwrap(); + let relay_y: RelayUrl = "https://my-relay-2.com".parse().unwrap(); fn addr(port: u16) -> SocketAddr { (std::net::IpAddr::V4(Ipv4Addr::LOCALHOST), port).into() @@ -603,9 +603,9 @@ mod tests { let direct_addresses_c = [addr(5000)]; let node_addr_a = NodeAddr::new(node_a) - .with_derp_url(derp_x) + .with_relay_url(relay_x) .with_direct_addresses(direct_addresses_a); - let node_addr_b = NodeAddr::new(node_b).with_derp_url(derp_y); + let node_addr_b = NodeAddr::new(node_b).with_relay_url(relay_y); let node_addr_c = NodeAddr::new(node_c).with_direct_addresses(direct_addresses_c); let node_addr_d = NodeAddr::new(node_d); @@ -645,7 +645,7 @@ mod tests { .lock() .insert_endpoint(Options { public_key, - derp_url: None, + relay_url: None, active: false, }) .id(); diff --git a/iroh-net/src/magicsock/node_map/best_addr.rs b/iroh-net/src/magicsock/node_map/best_addr.rs index 57a264e5bd..2a762bc901 100644 --- a/iroh-net/src/magicsock/node_map/best_addr.rs +++ b/iroh-net/src/magicsock/node_map/best_addr.rs @@ -10,7 +10,7 @@ use tracing::{debug, info}; use crate::magicsock::metrics::Metrics as MagicsockMetrics; -/// How long we trust a UDP address as the exclusive path (without using DERP) without having heard a Pong reply. +/// How long we trust a UDP address as the exclusive path (without using relay) without having heard a Pong reply. const TRUST_UDP_ADDR_DURATION: Duration = Duration::from_millis(6500); #[derive(Debug, Default)] @@ -81,13 +81,13 @@ impl BestAddr { self.0.is_none() } - pub fn clear(&mut self, reason: ClearReason, has_derp: bool) -> bool { + pub fn clear(&mut self, reason: ClearReason, has_relay: bool) -> bool { if let Some(addr) = self.addr() { self.0 = None; - info!(?reason, ?has_derp, old_addr = %addr, "clearing best_addr"); + info!(?reason, ?has_relay, old_addr = %addr, "clearing best_addr"); // no longer relying on the direct connection inc!(MagicsockMetrics, num_direct_conns_removed); - if has_derp { + if has_relay { // we are now relying on the relay connection, add a relay conn inc!(MagicsockMetrics, num_relay_conns_added); } @@ -101,10 +101,10 @@ impl BestAddr { &mut self, addr: SocketAddr, reason: ClearReason, - has_derp: bool, + has_relay: bool, ) -> bool { match &self.addr() { - Some(best_addr) if *best_addr == addr => self.clear(reason, has_derp), + Some(best_addr) if *best_addr == addr => self.clear(reason, has_relay), _ => false, } } @@ -118,11 +118,11 @@ impl BestAddr { addr: SocketAddr, confirmed_before: Instant, reason: ClearReason, - has_derp: bool, + has_relay: bool, ) { if let Some(ref inner) = self.0 { if inner.addr.addr == addr && inner.confirmed_at < confirmed_before { - self.clear(reason, has_derp); + self.clear(reason, has_relay); } } } @@ -144,16 +144,16 @@ impl BestAddr { latency: Duration, source: Source, confirmed_at: Instant, - has_derp: bool, + has_relay: bool, ) { match self.0.as_mut() { None => { - self.insert(addr, latency, source, confirmed_at, has_derp); + self.insert(addr, latency, source, confirmed_at, has_relay); } Some(state) => { let candidate = AddrLatency { addr, latency }; if !state.is_trusted(confirmed_at) || candidate.is_better_than(&state.addr) { - self.insert(addr, latency, source, confirmed_at, has_derp); + self.insert(addr, latency, source, confirmed_at, has_relay); } else if state.addr.addr == addr { state.confirmed_at = confirmed_at; state.trust_until = Some(source.trust_until(confirmed_at)); @@ -168,7 +168,7 @@ impl BestAddr { latency: Duration, source: Source, confirmed_at: Instant, - has_derp: bool, + has_relay: bool, ) { let trust_until = source.trust_until(confirmed_at); @@ -199,10 +199,10 @@ impl BestAddr { confirmed_at, }; self.0 = Some(inner); - if was_empty && has_derp { + if was_empty && has_relay { // we now have a direct connection, adjust direct connection count inc!(MagicsockMetrics, num_direct_conns_added); - if has_derp { + if has_relay { // we no longer rely on the relay connection, decrease the relay connection // count inc!(MagicsockMetrics, num_relay_conns_removed); diff --git a/iroh-net/src/magicsock/node_map/endpoint.rs b/iroh-net/src/magicsock/node_map/endpoint.rs index 510a994da6..d312e60885 100644 --- a/iroh-net/src/magicsock/node_map/endpoint.rs +++ b/iroh-net/src/magicsock/node_map/endpoint.rs @@ -12,14 +12,14 @@ use tokio::sync::mpsc; use tracing::{debug, info, instrument, trace, warn}; use crate::{ - derp::DerpUrl, disco::{self, SendAddr}, key::PublicKey, magic_endpoint::AddrInfo, magicsock::{Timer, HEARTBEAT_INTERVAL}, net::ip::is_unicast_link_local, + relay::RelayUrl, stun, - util::derp_only_mode, + util::relay_only_mode, NodeAddr, NodeId, }; @@ -50,7 +50,7 @@ const GOOD_ENOUGH_LATENCY: Duration = Duration::from_millis(5); /// It's also the idle time at which we stop doing STUN queries to keep NAT mappings alive. const SESSION_ACTIVE_TIMEOUT: Duration = Duration::from_secs(45); -/// How often we try to upgrade to a better patheven if we have some non-DERP route that works. +/// How often we try to upgrade to a better patheven if we have some non-relay route that works. const UPGRADE_INTERVAL: Duration = Duration::from_secs(60); /// How long until we send a stayin alive ping @@ -58,7 +58,10 @@ const STAYIN_ALIVE_MIN_ELAPSED: Duration = Duration::from_secs(2); #[derive(Debug)] pub(in crate::magicsock) enum PingAction { - SendCallMeMaybe { derp_url: DerpUrl, dst_node: NodeId }, + SendCallMeMaybe { + relay_url: RelayUrl, + dst_node: NodeId, + }, SendPing(SendPing), } @@ -99,7 +102,7 @@ pub enum PingRole { /// looser term. /// /// The whole point of the magicsock is that we can have multiple **paths** to a particular -/// endpoint. One of these paths is via the endpoint's home derper but as we establish a +/// endpoint. One of these paths is via the endpoint's home relay node but as we establish a /// connection we'll hopefully discover more direct paths. /// /// [`MagicEndpoint`]: crate::MagicEndpoint @@ -115,11 +118,11 @@ pub(super) struct Endpoint { node_id: NodeId, /// The last time we pinged all endpoints. last_full_ping: Option, - /// The url of DERP node that we can relay over to communicate. + /// The url of relay node that we can relay over to communicate. /// /// The fallback/bootstrap path, if non-zero (non-zero for well-behaved clients). - derp_url: Option<(DerpUrl, PathState)>, - /// Best non-DERP path, i.e. a UDP address. + relay_url: Option<(RelayUrl, PathState)>, + /// Best non-relay path, i.e. a UDP address. best_addr: BestAddr, /// State for each of this node's direct paths. direct_addr_state: BTreeMap, @@ -143,7 +146,7 @@ pub(super) struct Endpoint { #[derive(Debug)] pub(super) struct Options { pub(super) public_key: PublicKey, - pub(super) derp_url: Option, + pub(super) relay_url: Option, /// Is this endpoint currently active (sending data)? pub(super) active: bool, } @@ -152,7 +155,7 @@ impl Endpoint { pub(super) fn new(id: usize, options: Options) -> Self { let quic_mapped_addr = QuicMappedAddr::generate(); - if options.derp_url.is_some() { + if options.relay_url.is_some() { // we potentially have a relay connection to the node inc!(MagicsockMetrics, num_relay_conns_added); } @@ -162,7 +165,7 @@ impl Endpoint { quic_mapped_addr, node_id: options.public_key, last_full_ping: None, - derp_url: options.derp_url.map(|url| (url, PathState::default())), + relay_url: options.relay_url.map(|url| (url, PathState::default())), best_addr: Default::default(), sent_pings: HashMap::new(), direct_addr_state: BTreeMap::new(), @@ -188,7 +191,7 @@ impl Endpoint { use best_addr::State::*; // Report our active connection. This replicates the logic of [`Endpoint::addr_for_send`] // without choosing a random candidate address if no best_addr is set. - let (conn_type, latency) = match (self.best_addr.state(now), self.derp_url.as_ref()) { + let (conn_type, latency) = match (self.best_addr.state(now), self.relay_url.as_ref()) { (Valid(addr), _) | (Outdated(addr), None) => { (ConnectionType::Direct(addr.addr), Some(addr.latency)) } @@ -221,7 +224,7 @@ impl Endpoint { EndpointInfo { id: self.id, node_id: self.node_id, - derp_url: self.derp_url(), + relay_url: self.relay_url(), addrs, conn_type, latency, @@ -229,22 +232,22 @@ impl Endpoint { } } - /// Returns the derp url of this endpoint - pub(super) fn derp_url(&self) -> Option { - self.derp_url.as_ref().map(|(url, _state)| url.clone()) + /// Returns the relay url of this endpoint + pub(super) fn relay_url(&self) -> Option { + self.relay_url.as_ref().map(|(url, _state)| url.clone()) } /// Returns the address(es) that should be used for sending the next packet. /// - /// Any or all of the UDP and DERP addrs may be non-zero. + /// Any or all of the UDP and relay addrs may be non-zero. fn addr_for_send( &mut self, now: &Instant, have_ipv6: bool, - ) -> (Option, Option) { - if derp_only_mode() { - debug!("in `DEV_DERP_ONLY` mode, giving the DERP address as the only viable address for this endpoint"); - return (None, self.derp_url()); + ) -> (Option, Option) { + if relay_only_mode() { + debug!("in `DEV_relay_ONLY` mode, giving the relay address as the only viable address for this endpoint"); + return (None, self.relay_url()); } // Update our best addr from candidate addresses (only if it is empty and if we have // recent pongs). @@ -257,16 +260,16 @@ impl Endpoint { (Some(best_addr.addr), None) } best_addr::State::Outdated(best_addr) => { - // If the address is outdated we use it, but send via derp at the same time. + // If the address is outdated we use it, but send via relay at the same time. // We also send disco pings so that it will become valid again if it still // works (i.e. we don't need to holepunch again). trace!(addr = %best_addr.addr, latency = ?best_addr.latency, - "best_addr is set but outdated, use best_addr and derp"); - (Some(best_addr.addr), self.derp_url()) + "best_addr is set but outdated, use best_addr and relay"); + (Some(best_addr.addr), self.relay_url()) } best_addr::State::Empty => { // No direct connection has been used before. If we know of any possible - // candidate addresses, randomly try to use one while also sending via derp + // candidate addresses, randomly try to use one while also sending via relay // at the same time. let addr = self .direct_addr_state @@ -277,8 +280,8 @@ impl Endpoint { }) .choose_stable(&mut rand::thread_rng()) .map(|ipp| SocketAddr::from(*ipp)); - trace!(udp_addr = ?addr, "best_addr is unset, use candidate addr and derp"); - (addr, self.derp_url()) + trace!(udp_addr = ?addr, "best_addr is unset, use candidate addr and relay"); + (addr, self.relay_url()) } } } @@ -325,7 +328,7 @@ impl Endpoint { pong.latency, best_addr::Source::BestCandidate, pong.pong_at, - self.derp_url.is_some(), + self.relay_url.is_some(), ); } } @@ -334,7 +337,7 @@ impl Endpoint { /// Whether we need to send another call-me-maybe to the endpoint. /// /// Basically we need to send a call-me-maybe if we need to find a better path. Maybe - /// we only have a derp path, or our path is expired. + /// we only have a relay path, or our path is expired. /// /// When a call-me-maybe message is sent we also need to send pings to all known paths /// of the endpoint. The [`Endpoint::send_call_me_maybe`] function takes care of this. @@ -385,12 +388,12 @@ impl Endpoint { addr, sp.at, ClearReason::PongTimeout, - self.derp_url.is_some(), + self.relay_url.is_some(), ); } - SendAddr::Derp(ref url) => { - if let Some((home_derp, relay_state)) = self.derp_url.as_mut() { - if home_derp == url { + SendAddr::Relay(ref url) => { + if let Some((home_relay, relay_state)) = self.relay_url.as_mut() { + if home_relay == url { // lost connectivity via relay relay_state.last_ping = None; } @@ -402,9 +405,9 @@ impl Endpoint { #[must_use = "pings must be handled"] fn start_ping(&self, dst: SendAddr, purpose: DiscoPingPurpose) -> Option { - if derp_only_mode() && !dst.is_derp() { - // don't attempt any hole punching in derp only mode - warn!("in `DEV_DERP_ONLY` mode, ignoring request to start a hole punching attempt."); + if relay_only_mode() && !dst.is_relay() { + // don't attempt any hole punching in relay only mode + warn!("in `DEV_relay_ONLY` mode, ignoring request to start a hole punching attempt."); return None; } let tx_id = stun::TransactionId::default(); @@ -438,9 +441,9 @@ impl Endpoint { path_found = true } } - SendAddr::Derp(ref url) => { - if let Some((home_derp, relay_state)) = self.derp_url.as_mut() { - if home_derp == url { + SendAddr::Relay(ref url) => { + if let Some((home_relay, relay_state)) = self.relay_url.as_mut() { + if home_relay == url { relay_state.last_ping.replace(now); path_found = true } @@ -498,21 +501,21 @@ impl Endpoint { } } - // We send pings regardless of whether we have a DerpUrl. If we were given any - // direct address paths to contact but no DerpUrl, we still need to send a DISCO + // We send pings regardless of whether we have a RelayUrl. If we were given any + // direct address paths to contact but no RelayUrl, we still need to send a DISCO // ping to the direct address paths so that the other node will learn about us and // accepts the connection. let mut msgs = self.send_pings(now); - if let Some(url) = self.derp_url() { + if let Some(url) = self.relay_url() { debug!(%url, "queue call-me-maybe"); msgs.push(PingAction::SendCallMeMaybe { - derp_url: url, + relay_url: url, dst_node: self.node_id, }); self.last_call_me_maybe = Some(now); } else { - debug!("can not send call-me-maybe, no DERP URL"); + debug!("can not send call-me-maybe, no relay URL"); } msgs @@ -529,19 +532,19 @@ impl Endpoint { // We allocate +1 in case the caller wants to add a call-me-maybe message. let mut ping_msgs = Vec::with_capacity(self.direct_addr_state.len() + 1); - if let Some((url, state)) = self.derp_url.as_ref() { + if let Some((url, state)) = self.relay_url.as_ref() { if state.needs_ping(&now) { - debug!(%url, "derp path needs ping"); + debug!(%url, "relay path needs ping"); if let Some(msg) = - self.start_ping(SendAddr::Derp(url.clone()), DiscoPingPurpose::Discovery) + self.start_ping(SendAddr::Relay(url.clone()), DiscoPingPurpose::Discovery) { ping_msgs.push(PingAction::SendPing(msg)) } } } - if derp_only_mode() { + if relay_only_mode() { warn!( - "in `DEV_DERP_ONLY` mode, ignoring request to respond to a hole punching attempt." + "in `DEV_relay_ONLY` mode, ignoring request to respond to a hole punching attempt." ); return ping_msgs; } @@ -571,24 +574,24 @@ impl Endpoint { pub(super) fn update_from_node_addr(&mut self, n: &AddrInfo) { if self.best_addr.is_empty() { - // we do not have a direct connection, so changing the derp information may + // we do not have a direct connection, so changing the relay information may // have an effect on our connection status - if self.derp_url.is_none() && n.derp_url.is_some() { + if self.relay_url.is_none() && n.relay_url.is_some() { // we did not have a relay connection before, but now we do inc!(MagicsockMetrics, num_relay_conns_added) - } else if self.derp_url.is_some() && n.derp_url.is_none() { + } else if self.relay_url.is_some() && n.relay_url.is_none() { // we had a relay connection before but do not have one now inc!(MagicsockMetrics, num_relay_conns_removed) } } - if n.derp_url.is_some() && n.derp_url != self.derp_url() { + if n.relay_url.is_some() && n.relay_url != self.relay_url() { debug!( - "Changing derper from {:?} to {:?}", - self.derp_url, n.derp_url + "Changing relay node from {:?} to {:?}", + self.relay_url, n.relay_url ); - self.derp_url = n - .derp_url + self.relay_url = n + .relay_url .as_ref() .map(|url| (url.clone(), PathState::default())); } @@ -601,12 +604,12 @@ impl Endpoint { debug!(new = ?n.direct_addresses , %paths, "added new direct paths for endpoint"); } - /// Clears all the endpoint's p2p state, reverting it to a DERP-only endpoint. + /// Clears all the endpoint's p2p state, reverting it to a relay-only endpoint. #[instrument(skip_all, fields(node = %self.node_id.fmt_short()))] pub(super) fn reset(&mut self) { self.last_full_ping = None; self.best_addr - .clear(ClearReason::Reset, self.derp_url.is_some()); + .clear(ClearReason::Reset, self.relay_url.is_some()); for es in self.direct_addr_state.values_mut() { es.last_ping = None; @@ -638,19 +641,19 @@ impl Endpoint { PingRole::NewEndpoint } }, - SendAddr::Derp(ref url) => { - match self.derp_url.as_mut() { + SendAddr::Relay(ref url) => { + match self.relay_url.as_mut() { Some((home_url, _state)) if home_url != url => { - // either the node changed derpers or we didn't have a relay address for the + // either the node changed relays or we didn't have a relay address for the // node. In both cases, trust the new confirmed url info!(%url, "new relay addr for node"); - self.derp_url = Some((url.clone(), PathState::with_ping(tx_id, now))); + self.relay_url = Some((url.clone(), PathState::with_ping(tx_id, now))); PingRole::NewEndpoint } Some((_home_url, state)) => state.handle_ping(tx_id, now), None => { info!(%url, "new relay addr for node"); - self.derp_url = Some((url.clone(), PathState::with_ping(tx_id, now))); + self.relay_url = Some((url.clone(), PathState::with_ping(tx_id, now))); PingRole::NewEndpoint } } @@ -732,7 +735,7 @@ impl Endpoint { self.best_addr.clear_if_equals( ip_port.into(), ClearReason::Inactive, - self.derp_url.is_some(), + self.relay_url.is_some(), ); } debug!( @@ -759,13 +762,13 @@ impl Endpoint { m: &disco::Pong, src: SendAddr, ) -> Option<(SocketAddr, PublicKey)> { - let is_derp = src.is_derp(); + let is_relay = src.is_relay(); trace!( tx = %hex::encode(m.tx_id), pong_src = %src, pong_ping_src = %m.src, - is_derp = %src.is_derp(), + is_relay = %src.is_relay(), "received pong" ); match self.sent_pings.remove(&m.tx_id) { @@ -787,7 +790,7 @@ impl Endpoint { src = %src, reported_ping_src = %m.src, ping_dst = %sp.to, - is_derp = %src.is_derp(), + is_relay = %src.is_relay(), latency = %latency.as_millis(), "received pong", ); @@ -815,7 +818,7 @@ impl Endpoint { "handled pong", ); } - SendAddr::Derp(ref url) => match self.derp_url.as_mut() { + SendAddr::Relay(ref url) => match self.relay_url.as_mut() { Some((home_url, state)) if home_url == url => { state.add_pong_reply(PongReply { latency, @@ -827,9 +830,9 @@ impl Endpoint { other => { // if we are here then we sent this ping, but the url changed // waiting for the response. It was either set to None or changed to - // another deper. This should either never happen or be extremely + // another relay. This should either never happen or be extremely // unlikely. Log and ignore for now - warn!(stored=?other, received=?url, "disco: ignoring pong via derp for different derper to last one stored"); + warn!(stored=?other, received=?url, "disco: ignoring pong via relay for different relay to the last one stored"); } }, } @@ -837,13 +840,13 @@ impl Endpoint { // Promote this pong response to our current best address if it's lower latency. // TODO(bradfitz): decide how latency vs. preference order affects decision if let SendAddr::Udp(to) = sp.to { - debug_assert!(!is_derp, "mismatching derp & udp"); + debug_assert!(!is_relay, "mismatching relay & udp"); self.best_addr.insert_if_better_or_reconfirm( to, latency, best_addr::Source::ReceivedPong, now, - self.derp_url.is_some(), + self.relay_url.is_some(), ); } @@ -924,17 +927,17 @@ impl Endpoint { self.last_used = Some(now); } - pub(super) fn receive_derp(&mut self, url: &DerpUrl, _src: &PublicKey, now: Instant) { - match self.derp_url.as_mut() { + pub(super) fn receive_relay(&mut self, url: &RelayUrl, _src: &PublicKey, now: Instant) { + match self.relay_url.as_mut() { Some((current_home, state)) if current_home == url => { // We received on the expected url. update state. state.last_payload_msg = Some(now); } Some((_current_home, _state)) => { - // we have a different url. we only update on ping, not on receive_derp. + // we have a different url. we only update on ping, not on receive_relay. } None => { - self.derp_url = Some((url.clone(), PathState::with_last_payload(now))); + self.relay_url = Some((url.clone(), PathState::with_last_payload(now))); } } self.last_used = Some(now); @@ -946,8 +949,8 @@ impl Endpoint { .direct_addr_state .get(&(*addr).into()) .and_then(|ep| ep.last_ping), - SendAddr::Derp(url) => self - .derp_url + SendAddr::Relay(url) => self + .relay_url .as_ref() .filter(|(home_url, _state)| home_url == url) .and_then(|(_home_url, state)| state.last_ping), @@ -1012,10 +1015,10 @@ impl Endpoint { pub(crate) fn get_send_addrs( &mut self, have_ipv6: bool, - ) -> (Option, Option, Vec) { + ) -> (Option, Option, Vec) { let now = Instant::now(); self.last_used.replace(now); - let (udp_addr, derp_url) = self.addr_for_send(&now, have_ipv6); + let (udp_addr, relay_url) = self.addr_for_send(&now, have_ipv6); let mut ping_msgs = Vec::new(); if self.want_call_me_maybe(&now) { @@ -1024,12 +1027,12 @@ impl Endpoint { trace!( ?udp_addr, - ?derp_url, + ?relay_url, pings = %ping_msgs.len(), "found send address", ); - (udp_addr, derp_url, ping_msgs) + (udp_addr, relay_url, ping_msgs) } /// Get the direct addresses for this endpoint. @@ -1043,7 +1046,7 @@ impl Endpoint { NodeAddr { node_id: self.node_id, info: AddrInfo { - derp_url: self.derp_url(), + relay_url: self.relay_url(), direct_addresses, }, } @@ -1061,7 +1064,7 @@ impl Endpoint { /// State about a particular path to another [`Endpoint`]. /// -/// This state is used for both the DERP path and any direct UDP paths. +/// This state is used for both the relay path and any direct UDP paths. #[derive(Debug, Clone, PartialEq, Eq, Hash, Default)] pub(super) struct PathState { /// The last (outgoing) ping time. @@ -1337,8 +1340,8 @@ pub struct EndpointInfo { pub id: usize, /// The public key of the endpoint. pub node_id: NodeId, - /// Derper, if available. - pub derp_url: Option, + /// relay server, if available. + pub relay_url: Option, /// List of addresses at which this node might be reachable, plus any latency information we /// have about that address and the last time the address was used. pub addrs: Vec, @@ -1367,15 +1370,15 @@ pub enum ConnectionType { /// Direct UDP connection #[display("direct")] Direct(SocketAddr), - /// Relay connection over DERP + /// Relay connection over relay #[display("relay")] - Relay(DerpUrl), - /// Both a UDP and a DERP connection are used. + Relay(RelayUrl), + /// Both a UDP and a relay connection are used. /// /// This is the case if we do have a UDP address, but are missing a recent confirmation that /// the address works. #[display("mixed")] - Mixed(SocketAddr, DerpUrl), + Mixed(SocketAddr, RelayUrl), /// We have no verified connection to this PublicKey #[display("none")] None, @@ -1395,12 +1398,13 @@ mod tests { #[test] fn test_endpoint_infos() { - let new_relay_and_state = |url: Option| url.map(|url| (url, PathState::default())); + let new_relay_and_state = + |url: Option| url.map(|url| (url, PathState::default())); let now = Instant::now(); let elapsed = Duration::from_secs(3); let later = now + elapsed; - let send_addr: DerpUrl = "https://my-derp.com".parse().unwrap(); + let send_addr: RelayUrl = "https://my-relay.com".parse().unwrap(); // endpoint with a `best_addr` that has a latency let pong_src = SendAddr::Udp("0.0.0.0:1".parse().unwrap()); let latency = Duration::from_millis(50); @@ -1425,7 +1429,7 @@ mod tests { quic_mapped_addr: QuicMappedAddr::generate(), node_id: key.public(), last_full_ping: None, - derp_url: new_relay_and_state(Some(send_addr.clone())), + relay_url: new_relay_and_state(Some(send_addr.clone())), best_addr: BestAddr::from_parts( ip_port.into(), latency, @@ -1440,13 +1444,13 @@ mod tests { ip_port.into(), ) }; - // endpoint w/ no best addr but a derp w/ latency + // endpoint w/ no best addr but a relay w/ latency let b_endpoint = { // let socket_addr = "0.0.0.0:9".parse().unwrap(); let relay_state = PathState::with_pong_reply(PongReply { latency, pong_at: now, - from: SendAddr::Derp(send_addr.clone()), + from: SendAddr::Relay(send_addr.clone()), pong_src: pong_src.clone(), }); let key = SecretKey::generate(); @@ -1455,7 +1459,7 @@ mod tests { quic_mapped_addr: QuicMappedAddr::generate(), node_id: key.public(), last_full_ping: None, - derp_url: Some((send_addr.clone(), relay_state)), + relay_url: Some((send_addr.clone(), relay_state)), best_addr: BestAddr::default(), direct_addr_state: BTreeMap::default(), sent_pings: HashMap::new(), @@ -1464,7 +1468,7 @@ mod tests { } }; - // endpoint w/ no best addr but a derp w/ no latency + // endpoint w/ no best addr but a relay w/ no latency let c_endpoint = { // let socket_addr = "0.0.0.0:8".parse().unwrap(); let endpoint_state = BTreeMap::new(); @@ -1474,7 +1478,7 @@ mod tests { quic_mapped_addr: QuicMappedAddr::generate(), node_id: key.public(), last_full_ping: None, - derp_url: new_relay_and_state(Some(send_addr.clone())), + relay_url: new_relay_and_state(Some(send_addr.clone())), best_addr: BestAddr::default(), direct_addr_state: endpoint_state, sent_pings: HashMap::new(), @@ -1499,7 +1503,7 @@ mod tests { let relay_state = PathState::with_pong_reply(PongReply { latency, pong_at: now, - from: SendAddr::Derp(send_addr.clone()), + from: SendAddr::Relay(send_addr.clone()), pong_src, }); let key = SecretKey::generate(); @@ -1509,7 +1513,7 @@ mod tests { quic_mapped_addr: QuicMappedAddr::generate(), node_id: key.public(), last_full_ping: None, - derp_url: Some((send_addr.clone(), relay_state)), + relay_url: Some((send_addr.clone(), relay_state)), best_addr: BestAddr::from_parts( socket_addr, Duration::from_millis(80), @@ -1528,7 +1532,7 @@ mod tests { EndpointInfo { id: a_endpoint.id, node_id: a_endpoint.node_id, - derp_url: a_endpoint.derp_url(), + relay_url: a_endpoint.relay_url(), addrs: Vec::from([DirectAddrInfo { addr: a_socket_addr, latency: Some(latency), @@ -1542,7 +1546,7 @@ mod tests { EndpointInfo { id: b_endpoint.id, node_id: b_endpoint.node_id, - derp_url: b_endpoint.derp_url(), + relay_url: b_endpoint.relay_url(), addrs: Vec::new(), conn_type: ConnectionType::Relay(send_addr.clone()), latency: Some(latency), @@ -1551,7 +1555,7 @@ mod tests { EndpointInfo { id: c_endpoint.id, node_id: c_endpoint.node_id, - derp_url: c_endpoint.derp_url(), + relay_url: c_endpoint.relay_url(), addrs: Vec::new(), conn_type: ConnectionType::Relay(send_addr.clone()), latency: None, @@ -1560,7 +1564,7 @@ mod tests { EndpointInfo { id: d_endpoint.id, node_id: d_endpoint.node_id, - derp_url: d_endpoint.derp_url(), + relay_url: d_endpoint.relay_url(), addrs: Vec::from([DirectAddrInfo { addr: d_socket_addr, latency: Some(latency), @@ -1611,7 +1615,7 @@ mod tests { let key = SecretKey::generate(); let opts = Options { public_key: key.public(), - derp_url: None, + relay_url: None, active: true, }; let mut ep = Endpoint::new(0, opts); @@ -1624,7 +1628,7 @@ mod tests { let ping_messages = ep.handle_call_me_maybe(call_me_maybe); - // We have no derper and no previous direct addresses, so we should get the same + // We have no relay server and no previous direct addresses, so we should get the same // number of pings as direct addresses in the call-me-maybe. assert_eq!(ping_messages.len(), my_numbers_count as usize); } diff --git a/iroh-net/src/magicsock/derp_actor.rs b/iroh-net/src/magicsock/relay_actor.rs similarity index 65% rename from iroh-net/src/magicsock/derp_actor.rs rename to iroh-net/src/magicsock/relay_actor.rs index 55395b9c49..f0585e9a88 100644 --- a/iroh-net/src/magicsock/derp_actor.rs +++ b/iroh-net/src/magicsock/relay_actor.rs @@ -19,49 +19,49 @@ use tokio_util::sync::CancellationToken; use tracing::{debug, info, info_span, trace, warn, Instrument}; use crate::{ - derp::{self, http::ClientError, DerpUrl, ReceivedMessage, MAX_PACKET_SIZE}, key::{PublicKey, PUBLIC_KEY_LENGTH}, + relay::{self, http::ClientError, ReceivedMessage, RelayUrl, MAX_PACKET_SIZE}, }; use super::{ActorMessage, Inner}; -use super::{DerpContents, Metrics as MagicsockMetrics}; +use super::{Metrics as MagicsockMetrics, RelayContents}; -/// How long a non-home DERP connection needs to be idle (last written to) before we close it. -const DERP_INACTIVE_CLEANUP_TIME: Duration = Duration::from_secs(60); +/// How long a non-home relay connection needs to be idle (last written to) before we close it. +const RELAY_INACTIVE_CLEANUP_TIME: Duration = Duration::from_secs(60); -/// How often `clean_stale_derp` runs when there are potentially-stale DERP connections to close. -const DERP_CLEAN_STALE_INTERVAL: Duration = Duration::from_secs(15); +/// How often `clean_stale_relay` runs when there are potentially-stale relay connections to close. +const RELAY_CLEAN_STALE_INTERVAL: Duration = Duration::from_secs(15); -pub(super) enum DerpActorMessage { +pub(super) enum RelayActorMessage { Send { - url: DerpUrl, - contents: DerpContents, + url: RelayUrl, + contents: RelayContents, peer: PublicKey, }, Connect { - url: DerpUrl, + url: RelayUrl, peer: Option, }, - NotePreferred(DerpUrl), - MaybeCloseDerpsOnRebind(Vec), + NotePreferred(RelayUrl), + MaybeCloseRelaysOnRebind(Vec), } -/// Contains fields for an active DERP connection. +/// Contains fields for an active relay connection. #[derive(Debug)] -struct ActiveDerp { +struct ActiveRelay { /// The time of the last request for its write /// channel (currently even if there was no write). last_write: Instant, msg_sender: mpsc::Sender, /// Contains optional alternate routes to use as an optimization instead of - /// contacting a peer via their home DERP connection. If they sent us a message - /// on this DERP connection (which should really only be on our DERP + /// contacting a peer via their home relay connection. If they sent us a message + /// on this relay connection (which should really only be on our relay /// home connection, or what was once our home), then we remember that route here to optimistically - /// use instead of creating a new DERP connection back to their home. - derp_routes: Vec, - url: DerpUrl, - derp_client: derp::http::Client, - derp_client_receiver: derp::http::ClientReceiver, + /// use instead of creating a new relay connection back to their home. + relay_routes: Vec, + url: RelayUrl, + relay_client: relay::http::Client, + relay_client_receiver: relay::http::ClientReceiver, /// The set of senders we know are present on this connection, based on /// messages we've received from the server. peer_present: HashSet, @@ -72,27 +72,27 @@ struct ActiveDerp { #[derive(Debug)] #[allow(clippy::large_enum_variant)] -enum ActiveDerpMessage { +enum ActiveRelayMessage { GetLastWrite(oneshot::Sender), Ping(oneshot::Sender>), GetLocalAddr(oneshot::Sender>), - GetPeerRoute(PublicKey, oneshot::Sender>), - GetClient(oneshot::Sender), + GetPeerRoute(PublicKey, oneshot::Sender>), + GetClient(oneshot::Sender), NotePreferred(bool), Shutdown, } -impl ActiveDerp { +impl ActiveRelay { fn new( - url: DerpUrl, - derp_client: derp::http::Client, - derp_client_receiver: derp::http::ClientReceiver, + url: RelayUrl, + relay_client: relay::http::Client, + relay_client_receiver: relay::http::ClientReceiver, msg_sender: mpsc::Sender, ) -> Self { - ActiveDerp { + ActiveRelay { last_write: Instant::now(), msg_sender, - derp_routes: Default::default(), + relay_routes: Default::default(), url, peer_present: HashSet::new(), backoff: backoff::exponential::ExponentialBackoffBuilder::new() @@ -101,13 +101,13 @@ impl ActiveDerp { .build(), last_packet_time: None, last_packet_src: None, - derp_client, - derp_client_receiver, + relay_client, + relay_client_receiver, } } - async fn run(mut self, mut inbox: mpsc::Receiver) -> anyhow::Result<()> { - self.derp_client + async fn run(mut self, mut inbox: mpsc::Receiver) -> anyhow::Result<()> { + self.relay_client .connect() .await .context("initial connection")?; @@ -117,42 +117,42 @@ impl ActiveDerp { Some(msg) = inbox.recv() => { trace!("tick: inbox: {:?}", msg); match msg { - ActiveDerpMessage::GetLastWrite(r) => { + ActiveRelayMessage::GetLastWrite(r) => { r.send(self.last_write).ok(); } - ActiveDerpMessage::Ping(r) => { - r.send(self.derp_client.ping().await).ok(); + ActiveRelayMessage::Ping(r) => { + r.send(self.relay_client.ping().await).ok(); } - ActiveDerpMessage::GetLocalAddr(r) => { - r.send(self.derp_client.local_addr().await).ok(); + ActiveRelayMessage::GetLocalAddr(r) => { + r.send(self.relay_client.local_addr().await).ok(); } - ActiveDerpMessage::GetClient(r) => { + ActiveRelayMessage::GetClient(r) => { self.last_write = Instant::now(); - r.send(self.derp_client.clone()).ok(); + r.send(self.relay_client.clone()).ok(); } - ActiveDerpMessage::NotePreferred(is_preferred) => { - self.derp_client.note_preferred(is_preferred).await; + ActiveRelayMessage::NotePreferred(is_preferred) => { + self.relay_client.note_preferred(is_preferred).await; } - ActiveDerpMessage::GetPeerRoute(peer, r) => { - let res = if self.derp_routes.contains(&peer) { - Some(self.derp_client.clone()) + ActiveRelayMessage::GetPeerRoute(peer, r) => { + let res = if self.relay_routes.contains(&peer) { + Some(self.relay_client.clone()) } else { None }; r.send(res).ok(); } - ActiveDerpMessage::Shutdown => { - self.derp_client.close().await.ok(); + ActiveRelayMessage::Shutdown => { + self.relay_client.close().await.ok(); break; } } } - msg = self.derp_client_receiver.recv() => { - trace!("tick: derp_client_receiver"); + msg = self.relay_client_receiver.recv() => { + trace!("tick: relay_client_receiver"); if let Some(msg) = msg { - if self.handle_derp_msg(msg).await == ReadResult::Break { + if self.handle_relay_msg(msg).await == ReadResult::Break { // fatal error - self.derp_client.close().await.ok(); + self.relay_client.close().await.ok(); break; } } @@ -166,7 +166,7 @@ impl ActiveDerp { Ok(()) } - async fn handle_derp_msg( + async fn handle_relay_msg( &mut self, msg: Result<(ReceivedMessage, usize), ClientError>, ) -> ReadResult { @@ -176,20 +176,20 @@ impl ActiveDerp { // Forget that all these peers have routes. let peers: Vec<_> = self.peer_present.drain().collect(); - self.derp_routes.retain(|peer| !peers.contains(peer)); + self.relay_routes.retain(|peer| !peers.contains(peer)); if matches!( err, - derp::http::ClientError::Closed | derp::http::ClientError::IPDisabled + relay::http::ClientError::Closed | relay::http::ClientError::IPDisabled ) { // drop client return ReadResult::Break; } - // If our DERP connection broke, it might be because our network + // If our relay connection broke, it might be because our network // conditions changed. Start that check. // TODO: - // self.re_stun("derp-recv-error").await; + // self.re_stun("relay-recv-error").await; // Back off a bit before reconnecting. match self.backoff.next_backoff() { @@ -215,11 +215,11 @@ impl ActiveDerp { } match msg { - derp::ReceivedMessage::ServerInfo { .. } => { + relay::ReceivedMessage::ServerInfo { .. } => { info!(%conn_gen, "connected"); ReadResult::Continue } - derp::ReceivedMessage::ReceivedPacket { source, data } => { + relay::ReceivedMessage::ReceivedPacket { source, data } => { trace!(len=%data.len(), "received msg"); // If this is a new sender we hadn't seen before, remember it and // register a route for this peer. @@ -233,24 +233,25 @@ impl ActiveDerp { self.last_packet_src = Some(source); if !self.peer_present.contains(&source) { self.peer_present.insert(source); - self.derp_routes.push(source); + self.relay_routes.push(source); } } - let res = DerpReadResult { + let res = RelayReadResult { url: self.url.clone(), src: source, buf: data, }; - if let Err(err) = self.msg_sender.try_send(ActorMessage::ReceiveDerp(res)) { - warn!("dropping received DERP packet: {:?}", err); + if let Err(err) = self.msg_sender.try_send(ActorMessage::ReceiveRelay(res)) + { + warn!("dropping received relay packet: {:?}", err); } ReadResult::Continue } - derp::ReceivedMessage::Ping(data) => { + relay::ReceivedMessage::Ping(data) => { // Best effort reply to the ping. - let dc = self.derp_client.clone(); + let dc = self.relay_client.clone(); tokio::task::spawn(async move { if let Err(err) = dc.send_pong(data).await { warn!("pong error: {:?}", err); @@ -258,9 +259,9 @@ impl ActiveDerp { }); ReadResult::Continue } - derp::ReceivedMessage::Health { .. } => ReadResult::Continue, - derp::ReceivedMessage::PeerGone(key) => { - self.derp_routes.retain(|peer| peer != &key); + relay::ReceivedMessage::Health { .. } => ReadResult::Continue, + relay::ReceivedMessage::PeerGone(key) => { + self.relay_routes.retain(|peer| peer != &key); ReadResult::Continue } other => { @@ -274,21 +275,21 @@ impl ActiveDerp { } } -pub(super) struct DerpActor { +pub(super) struct RelayActor { conn: Arc, - /// DERP Url -> connection to the node - active_derp: BTreeMap, JoinHandle<()>)>, + /// relay Url -> connection to the node + active_relay: BTreeMap, JoinHandle<()>)>, msg_sender: mpsc::Sender, - ping_tasks: JoinSet<(DerpUrl, bool)>, + ping_tasks: JoinSet<(RelayUrl, bool)>, cancel_token: CancellationToken, } -impl DerpActor { +impl RelayActor { pub(super) fn new(conn: Arc, msg_sender: mpsc::Sender) -> Self { let cancel_token = CancellationToken::new(); - DerpActor { + Self { conn, - active_derp: Default::default(), + active_relay: Default::default(), msg_sender, ping_tasks: Default::default(), cancel_token, @@ -299,10 +300,10 @@ impl DerpActor { self.cancel_token.clone() } - pub(super) async fn run(mut self, mut receiver: mpsc::Receiver) { + pub(super) async fn run(mut self, mut receiver: mpsc::Receiver) { let mut cleanup_timer = time::interval_at( - time::Instant::now() + DERP_CLEAN_STALE_INTERVAL, - DERP_CLEAN_STALE_INTERVAL, + time::Instant::now() + RELAY_CLEAN_STALE_INTERVAL, + RELAY_CLEAN_STALE_INTERVAL, ); loop { @@ -317,7 +318,7 @@ impl DerpActor { if !ping_success { with_cancel( self.cancel_token.child_token(), - self.close_or_reconnect_derp(&url, "rebind-ping-fail") + self.close_or_reconnect_relay(&url, "rebind-ping-fail") ).await; } } @@ -326,54 +327,54 @@ impl DerpActor { } _ = cleanup_timer.tick() => { trace!("tick: cleanup"); - with_cancel(self.cancel_token.child_token(), self.clean_stale_derp()).await; + with_cancel(self.cancel_token.child_token(), self.clean_stale_relay()).await; } else => { - trace!("shutting down derp recv loop"); + trace!("shutting down relay recv loop"); break; } } } // try shutdown - self.close_all_derp("conn-close").await; + self.close_all_relay("conn-close").await; } - async fn handle_msg(&mut self, msg: DerpActorMessage) { + async fn handle_msg(&mut self, msg: RelayActorMessage) { match msg { - DerpActorMessage::Send { + RelayActorMessage::Send { url, contents, peer, } => { - self.send_derp(&url, contents, peer).await; + self.send_relay(&url, contents, peer).await; } - DerpActorMessage::Connect { url, peer } => { - self.connect_derp(&url, peer.as_ref()).await; + RelayActorMessage::Connect { url, peer } => { + self.connect_relay(&url, peer.as_ref()).await; } - DerpActorMessage::NotePreferred(my_derp) => { - self.note_preferred(&my_derp).await; + RelayActorMessage::NotePreferred(my_relay) => { + self.note_preferred(&my_relay).await; } - DerpActorMessage::MaybeCloseDerpsOnRebind(ifs) => { - self.maybe_close_derps_on_rebind(&ifs).await; + RelayActorMessage::MaybeCloseRelaysOnRebind(ifs) => { + self.maybe_close_relays_on_rebind(&ifs).await; } } } - async fn note_preferred(&self, my_url: &DerpUrl) { - futures::future::join_all(self.active_derp.iter().map(|(url, (s, _))| async move { + async fn note_preferred(&self, my_url: &RelayUrl) { + futures::future::join_all(self.active_relay.iter().map(|(url, (s, _))| async move { let is_preferred = url == my_url; - s.send(ActiveDerpMessage::NotePreferred(is_preferred)) + s.send(ActiveRelayMessage::NotePreferred(is_preferred)) .await .ok() })) .await; } - async fn send_derp(&mut self, url: &DerpUrl, contents: DerpContents, peer: PublicKey) { - trace!(%url, peer = %peer.fmt_short(),len = contents.iter().map(|c| c.len()).sum::(), "sending derp"); - // Derp Send - let derp_client = self.connect_derp(url, Some(&peer)).await; + async fn send_relay(&mut self, url: &RelayUrl, contents: RelayContents, peer: PublicKey) { + trace!(%url, peer = %peer.fmt_short(),len = contents.iter().map(|c| c.len()).sum::(), "sending over relay"); + // Relay Send + let relay_client = self.connect_relay(url, Some(&peer)).await; for content in &contents { trace!(%url, ?peer, "sending {}B", content.len()); } @@ -386,13 +387,13 @@ impl DerpActor { // But we have no guarantee that the total size of the contents including // length prefix will be smaller than the payload size. for packet in PacketizeIter::<_, PAYLAOD_SIZE>::new(contents) { - match derp_client.send(peer, packet).await { + match relay_client.send(peer, packet).await { Ok(_) => { - inc_by!(MagicsockMetrics, send_derp, total_bytes); + inc_by!(MagicsockMetrics, send_relay, total_bytes); } Err(err) => { warn!(%url, "send: failed {:?}", err); - inc!(MagicsockMetrics, send_derp_error); + inc!(MagicsockMetrics, send_relay_error); } } } @@ -405,12 +406,12 @@ impl DerpActor { } /// Returns `true`if the message was sent successfully. - async fn send_to_active(&mut self, url: &DerpUrl, msg: ActiveDerpMessage) -> bool { - match self.active_derp.get(url) { + async fn send_to_active(&mut self, url: &RelayUrl, msg: ActiveRelayMessage) -> bool { + match self.active_relay.get(url) { Some((s, _)) => match s.send(msg).await { Ok(_) => true, Err(mpsc::error::SendError(_)) => { - self.close_derp(url, "sender-closed").await; + self.close_relay(url, "sender-closed").await; false } }, @@ -418,20 +419,20 @@ impl DerpActor { } } - /// Connect to the given derp node. - async fn connect_derp( + /// Connect to the given relay node. + async fn connect_relay( &mut self, - url: &DerpUrl, + url: &RelayUrl, peer: Option<&PublicKey>, - ) -> derp::http::Client { - // See if we have a connection open to that DERP node ID first. If so, might as + ) -> relay::http::Client { + // See if we have a connection open to that relay node ID first. If so, might as // well use it. (It's a little arbitrary whether we use this one vs. the reverse route // below when we have both.) { let (os, or) = oneshot::channel(); if self - .send_to_active(url, ActiveDerpMessage::GetClient(os)) + .send_to_active(url, ActiveRelayMessage::GetClient(os)) .await { if let Ok(client) = or.await { @@ -440,15 +441,15 @@ impl DerpActor { } } - // If we don't have an open connection to the peer's home DERP - // node, see if we have an open connection to a DERP node + // If we don't have an open connection to the peer's home relay + // node, see if we have an open connection to a relay node // where we'd heard from that peer already. For instance, - // perhaps peer's home is Frankfurt, but they dialed our home DERP + // perhaps peer's home is Frankfurt, but they dialed our home relay // node in SF to reach us, so we can reply to them using our // SF connection rather than dialing Frankfurt. if let Some(peer) = peer { for url in self - .active_derp + .active_relay .keys() .cloned() .collect::>() @@ -456,7 +457,7 @@ impl DerpActor { { let (os, or) = oneshot::channel(); if self - .send_to_active(&url, ActiveDerpMessage::GetPeerRoute(*peer, os)) + .send_to_active(&url, ActiveRelayMessage::GetPeerRoute(*peer, os)) .await { if let Ok(Some(client)) = or.await { @@ -471,21 +472,21 @@ impl DerpActor { } else { "home-keep-alive".to_string() }; - info!("adding connection to derp-{url} for {why}"); + info!("adding connection to relay-{url} for {why}"); - let my_derp = self.conn.my_derp(); + let my_relay = self.conn.my_relay(); let ipv6_reported = self.conn.ipv6_reported.clone(); let url = url.clone(); let url1 = url.clone(); // building a client does not dial - let (dc, dc_receiver) = derp::http::ClientBuilder::new(url1.clone()) + let (dc, dc_receiver) = relay::http::ClientBuilder::new(url1.clone()) .address_family_selector(move || { let ipv6_reported = ipv6_reported.clone(); Box::pin(async move { ipv6_reported.load(Ordering::Relaxed) }) }) .can_ack_pings(true) - .is_preferred(my_derp.as_ref() == Some(&url1)) + .is_preferred(my_relay.as_ref() == Some(&url1)) .build(self.conn.secret_key.clone()); let (s, r) = mpsc::channel(64); @@ -495,34 +496,34 @@ impl DerpActor { let url1 = url.clone(); let handle = tokio::task::spawn( async move { - let ad = ActiveDerp::new(url1, c, dc_receiver, msg_sender); + let ad = ActiveRelay::new(url1, c, dc_receiver, msg_sender); if let Err(err) = ad.run(r).await { warn!("connection error: {:?}", err); } } - .instrument(info_span!("active-derp", %url)), + .instrument(info_span!("active-relay", %url)), ); // Insert, to make sure we do not attempt to double connect. - self.active_derp.insert(url.clone(), (s, handle)); + self.active_relay.insert(url.clone(), (s, handle)); - inc!(MagicsockMetrics, num_derp_conns_added); + inc!(MagicsockMetrics, num_relay_conns_added); - self.log_active_derp(); + self.log_active_relay(); dc } - /// Closes the DERP connections not originating from a local IP address. + /// Closes the relay connections not originating from a local IP address. /// - /// Called in response to a rebind, any DERP connection originating from an address + /// Called in response to a rebind, any relay connection originating from an address /// that's not known to be currently a local IP address should be closed. All the other - /// DERP connections are pinged. - async fn maybe_close_derps_on_rebind(&mut self, okay_local_ips: &[IpAddr]) { + /// relay connections are pinged. + async fn maybe_close_relays_on_rebind(&mut self, okay_local_ips: &[IpAddr]) { let mut tasks = Vec::new(); for url in self - .active_derp + .active_relay .keys() .cloned() .collect::>() @@ -530,7 +531,7 @@ impl DerpActor { { let (os, or) = oneshot::channel(); let la = if self - .send_to_active(&url, ActiveDerpMessage::GetLocalAddr(os)) + .send_to_active(&url, ActiveRelayMessage::GetLocalAddr(os)) .await { match or.await { @@ -551,7 +552,9 @@ impl DerpActor { } let (os, or) = oneshot::channel(); - let ping_sent = self.send_to_active(&url, ActiveDerpMessage::Ping(os)).await; + let ping_sent = self + .send_to_active(&url, ActiveRelayMessage::Ping(os)) + .await; self.ping_tasks.spawn(async move { let ping_success = time::timeout(Duration::from_secs(3), async { @@ -569,35 +572,35 @@ impl DerpActor { } for (url, why) in tasks { - self.close_or_reconnect_derp(&url, why).await; + self.close_or_reconnect_relay(&url, why).await; } - self.log_active_derp(); + self.log_active_relay(); } - /// Closes the DERP connection to the provided `url` and starts reconnecting it if it's - /// our current home DERP. - async fn close_or_reconnect_derp(&mut self, url: &DerpUrl, why: &'static str) { - self.close_derp(url, why).await; - if self.conn.my_derp().as_ref() == Some(url) { - self.connect_derp(url, None).await; + /// Closes the relay connection to the provided `url` and starts reconnecting it if it's + /// our current home relay. + async fn close_or_reconnect_relay(&mut self, url: &RelayUrl, why: &'static str) { + self.close_relay(url, why).await; + if self.conn.my_relay().as_ref() == Some(url) { + self.connect_relay(url, None).await; } } - async fn clean_stale_derp(&mut self) { - trace!("checking {} derps for staleness", self.active_derp.len()); + async fn clean_stale_relay(&mut self) { + trace!("checking {} relays for staleness", self.active_relay.len()); let now = Instant::now(); let mut to_close = Vec::new(); - for (i, (s, _)) in &self.active_derp { - if Some(i) == self.conn.my_derp().as_ref() { + for (i, (s, _)) in &self.active_relay { + if Some(i) == self.conn.my_relay().as_ref() { continue; } let (os, or) = oneshot::channel(); - match s.send(ActiveDerpMessage::GetLastWrite(os)).await { + match s.send(ActiveRelayMessage::GetLastWrite(os)).await { Ok(_) => match or.await { Ok(last_write) => { - if last_write.duration_since(now) > DERP_INACTIVE_CLEANUP_TIME { + if last_write.duration_since(now) > RELAY_INACTIVE_CLEANUP_TIME { to_close.push(i.clone()); } } @@ -613,56 +616,56 @@ impl DerpActor { let dirty = !to_close.is_empty(); trace!( - "closing {} of {} derps", + "closing {} of {} relays", to_close.len(), - self.active_derp.len() + self.active_relay.len() ); for i in to_close { - self.close_derp(&i, "idle").await; + self.close_relay(&i, "idle").await; } if dirty { - self.log_active_derp(); + self.log_active_relay(); } } - async fn close_all_derp(&mut self, why: &'static str) { - if self.active_derp.is_empty() { + async fn close_all_relay(&mut self, why: &'static str) { + if self.active_relay.is_empty() { return; } // Need to collect to avoid double borrow - let urls: Vec<_> = self.active_derp.keys().cloned().collect(); + let urls: Vec<_> = self.active_relay.keys().cloned().collect(); for url in urls { - self.close_derp(&url, why).await; + self.close_relay(&url, why).await; } - self.log_active_derp(); + self.log_active_relay(); } - async fn close_derp(&mut self, url: &DerpUrl, why: &'static str) { - if let Some((s, t)) = self.active_derp.remove(url) { + async fn close_relay(&mut self, url: &RelayUrl, why: &'static str) { + if let Some((s, t)) = self.active_relay.remove(url) { debug!(%url, "closing connection: {}", why); - s.send(ActiveDerpMessage::Shutdown).await.ok(); + s.send(ActiveRelayMessage::Shutdown).await.ok(); t.abort(); // ensure the task is shutdown - inc!(MagicsockMetrics, num_derp_conns_removed); + inc!(MagicsockMetrics, num_relay_conns_removed); } } - fn log_active_derp(&self) { - debug!("{} active derp conns{}", self.active_derp.len(), { + fn log_active_relay(&self) { + debug!("{} active relay conns{}", self.active_relay.len(), { let mut s = String::new(); - if !self.active_derp.is_empty() { + if !self.active_relay.is_empty() { s += ":"; - for node in self.active_derp_sorted() { - s += &format!(" derp-{}", node,); + for node in self.active_relay_sorted() { + s += &format!(" relay-{}", node,); } } s }); } - fn active_derp_sorted(&self) -> impl Iterator { - let mut ids: Vec<_> = self.active_derp.keys().cloned().collect(); + fn active_relay_sorted(&self) -> impl Iterator { + let mut ids: Vec<_> = self.active_relay.keys().cloned().collect(); ids.sort(); ids.into_iter() @@ -670,8 +673,8 @@ impl DerpActor { } #[derive(derive_more::Debug)] -pub(super) struct DerpReadResult { - pub(super) url: DerpUrl, +pub(super) struct RelayReadResult { + pub(super) url: RelayUrl, pub(super) src: PublicKey, /// packet data #[debug(skip)] diff --git a/iroh-net/src/metrics.rs b/iroh-net/src/metrics.rs index f979dbe742..8449a33572 100644 --- a/iroh-net/src/metrics.rs +++ b/iroh-net/src/metrics.rs @@ -1,5 +1,5 @@ //! Co-locating all of the iroh-net metrics structs -pub use crate::derp::Metrics as DerpMetrics; pub use crate::magicsock::Metrics as MagicsockMetrics; pub use crate::netcheck::Metrics as NetcheckMetrics; pub use crate::portmapper::Metrics as PortmapMetrics; +pub use crate::relay::Metrics as RelayMetrics; diff --git a/iroh-net/src/net/interfaces.rs b/iroh-net/src/net/interfaces.rs index 9671bd1bf9..20deeca43f 100644 --- a/iroh-net/src/net/interfaces.rs +++ b/iroh-net/src/net/interfaces.rs @@ -451,8 +451,8 @@ mod tests { let link_local = Ipv6Addr::new(0xfe80, 0, 0, 0, 0xcbc9, 0x6aff, 0x5b07, 0x4a9e); assert!(!is_usable_v6(&link_local.into())); - let derp_use1 = Ipv6Addr::new(0x2a01, 0x4ff, 0xf0, 0xc4a1, 0, 0, 0, 0x1); - assert!(is_usable_v6(&derp_use1.into())); + let relay_use1 = Ipv6Addr::new(0x2a01, 0x4ff, 0xf0, 0xc4a1, 0, 0, 0, 0x1); + assert!(is_usable_v6(&relay_use1.into())); let random_2603 = Ipv6Addr::new(0x2603, 0x3ff, 0xf1, 0xc3aa, 0x1, 0x2, 0x3, 0x1); assert!(is_usable_v6(&random_2603.into())); diff --git a/iroh-net/src/netcheck.rs b/iroh-net/src/netcheck.rs index e06a932ea3..60f91de567 100644 --- a/iroh-net/src/netcheck.rs +++ b/iroh-net/src/netcheck.rs @@ -19,13 +19,13 @@ use tokio::time::{Duration, Instant}; use tokio_util::sync::CancellationToken; use tracing::{debug, error, info_span, trace, warn, Instrument}; -use crate::derp::DerpUrl; use crate::net::ip::to_canonical; use crate::net::{IpFamily, UdpSocket}; +use crate::relay::RelayUrl; use crate::util::CancelOnDrop; -use super::derp::DerpMap; use super::portmapper; +use super::relay::RelayMap; use super::stun; mod metrics; @@ -79,13 +79,13 @@ pub struct Report { /// Probe indicating the presence of port mapping protocols on the LAN. pub portmap_probe: Option, /// `None` for unknown - pub preferred_derp: Option, - /// keyed by DERP Url - pub derp_latency: DerpLatencies, - /// keyed by DERP Url - pub derp_v4_latency: DerpLatencies, - /// keyed by DERP Url - pub derp_v6_latency: DerpLatencies, + pub preferred_relay: Option, + /// keyed by relay Url + pub relay_latency: RelayLatencies, + /// keyed by relay Url + pub relay_v4_latency: RelayLatencies, + /// keyed by relay Url + pub relay_v6_latency: RelayLatencies, /// ip:port of global IPv4 pub global_v4: Option, /// `[ip]:port` of global IPv6 @@ -101,33 +101,33 @@ impl fmt::Display for Report { } } -/// Latencies per DERP node. +/// Latencies per relay node. #[derive(Debug, Default, PartialEq, Eq, Clone)] -pub struct DerpLatencies(BTreeMap); +pub struct RelayLatencies(BTreeMap); -impl DerpLatencies { +impl RelayLatencies { fn new() -> Self { Default::default() } - /// Updates a derp's latency, if it is faster than before. - fn update_derp(&mut self, url: DerpUrl, latency: Duration) { + /// Updates a relay's latency, if it is faster than before. + fn update_relay(&mut self, url: RelayUrl, latency: Duration) { let val = self.0.entry(url).or_insert(latency); if latency < *val { *val = latency; } } - /// Merges another [`DerpLatencies`] into this one. + /// Merges another [`RelayLatencies`] into this one. /// - /// For each derp the latency is updated using [`DerpLatencies::update_derp`]. - fn merge(&mut self, other: &DerpLatencies) { + /// For each relay the latency is updated using [`RelayLatencies::update_relay`]. + fn merge(&mut self, other: &RelayLatencies) { for (url, latency) in other.iter() { - self.update_derp(url.clone(), latency); + self.update_relay(url.clone(), latency); } } - /// Returns the maximum latency for all derps. + /// Returns the maximum latency for all relays. /// /// If there are not yet any latencies this will return [`DEFAULT_MAX_LATENCY`]. fn max_latency(&self) -> Duration { @@ -138,8 +138,8 @@ impl DerpLatencies { .unwrap_or(DEFAULT_MAX_LATENCY) } - /// Returns an iterator over all the derps and their latencies. - pub fn iter(&self) -> impl Iterator + '_ { + /// Returns an iterator over all the relays and their latencies. + pub fn iter(&self) -> impl Iterator + '_ { self.0.iter().map(|(k, v)| (k, *v)) } @@ -151,7 +151,7 @@ impl DerpLatencies { self.0.is_empty() } - fn get(&self, url: &DerpUrl) -> Option { + fn get(&self, url: &RelayUrl) -> Option { self.0.get(url).copied() } } @@ -180,7 +180,7 @@ pub struct Client { #[derive(Debug)] struct Reports { - /// Do a full derp scan, even if last is `Some`. + /// Do a full relay scan, even if last is `Some`. next_full: bool, /// Some previous reports. prev: HashMap>, @@ -256,7 +256,7 @@ impl Client { /// may not be as reliable. pub async fn get_report( &mut self, - dm: DerpMap, + dm: RelayMap, stun_conn4: Option>, stun_conn6: Option>, ) -> Result> { @@ -270,16 +270,16 @@ impl Client { /// Get report with channel pub async fn get_report_channel( &mut self, - dm: DerpMap, + dm: RelayMap, stun_conn4: Option>, stun_conn6: Option>, ) -> Result>>> { - // TODO: consider if DerpMap should be made to easily clone? It seems expensive + // TODO: consider if RelayMap should be made to easily clone? It seems expensive // right now. let (tx, rx) = oneshot::channel(); self.addr .send(Message::RunCheck { - derp_map: dm, + relay_map: dm, stun_sock_v4: stun_conn4, stun_sock_v6: stun_conn6, response_tx: tx, @@ -307,8 +307,8 @@ pub(crate) enum Message { /// Only one netcheck can be run at a time, trying to run multiple concurrently will /// fail. RunCheck { - /// The derp configuration. - derp_map: DerpMap, + /// The relay configuration. + relay_map: RelayMap, /// Socket to send IPv4 STUN probes from. /// /// Responses are never read from this socket, they must be passed in via the @@ -444,12 +444,12 @@ impl Actor { trace!(?msg, "handling message"); match msg { Message::RunCheck { - derp_map, + relay_map, stun_sock_v4, stun_sock_v6, response_tx, } => { - self.handle_run_check(derp_map, stun_sock_v4, stun_sock_v6, response_tx); + self.handle_run_check(relay_map, stun_sock_v4, stun_sock_v6, response_tx); } Message::ReportReady { report } => { self.handle_report_ready(report); @@ -474,7 +474,7 @@ impl Actor { /// sockets you will be using. fn handle_run_check( &mut self, - derp_map: DerpMap, + relay_map: RelayMap, stun_sock_v4: Option>, stun_sock_v6: Option>, response_tx: oneshot::Sender>>, @@ -522,7 +522,7 @@ impl Actor { self.addr(), self.reports.last.clone(), self.port_mapper.clone(), - derp_map, + relay_map, stun_sock_v4, stun_sock_v6, ); @@ -614,23 +614,23 @@ impl Actor { } fn finish_and_store_report(&mut self, report: Report) -> Arc { - let report = self.add_report_history_and_set_preferred_derp(report); + let report = self.add_report_history_and_set_preferred_relay(report); debug!("{report:?}"); report } - /// Adds `r` to the set of recent Reports and mutates `r.preferred_derp` to contain the best recent one. + /// Adds `r` to the set of recent Reports and mutates `r.preferred_relay` to contain the best recent one. /// `r` is stored ref counted and a reference is returned. - fn add_report_history_and_set_preferred_derp(&mut self, mut r: Report) -> Arc { - let mut prev_derp = None; + fn add_report_history_and_set_preferred_relay(&mut self, mut r: Report) -> Arc { + let mut prev_relay = None; if let Some(ref last) = self.reports.last { - prev_derp = last.preferred_derp.clone(); + prev_relay = last.preferred_relay.clone(); } let now = Instant::now(); const MAX_AGE: Duration = Duration::from_secs(5 * 60); - // derp ID => its best recent latency in last MAX_AGE - let mut best_recent = DerpLatencies::new(); + // relay ID => its best recent latency in last MAX_AGE + let mut best_recent = RelayLatencies::new(); // chain the current report as we are still mutating it let prevs_iter = self @@ -646,39 +646,39 @@ impl Actor { to_remove.push(*t); continue; } - best_recent.merge(&pr.derp_latency); + best_recent.merge(&pr.relay_latency); } for t in to_remove { self.reports.prev.remove(&t); } - // Then, pick which currently-alive DERP server from the + // Then, pick which currently-alive relay server from the // current report has the best latency over the past MAX_AGE. let mut best_any = Duration::default(); - let mut old_derp_cur_latency = Duration::default(); + let mut old_relay_cur_latency = Duration::default(); { - for (url, duration) in r.derp_latency.iter() { - if Some(url) == prev_derp.as_ref() { - old_derp_cur_latency = duration; + for (url, duration) in r.relay_latency.iter() { + if Some(url) == prev_relay.as_ref() { + old_relay_cur_latency = duration; } if let Some(best) = best_recent.get(url) { - if r.preferred_derp.is_none() || best < best_any { + if r.preferred_relay.is_none() || best < best_any { best_any = best; - r.preferred_derp.replace(url.clone()); + r.preferred_relay.replace(url.clone()); } } } - // If we're changing our preferred DERP but the old one's still + // If we're changing our preferred relay but the old one's still // accessible and the new one's not much better, just stick with // where we are. - if prev_derp.is_some() - && r.preferred_derp != prev_derp - && !old_derp_cur_latency.is_zero() - && best_any > old_derp_cur_latency / 3 * 2 + if prev_relay.is_some() + && r.preferred_relay != prev_relay + && !old_relay_cur_latency.is_zero() + && best_any > old_relay_cur_latency / 3 * 2 { - r.preferred_derp = prev_derp; + r.preferred_relay = prev_relay; } } @@ -780,10 +780,10 @@ mod tests { use tokio::time; use tracing::info; - use crate::defaults::{DEFAULT_DERP_STUN_PORT, EU_DERP_HOSTNAME}; - use crate::derp::DerpNode; + use crate::defaults::{DEFAULT_RELAY_STUN_PORT, EU_RELAY_HOSTNAME}; use crate::net::IpFamily; use crate::ping::Pinger; + use crate::relay::RelayNode; use super::*; @@ -794,7 +794,7 @@ mod tests { stun::test::serve("0.0.0.0".parse().unwrap()).await?; let mut client = Client::new(None)?; - let dm = stun::test::derp_map_of([stun_addr].into_iter()); + let dm = stun::test::relay_map_of([stun_addr].into_iter()); // Note that the ProbePlan will change with each iteration. for i in 0..5 { @@ -803,18 +803,18 @@ mod tests { assert!(r.udp, "want UDP"); assert_eq!( - r.derp_latency.len(), + r.relay_latency.len(), 1, - "expected 1 key in DERPLatency; got {}", - r.derp_latency.len() + "expected 1 key in RelayLatency; got {}", + r.relay_latency.len() ); assert!( - r.derp_latency.iter().next().is_some(), - "expected key 1 in DERPLatency; got {:?}", - r.derp_latency + r.relay_latency.iter().next().is_some(), + "expected key 1 in RelayLatency; got {:?}", + r.relay_latency ); assert!(r.global_v4.is_some(), "expected globalV4 set"); - assert!(r.preferred_derp.is_some(),); + assert!(r.preferred_relay.is_some(),); } assert!( @@ -831,12 +831,12 @@ mod tests { let _guard = iroh_test::logging::setup(); let mut client = Client::new(None).context("failed to create netcheck client")?; - let url: DerpUrl = format!("https://{}", EU_DERP_HOSTNAME).parse().unwrap(); + let url: RelayUrl = format!("https://{}", EU_RELAY_HOSTNAME).parse().unwrap(); - let dm = DerpMap::from_nodes([DerpNode { + let dm = RelayMap::from_nodes([RelayNode { url: url.clone(), stun_only: true, - stun_port: DEFAULT_DERP_STUN_PORT, + stun_port: DEFAULT_RELAY_STUN_PORT, }]) .expect("hardcoded"); @@ -851,21 +851,21 @@ mod tests { if r.udp { assert_eq!( - r.derp_latency.len(), + r.relay_latency.len(), 1, - "expected 1 key in DERPLatency; got {}", - r.derp_latency.len() + "expected 1 key in RelayLatency; got {}", + r.relay_latency.len() ); assert!( - r.derp_latency.iter().next().is_some(), - "expected key 1 in DERPLatency; got {:?}", - r.derp_latency + r.relay_latency.iter().next().is_some(), + "expected key 1 in RelayLatency; got {:?}", + r.relay_latency ); assert!( r.global_v4.is_some() || r.global_v6.is_some(), "expected at least one of global_v4 or global_v6" ); - assert!(r.preferred_derp.is_some()); + assert!(r.preferred_relay.is_some()); } else { eprintln!("missing UDP, probe not returned by network"); } @@ -884,7 +884,7 @@ mod tests { // the STUN server being blocked will look like from the client's perspective. let blackhole = tokio::net::UdpSocket::bind("127.0.0.1:0").await?; let stun_addr = blackhole.local_addr()?; - let dm = stun::test::derp_map_of_opts([(stun_addr, false)].into_iter()); + let dm = stun::test::relay_map_of_opts([(stun_addr, false)].into_iter()); // Now create a client and generate a report. let mut client = Client::new(None)?; @@ -913,10 +913,12 @@ mod tests { captive_portal: r.captive_portal, // If we can ping we expect to have this. icmpv4: want_icmpv4, - // If we had a pinger, we'll have some latencies filled in and a preferred derp - derp_latency: can_ping.then(|| r.derp_latency.clone()).unwrap_or_default(), - preferred_derp: can_ping - .then_some(r.preferred_derp.clone()) + // If we had a pinger, we'll have some latencies filled in and a preferred relay + relay_latency: can_ping + .then(|| r.relay_latency.clone()) + .unwrap_or_default(), + preferred_relay: can_ping + .then_some(r.preferred_relay.clone()) .unwrap_or_default(), ..Default::default() }; @@ -927,21 +929,21 @@ mod tests { } #[tokio::test(flavor = "current_thread", start_paused = true)] - async fn test_add_report_history_set_preferred_derp() -> Result<()> { - fn derp_url(i: u16) -> DerpUrl { + async fn test_add_report_history_set_preferred_relay() -> Result<()> { + fn relay_url(i: u16) -> RelayUrl { format!("http://{i}.com").parse().unwrap() } - // report returns a *Report from (DERP host, Duration)+ pairs. + // report returns a *Report from (relay host, Duration)+ pairs. fn report(a: impl IntoIterator) -> Option> { let mut report = Report::default(); for (s, d) in a { - assert!(s.starts_with('d'), "invalid derp server key"); + assert!(s.starts_with('d'), "invalid relay server key"); let id: u16 = s[1..].parse().unwrap(); report - .derp_latency + .relay_latency .0 - .insert(derp_url(id), Duration::from_secs(d)); + .insert(relay_url(id), Duration::from_secs(d)); } Some(Arc::new(report)) @@ -954,8 +956,8 @@ mod tests { struct Test { name: &'static str, steps: Vec, - /// want PreferredDERP on final step - want_derp: Option, + /// want PreferredRelay on final step + want_relay: Option, // wanted len(c.prev) want_prev_len: usize, } @@ -968,7 +970,7 @@ mod tests { r: report([("d1", 2), ("d2", 3)]), }], want_prev_len: 1, - want_derp: Some(derp_url(1)), + want_relay: Some(relay_url(1)), }, Test { name: "with_two", @@ -983,7 +985,7 @@ mod tests { }, ], want_prev_len: 2, - want_derp: Some(derp_url(1)), // t0's d1 of 2 is still best + want_relay: Some(relay_url(1)), // t0's d1 of 2 is still best }, Test { name: "but_now_d1_gone", @@ -1002,7 +1004,7 @@ mod tests { }, ], want_prev_len: 3, - want_derp: Some(derp_url(2)), // only option + want_relay: Some(relay_url(2)), // only option }, Test { name: "d1_is_back", @@ -1025,7 +1027,7 @@ mod tests { }, // same as 2 seconds ago ], want_prev_len: 4, - want_derp: Some(derp_url(1)), // t0's d1 of 2 is still best + want_relay: Some(relay_url(1)), // t0's d1 of 2 is still best }, Test { name: "things_clean_up", @@ -1052,10 +1054,10 @@ mod tests { }, ], want_prev_len: 1, // t=[0123]s all gone. (too old, older than 10 min) - want_derp: Some(derp_url(3)), // only option + want_relay: Some(relay_url(3)), // only option }, Test { - name: "preferred_derp_hysteresis_no_switch", + name: "preferred_relay_hysteresis_no_switch", steps: vec![ Step { after: 0, @@ -1067,10 +1069,10 @@ mod tests { }, ], want_prev_len: 2, - want_derp: Some(derp_url(1)), // 2 didn't get fast enough + want_relay: Some(relay_url(1)), // 2 didn't get fast enough }, Test { - name: "preferred_derp_hysteresis_do_switch", + name: "preferred_relay_hysteresis_do_switch", steps: vec![ Step { after: 0, @@ -1082,7 +1084,7 @@ mod tests { }, ], want_prev_len: 2, - want_derp: Some(derp_url(2)), // 2 got fast enough + want_relay: Some(relay_url(2)), // 2 got fast enough }, ]; for mut tt in tests { @@ -1092,15 +1094,15 @@ mod tests { // trigger the timer time::advance(Duration::from_secs(s.after)).await; let r = Arc::try_unwrap(s.r.take().unwrap()).unwrap(); - s.r = Some(actor.add_report_history_and_set_preferred_derp(r)); + s.r = Some(actor.add_report_history_and_set_preferred_relay(r)); } let last_report = tt.steps.last().unwrap().r.clone().unwrap(); let got = actor.reports.prev.len(); let want = tt.want_prev_len; assert_eq!(got, want, "prev length"); - let got = &last_report.preferred_derp; - let want = &tt.want_derp; - assert_eq!(got, want, "preferred_derp"); + let got = &last_report.preferred_relay; + let want = &tt.want_relay; + assert_eq!(got, want, "preferred_relay"); } Ok(()) @@ -1116,9 +1118,9 @@ mod tests { // need to be a STUN request, but STUN already has a unique transaction ID which we // can easily use to identify the packet. - // Setup STUN server and create derpmap. + // Setup STUN server and create relay_map. let (stun_addr, _stun_stats, _done) = stun::test::serve_v4().await?; - let dm = stun::test::derp_map_of([stun_addr].into_iter()); + let dm = stun::test::relay_map_of([stun_addr].into_iter()); dbg!(&dm); let mut client = Client::new(None)?; diff --git a/iroh-net/src/netcheck/reportgen.rs b/iroh-net/src/netcheck/reportgen.rs index 79ff30d41c..5f9ae7eb92 100644 --- a/iroh-net/src/netcheck/reportgen.rs +++ b/iroh-net/src/netcheck/reportgen.rs @@ -31,14 +31,14 @@ use tokio::time::{self, Instant}; use tracing::{debug, debug_span, error, info_span, trace, warn, Instrument, Span}; use super::NetcheckMetrics; -use crate::defaults::DEFAULT_DERP_STUN_PORT; -use crate::derp::{DerpMap, DerpNode, DerpUrl}; +use crate::defaults::DEFAULT_RELAY_STUN_PORT; use crate::dns::{lookup_ipv4, lookup_ipv6}; use crate::net::interfaces; use crate::net::ip; use crate::net::UdpSocket; use crate::netcheck::{self, Report}; use crate::ping::{PingError, Pinger}; +use crate::relay::{RelayMap, RelayNode, RelayUrl}; use crate::util::{CancelOnDrop, MaybeFuture}; use crate::{portmapper, stun}; @@ -91,7 +91,7 @@ impl Client { netcheck: netcheck::Addr, last_report: Option>, port_mapper: Option, - derp_map: DerpMap, + relay_map: RelayMap, stun_sock4: Option>, stun_sock6: Option>, ) -> Self { @@ -107,7 +107,7 @@ impl Client { last_report, port_mapper, incremental, - derp_map, + relay_map, stun_sock4, stun_sock6, report: Report::default(), @@ -154,7 +154,7 @@ enum Message { // TODO: Ideally we remove the need for this message and the logic is inverted: once we // get a probe result we cancel all probes that are no longer needed. But for now it's // this way around to ease conversion. - ProbeWouldHelp(Probe, Arc, oneshot::Sender), + ProbeWouldHelp(Probe, Arc, oneshot::Sender), /// Abort all remaining probes. AbortProbes, } @@ -176,8 +176,8 @@ struct Actor { last_report: Option>, /// The portmapper client, if there is one. port_mapper: Option, - /// The DERP configuration. - derp_map: DerpMap, + /// The relay configuration. + relay_map: RelayMap, /// Socket to send IPv4 STUN requests from. stun_sock4: Option>, /// Socket so send IPv6 STUN requests from. @@ -335,8 +335,8 @@ impl Actor { self.report.hair_pinning = Some(works); self.outstanding_tasks.hairpin = false; } - Message::ProbeWouldHelp(probe, derp_node, response_tx) => { - let res = self.probe_would_help(probe, derp_node); + Message::ProbeWouldHelp(probe, relay_node, response_tx) => { + let res = self.probe_would_help(probe, relay_node); if response_tx.send(res).is_err() { debug!("probe dropped before ProbeWouldHelp response sent"); } @@ -359,20 +359,20 @@ impl Actor { } } - // Once we've heard from enough derpers (3), start a timer to give up on the other + // Once we've heard from enough relay servers (3), start a timer to give up on the other // probes. The timer's duration is a function of whether this is our initial full // probe or an incremental one. For incremental ones, wait for the duration of the - // slowest derp. For initial ones, double that. - let enough_derpers = std::cmp::min(self.derp_map.len(), ENOUGH_NODES); - if self.report.derp_latency.len() == enough_derpers { - let timeout = self.report.derp_latency.max_latency(); + // slowest relay. For initial ones, double that. + let enough_relays = std::cmp::min(self.relay_map.len(), ENOUGH_NODES); + if self.report.relay_latency.len() == enough_relays { + let timeout = self.report.relay_latency.max_latency(); let timeout = match self.incremental { true => timeout, false => timeout * 2, }; let reportcheck = self.addr(); debug!( - reports=self.report.derp_latency.len(), + reports=self.report.relay_latency.len(), delay=?timeout, "Have enough probe reports, aborting further probes soon", ); @@ -393,14 +393,14 @@ impl Actor { } /// Whether running this probe would still improve our report. - fn probe_would_help(&mut self, probe: Probe, derp_node: Arc) -> bool { - // If the probe is for a derp we don't yet know about, that would help. - if self.report.derp_latency.get(&derp_node.url).is_none() { + fn probe_would_help(&mut self, probe: Probe, relay_node: Arc) -> bool { + // If the probe is for a relay we don't yet know about, that would help. + if self.report.relay_latency.get(&relay_node.url).is_none() { return true; } // If the probe is for IPv6 and we don't yet have an IPv6 report, that would help. - if probe.proto() == ProbeProto::StunIpv6 && self.report.derp_v6_latency.is_empty() { + if probe.proto() == ProbeProto::StunIpv6 && self.report.relay_v6_latency.is_empty() { return true; } @@ -468,13 +468,13 @@ impl Actor { // it's unnecessary. if !self.incremental { // Even if we're doing a non-incremental update, we may want to try our - // preferred DERP derp for captive portal detection. - let preferred_derp = self + // preferred relay for captive portal detection. + let preferred_relay = self .last_report .as_ref() - .and_then(|l| l.preferred_derp.clone()); + .and_then(|l| l.preferred_relay.clone()); - let dm = self.derp_map.clone(); + let dm = self.relay_map.clone(); self.outstanding_tasks.captive_task = true; MaybeFuture { inner: Some(Box::pin(async move { @@ -482,7 +482,7 @@ impl Actor { debug!("Captive portal check started after {CAPTIVE_PORTAL_DELAY:?}"); let captive_portal_check = tokio::time::timeout( CAPTIVE_PORTAL_TIMEOUT, - check_captive_portal(&dm, preferred_derp) + check_captive_portal(&dm, preferred_relay) .instrument(debug_span!("captive-portal")), ); match captive_portal_check.await { @@ -533,8 +533,8 @@ impl Actor { let if_state = interfaces::State::new().await; debug!(%if_state, "Local interfaces"); let plan = match self.last_report { - Some(ref report) => ProbePlan::with_last_report(&self.derp_map, &if_state, report), - None => ProbePlan::initial(&self.derp_map, &if_state), + Some(ref report) => ProbePlan::with_last_report(&self.relay_map, &if_state, report), + None => ProbePlan::initial(&self.relay_map, &if_state), }; trace!(%plan, "probe plan"); @@ -551,7 +551,7 @@ impl Actor { let reportstate = self.addr(); let stun_sock4 = self.stun_sock4.clone(); let stun_sock6 = self.stun_sock6.clone(); - let derp_node = probe.node().clone(); + let relay_node = probe.node().clone(); let probe = probe.clone(); let netcheck = self.netcheck.clone(); let pinger = pinger.clone(); @@ -561,7 +561,7 @@ impl Actor { reportstate, stun_sock4, stun_sock6, - derp_node, + relay_node, probe.clone(), netcheck, pinger, @@ -633,7 +633,7 @@ struct ProbeReport { icmpv4: Option, /// Whether we can send ICMPv6 packets, `None` if not checked. icmpv6: Option, - /// The latency to the derp node. + /// The latency to the relay node. latency: Option, /// The probe that generated this report. probe: Probe, @@ -678,7 +678,7 @@ async fn run_probe( reportstate: Addr, stun_sock4: Option>, stun_sock6: Option>, - derp_node: Arc, + relay_node: Arc, probe: Probe, netcheck: netcheck::Addr, pinger: Pinger, @@ -693,7 +693,7 @@ async fn run_probe( if let Err(err) = reportstate .send(Message::ProbeWouldHelp( probe.clone(), - derp_node.clone(), + relay_node.clone(), would_help_tx, )) .await @@ -715,9 +715,9 @@ async fn run_probe( )); } - let derp_addr = get_derp_addr(&derp_node, probe.proto()) + let relay_addr = get_relay_addr(&relay_node, probe.proto()) .await - .context("no derp node addr") + .context("no relay node addr") .map_err(|e| ProbeError::AbortSet(e, probe.clone()))?; let mut result = ProbeReport::new(probe.clone()); @@ -730,7 +730,7 @@ async fn run_probe( }; match maybe_sock { Some(sock) => { - result = run_stun_probe(sock, derp_addr, netcheck, probe).await?; + result = run_stun_probe(sock, relay_addr, netcheck, probe).await?; } None => { return Err(ProbeError::AbortSet( @@ -741,7 +741,7 @@ async fn run_probe( } } Probe::IcmpV4 { .. } | Probe::IcmpV6 { .. } => { - result = run_icmp_probe(probe, derp_addr, pinger).await? + result = run_icmp_probe(probe, relay_addr, pinger).await? } Probe::Https { ref node, .. } => { debug!("sending probe HTTPS"); @@ -772,13 +772,13 @@ async fn run_probe( /// Run a STUN IPv4 or IPv6 probe. async fn run_stun_probe( sock: &Arc, - derp_addr: SocketAddr, + relay_addr: SocketAddr, netcheck: netcheck::Addr, probe: Probe, ) -> Result { match probe.proto() { - ProbeProto::StunIpv4 => debug_assert!(derp_addr.is_ipv4()), - ProbeProto::StunIpv6 => debug_assert!(derp_addr.is_ipv6()), + ProbeProto::StunIpv4 => debug_assert!(relay_addr.is_ipv4()), + ProbeProto::StunIpv6 => debug_assert!(relay_addr.is_ipv6()), _ => debug_assert!(false, "wrong probe"), } let txid = stun::TransactionId::default(); @@ -803,9 +803,9 @@ async fn run_stun_probe( .map_err(|e| ProbeError::Error(e.into(), probe.clone()))?; // Send the probe. - match sock.send_to(&req, derp_addr).await { + match sock.send_to(&req, relay_addr).await { Ok(n) if n == req.len() => { - debug!(%derp_addr, %txid, "sending {} probe", probe.proto()); + debug!(%relay_addr, %txid, "sending {} probe", probe.proto()); let mut result = ProbeReport::new(probe.clone()); if matches!(probe, Probe::StunIpv4 { .. }) { @@ -824,7 +824,7 @@ async fn run_stun_probe( } Ok(n) => { let err = anyhow!("Failed to send full STUN request: {}", probe.proto()); - error!(%derp_addr, sent_len=n, req_len=req.len(), "{err:#}"); + error!(%relay_addr, sent_len=n, req_len=req.len(), "{err:#}"); Err(ProbeError::Error(err, probe.clone())) } Err(err) => { @@ -838,7 +838,7 @@ async fn run_stun_probe( // but it is already emitted. So hack around this. match format!("{kind:?}").as_str() { "NetworkUnreachable" => { - debug!(%derp_addr, "{err:#}"); + debug!(%relay_addr, "{err:#}"); Err(ProbeError::AbortSet(err, probe.clone())) } _ => { @@ -855,15 +855,15 @@ async fn run_stun_probe( /// return a "204 No Content" response and checking if that's what we get. /// /// The boolean return is whether we think we have a captive portal. -async fn check_captive_portal(dm: &DerpMap, preferred_derp: Option) -> Result { - // If we have a preferred DERP node and we can use it for non-STUN requests, try that; +async fn check_captive_portal(dm: &RelayMap, preferred_relay: Option) -> Result { + // If we have a preferred relay node and we can use it for non-STUN requests, try that; // otherwise, pick a random one suitable for non-STUN requests. - let preferred_derp = preferred_derp.and_then(|url| match dm.get_node(&url) { + let preferred_relay = preferred_relay.and_then(|url| match dm.get_node(&url) { Some(node) if node.stun_only => Some(url), _ => None, }); - let url = match preferred_derp { + let url = match preferred_relay { Some(url) => url, None => { let urls: Vec<_> = dm @@ -872,7 +872,7 @@ async fn check_captive_portal(dm: &DerpMap, preferred_derp: Option) -> .map(|n| n.url.clone()) .collect(); if urls.is_empty() { - debug!("No suitable Derp node for captive portal check"); + debug!("No suitable relay node for captive portal check"); return Ok(false); } @@ -888,7 +888,7 @@ async fn check_captive_portal(dm: &DerpMap, preferred_derp: Option) -> .build()?; // Note: the set of valid characters in a challenge and the total - // length is limited; see is_challenge_char in bin/derper for more + // length is limited; see is_challenge_char in bin/iroh-relay for more // details. let host_name = url.host_str().unwrap_or_default(); @@ -918,55 +918,55 @@ async fn check_captive_portal(dm: &DerpMap, preferred_derp: Option) -> Ok(has_captive) } -/// Returns the IP address to use to communicate to this derp node. +/// Returns the IP address to use to communicate to this relay node. /// /// *proto* specifies the protocol of the probe. Depending on the protocol we may return -/// different results. Obviously IPv4 vs IPv6 but a [`DerpNode`] may also have disabled +/// different results. Obviously IPv4 vs IPv6 but a [`RelayNode`] may also have disabled /// some protocols. -async fn get_derp_addr(derp_node: &DerpNode, proto: ProbeProto) -> Result { - let port = if derp_node.stun_port == 0 { - DEFAULT_DERP_STUN_PORT +async fn get_relay_addr(relay_node: &RelayNode, proto: ProbeProto) -> Result { + let port = if relay_node.stun_port == 0 { + DEFAULT_RELAY_STUN_PORT } else { - derp_node.stun_port + relay_node.stun_port }; - if derp_node.stun_only && !matches!(proto, ProbeProto::StunIpv4 | ProbeProto::StunIpv6) { - bail!("Derp node not suitable for non-STUN probes"); + if relay_node.stun_only && !matches!(proto, ProbeProto::StunIpv4 | ProbeProto::StunIpv6) { + bail!("Relay node not suitable for non-STUN probes"); } match proto { - ProbeProto::StunIpv4 | ProbeProto::IcmpV4 => match derp_node.url.host() { + ProbeProto::StunIpv4 | ProbeProto::IcmpV4 => match relay_node.url.host() { Some(url::Host::Domain(hostname)) => { - debug!(?proto, %hostname, "Performing DNS A lookup for derp addr"); + debug!(?proto, %hostname, "Performing DNS A lookup for relay addr"); match lookup_ipv4(hostname, DNS_TIMEOUT).await { Ok(addrs) => addrs .first() .map(|addr| ip::to_canonical(*addr)) .map(|addr| SocketAddr::new(addr, port)) - .ok_or(anyhow!("No suitable derp addr found")), - Err(err) => Err(err.context("No suitable derp addr found")), + .ok_or(anyhow!("No suitable relay addr found")), + Err(err) => Err(err.context("No suitable relay addr found")), } } Some(url::Host::Ipv4(addr)) => Ok(SocketAddr::new(addr.into(), port)), - Some(url::Host::Ipv6(_addr)) => Err(anyhow!("No suitable derp addr found")), - None => Err(anyhow!("No valid hostname in DerpUrl")), + Some(url::Host::Ipv6(_addr)) => Err(anyhow!("No suitable relay addr found")), + None => Err(anyhow!("No valid hostname in RelayUrl")), }, - ProbeProto::StunIpv6 | ProbeProto::IcmpV6 => match derp_node.url.host() { + ProbeProto::StunIpv6 | ProbeProto::IcmpV6 => match relay_node.url.host() { Some(url::Host::Domain(hostname)) => { - debug!(?proto, %hostname, "Performing DNS AAAA lookup for derp addr"); + debug!(?proto, %hostname, "Performing DNS AAAA lookup for relay addr"); match lookup_ipv6(hostname, DNS_TIMEOUT).await { Ok(addrs) => addrs .first() .map(|addr| ip::to_canonical(*addr)) .map(|addr| SocketAddr::new(addr, port)) - .ok_or(anyhow!("No suitable derp addr found")), - Err(err) => Err(err.context("No suitable derp addr found")), + .ok_or(anyhow!("No suitable relay addr found")), + Err(err) => Err(err.context("No suitable relay addr found")), } } - Some(url::Host::Ipv4(_addr)) => Err(anyhow!("No suitable derp addr found")), + Some(url::Host::Ipv4(_addr)) => Err(anyhow!("No suitable relay addr found")), Some(url::Host::Ipv6(addr)) => Ok(SocketAddr::new(addr.into(), port)), - None => Err(anyhow!("No valid hostname in DerpUrl")), + None => Err(anyhow!("No valid hostname in RelayUrl")), }, ProbeProto::Https => Err(anyhow!("Not implemented")), @@ -979,18 +979,18 @@ async fn get_derp_addr(derp_node: &DerpNode, proto: ProbeProto) -> Result Result { match probe.proto() { - ProbeProto::IcmpV4 => debug_assert!(derp_addr.is_ipv4()), - ProbeProto::IcmpV6 => debug_assert!(derp_addr.is_ipv6()), + ProbeProto::IcmpV4 => debug_assert!(relay_addr.is_ipv4()), + ProbeProto::IcmpV6 => debug_assert!(relay_addr.is_ipv6()), _ => debug_assert!(false, "wrong probe"), } const DATA: &[u8; 15] = b"iroh icmp probe"; - debug!(dst = %derp_addr, len = DATA.len(), "ICMP Ping started"); + debug!(dst = %relay_addr, len = DATA.len(), "ICMP Ping started"); let latency = pinger - .send(derp_addr.ip(), DATA) + .send(relay_addr.ip(), DATA) .await .map_err(|err| match err { PingError::Client(err) => ProbeError::AbortSet( @@ -999,10 +999,10 @@ async fn run_icmp_probe( ), PingError::Ping(err) => ProbeError::Error(err.into(), probe.clone()), })?; - debug!(dst = %derp_addr, len = DATA.len(), ?latency, "ICMP ping done"); + debug!(dst = %relay_addr, len = DATA.len(), ?latency, "ICMP ping done"); let mut report = ProbeReport::new(probe); report.latency = Some(latency); - match derp_addr { + match relay_addr { SocketAddr::V4(_) => { report.ipv4_can_send = true; report.icmpv4 = Some(true); @@ -1016,21 +1016,21 @@ async fn run_icmp_probe( } #[allow(clippy::unused_async)] -async fn measure_https_latency(_node: &DerpNode) -> Result<(Duration, IpAddr)> { +async fn measure_https_latency(_node: &RelayNode) -> Result<(Duration, IpAddr)> { bail!("not implemented"); // TODO: - // - needs derphttp::Client + // - needs relayhttp::Client // - measurement hooks to measure server processing time // metricHTTPSend.Add(1) // let ctx, cancel := context.WithTimeout(httpstat.WithHTTPStat(ctx, &result), overallProbeTimeout); - // let dc := derphttp.NewNetcheckClient(c.logf); + // let dc := relayhttp.NewNetcheckClient(c.logf); // let tlsConn, tcpConn, node := dc.DialRegionTLS(ctx, reg)?; // if ta, ok := tlsConn.RemoteAddr().(*net.TCPAddr); - // req, err := http.NewRequestWithContext(ctx, "GET", "https://"+node.HostName+"/derp/latency-check", nil); + // req, err := http.NewRequestWithContext(ctx, "GET", "https://"+node.HostName+"/relay/latency-check", nil); // resp, err := hc.Do(req); - // // DERPs should give us a nominal status code, so anything else is probably + // // relays should give us a nominal status code, so anything else is probably // // an access denied by a MITM proxy (or at the very least a signal not to // // trust this latency check). // if resp.StatusCode > 299 { @@ -1046,11 +1046,11 @@ async fn measure_https_latency(_node: &DerpNode) -> Result<(Duration, IpAddr)> { /// Updates a netcheck [`Report`] with a new [`ProbeReport`]. fn update_report(report: &mut Report, probe_report: ProbeReport) { - let derp_node = probe_report.probe.node(); + let relay_node = probe_report.probe.node(); if let Some(latency) = probe_report.latency { report - .derp_latency - .update_derp(derp_node.url.clone(), latency); + .relay_latency + .update_relay(relay_node.url.clone(), latency); if matches!( probe_report.probe.proto(), @@ -1062,8 +1062,8 @@ fn update_report(report: &mut Report, probe_report: ProbeReport) { Some(SocketAddr::V4(ipp)) => { report.ipv4 = true; report - .derp_v4_latency - .update_derp(derp_node.url.clone(), latency); + .relay_v4_latency + .update_relay(relay_node.url.clone(), latency); if report.global_v4.is_none() { report.global_v4 = Some(ipp); } else if report.global_v4 != Some(ipp) { @@ -1075,8 +1075,8 @@ fn update_report(report: &mut Report, probe_report: ProbeReport) { Some(SocketAddr::V6(ipp)) => { report.ipv6 = true; report - .derp_v6_latency - .update_derp(derp_node.url.clone(), latency); + .relay_v6_latency + .update_relay(relay_node.url.clone(), latency); if report.global_v6.is_none() { report.global_v6 = Some(ipp); } else if report.global_v6 != Some(ipp) { @@ -1087,7 +1087,7 @@ fn update_report(report: &mut Report, probe_report: ProbeReport) { } } None => { - // If we are here we had a derper latency reported from a STUN probe. + // If we are here we had a relay server latency reported from a STUN probe. // Thus we must have a reported address. debug_assert!(probe_report.addr.is_some()); } @@ -1112,16 +1112,16 @@ mod tests { use super::*; - use crate::defaults::{default_eu_derp_node, default_na_derp_node}; + use crate::defaults::{default_eu_relay_node, default_na_relay_node}; #[test] fn test_update_report_stun_working() { - let eu_derper = Arc::new(default_eu_derp_node()); - let na_derper = Arc::new(default_na_derp_node()); + let eu_relayer = Arc::new(default_eu_relay_node()); + let na_relayer = Arc::new(default_na_relay_node()); let mut report = Report::default(); - // A STUN IPv4 probe from the EU derper. + // A STUN IPv4 probe from the EU relay server. let probe_report_eu = ProbeReport { ipv4_can_send: true, ipv6_can_send: false, @@ -1130,7 +1130,7 @@ mod tests { latency: Some(Duration::from_millis(5)), probe: Probe::StunIpv4 { delay: Duration::ZERO, - node: eu_derper.clone(), + node: eu_relayer.clone(), }, addr: Some((Ipv4Addr::new(203, 0, 113, 1), 1234).into()), }; @@ -1138,11 +1138,11 @@ mod tests { assert!(report.udp); assert_eq!( - report.derp_latency.get(&eu_derper.url).unwrap(), + report.relay_latency.get(&eu_relayer.url).unwrap(), Duration::from_millis(5) ); assert_eq!( - report.derp_v4_latency.get(&eu_derper.url).unwrap(), + report.relay_v4_latency.get(&eu_relayer.url).unwrap(), Duration::from_millis(5) ); assert!(report.ipv4_can_send); @@ -1153,7 +1153,7 @@ mod tests { latency: Some(Duration::from_millis(8)), probe: Probe::StunIpv4 { delay: Duration::ZERO, - node: na_derper.clone(), + node: na_relayer.clone(), }, ..probe_report_eu }; @@ -1161,11 +1161,11 @@ mod tests { assert!(report.udp); assert_eq!( - report.derp_latency.get(&eu_derper.url).unwrap(), + report.relay_latency.get(&eu_relayer.url).unwrap(), Duration::from_millis(5) ); assert_eq!( - report.derp_v4_latency.get(&eu_derper.url).unwrap(), + report.relay_v4_latency.get(&eu_relayer.url).unwrap(), Duration::from_millis(5) ); assert!(report.ipv4_can_send); @@ -1180,7 +1180,7 @@ mod tests { latency: Some(Duration::from_millis(4)), probe: Probe::StunIpv6 { delay: Duration::ZERO, - node: eu_derper.clone(), + node: eu_relayer.clone(), }, addr: Some((Ipv6Addr::new(2001, 0xdb8, 0, 0, 0, 0, 0, 1), 1234).into()), }; @@ -1188,11 +1188,11 @@ mod tests { assert!(report.udp); assert_eq!( - report.derp_latency.get(&eu_derper.url).unwrap(), + report.relay_latency.get(&eu_relayer.url).unwrap(), Duration::from_millis(4) ); assert_eq!( - report.derp_v6_latency.get(&eu_derper.url).unwrap(), + report.relay_v6_latency.get(&eu_relayer.url).unwrap(), Duration::from_millis(4) ); assert!(report.ipv4_can_send); @@ -1201,12 +1201,12 @@ mod tests { #[test] fn test_update_report_icmp() { - let eu_derper = Arc::new(default_eu_derp_node()); - let na_derper = Arc::new(default_na_derp_node()); + let eu_relayer = Arc::new(default_eu_relay_node()); + let na_relayer = Arc::new(default_na_relay_node()); let mut report = Report::default(); - // An ICMPv4 probe from the EU derper. + // An ICMPv4 probe from the EU relay server. let probe_report_eu = ProbeReport { ipv4_can_send: true, ipv6_can_send: false, @@ -1215,7 +1215,7 @@ mod tests { latency: Some(Duration::from_millis(5)), probe: Probe::IcmpV4 { delay: Duration::ZERO, - node: eu_derper.clone(), + node: eu_relayer.clone(), }, addr: Some((Ipv4Addr::new(203, 0, 113, 1), 1234).into()), }; @@ -1234,7 +1234,7 @@ mod tests { latency: None, probe: Probe::IcmpV4 { delay: Duration::ZERO, - node: na_derper.clone(), + node: na_relayer.clone(), }, addr: None, }; @@ -1251,7 +1251,7 @@ mod tests { latency: Some(Duration::from_millis(5)), probe: Probe::StunIpv4 { delay: Duration::ZERO, - node: eu_derper.clone(), + node: eu_relayer.clone(), }, addr: Some((Ipv4Addr::new(203, 0, 113, 1), 1234).into()), }; @@ -1310,17 +1310,17 @@ mod tests { // TODO: Not sure what about IPv6 pings using sysctl. #[cfg_attr(target_os = "windows", ignore = "flaky")] #[tokio::test] - async fn test_icmpk_probe_eu_derper() { + async fn test_icmpk_probe_eu_relayer() { let _logging_guard = iroh_test::logging::setup(); let pinger = Pinger::new(); - let derper = default_eu_derp_node(); - let addr = get_derp_addr(&derper, ProbeProto::IcmpV4) + let relay = default_eu_relay_node(); + let addr = get_relay_addr(&relay, ProbeProto::IcmpV4) .await .map_err(|err| format!("{err:#}")) .unwrap(); let probe = Probe::IcmpV4 { delay: Duration::from_secs(0), - node: Arc::new(derper), + node: Arc::new(relay), }; // A singe ICMP packet might get lost. Try several and take the first. diff --git a/iroh-net/src/netcheck/reportgen/probes.rs b/iroh-net/src/netcheck/reportgen/probes.rs index 03a7f397f8..130ccd8fe7 100644 --- a/iroh-net/src/netcheck/reportgen/probes.rs +++ b/iroh-net/src/netcheck/reportgen/probes.rs @@ -1,6 +1,6 @@ -//! The DERP probes. +//! The relay probes. //! -//! All the probes try and establish the latency to the DERP servers. Preferably the STUN +//! All the probes try and establish the latency to the relay servers. Preferably the STUN //! probes work and we also learn about our public IP addresses and ports. But fallback //! probes for HTTPS and ICMP exist as well. @@ -11,9 +11,9 @@ use std::sync::Arc; use anyhow::{ensure, Result}; use tokio::time::Duration; -use crate::derp::{DerpMap, DerpNode, DerpUrl}; use crate::net::interfaces; use crate::netcheck::Report; +use crate::relay::{RelayMap, RelayNode, RelayUrl}; /// The retransmit interval used when netcheck first runs. /// @@ -25,10 +25,10 @@ const DEFAULT_INITIAL_RETRANSMIT: Duration = Duration::from_millis(100); /// The retransmit interval used when a previous report exists but is missing latency. /// /// When in an active steady-state, i.e. a previous report exists, we use the latency of the -/// previous report to determine the retransmit interval. However when this previous derp +/// previous report to determine the retransmit interval. However when this previous relay /// latency is missing this default is used. /// -/// This is a somewhat conservative guess because if we have no data, likely the DERP node +/// This is a somewhat conservative guess because if we have no data, likely the relay node /// is very far away and we have no data because we timed out the last time we probed it. const DEFAULT_ACTIVE_RETRANSMIT_DELAY: Duration = Duration::from_millis(200); @@ -39,9 +39,9 @@ const DEFAULT_ACTIVE_RETRANSMIT_DELAY: Duration = Duration::from_millis(200); /// time. const ACTIVE_RETRANSMIT_EXTRA_DELAY: Duration = Duration::from_millis(50); -/// The number of fastest derpers to periodically re-query during incremental netcheck -/// reports. (During a full report, all derpers are scanned.) -const NUM_INCREMENTAL_DERPERS: usize = 3; +/// The number of fastest relays to periodically re-query during incremental netcheck +/// reports. (During a full report, all relay servers are scanned.) +const NUM_INCREMENTAL_RELAYS: usize = 3; /// The protocol used to time a node's latency. #[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, derive_more::Display)] @@ -68,28 +68,28 @@ pub(super) enum Probe { /// are for retries on UDP loss or timeout. delay: Duration, - /// The DERP server to send this probe to. - node: Arc, + /// The relay server to send this probe to. + node: Arc, }, #[display("STUN Ipv6 after {delay:?} to {node}")] StunIpv6 { delay: Duration, - node: Arc, + node: Arc, }, #[display("HTTPS after {delay:?} to {node}")] Https { delay: Duration, - node: Arc, + node: Arc, }, #[display("ICMPv4 after {delay:?} to {node}")] IcmpV4 { delay: Duration, - node: Arc, + node: Arc, }, #[display("ICMPv6 after {delay:?} to {node}")] IcmpV6 { delay: Duration, - node: Arc, + node: Arc, }, } @@ -114,7 +114,7 @@ impl Probe { } } - pub(super) fn node(&self) -> &Arc { + pub(super) fn node(&self) -> &Arc { match self { Probe::StunIpv4 { node, .. } | Probe::StunIpv6 { node, .. } @@ -127,7 +127,7 @@ impl Probe { /// A probe set is a sequence of similar [`Probe`]s with delays between them. /// -/// The probes are to the same Derper and of the same [`ProbeProto`] but will have different +/// The probes are to the same Relayer and of the same [`ProbeProto`] but will have different /// delays. The delays are effectively retries, though they do not wait for the previous /// probe to be finished. The first successful probe will cancel all other probes in the /// set. @@ -199,10 +199,10 @@ pub(super) struct ProbePlan(BTreeSet); impl ProbePlan { /// Creates an initial probe plan. - pub(super) fn initial(derp_map: &DerpMap, if_state: &interfaces::State) -> Self { + pub(super) fn initial(relay_map: &RelayMap, if_state: &interfaces::State) -> Self { let mut plan = Self(BTreeSet::new()); - for derp_node in derp_map.nodes() { + for relay_node in relay_map.nodes() { let mut stun_ipv4_probes = ProbeSet::new(ProbeProto::StunIpv4); let mut stun_ipv6_probes = ProbeSet::new(ProbeProto::StunIpv6); @@ -213,7 +213,7 @@ impl ProbePlan { stun_ipv4_probes .push(Probe::StunIpv4 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("adding StunIpv4 probe to a StunIpv4 probe set"); } @@ -221,7 +221,7 @@ impl ProbePlan { stun_ipv6_probes .push(Probe::StunIpv6 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("adding StunIpv6 probe to a StunIpv6 probe set"); } @@ -240,14 +240,14 @@ impl ProbePlan { https_probes .push(Probe::Https { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("adding Https probe to a Https probe set"); if if_state.have_v4 { icmp_probes_ipv4 .push(Probe::IcmpV4 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("adding Icmp probe to an Icmp probe set"); } @@ -255,7 +255,7 @@ impl ProbePlan { icmp_probes_ipv6 .push(Probe::IcmpV6 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("adding IcmpIpv6 probe to and IcmpIpv6 probe set"); } @@ -269,21 +269,21 @@ impl ProbePlan { /// Creates a follow up probe plan using a previous netcheck report. pub(super) fn with_last_report( - derp_map: &DerpMap, + relay_map: &RelayMap, if_state: &interfaces::State, last_report: &Report, ) -> Self { - if last_report.derp_latency.is_empty() { - return Self::initial(derp_map, if_state); + if last_report.relay_latency.is_empty() { + return Self::initial(relay_map, if_state); } let mut plan = Self(Default::default()); - let had_stun_ipv4 = !last_report.derp_v4_latency.is_empty(); - let had_stun_ipv6 = !last_report.derp_v6_latency.is_empty(); + let had_stun_ipv4 = !last_report.relay_v4_latency.is_empty(); + let had_stun_ipv6 = !last_report.relay_v6_latency.is_empty(); let had_both = if_state.have_v6 && had_stun_ipv4 && had_stun_ipv6; - let sorted_derps = sort_derps(derp_map, last_report); - for (ri, (url, derp_node)) in sorted_derps.into_iter().enumerate() { - if ri == NUM_INCREMENTAL_DERPERS { + let sorted_relays = sort_relays(relay_map, last_report); + for (ri, (url, relay_node)) in sorted_relays.into_iter().enumerate() { + if ri == NUM_INCREMENTAL_RELAYS { break; } let mut do4 = if_state.have_v4; @@ -308,13 +308,13 @@ impl ProbePlan { if !is_fastest_two && !had_stun_ipv6 { do6 = false; } - if Some(url) == last_report.preferred_derp.as_ref() { - // But if we already had a DERP home, try extra hard to + if Some(url) == last_report.preferred_relay.as_ref() { + // But if we already had a relay home, try extra hard to // make sure it's there so we don't flip flop around. attempts = 4; } let retransmit_delay = last_report - .derp_latency + .relay_latency .get(url) .map(|l| l * 120 / 100) // increases latency by 20%, why? .unwrap_or(DEFAULT_ACTIVE_RETRANSMIT_DELAY); @@ -329,7 +329,7 @@ impl ProbePlan { stun_ipv4_probes .push(Probe::StunIpv4 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("Pushing StunIpv4 Probe to StunIpv4 ProbeSet"); } @@ -337,7 +337,7 @@ impl ProbePlan { stun_ipv6_probes .push(Probe::StunIpv6 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("Pushing StunIpv6 Probe to StunIpv6 ProbeSet"); } @@ -357,14 +357,14 @@ impl ProbePlan { https_probes .push(Probe::Https { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("Pushing Https Probe to an Https ProbeSet"); if do4 { icmp_v4_probes .push(Probe::IcmpV4 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("Pushing IcmpV4 Probe to an Icmp ProbeSet"); } @@ -372,7 +372,7 @@ impl ProbePlan { icmp_v6_probes .push(Probe::IcmpV6 { delay, - node: derp_node.clone(), + node: relay_node.clone(), }) .expect("Pusying IcmpV6 Probe to an IcmpV6 ProbeSet"); } @@ -427,18 +427,18 @@ impl FromIterator for ProbePlan { } } -/// Sorts the nodes in the [`DerpMap`] from fastest to slowest. +/// Sorts the nodes in the [`RelayMap`] from fastest to slowest. /// -/// This uses the latencies from the last report to determine the order. Derp Nodes with no +/// This uses the latencies from the last report to determine the order. Relay Nodes with no /// data are at the end. -fn sort_derps<'a>( - derp_map: &'a DerpMap, +fn sort_relays<'a>( + relay_map: &'a RelayMap, last_report: &Report, -) -> Vec<(&'a DerpUrl, &'a Arc)> { - let mut prev: Vec<_> = derp_map.nodes().collect(); +) -> Vec<(&'a RelayUrl, &'a Arc)> { + let mut prev: Vec<_> = relay_map.nodes().collect(); prev.sort_by(|a, b| { - let latencies_a = last_report.derp_latency.get(&a.url); - let latencies_b = last_report.derp_latency.get(&b.url); + let latencies_a = last_report.relay_latency.get(&a.url); + let latencies_b = last_report.relay_latency.get(&b.url); match (latencies_a, latencies_b) { (Some(_), None) => { // Non-zero sorts before zero. @@ -449,7 +449,7 @@ fn sort_derps<'a>( std::cmp::Ordering::Greater } (None, None) => { - // For both empty latencies sort by derp_id. + // For both empty latencies sort by relay_id. a.url.cmp(&b.url) } (Some(_), Some(_)) => match latencies_a.cmp(&latencies_b) { @@ -466,19 +466,19 @@ fn sort_derps<'a>( mod tests { use pretty_assertions::assert_eq; - use crate::defaults::default_derp_map; + use crate::defaults::default_relay_map; use crate::net::interfaces; - use crate::netcheck::DerpLatencies; + use crate::netcheck::RelayLatencies; use super::*; #[tokio::test] async fn test_initial_probeplan() { - let derp_map = default_derp_map(); - let derp_node_1 = derp_map.nodes().next().unwrap(); - let derp_node_2 = derp_map.nodes().nth(1).unwrap(); + let relay_map = default_relay_map(); + let relay_node_1 = relay_map.nodes().next().unwrap(); + let relay_node_2 = relay_map.nodes().nth(1).unwrap(); let if_state = interfaces::State::fake(); - let plan = ProbePlan::initial(&derp_map, &if_state); + let plan = ProbePlan::initial(&relay_map, &if_state); let expected_plan: ProbePlan = [ ProbeSet { @@ -486,15 +486,15 @@ mod tests { probes: vec![ Probe::StunIpv4 { delay: Duration::ZERO, - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv4 { delay: Duration::from_millis(100), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv4 { delay: Duration::from_millis(200), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -503,15 +503,15 @@ mod tests { probes: vec![ Probe::StunIpv6 { delay: Duration::ZERO, - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv6 { delay: Duration::from_millis(100), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv6 { delay: Duration::from_millis(200), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -520,15 +520,15 @@ mod tests { probes: vec![ Probe::Https { delay: Duration::from_millis(300), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::Https { delay: Duration::from_millis(400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::Https { delay: Duration::from_millis(500), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -537,15 +537,15 @@ mod tests { probes: vec![ Probe::IcmpV4 { delay: Duration::from_millis(300), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV4 { delay: Duration::from_millis(400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV4 { delay: Duration::from_millis(500), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -554,15 +554,15 @@ mod tests { probes: vec![ Probe::IcmpV6 { delay: Duration::from_millis(300), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV6 { delay: Duration::from_millis(400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV6 { delay: Duration::from_millis(500), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -571,15 +571,15 @@ mod tests { probes: vec![ Probe::StunIpv4 { delay: Duration::ZERO, - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv4 { delay: Duration::from_millis(100), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv4 { delay: Duration::from_millis(200), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -588,15 +588,15 @@ mod tests { probes: vec![ Probe::StunIpv6 { delay: Duration::ZERO, - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv6 { delay: Duration::from_millis(100), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv6 { delay: Duration::from_millis(200), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -605,15 +605,15 @@ mod tests { probes: vec![ Probe::Https { delay: Duration::from_millis(600), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::Https { delay: Duration::from_millis(700), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::Https { delay: Duration::from_millis(800), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -622,15 +622,15 @@ mod tests { probes: vec![ Probe::IcmpV4 { delay: Duration::from_millis(600), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::IcmpV4 { delay: Duration::from_millis(700), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::IcmpV4 { delay: Duration::from_millis(800), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -639,15 +639,15 @@ mod tests { probes: vec![ Probe::StunIpv4 { delay: Duration::ZERO, - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv4 { delay: Duration::from_millis(100), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv4 { delay: Duration::from_millis(200), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -656,15 +656,15 @@ mod tests { probes: vec![ Probe::IcmpV6 { delay: Duration::from_millis(600), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::IcmpV6 { delay: Duration::from_millis(700), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::IcmpV6 { delay: Duration::from_millis(800), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -686,13 +686,13 @@ mod tests { async fn test_plan_with_report() { for i in 0..10 { println!("round {}", i); - let derp_map = default_derp_map(); - let derp_node_1 = derp_map.nodes().next().unwrap().clone(); - let derp_node_2 = derp_map.nodes().nth(1).unwrap().clone(); + let relay_map = default_relay_map(); + let relay_node_1 = relay_map.nodes().next().unwrap().clone(); + let relay_node_2 = relay_map.nodes().nth(1).unwrap().clone(); let if_state = interfaces::State::fake(); - let mut latencies = DerpLatencies::new(); - latencies.update_derp(derp_node_1.url.clone(), Duration::from_millis(2)); - latencies.update_derp(derp_node_2.url.clone(), Duration::from_millis(2)); + let mut latencies = RelayLatencies::new(); + latencies.update_relay(relay_node_1.url.clone(), Duration::from_millis(2)); + latencies.update_relay(relay_node_2.url.clone(), Duration::from_millis(2)); let last_report = Report { udp: true, ipv6: true, @@ -706,34 +706,34 @@ mod tests { mapping_varies_by_dest_ipv6: Some(false), hair_pinning: Some(true), portmap_probe: None, - preferred_derp: Some(derp_node_1.url.clone()), - derp_latency: latencies.clone(), - derp_v4_latency: latencies.clone(), - derp_v6_latency: latencies.clone(), + preferred_relay: Some(relay_node_1.url.clone()), + relay_latency: latencies.clone(), + relay_v4_latency: latencies.clone(), + relay_v6_latency: latencies.clone(), global_v4: None, global_v6: None, captive_portal: None, }; - let plan = ProbePlan::with_last_report(&derp_map, &if_state, &last_report); + let plan = ProbePlan::with_last_report(&relay_map, &if_state, &last_report); let expected_plan: ProbePlan = [ ProbeSet { proto: ProbeProto::StunIpv4, probes: vec![ Probe::StunIpv4 { delay: Duration::ZERO, - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv4 { delay: Duration::from_micros(52_400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv4 { delay: Duration::from_micros(104_800), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv4 { delay: Duration::from_micros(157_200), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -742,19 +742,19 @@ mod tests { probes: vec![ Probe::StunIpv6 { delay: Duration::ZERO, - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv6 { delay: Duration::from_micros(52_400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv6 { delay: Duration::from_micros(104_800), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::StunIpv6 { delay: Duration::from_micros(157_200), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -763,19 +763,19 @@ mod tests { probes: vec![ Probe::Https { delay: Duration::from_micros(207_200), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::Https { delay: Duration::from_micros(259_600), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::Https { delay: Duration::from_micros(312_000), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::Https { delay: Duration::from_micros(364_400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -784,19 +784,19 @@ mod tests { probes: vec![ Probe::IcmpV4 { delay: Duration::from_micros(207_200), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV4 { delay: Duration::from_micros(259_600), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV4 { delay: Duration::from_micros(312_000), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV4 { delay: Duration::from_micros(364_400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -805,19 +805,19 @@ mod tests { probes: vec![ Probe::IcmpV6 { delay: Duration::from_micros(207_200), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV6 { delay: Duration::from_micros(259_600), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV6 { delay: Duration::from_micros(312_000), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, Probe::IcmpV6 { delay: Duration::from_micros(364_400), - node: derp_node_1.clone(), + node: relay_node_1.clone(), }, ], }, @@ -826,11 +826,11 @@ mod tests { probes: vec![ Probe::StunIpv4 { delay: Duration::ZERO, - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv4 { delay: Duration::from_micros(52_400), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -839,11 +839,11 @@ mod tests { probes: vec![ Probe::StunIpv6 { delay: Duration::ZERO, - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::StunIpv6 { delay: Duration::from_micros(52_400), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -852,11 +852,11 @@ mod tests { probes: vec![ Probe::Https { delay: Duration::from_micros(414_400), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::Https { delay: Duration::from_micros(466_800), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -865,11 +865,11 @@ mod tests { probes: vec![ Probe::IcmpV4 { delay: Duration::from_micros(414_400), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::IcmpV4 { delay: Duration::from_micros(466_800), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -878,11 +878,11 @@ mod tests { probes: vec![ Probe::IcmpV6 { delay: Duration::from_micros(414_400), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, Probe::IcmpV6 { delay: Duration::from_micros(466_800), - node: derp_node_2.clone(), + node: relay_node_2.clone(), }, ], }, @@ -903,17 +903,17 @@ mod tests { } fn create_last_report( - url_1: &DerpUrl, + url_1: &RelayUrl, latency_1: Option, - url_2: &DerpUrl, + url_2: &RelayUrl, latency_2: Option, ) -> Report { - let mut latencies = DerpLatencies::new(); + let mut latencies = RelayLatencies::new(); if let Some(latency_1) = latency_1 { - latencies.update_derp(url_1.clone(), latency_1); + latencies.update_relay(url_1.clone(), latency_1); } if let Some(latency_2) = latency_2 { - latencies.update_derp(url_2.clone(), latency_2); + latencies.update_relay(url_2.clone(), latency_2); } Report { udp: true, @@ -928,10 +928,10 @@ mod tests { mapping_varies_by_dest_ipv6: Some(false), hair_pinning: Some(true), portmap_probe: None, - preferred_derp: Some(url_1.clone()), - derp_latency: latencies.clone(), - derp_v4_latency: latencies.clone(), - derp_v6_latency: latencies.clone(), + preferred_relay: Some(url_1.clone()), + relay_latency: latencies.clone(), + relay_v4_latency: latencies.clone(), + relay_v6_latency: latencies.clone(), global_v4: None, global_v6: None, captive_portal: None, @@ -939,17 +939,17 @@ mod tests { } #[test] - fn test_derp_sort_two_latencies() { - let derp_map = default_derp_map(); - let r1 = derp_map.nodes().next().unwrap(); - let r2 = derp_map.nodes().nth(1).unwrap(); + fn test_relay_sort_two_latencies() { + let relay_map = default_relay_map(); + let r1 = relay_map.nodes().next().unwrap(); + let r2 = relay_map.nodes().nth(1).unwrap(); let last_report = create_last_report( &r1.url, Some(Duration::from_millis(1)), &r2.url, Some(Duration::from_millis(2)), ); - let sorted: Vec<_> = sort_derps(&derp_map, &last_report) + let sorted: Vec<_> = sort_relays(&relay_map, &last_report) .iter() .map(|(url, _reg)| *url) .collect(); @@ -957,17 +957,17 @@ mod tests { } #[test] - fn test_derp_sort_equal_latencies() { - let derp_map = default_derp_map(); - let r1 = derp_map.nodes().next().unwrap(); - let r2 = derp_map.nodes().nth(1).unwrap(); + fn test_relay_sort_equal_latencies() { + let relay_map = default_relay_map(); + let r1 = relay_map.nodes().next().unwrap(); + let r2 = relay_map.nodes().nth(1).unwrap(); let last_report = create_last_report( &r1.url, Some(Duration::from_millis(2)), &r2.url, Some(Duration::from_millis(2)), ); - let sorted: Vec<_> = sort_derps(&derp_map, &last_report) + let sorted: Vec<_> = sort_relays(&relay_map, &last_report) .iter() .map(|(url, _)| *url) .collect(); @@ -975,14 +975,14 @@ mod tests { } #[test] - fn test_derp_sort_missing_latency() { - let derp_map = default_derp_map(); - let r1 = derp_map.nodes().next().unwrap(); - let r2 = derp_map.nodes().nth(1).unwrap(); + fn test_relay_sort_missing_latency() { + let relay_map = default_relay_map(); + let r1 = relay_map.nodes().next().unwrap(); + let r2 = relay_map.nodes().nth(1).unwrap(); let last_report = create_last_report(&r1.url, None, &r2.url, Some(Duration::from_millis(2))); - let sorted: Vec<_> = sort_derps(&derp_map, &last_report) + let sorted: Vec<_> = sort_relays(&relay_map, &last_report) .iter() .map(|(url, _)| *url) .collect(); @@ -990,7 +990,7 @@ mod tests { let last_report = create_last_report(&r1.url, Some(Duration::from_millis(2)), &r2.url, None); - let sorted: Vec<_> = sort_derps(&derp_map, &last_report) + let sorted: Vec<_> = sort_relays(&relay_map, &last_report) .iter() .map(|(url, _)| *url) .collect(); @@ -998,17 +998,17 @@ mod tests { } #[test] - fn test_derp_derp_sort_no_latency() { - let derp_map = default_derp_map(); - let r1 = derp_map.nodes().next().unwrap(); - let r2 = derp_map.nodes().nth(1).unwrap(); + fn test_relay_sort_no_latency() { + let relay_map = default_relay_map(); + let r1 = relay_map.nodes().next().unwrap(); + let r2 = relay_map.nodes().nth(1).unwrap(); let last_report = create_last_report(&r1.url, None, &r2.url, None); - let sorted: Vec<_> = sort_derps(&derp_map, &last_report) + let sorted: Vec<_> = sort_relays(&relay_map, &last_report) .iter() .map(|(url, _)| *url) .collect(); - // sorted by derp id only + // sorted by relay url only assert_eq!(sorted, vec![&r1.url, &r2.url]); } } diff --git a/iroh-net/src/ping.rs b/iroh-net/src/ping.rs index c07419cb9e..322974642e 100644 --- a/iroh-net/src/ping.rs +++ b/iroh-net/src/ping.rs @@ -157,7 +157,7 @@ mod tests { Ok(()) } - // See netcheck::reportgen::tests::test_icmp_probe_eu_derper for permissions to ping. + // See netcheck::reportgen::tests::test_icmp_probe_eu_relay for permissions to ping. #[tokio::test] async fn test_ping_localhost() { let _guard = iroh_test::logging::setup(); diff --git a/iroh-net/src/relay.rs b/iroh-net/src/relay.rs new file mode 100644 index 0000000000..13dc332f75 --- /dev/null +++ b/iroh-net/src/relay.rs @@ -0,0 +1,29 @@ +//! Package `relay` implements a revised version of the Designated Encrypted Relay for Packets (DERP) +//! protocol written by Tailscale. +// +//! The relay routes packets to clients using curve25519 keys as addresses. +// +//! The relay is used to proxy encrypted QUIC packets through the relay servers when +//! a direct path cannot be found or opened. The relay is a last resort. If both sides +//! have very aggressive NATs, or firewalls, or no IPv6, we use the relay connection. +//! Based on tailscale/derp/derp.go + +#![deny(missing_docs, rustdoc::broken_intra_doc_links)] + +pub(crate) mod client; +pub(crate) mod client_conn; +pub(crate) mod clients; +mod codec; +pub mod http; +mod map; +mod metrics; +pub(crate) mod server; +pub(crate) mod types; + +pub use self::client::{Client as RelayClient, ReceivedMessage}; +pub use self::codec::MAX_PACKET_SIZE; +pub use self::http::Client as HttpClient; +pub use self::map::{RelayMap, RelayMode, RelayNode}; +pub use self::metrics::Metrics; +pub use self::server::{ClientConnHandler, MaybeTlsStream as MaybeTlsStreamServer, Server}; +pub use iroh_base::node_addr::RelayUrl; diff --git a/iroh-net/src/derp/client.rs b/iroh-net/src/relay/client.rs similarity index 98% rename from iroh-net/src/derp/client.rs rename to iroh-net/src/relay/client.rs index 494794feaa..d9f44b6832 100644 --- a/iroh-net/src/derp/client.rs +++ b/iroh-net/src/relay/client.rs @@ -34,7 +34,7 @@ impl PartialEq for Client { impl Eq for Client {} -/// A DERP Client. +/// A relay Client. /// Cheaply clonable. /// Call `close` to shutdown the write loop and read functionality. #[derive(Debug, Clone)] @@ -49,7 +49,7 @@ pub struct ClientReceiver { } impl ClientReceiver { - /// Reads a messages from a DERP server. + /// Reads a messages from a relay server. /// /// Once it returns an error, the [`Client`] is dead forever. pub async fn recv(&mut self) -> Result { @@ -62,7 +62,7 @@ impl ClientReceiver { } } -type DerpReader = FramedRead, DerpCodec>; +type RelayReader = FramedRead, DerpCodec>; #[derive(derive_more::Debug)] pub struct InnerClient { @@ -83,7 +83,7 @@ impl Client { /// /// Errors if the packet is larger than [`super::MAX_PACKET_SIZE`] pub async fn send(&self, dstkey: PublicKey, packet: Bytes) -> Result<()> { - trace!(%dstkey, len = packet.len(), "[DERP] send"); + trace!(%dstkey, len = packet.len(), "[RELAY] send"); self.inner .writer_channel @@ -252,7 +252,7 @@ impl ClientWriter { /// The Builder returns a [`Client`] starts a [`ClientWriter`] run task. pub struct ClientBuilder { secret_key: SecretKey, - reader: DerpReader, + reader: RelayReader, writer: FramedWrite, DerpCodec>, local_addr: SocketAddr, is_prober: bool, @@ -316,7 +316,7 @@ impl ClientBuilder { }; debug!("server_handshake: sending client_key: {:?}", &client_info); let shared_secret = self.secret_key.shared(&server_key); - crate::derp::codec::send_client_key( + crate::relay::codec::send_client_key( &mut self.writer, &shared_secret, &self.secret_key.public(), diff --git a/iroh-net/src/derp/client_conn.rs b/iroh-net/src/relay/client_conn.rs similarity index 98% rename from iroh-net/src/derp/client_conn.rs rename to iroh-net/src/relay/client_conn.rs index 136ce9a509..0f82d45756 100644 --- a/iroh-net/src/derp/client_conn.rs +++ b/iroh-net/src/relay/client_conn.rs @@ -457,8 +457,8 @@ impl ClientConnIo { mod tests { use std::sync::Arc; - use crate::derp::codec::{recv_frame, FrameType}; use crate::key::SecretKey; + use crate::relay::codec::{recv_frame, FrameType}; use super::*; @@ -559,7 +559,7 @@ mod tests { // send packet println!(" send packet"); let data = b"hello world!"; - crate::derp::client::send_packet(&mut io_rw, &None, target, Bytes::from_static(data)) + crate::relay::client::send_packet(&mut io_rw, &None, target, Bytes::from_static(data)) .await?; let msg = server_channel_r.recv().await.unwrap(); match msg { @@ -579,7 +579,7 @@ mod tests { let mut disco_data = crate::disco::MAGIC.as_bytes().to_vec(); disco_data.extend_from_slice(target.as_bytes()); disco_data.extend_from_slice(data); - crate::derp::client::send_packet(&mut io_rw, &None, target, disco_data.clone().into()) + crate::relay::client::send_packet(&mut io_rw, &None, target, disco_data.clone().into()) .await?; let msg = server_channel_r.recv().await.unwrap(); match msg { @@ -634,7 +634,7 @@ mod tests { let data = b"hello world!"; let target = SecretKey::generate().public(); - crate::derp::client::send_packet(&mut io_rw, &None, target, Bytes::from_static(data)) + crate::relay::client::send_packet(&mut io_rw, &None, target, Bytes::from_static(data)) .await?; let msg = server_channel_r.recv().await.unwrap(); match msg { diff --git a/iroh-net/src/derp/clients.rs b/iroh-net/src/relay/clients.rs similarity index 98% rename from iroh-net/src/derp/clients.rs rename to iroh-net/src/relay/clients.rs index 09739746b4..b91f4a066e 100644 --- a/iroh-net/src/derp/clients.rs +++ b/iroh-net/src/relay/clients.rs @@ -28,7 +28,7 @@ const RETRIES: usize = 3; // // "Represents one or more connections to a client // -// In the common cast, the client should only have one connection to the DERP server for a given +// In the common cast, the client should only have one connection to the relay server for a given // key. When they're connected multiple times, we record their set of connection, and keep their // connections open to make them happy (to keep them from spinning, etc) and keep track of which // is the latest connection. If only the last is sending traffic, that last one is the active @@ -257,11 +257,11 @@ mod tests { use super::*; use crate::{ - derp::{ + key::SecretKey, + relay::{ client_conn::ClientConnBuilder, codec::{recv_frame, DerpCodec, Frame, FrameType}, }, - key::SecretKey, }; use anyhow::Result; @@ -279,7 +279,7 @@ mod tests { ClientConnBuilder { key, conn_num, - io: Framed::new(crate::derp::server::MaybeTlsStream::Test(io), DerpCodec), + io: Framed::new(crate::relay::server::MaybeTlsStream::Test(io), DerpCodec), write_timeout: None, channel_capacity: 10, server_channel, diff --git a/iroh-net/src/derp/codec.rs b/iroh-net/src/relay/codec.rs similarity index 99% rename from iroh-net/src/derp/codec.rs rename to iroh-net/src/relay/codec.rs index 667927043f..670c709651 100644 --- a/iroh-net/src/derp/codec.rs +++ b/iroh-net/src/relay/codec.rs @@ -9,7 +9,7 @@ use tokio_util::codec::{Decoder, Encoder}; use super::types::ClientInfo; use crate::key::{PublicKey, SecretKey, SharedSecret}; -/// The maximum size of a packet sent over DERP. +/// The maximum size of a packet sent over relay. /// (This only includes the data bytes visible to magicsock, not /// including its on-wire framing overhead) pub const MAX_PACKET_SIZE: usize = 64 * 1024; @@ -101,7 +101,7 @@ pub(crate) enum FrameType { /// Payload is two big endian u32 durations in milliseconds: when to reconnect, /// and how long to try total. /// - /// Handled on the `[derp::Client]`, but currently never sent on the `[derp::Server]` + /// Handled on the `[relay::Client]`, but currently never sent on the `[relay::Server]` Restarting = 15, /// 32B src pub key + 32B dst pub key + packet bytes ForwardPacket = 16, @@ -542,7 +542,7 @@ pub(super) async fn recv_frame> + Unpin>( mod tests { use tokio_util::codec::{FramedRead, FramedWrite}; - use crate::derp::codec::DerpCodec; + use crate::relay::codec::DerpCodec; use super::*; diff --git a/iroh-net/src/derp/http.rs b/iroh-net/src/relay/http.rs similarity index 95% rename from iroh-net/src/derp/http.rs rename to iroh-net/src/relay/http.rs index afddb7c36d..8d8a82ff2c 100644 --- a/iroh-net/src/derp/http.rs +++ b/iroh-net/src/relay/http.rs @@ -1,4 +1,4 @@ -//! An http specific DERP Client and DERP Server. Allows for using tls or non tls connection +//! An http specific relay Client and relay Server. Allows for using tls or non tls connection //! upgrades. //! mod client; @@ -43,8 +43,8 @@ mod tests { use tracing::{info, info_span, Instrument}; use tracing_subscriber::{prelude::*, EnvFilter}; - use crate::derp::ReceivedMessage; use crate::key::{PublicKey, SecretKey}; + use crate::relay::ReceivedMessage; #[tokio::test] async fn test_http_clients_and_server() -> Result<()> { @@ -72,19 +72,19 @@ mod tests { } }; info!("addr: {addr}:{port}"); - let derp_addr: Url = format!("http://{addr}:{port}").parse().unwrap(); + let relay_addr: Url = format!("http://{addr}:{port}").parse().unwrap(); // create clients let (a_key, mut a_recv, client_a_task, client_a) = { let span = info_span!("client-a"); let _guard = span.enter(); - create_test_client(a_key, derp_addr.clone()) + create_test_client(a_key, relay_addr.clone()) }; info!("created client {a_key:?}"); let (b_key, mut b_recv, client_b_task, client_b) = { let span = info_span!("client-b"); let _guard = span.enter(); - create_test_client(b_key, derp_addr) + create_test_client(b_key, relay_addr) }; info!("created client {b_key:?}"); @@ -201,7 +201,7 @@ mod tests { anyhow::bail!("cannot get ipv4 addr from socket addr {addr:?}"); } }; - info!("DERP listening on: {addr}:{port}"); + info!("Relay listening on: {addr}:{port}"); let url: Url = format!("https://localhost:{port}").parse().unwrap(); diff --git a/iroh-net/src/derp/http/client.rs b/iroh-net/src/relay/http/client.rs similarity index 90% rename from iroh-net/src/derp/http/client.rs rename to iroh-net/src/relay/http/client.rs index 10e758526f..64203335c1 100644 --- a/iroh-net/src/derp/http/client.rs +++ b/iroh-net/src/relay/http/client.rs @@ -22,13 +22,13 @@ use tokio::time::Instant; use tracing::{debug, error, info_span, trace, warn, Instrument}; use url::Url; -use crate::derp::DerpUrl; -use crate::derp::{ - client::Client as DerpClient, client::ClientBuilder as DerpClientBuilder, - client::ClientReceiver as DerpClientReceiver, ReceivedMessage, -}; use crate::dns::lookup_ipv4_ipv6; use crate::key::{PublicKey, SecretKey}; +use crate::relay::RelayUrl; +use crate::relay::{ + client::Client as RelayClient, client::ClientBuilder as RelayClientBuilder, + client::ClientReceiver as RelayClientReceiver, ReceivedMessage, +}; use crate::util::AbortingJoinHandle; const DIAL_NODE_TIMEOUT: Duration = Duration::from_millis(1500); @@ -42,8 +42,8 @@ pub enum ClientError { /// The client is closed #[error("client is closed")] Closed, - /// There no underlying derp [`super::client::Client`] client exists for this http derp [`Client`] - #[error("no derp client")] + /// There no underlying relay [`super::client::Client`] client exists for this http relay [`Client`] + #[error("no relay client")] NoClient, /// There was an error sending a packet #[error("error sending a packet")] @@ -54,14 +54,14 @@ pub enum ClientError { /// There was a connection timeout error #[error("connect timeout")] ConnectTimeout, - /// No derp nodes are available - #[error("DERP node is not available")] - DerpNodeNotAvail, - /// No derp nodes are available with that name + /// No relay nodes are available + #[error("Relay node is not available")] + RelayNodeNotAvail, + /// No relay nodes are available with that name #[error("no nodes available for {0}")] NoNodeForTarget(String), - /// The derp node specified only allows STUN requests - #[error("no derp nodes found for {0}, only are stun_only nodes")] + /// The relay node specified only allows STUN requests + #[error("no relay nodes found for {0}, only are stun_only nodes")] StunOnlyNodesFound(String), /// There was an error dialing #[error("dial error")] @@ -69,7 +69,7 @@ pub enum ClientError { /// There was an error from the task doing the dialing #[error("dial error")] DialTask(#[from] tokio::task::JoinError), - /// Both IPv4 and IPv6 are disabled for this derp node + /// Both IPv4 and IPv6 are disabled for this relay node #[error("both IPv4 and IPv6 are explicitly disabled for this node")] IPDisabled, /// No local addresses exist @@ -87,8 +87,8 @@ pub enum ClientError { /// The connection failed to upgrade #[error("failed to upgrade connection: {0}")] Upgrade(String), - /// The derp [`super::client::Client`] failed to build - #[error("failed to build derp client: {0}")] + /// The relay [`super::client::Client`] failed to build + #[error("failed to build relay client: {0}")] Build(String), /// The ping request timed out #[error("ping timeout")] @@ -113,7 +113,7 @@ pub enum ClientError { ActorGone, } -/// An HTTP DERP client. +/// An HTTP Relay client. /// /// Cheaply clonable. #[derive(Clone, Debug)] @@ -126,7 +126,7 @@ pub struct Client { #[derive(Debug)] enum ActorMessage { - Connect(oneshot::Sender>), + Connect(oneshot::Sender>), NotePreferred(bool), LocalAddr(oneshot::Sender, ClientError>>), Ping(oneshot::Sender>), @@ -148,7 +148,7 @@ struct Actor { secret_key: SecretKey, can_ack_pings: bool, is_preferred: bool, - derp_client: Option<(DerpClient, DerpClientReceiver)>, + relay_client: Option<(RelayClient, RelayClientReceiver)>, is_closed: bool, #[debug("address family selector callback")] address_family_selector: @@ -156,7 +156,7 @@ struct Actor { conn_gen: usize, is_prober: bool, server_public_key: Option, - url: DerpUrl, + url: RelayUrl, #[debug("TlsConnector")] tls_connector: tokio_rustls::TlsConnector, pings: PingTracker, @@ -199,7 +199,7 @@ pub struct ClientBuilder { /// Expected PublicKey of the server server_public_key: Option, /// Server url. - url: DerpUrl, + url: RelayUrl, } impl std::fmt::Debug for ClientBuilder { @@ -214,7 +214,7 @@ impl std::fmt::Debug for ClientBuilder { impl ClientBuilder { /// Create a new [`ClientBuilder`] - pub fn new(url: impl Into) -> Self { + pub fn new(url: impl Into) -> Self { ClientBuilder { can_ack_pings: false, is_preferred: false, @@ -226,13 +226,13 @@ impl ClientBuilder { } /// Sets the server url - pub fn server_url(mut self, url: impl Into) -> Self { + pub fn server_url(mut self, url: impl Into) -> Self { self.url = url.into(); self } /// Returns if we should prefer ipv6 - /// it replaces the derphttp.AddressFamilySelector we pass + /// it replaces the relayhttp.AddressFamilySelector we pass /// It provides the hint as to whether in an IPv4-vs-IPv6 race that /// IPv4 should be held back a bit to give IPv6 a better-than-50/50 /// chance of winning. We only return true when we believe IPv6 will @@ -293,7 +293,7 @@ impl ClientBuilder { secret_key: key, can_ack_pings: self.can_ack_pings, is_preferred: self.is_preferred, - derp_client: None, + relay_client: None, is_closed: false, address_family_selector: self.address_family_selector, conn_gen: 0, @@ -357,13 +357,13 @@ impl Client { } } - /// Connect to a Derp Server and returns the underlying Derp Client. + /// Connect to a relay Server and returns the underlying relay Client. /// /// Returns [`ClientError::Closed`] if the [`Client`] is closed. /// - /// If there is already an active derp connection, returns the already - /// connected [`crate::derp::client::Client`]. - pub async fn connect(&self) -> Result<(DerpClient, usize), ClientError> { + /// If there is already an active relay connection, returns the already + /// connected [`crate::relay::client::Client`]. + pub async fn connect(&self) -> Result<(RelayClient, usize), ClientError> { self.send_actor(ActorMessage::Connect).await } @@ -375,7 +375,7 @@ impl Client { .ok(); } - /// Get the local addr of the connection. If there is no current underlying derp connection + /// Get the local addr of the connection. If there is no current underlying relay connection /// or the [`Client`] is closed, returns `None`. pub async fn local_addr(&self) -> Option { self.send_actor(ActorMessage::LocalAddr) @@ -393,10 +393,10 @@ impl Client { /// Send a pong back to the server. /// - /// If there is no underlying active derp connection, it creates one before attempting to + /// If there is no underlying active relay connection, it creates one before attempting to /// send the pong message. /// - /// If there is an error sending pong, it closes the underlying derp connection before + /// If there is an error sending pong, it closes the underlying relay connection before /// returning. pub async fn send_pong(&self, data: [u8; 8]) -> Result<(), ClientError> { self.send_actor(|s| ActorMessage::Pong(data, s)).await @@ -404,26 +404,26 @@ impl Client { /// Send a packet to the server. /// - /// If there is no underlying active derp connection, it creates one before attempting to + /// If there is no underlying active relay connection, it creates one before attempting to /// send the message. /// - /// If there is an error sending the packet, it closes the underlying derp connection before + /// If there is an error sending the packet, it closes the underlying relay connection before /// returning. pub async fn send(&self, dst_key: PublicKey, b: Bytes) -> Result<(), ClientError> { self.send_actor(|s| ActorMessage::Send(dst_key, b, s)).await } - /// Close the http derp connection. + /// Close the http relay connection. pub async fn close(self) -> Result<(), ClientError> { self.send_actor(ActorMessage::Close).await } - /// Disconnect the http derp connection. + /// Disconnect the http relay connection. pub async fn close_for_reconnect(&self) -> Result<(), ClientError> { self.send_actor(ActorMessage::CloseForReconnect).await } - /// Returns `true` if the underlying derp connection is established. + /// Returns `true` if the underlying relay connection is established. pub async fn is_connected(&self) -> Result { self.send_actor(ActorMessage::IsConnected).await } @@ -491,36 +491,36 @@ impl Actor { async fn connect( &mut self, - ) -> Result<(DerpClient, &'_ mut DerpClientReceiver, usize), ClientError> { + ) -> Result<(RelayClient, &'_ mut RelayClientReceiver, usize), ClientError> { if self.is_closed { return Err(ClientError::Closed); } async move { - if self.derp_client.is_none() { + if self.relay_client.is_none() { trace!("no connection, trying to connect"); - let (derp_client, receiver) = + let (relay_client, receiver) = tokio::time::timeout(CONNECT_TIMEOUT, self.connect_0()) .await .map_err(|_| ClientError::ConnectTimeout)??; - self.derp_client = Some((derp_client, receiver)); + self.relay_client = Some((relay_client, receiver)); self.next_conn(); } let count = self.current_conn(); - let (derp_client, receiver) = self - .derp_client + let (relay_client, receiver) = self + .relay_client .as_mut() .map(|(c, r)| (c.clone(), r)) .expect("just inserted"); trace!("already had connection"); - Ok((derp_client, receiver, count)) + Ok((relay_client, receiver, count)) } .instrument(info_span!("connect")) .await } - async fn connect_0(&self) -> Result<(DerpClient, DerpClientReceiver), ClientError> { + async fn connect_0(&self) -> Result<(RelayClient, RelayClientReceiver), ClientError> { let tcp_stream = self.dial_url().await?; let local_addr = tcp_stream @@ -566,8 +566,8 @@ impl Actor { let (reader, writer) = downcast_upgrade(upgraded).map_err(|e| ClientError::Upgrade(e.to_string()))?; - let (derp_client, receiver) = - DerpClientBuilder::new(self.secret_key.clone(), local_addr, reader, writer) + let (relay_client, receiver) = + RelayClientBuilder::new(self.secret_key.clone(), local_addr, reader, writer) .can_ack_pings(self.can_ack_pings) .prober(self.is_prober) .server_public_key(self.server_public_key) @@ -575,16 +575,16 @@ impl Actor { .await .map_err(|e| ClientError::Build(e.to_string()))?; - if self.is_preferred && derp_client.note_preferred(true).await.is_err() { - derp_client.close().await; + if self.is_preferred && relay_client.note_preferred(true).await.is_err() { + relay_client.close().await; return Err(ClientError::Send); } trace!("connect_0 done"); - Ok((derp_client, receiver)) + Ok((relay_client, receiver)) } - /// Sends the HTTP upgrade request to the derper. + /// Sends the HTTP upgrade request to the relay server. async fn start_upgrade(io: T) -> Result, ClientError> where T: AsyncRead + AsyncWrite + Send + Unpin + 'static, @@ -621,14 +621,14 @@ impl Actor { // only send the preference if we already have a connection let res = { - if let Some((ref client, _)) = self.derp_client { + if let Some((ref client, _)) = self.relay_client { client.note_preferred(is_preferred).await } else { return; } }; // need to do this outside the above closure because they rely on the same lock - // if there was an error sending, close the underlying derp connection + // if there was an error sending, close the underlying relay connection if res.is_err() { self.close_for_reconnect().await; } @@ -638,7 +638,7 @@ impl Actor { if self.is_closed { return None; } - if let Some((ref client, _)) = self.derp_client { + if let Some((ref client, _)) = self.relay_client { match client.local_addr() { Ok(addr) => return Some(addr), _ => return None, @@ -708,7 +708,7 @@ impl Actor { if self.is_closed { return false; } - self.derp_client.is_some() + self.relay_client.is_some() } fn current_conn(&self) -> usize { @@ -815,11 +815,11 @@ impl Actor { } } - /// Close the underlying derp connection. The next time the client takes some action that + /// Close the underlying relay connection. The next time the client takes some action that /// requires a connection, it will call `connect`. async fn close_for_reconnect(&mut self) { debug!("close for reconnect"); - if let Some((client, _)) = self.derp_client.take() { + if let Some((client, _)) = self.relay_client.take() { client.close().await } } @@ -918,7 +918,7 @@ mod tests { // ensure that the client will bubble up any connection error & not // just loop ad infinitum attempting to connect if client_receiver.recv().await.and_then(|s| s.ok()).is_some() { - bail!("expected client with bad derp node detail to return with an error"); + bail!("expected client with bad relay node detail to return with an error"); } Ok(()) } diff --git a/iroh-net/src/derp/http/server.rs b/iroh-net/src/relay/http/server.rs similarity index 79% rename from iroh-net/src/derp/http/server.rs rename to iroh-net/src/relay/http/server.rs index 354a432114..b151212a1b 100644 --- a/iroh-net/src/derp/http/server.rs +++ b/iroh-net/src/relay/http/server.rs @@ -19,10 +19,10 @@ use tokio_rustls_acme::AcmeAcceptor; use tokio_util::sync::CancellationToken; use tracing::{debug, error, info, info_span, warn, Instrument}; -use crate::derp::http::HTTP_UPGRADE_PROTOCOL; -use crate::derp::server::{ClientConnHandler, MaybeTlsStream}; -use crate::derp::MaybeTlsStreamServer; use crate::key::SecretKey; +use crate::relay::http::HTTP_UPGRADE_PROTOCOL; +use crate::relay::server::{ClientConnHandler, MaybeTlsStream}; +use crate::relay::MaybeTlsStreamServer; type BytesBody = http_body_util::Full; type HyperError = Box; @@ -54,11 +54,11 @@ fn downcast_upgrade(upgraded: Upgraded) -> Result<(MaybeTlsStream, Bytes)> { } /// The server HTTP handler to do HTTP upgrades -async fn derp_connection_handler( +async fn relay_connection_handler( conn_handler: &ClientConnHandler, upgraded: Upgraded, ) -> Result<()> { - debug!("derp_connection upgraded"); + debug!("relay_connection upgraded"); let (io, read_buf) = downcast_upgrade(upgraded)?; ensure!( read_buf.is_empty(), @@ -69,18 +69,18 @@ async fn derp_connection_handler( conn_handler.accept(io).await } -/// A Derp Server handler. Created using [`ServerBuilder::spawn`], it starts a derp server +/// A Relay Server handler. Created using [`ServerBuilder::spawn`], it starts a relay server /// listening over HTTP or HTTPS. #[derive(Debug)] pub struct Server { addr: SocketAddr, - server: Option, + server: Option, http_server_task: JoinHandle<()>, cancel_server_loop: CancellationToken, } impl Server { - /// Close the underlying derp server and the HTTP(S) server task + /// Close the underlying relay server and the HTTP(S) server task pub async fn shutdown(self) { if let Some(server) = self.server { server.close().await; @@ -107,19 +107,19 @@ pub struct TlsConfig { pub acceptor: TlsAcceptor, } -/// Build a Derp Server that communicates over HTTP or HTTPS, on a given address. +/// Build a Relay Server that communicates over HTTP or HTTPS, on a given address. /// -/// Defaults to handling "derp" requests on the "/derp" endpoint. +/// Defaults to handling relay requests on the "/derp" endpoint. /// -/// If no [`SecretKey`] is provided, it is assumed that you will provide a `derp_override` function -/// that handles requests to the derp endpoint. Not providing a `derp_override` in this case will +/// If no [`SecretKey`] is provided, it is assumed that you will provide a `relay_override` function +/// that handles requests to the relay endpoint. Not providing a `relay_override` in this case will /// result in an error on `spawn`. #[derive(derive_more::Debug)] pub struct ServerBuilder { /// The secret key for this Server. /// - /// When `None`, you must also provide a `derp_override` function that - /// will be run when someone hits the derp endpoint. + /// When `None`, you must also provide a `relay_override` function that + /// will be run when someone hits the relay endpoint. secret_key: Option, /// The ip + port combination for this server. addr: SocketAddr, @@ -128,14 +128,14 @@ pub struct ServerBuilder { /// When `None`, the server will serve HTTP, otherwise it will serve HTTPS. tls_config: Option, /// A map of request handlers to routes. Used when certain routes in your server should be made - /// available at the same port as the derp server, and so must be handled along side requests - /// to the derp endpoint. + /// available at the same port as the relay server, and so must be handled along side requests + /// to the relay endpoint. handlers: Handlers, /// Defaults to `GET` request at "/derp". - derp_endpoint: &'static str, - /// Use a custom derp response handler. Typically used when you want to disable any derp connections. - #[debug("{}", derp_override.as_ref().map_or("None", |_| "Some(Box, ResponseBuilder) -> Result + Send + Sync + 'static>)"))] - derp_override: Option, + relay_endpoint: &'static str, + /// Use a custom relay response handler. Typically used when you want to disable any relay connections. + #[debug("{}", relay_override.as_ref().map_or("None", |_| "Some(Box, ResponseBuilder) -> Result + Send + Sync + 'static>)"))] + relay_override: Option, /// Headers to use for HTTP or HTTPS messages. headers: HeaderMap, /// 404 not found response @@ -153,21 +153,21 @@ impl ServerBuilder { addr, tls_config: None, handlers: Default::default(), - derp_endpoint: "/derp", - derp_override: None, + relay_endpoint: "/derp", + relay_override: None, headers: HeaderMap::new(), not_found_fn: None, } } - /// The [`SecretKey`] identity for this derp server. When set to `None`, the builder assumes - /// you do not want to run a derp service. + /// The [`SecretKey`] identity for this relay server. When set to `None`, the builder assumes + /// you do not want to run a relay service. pub fn secret_key(mut self, secret_key: Option) -> Self { self.secret_key = secret_key; self } - /// Serve derp content using TLS. + /// Serve relay content using TLS. pub fn tls_config(mut self, config: Option) -> Self { self.tls_config = config; self @@ -190,16 +190,16 @@ impl ServerBuilder { self } - /// Handle the derp endpoint in a custom way. This is required if no [`SecretKey`] was provided + /// Handle the relay endpoint in a custom way. This is required if no [`SecretKey`] was provided /// to the builder. - pub fn derp_override(mut self, handler: HyperHandler) -> Self { - self.derp_override = Some(handler); + pub fn relay_override(mut self, handler: HyperHandler) -> Self { + self.relay_override = Some(handler); self } - /// Change the derp endpoint from "/derp" to `endpoint`. - pub fn derp_endpoint(mut self, endpoint: &'static str) -> Self { - self.derp_endpoint = endpoint; + /// Change the relay endpoint from "/derp" to `endpoint`. + pub fn relay_endpoint(mut self, endpoint: &'static str) -> Self { + self.relay_endpoint = endpoint; self } @@ -211,20 +211,20 @@ impl ServerBuilder { self } - /// Build and spawn an HTTP(S) derp Server + /// Build and spawn an HTTP(S) relay Server pub async fn spawn(self) -> Result { - ensure!(self.secret_key.is_some() || self.derp_override.is_some(), "Must provide a `SecretKey` for the derp server OR pass in an override function for the 'derp' endpoint"); - let (derp_handler, derp_server) = if let Some(secret_key) = self.secret_key { - let server = crate::derp::server::Server::new(secret_key.clone()); + ensure!(self.secret_key.is_some() || self.relay_override.is_some(), "Must provide a `SecretKey` for the relay server OR pass in an override function for the 'relay' endpoint"); + let (relay_handler, relay_server) = if let Some(secret_key) = self.secret_key { + let server = crate::relay::server::Server::new(secret_key.clone()); ( - DerpHandler::ConnHandler(server.client_conn_handler(self.headers.clone())), + RelayHandler::ConnHandler(server.client_conn_handler(self.headers.clone())), Some(server), ) } else { ( - DerpHandler::Override( - self.derp_override - .context("no derp handler override but also no secret key")?, + RelayHandler::Override( + self.relay_override + .context("no relay handler override but also no secret key")?, ), None, ) @@ -242,10 +242,10 @@ impl ServerBuilder { }), }; - let service = DerpService::new( + let service = RelayService::new( self.handlers, - derp_handler, - self.derp_endpoint, + relay_handler, + self.relay_endpoint, not_found_fn, self.headers, ); @@ -253,7 +253,7 @@ impl ServerBuilder { let server_state = ServerState { addr: self.addr, tls_config: self.tls_config, - server: derp_server, + server: relay_server, service, }; @@ -265,8 +265,8 @@ impl ServerBuilder { struct ServerState { addr: SocketAddr, tls_config: Option, - server: Option, - service: DerpService, + server: Option, + service: RelayService, } impl ServerState { @@ -280,7 +280,7 @@ impl ServerState { let cancel_server_loop = CancellationToken::new(); let addr = listener.local_addr()?; let http_str = self.tls_config.as_ref().map_or("HTTP", |_| "HTTPS"); - info!("[{http_str}] derp: serving on {addr}"); + info!("[{http_str}] relay: serving on {addr}"); let cancel = cancel_server_loop.clone(); let task = tokio::task::spawn(async move { // create a join set to track all our connection tasks @@ -293,7 +293,7 @@ impl ServerState { } res = listener.accept() => match res { Ok((stream, peer_addr)) => { - debug!("[{http_str}] derp: Connection opened from {peer_addr}"); + debug!("[{http_str}] relay: Connection opened from {peer_addr}"); let tls_config = self.tls_config.clone(); let service = self.service.clone(); // spawn a task to handle the connection @@ -302,19 +302,19 @@ impl ServerState { .handle_connection(stream, tls_config) .await { - error!("[{http_str}] derp: failed to handle connection: {e}"); + error!("[{http_str}] relay: failed to handle connection: {e}"); } }.instrument(info_span!("conn", peer = %peer_addr))); } Err(err) => { - error!("[{http_str}] derp: failed to accept connection: {err}"); + error!("[{http_str}] relay: failed to accept connection: {err}"); } } } } set.shutdown().await; - debug!("[{http_str}] derp: server has been shutdown."); - }.instrument(info_span!("derp-http-serve"))); + debug!("[{http_str}] relay: server has been shutdown."); + }.instrument(info_span!("relay-http-serve"))); Ok(Server { addr, @@ -360,7 +360,7 @@ impl Service> for ClientConnHandler { match hyper::upgrade::on(&mut req).await { Ok(upgraded) => { if let Err(e) = - derp_connection_handler(&closure_conn_handler, upgraded).await + relay_connection_handler(&closure_conn_handler, upgraded).await { tracing::warn!( "upgrade to \"{HTTP_UPGRADE_PROTOCOL}\": io error: {:?}", @@ -390,23 +390,23 @@ impl Service> for ClientConnHandler { } } -impl Service> for DerpService { +impl Service> for RelayService { type Response = Response; type Error = HyperError; type Future = Pin> + Send>>; fn call(&self, req: Request) -> Self::Future { - // if the request hits the derp endpoint - if req.method() == hyper::Method::GET && req.uri().path() == self.0.derp_endpoint { - match &self.0.derp_handler { - DerpHandler::Override(f) => { + // if the request hits the relay endpoint + if req.method() == hyper::Method::GET && req.uri().path() == self.0.relay_endpoint { + match &self.0.relay_handler { + RelayHandler::Override(f) => { // see if we have some override response let res = f(req, self.0.default_response()); return Box::pin(async move { res }); } - DerpHandler::ConnHandler(handler) => { + RelayHandler::ConnHandler(handler) => { let h = handler.clone(); - // otherwise handle the derp connection as normal + // otherwise handle the relay connection as normal return Box::pin(async move { h.call(req).await.map_err(Into::into) }); } } @@ -423,26 +423,26 @@ impl Service> for DerpService { } } -/// The hyper Service that servers the actual derp endpoints +/// The hyper Service that servers the actual relay endpoints #[derive(Clone, Debug)] -struct DerpService(Arc); +struct RelayService(Arc); #[derive(derive_more::Debug)] struct Inner { - pub derp_handler: DerpHandler, - pub derp_endpoint: &'static str, + pub relay_handler: RelayHandler, + pub relay_endpoint: &'static str, #[debug("Box Result> + Send + Sync + 'static>")] pub not_found_fn: HyperHandler, pub handlers: Handlers, pub headers: HeaderMap, } -/// Action to take when a connection is made at the derp endpoint.` +/// Action to take when a connection is made at the relay endpoint.` #[derive(derive_more::Debug)] -enum DerpHandler { - /// Pass the connection to a [`ClientConnHandler`] to get added to the derp server. The default. +enum RelayHandler { + /// Pass the connection to a [`ClientConnHandler`] to get added to the relay server. The default. ConnHandler(ClientConnHandler), - /// Return some static response. Used when the http(s) should be running, but the derp portion + /// Return some static response. Used when the http(s) should be running, but the relay portion /// of the server is disabled. // TODO: Can we remove this debug override? Override( @@ -474,18 +474,18 @@ pub enum TlsAcceptor { Manual(#[debug("tokio_rustls::TlsAcceptor")] tokio_rustls::TlsAcceptor), } -impl DerpService { +impl RelayService { fn new( handlers: Handlers, - derp_handler: DerpHandler, - derp_endpoint: &'static str, + relay_handler: RelayHandler, + relay_endpoint: &'static str, not_found_fn: HyperHandler, headers: HeaderMap, ) -> Self { Self(Arc::new(Inner { - derp_handler, + relay_handler, handlers, - derp_endpoint, + relay_endpoint, not_found_fn, headers, })) diff --git a/iroh-net/src/derp/map.rs b/iroh-net/src/relay/map.rs similarity index 54% rename from iroh-net/src/derp/map.rs rename to iroh-net/src/relay/map.rs index dc7b0fcd39..ede590a7ae 100644 --- a/iroh-net/src/derp/map.rs +++ b/iroh-net/src/relay/map.rs @@ -5,35 +5,35 @@ use std::{collections::BTreeMap, fmt, sync::Arc}; use anyhow::{ensure, Result}; use serde::{Deserialize, Serialize}; -use crate::defaults::DEFAULT_DERP_STUN_PORT; +use crate::defaults::DEFAULT_RELAY_STUN_PORT; -use super::DerpUrl; +use super::RelayUrl; -/// Configuration options for the Derp servers of the magic endpoint. +/// Configuration options for the relay servers of the magic endpoint. #[derive(Debug, Clone, PartialEq, Eq)] -pub enum DerpMode { - /// Disable Derp servers completely. +pub enum RelayMode { + /// Disable relay servers completely. Disabled, - /// Use the default Derp map, with Derp servers from n0. + /// Use the default relay map, with relay servers from n0. Default, - /// Use a custom Derp map. - Custom(DerpMap), + /// Use a custom relay map. + Custom(RelayMap), } -/// Configuration of all the Derp servers that can be used. +/// Configuration of all the relay servers that can be used. #[derive(Debug, Clone, PartialEq, Eq)] -pub struct DerpMap { - /// A map of the different derp IDs to the [`DerpNode`] information - nodes: Arc>>, +pub struct RelayMap { + /// A map of the different relay IDs to the [`RelayNode`] information + nodes: Arc>>, } -impl DerpMap { - /// Returns the sorted DERP URLs. - pub fn urls(&self) -> impl Iterator { +impl RelayMap { + /// Returns the sorted relay URLs. + pub fn urls(&self) -> impl Iterator { self.nodes.keys() } - /// Create an empty Derp map. + /// Create an empty relay map. pub fn empty() -> Self { Self { nodes: Default::default(), @@ -41,17 +41,17 @@ impl DerpMap { } /// Returns an `Iterator` over all known nodes. - pub fn nodes(&self) -> impl Iterator> { + pub fn nodes(&self) -> impl Iterator> { self.nodes.values() } /// Is this a known node? - pub fn contains_node(&self, url: &DerpUrl) -> bool { + pub fn contains_node(&self, url: &RelayUrl) -> bool { self.nodes.contains_key(url) } /// Get the given node. - pub fn get_node(&self, url: &DerpUrl) -> Option<&Arc> { + pub fn get_node(&self, url: &RelayUrl) -> Option<&Arc> { self.nodes.get(url) } @@ -65,15 +65,15 @@ impl DerpMap { self.nodes.is_empty() } - /// Creates a new [`DerpMap`] with a single Derp server configured. + /// Creates a new [`RelayMap] with a single relay server configured. /// /// Allows to set a custom STUN port and different IP addresses for IPv4 and IPv6. /// If IP addresses are provided, no DNS lookup will be performed. - pub fn default_from_node(url: DerpUrl, stun_port: u16) -> Self { + pub fn default_from_node(url: RelayUrl, stun_port: u16) -> Self { let mut nodes = BTreeMap::new(); nodes.insert( url.clone(), - DerpNode { + RelayNode { url, stun_only: false, stun_port, @@ -81,55 +81,55 @@ impl DerpMap { .into(), ); - DerpMap { + RelayMap { nodes: Arc::new(nodes), } } - /// Returns a [`DerpMap`] from a [`DerpUrl`]. + /// Returns a [`RelayMap] from a [`RelayUrl`]. /// /// This will use the default STUN port and IP addresses resolved from the URL's host name via DNS. - /// Derp nodes are specified at <../../../docs/derp_nodes.md> - pub fn from_url(url: DerpUrl) -> Self { - Self::default_from_node(url, DEFAULT_DERP_STUN_PORT) + /// relay nodes are specified at <../../../docs/relay_nodes.md> + pub fn from_url(url: RelayUrl) -> Self { + Self::default_from_node(url, DEFAULT_RELAY_STUN_PORT) } - /// Constructs the [`DerpMap`] from an iterator of [`DerpNode`]s. - pub fn from_nodes(value: impl IntoIterator) -> Result { + /// Constructs the [`RelayMap] from an iterator of [`RelayNode`]s. + pub fn from_nodes(value: impl IntoIterator) -> Result { let mut map = BTreeMap::new(); for node in value.into_iter() { ensure!(!map.contains_key(&node.url), "Duplicate node url"); map.insert(node.url.clone(), node.into()); } - Ok(DerpMap { nodes: map.into() }) + Ok(RelayMap { nodes: map.into() }) } } -impl fmt::Display for DerpMap { +impl fmt::Display for RelayMap { fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result { fmt::Debug::fmt(&self, f) } } -/// Information on a specific derp server. +/// Information on a specific relay server. /// /// Includes the Url where it can be dialed. #[derive(Debug, Clone, PartialEq, Eq, Serialize, Deserialize, PartialOrd, Ord)] -pub struct DerpNode { - /// The [`DerpUrl`] where this derp server can be dialed. - pub url: DerpUrl, - /// Whether this derp server should only be used for STUN requests. +pub struct RelayNode { + /// The [`RelayUrl`] where this relay server can be dialed. + pub url: RelayUrl, + /// Whether this relay server should only be used for STUN requests. /// - /// This essentially allows you to use a normal STUN server as a DERP node, no DERP + /// This essentially allows you to use a normal STUN server as a relay node, no relay /// functionality is used. pub stun_only: bool, - /// The stun port of the derp server. + /// The stun port of the relay server. /// /// Setting this to `0` means the default STUN port is used. pub stun_port: u16, } -impl fmt::Display for DerpNode { +impl fmt::Display for RelayNode { fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { write!(f, "{}", self.url) } diff --git a/iroh-net/src/derp/metrics.rs b/iroh-net/src/relay/metrics.rs similarity index 98% rename from iroh-net/src/derp/metrics.rs rename to iroh-net/src/relay/metrics.rs index 1e64a5ef19..3100d857f7 100644 --- a/iroh-net/src/derp/metrics.rs +++ b/iroh-net/src/relay/metrics.rs @@ -3,7 +3,7 @@ use iroh_metrics::{ struct_iterable::Iterable, }; -/// Metrics tracked for the DERP server +/// Metrics tracked for the relay server #[allow(missing_docs)] #[derive(Debug, Clone, Iterable)] pub struct Metrics { @@ -126,6 +126,6 @@ impl Default for Metrics { impl Metric for Metrics { fn name() -> &'static str { - "derpserver" + "relayserver" } } diff --git a/iroh-net/src/derp/server.rs b/iroh-net/src/relay/server.rs similarity index 97% rename from iroh-net/src/derp/server.rs rename to iroh-net/src/relay/server.rs index 0d455bee6a..a354fca028 100644 --- a/iroh-net/src/derp/server.rs +++ b/iroh-net/src/relay/server.rs @@ -40,9 +40,9 @@ fn new_conn_num() -> usize { pub(crate) const WRITE_TIMEOUT: Duration = Duration::from_secs(2); -/// A DERP server. +/// A relay server. /// -/// Responsible for managing connections to derp [`super::client::Client`]s, sending packets from one client to another. +/// Responsible for managing connections to relay [`super::client::Client`]s, sending packets from one client to another. #[derive(Debug)] pub struct Server { /// Optionally specifies how long to wait before failing when writing @@ -75,7 +75,7 @@ impl Server { let done = cancel_token.clone(); let server_task = tokio::spawn( async move { server_actor.run(done).await } - .instrument(info_span!("derp.server", me = %key.public().fmt_short())), + .instrument(info_span!("relay.server", me = %key.public().fmt_short())), ); let meta_cert = init_meta_cert(&key.public()); Self { @@ -120,7 +120,7 @@ impl Server { } } - /// Whether or not the derp [Server] is closed. + /// Whether or not the relay [Server] is closed. pub fn is_closed(&self) -> bool { self.closed } @@ -323,7 +323,7 @@ impl ServerActor { let key = client_builder.key; report_usage_stats(&UsageStatsReport::new( - "derp_accepts".to_string(), + "relay_accepts".to_string(), self.key.to_string(), 1, None, // TODO(arqu): attribute to user id; possibly with the re-introduction of request tokens or other auth @@ -359,16 +359,16 @@ impl ServerActor { } /// Initializes the [`Server`] with a self-signed x509 cert -/// encoding this server's public key and protocol version. "cmd/derp_server +/// encoding this server's public key and protocol version. "cmd/relay_server /// then sends this after the Let's Encrypt leaf + intermediate certs after /// the ServerHello (encrypted in TLS 1.3, not that is matters much). /// /// Then the client can save a round trime getting that and can start speaking -/// DERP right away. (we don't use ALPN because that's sent in the clear and +/// relay right away. (we don't use ALPN because that's sent in the clear and /// we're being paranoid to not look too weird to any middleboxes, given that -/// DERP is an ultimate fallback path). But since the post-ServerHello certs +/// relay is an ultimate fallback path). But since the post-ServerHello certs /// are encrypted we can have the client also use them as a signal to be able -/// to start speaking DERP right away, starting with its identity proof, +/// to start speaking relay right away, starting with its identity proof, /// encrypted to the server's public key. /// /// This RTT optimization fails where there's a corp-mandated TLS proxy with @@ -470,7 +470,7 @@ impl AsyncWrite for MaybeTlsStream { mod tests { use super::*; - use crate::derp::{ + use crate::relay::{ client::ClientBuilder, client_conn::ClientConnBuilder, codec::{recv_frame, DerpCodec, FrameType}, @@ -516,7 +516,7 @@ mod tests { // run server actor let server_task = tokio::spawn( async move { server_actor.run(server_done).await } - .instrument(info_span!("derp.server")), + .instrument(info_span!("relay.server")), ); let key_a = SecretKey::generate().public(); @@ -538,7 +538,7 @@ mod tests { // write message from b to a let msg = b"hello world!"; - crate::derp::client::send_packet(&mut b_io, &None, key_a, Bytes::from_static(msg)).await?; + crate::relay::client::send_packet(&mut b_io, &None, key_a, Bytes::from_static(msg)).await?; // get message on a's reader let frame = recv_frame(FrameType::RecvPacket, &mut a_io).await?; @@ -594,7 +594,7 @@ mod tests { let expect_server_key = handler.secret_key.public(); let client_task: JoinHandle> = tokio::spawn(async move { // get the server key - let got_server_key = crate::derp::client::recv_server_key(&mut client_reader).await?; + let got_server_key = crate::relay::client::recv_server_key(&mut client_reader).await?; assert_eq!(expect_server_key, got_server_key); // send the client info @@ -605,7 +605,7 @@ mod tests { mesh_key: None, }; let shared_secret = client_key.shared(&got_server_key); - crate::derp::codec::send_client_key( + crate::relay::codec::send_client_key( &mut client_writer, &shared_secret, &client_key.public(), diff --git a/iroh-net/src/derp/types.rs b/iroh-net/src/relay/types.rs similarity index 100% rename from iroh-net/src/derp/types.rs rename to iroh-net/src/relay/types.rs diff --git a/iroh-net/src/stun.rs b/iroh-net/src/stun.rs index 9d1a98e939..15a297eacb 100644 --- a/iroh-net/src/stun.rs +++ b/iroh-net/src/stun.rs @@ -157,7 +157,7 @@ pub mod test { }; use crate::{ - derp::{DerpMap, DerpNode, DerpUrl}, + relay::{RelayMap, RelayNode, RelayUrl}, test_utils::CleanupDropGuard, }; @@ -180,23 +180,23 @@ pub mod test { } } - pub fn derp_map_of(stun: impl Iterator) -> DerpMap { - derp_map_of_opts(stun.map(|addr| (addr, true))) + pub fn relay_map_of(stun: impl Iterator) -> RelayMap { + relay_map_of_opts(stun.map(|addr| (addr, true))) } - pub fn derp_map_of_opts(stun: impl Iterator) -> DerpMap { + pub fn relay_map_of_opts(stun: impl Iterator) -> RelayMap { let nodes = stun.map(|(addr, stun_only)| { let host = addr.ip(); let port = addr.port(); - let url: DerpUrl = format!("http://{host}:{port}").parse().unwrap(); - DerpNode { + let url: RelayUrl = format!("http://{host}:{port}").parse().unwrap(); + RelayNode { url, stun_port: port, stun_only, } }); - DerpMap::from_nodes(nodes).expect("generated invalid nodes") + RelayMap::from_nodes(nodes).expect("generated invalid nodes") } /// Sets up a simple STUN server binding to `0.0.0.0:0`. diff --git a/iroh-net/src/test_utils.rs b/iroh-net/src/test_utils.rs index ffb2fa9317..6292349a2b 100644 --- a/iroh-net/src/test_utils.rs +++ b/iroh-net/src/test_utils.rs @@ -4,8 +4,8 @@ use anyhow::Result; use tokio::sync::oneshot; use tracing::{error_span, info_span, Instrument}; -use crate::derp::{DerpMap, DerpNode, DerpUrl}; use crate::key::SecretKey; +use crate::relay::{RelayMap, RelayNode, RelayUrl}; /// A drop guard to clean up test infrastructure. /// @@ -17,31 +17,31 @@ use crate::key::SecretKey; #[allow(dead_code)] pub(crate) struct CleanupDropGuard(pub(crate) oneshot::Sender<()>); -/// Runs a DERP server with STUN enabled suitable for tests. +/// Runs a relay server with STUN enabled suitable for tests. /// -/// The returned `Url` is the url of the DERP server in the returned [`DerpMap`], it +/// The returned `Url` is the url of the relay server in the returned [`RelayMap`], it /// is always `Some` as that is how the [`MagicEndpoint::connect`] API expects it. /// /// [`MagicEndpoint::connect`]: crate::magic_endpoint::MagicEndpoint -pub(crate) async fn run_derper() -> Result<(DerpMap, DerpUrl, CleanupDropGuard)> { +pub(crate) async fn run_relay_server() -> Result<(RelayMap, RelayUrl, CleanupDropGuard)> { let server_key = SecretKey::generate(); let me = server_key.public().fmt_short(); - let tls_config = crate::derp::http::make_tls_config(); - let server = crate::derp::http::ServerBuilder::new("127.0.0.1:0".parse().unwrap()) + let tls_config = crate::relay::http::make_tls_config(); + let server = crate::relay::http::ServerBuilder::new("127.0.0.1:0".parse().unwrap()) .secret_key(Some(server_key)) .tls_config(Some(tls_config)) .spawn() - .instrument(error_span!("derper", %me)) + .instrument(error_span!("relay server", %me)) .await?; let https_addr = server.addr(); - println!("DERP listening on {:?}", https_addr); + println!("relay listening on {:?}", https_addr); let (stun_addr, _, stun_drop_guard) = crate::stun::test::serve(server.addr().ip()).await?; - let url: DerpUrl = format!("https://localhost:{}", https_addr.port()) + let url: RelayUrl = format!("https://localhost:{}", https_addr.port()) .parse() .unwrap(); - let m = DerpMap::from_nodes([DerpNode { + let m = RelayMap::from_nodes([RelayNode { url: url.clone(), stun_only: false, stun_port: stun_addr.port(), @@ -57,7 +57,7 @@ pub(crate) async fn run_derper() -> Result<(DerpMap, DerpUrl, CleanupDropGuard)> rx.await.ok(); server.shutdown().await; } - .instrument(info_span!("derp-stun-cleanup")), + .instrument(info_span!("relay-stun-cleanup")), ); Ok((m, url, CleanupDropGuard(tx))) diff --git a/iroh-net/src/util.rs b/iroh-net/src/util.rs index 9c156ddcf4..f1eee67971 100644 --- a/iroh-net/src/util.rs +++ b/iroh-net/src/util.rs @@ -81,11 +81,11 @@ impl Future for MaybeFuture { } } -/// Check if we are running in "derp only" mode, as informed -/// by the compile time env var `DEV_DERP_ONLY`. +/// Check if we are running in "relay only" mode, as informed +/// by the compile time env var `DEV_RELAY_ONLY`. /// -/// "derp only" mode implies we only use the relay to communicate +/// "relay only" mode implies we only use the relay to communicate /// and do not attempt to do any hole punching. -pub(crate) fn derp_only_mode() -> bool { - std::option_env!("DEV_DERP_ONLY").is_some() +pub(crate) fn relay_only_mode() -> bool { + std::option_env!("DEV_RELAY_ONLY").is_some() } diff --git a/iroh/examples/collection-fetch.rs b/iroh/examples/collection-fetch.rs index 4040fe9fc0..1575a09200 100644 --- a/iroh/examples/collection-fetch.rs +++ b/iroh/examples/collection-fetch.rs @@ -45,9 +45,9 @@ async fn main() -> Result<()> { println!("\t{:?}", addr); } println!( - "node DERP server url: {:?}", - node.my_derp() - .expect("a default DERP url should be provided") + "node relay server url: {:?}", + node.my_relay() + .expect("a default relay url should be provided") .to_string() ); let req = BlobDownloadRequest { @@ -61,9 +61,9 @@ async fn main() -> Result<()> { format: ticket.format(), // The `peer` field is a `NodeAddr`, which combines all of the known address information we have for the remote node. - // This includes the `node_id` (or `PublicKey` of the node), any direct UDP addresses we know about for that node, as well as the DERP url of that node. The DERP url is the url of the DERP server that that node is connected to. - // If the direct UDP addresses to that node do not work, than we can use the DERP node to attempt to holepunch between your current node and the remote node. - // If holepunching fails, iroh will use the DERP node to proxy a connection to the remote node over HTTPS. + // This includes the `node_id` (or `PublicKey` of the node), any direct UDP addresses we know about for that node, as well as the relay url of that node. The relay url is the url of the relay server that that node is connected to. + // If the direct UDP addresses to that node do not work, than we can use the relay node to attempt to holepunch between your current node and the remote node. + // If holepunching fails, iroh will use the relay node to proxy a connection to the remote node over HTTPS. // Thankfully, the ticket contains all of this information peer: ticket.node_addr().clone(), diff --git a/iroh/examples/collection-provide.rs b/iroh/examples/collection-provide.rs index 7c52a95868..1ef27561c3 100644 --- a/iroh/examples/collection-provide.rs +++ b/iroh/examples/collection-provide.rs @@ -54,11 +54,11 @@ async fn main() -> anyhow::Result<()> { println!("\t{:?}", addr); } println!( - "node DERP server url: {:?}", + "node relay server url: {:?}", ticket .node_addr() - .derp_url() - .expect("a default DERP url should be provided") + .relay_url() + .expect("a default relay url should be provided") .to_string() ); // print the ticket, containing all the above information diff --git a/iroh/examples/hello-world-fetch.rs b/iroh/examples/hello-world-fetch.rs index 71b5c30b83..d3b3a4de55 100644 --- a/iroh/examples/hello-world-fetch.rs +++ b/iroh/examples/hello-world-fetch.rs @@ -45,9 +45,9 @@ async fn main() -> Result<()> { println!("\t{:?}", addr); } println!( - "node DERP server url: {:?}", - node.my_derp() - .expect("a default DERP url should be provided") + "node relay server url: {:?}", + node.my_relay() + .expect("a default relay url should be provided") .to_string() ); let req = BlobDownloadRequest { @@ -61,9 +61,9 @@ async fn main() -> Result<()> { format: ticket.format(), // The `peer` field is a `NodeAddr`, which combines all of the known address information we have for the remote node. - // This includes the `node_id` (or `PublicKey` of the node), any direct UDP addresses we know about for that node, as well as the DERP url of that node. The DERP url is the url of the DERP server that that node is connected to. - // If the direct UDP addresses to that node do not work, than we can use the DERP node to attempt to holepunch between your current node and the remote node. - // If holepunching fails, iroh will use the DERP node to proxy a connection to the remote node over HTTPS. + // This includes the `node_id` (or `PublicKey` of the node), any direct UDP addresses we know about for that node, as well as the relay url of that node. The relay url is the url of the relay server that that node is connected to. + // If the direct UDP addresses to that node do not work, than we can use the relay node to attempt to holepunch between your current node and the remote node. + // If holepunching fails, iroh will use the relay node to proxy a connection to the remote node over HTTPS. // Thankfully, the ticket contains all of this information peer: ticket.node_addr().clone(), diff --git a/iroh/examples/hello-world-provide.rs b/iroh/examples/hello-world-provide.rs index d0613f1f84..663895e5f4 100644 --- a/iroh/examples/hello-world-provide.rs +++ b/iroh/examples/hello-world-provide.rs @@ -36,11 +36,11 @@ async fn main() -> anyhow::Result<()> { println!("\t{:?}", addr); } println!( - "node DERP server url: {:?}", + "node relay server url: {:?}", ticket .node_addr() - .derp_url() - .expect("a default DERP url should be provided") + .relay_url() + .expect("a default relay url should be provided") .to_string() ); // print the ticket, containing all the above information diff --git a/iroh/src/client/blobs.rs b/iroh/src/client/blobs.rs index efc1d97503..c42e7583cf 100644 --- a/iroh/src/client/blobs.rs +++ b/iroh/src/client/blobs.rs @@ -262,15 +262,15 @@ where let NodeStatusResponse { addr, .. } = self.rpc.rpc(NodeStatusRequest).await??; let mut node_addr = NodeAddr::new(addr.node_id); match ticket_options { - ShareTicketOptions::DerpAndAddresses => { + ShareTicketOptions::RelayAndAddresses => { node_addr = node_addr.with_direct_addresses(addr.direct_addresses().copied()); - if let Some(url) = addr.derp_url() { - node_addr = node_addr.with_derp_url(url.clone()); + if let Some(url) = addr.relay_url() { + node_addr = node_addr.with_relay_url(url.clone()); } } - ShareTicketOptions::Derp => { - if let Some(url) = addr.derp_url() { - node_addr = node_addr.with_derp_url(url.clone()); + ShareTicketOptions::Relay => { + if let Some(url) = addr.relay_url() { + node_addr = node_addr.with_relay_url(url.clone()); } } ShareTicketOptions::Addresses => { @@ -300,11 +300,11 @@ where Copy, Clone, PartialEq, Eq, Default, Debug, derive_more::Display, derive_more::FromStr, )] pub enum ShareTicketOptions { - /// Include both the derp URL and the direct addresses. + /// Include both the relay URL and the direct addresses. #[default] - DerpAndAddresses, - /// Only include the derp URL. - Derp, + RelayAndAddresses, + /// Only include the relay URL. + Relay, /// Only include the direct addresses. Addresses, } diff --git a/iroh/src/dial.rs b/iroh/src/dial.rs index 51b3cdfe20..4723ffa303 100644 --- a/iroh/src/dial.rs +++ b/iroh/src/dial.rs @@ -1,8 +1,8 @@ //! Utilities to dial a node. use anyhow::Context; -use iroh_net::derp::{DerpMap, DerpMode}; use iroh_net::key::SecretKey; +use iroh_net::relay::{RelayMap, RelayMode}; use iroh_net::NodeAddr; /// Options for the client @@ -14,8 +14,8 @@ pub struct Options { pub peer: NodeAddr, /// Whether to log the SSL keys when `SSLKEYLOGFILE` environment variable is set pub keylog: bool, - /// The configuration of the derp services - pub derp_map: Option, + /// The configuration of the relay services + pub relay_map: Option, } /// Create a new endpoint and dial a peer, returning the connection @@ -27,11 +27,11 @@ pub async fn dial(opts: Options) -> anyhow::Result { let endpoint = iroh_net::MagicEndpoint::builder() .secret_key(opts.secret_key) .keylog(opts.keylog); - let derp_mode = match opts.derp_map { - Some(derp_map) => DerpMode::Custom(derp_map), - None => DerpMode::Default, + let relay_mode = match opts.relay_map { + Some(relay_map) => RelayMode::Custom(relay_map), + None => RelayMode::Default, }; - let endpoint = endpoint.derp_mode(derp_mode); + let endpoint = endpoint.relay_mode(relay_mode); let endpoint = endpoint.bind(0).await?; endpoint .connect(opts.peer, iroh_bytes::protocol::ALPN) diff --git a/iroh/src/metrics.rs b/iroh/src/metrics.rs index c19a47eef0..0fba864ef3 100644 --- a/iroh/src/metrics.rs +++ b/iroh/src/metrics.rs @@ -42,7 +42,7 @@ pub fn try_init_metrics_collection() -> std::io::Result<()> { metrics.insert(iroh_net::metrics::MagicsockMetrics::new(reg)); metrics.insert(iroh_net::metrics::NetcheckMetrics::new(reg)); metrics.insert(iroh_net::metrics::PortmapMetrics::new(reg)); - metrics.insert(iroh_net::metrics::DerpMetrics::new(reg)); + metrics.insert(iroh_net::metrics::RelayMetrics::new(reg)); }) } @@ -70,7 +70,7 @@ pub fn get_metrics() -> anyhow::Result> { &mut map, ); collect( - core.get_collector::(), + core.get_collector::(), &mut map, ); Ok(map) diff --git a/iroh/src/node.rs b/iroh/src/node.rs index 5f5cc0b01a..759763a066 100644 --- a/iroh/src/node.rs +++ b/iroh/src/node.rs @@ -19,8 +19,8 @@ use futures::{FutureExt, StreamExt}; use iroh_bytes::store::Store as BaoStore; use iroh_bytes::BlobFormat; use iroh_bytes::Hash; -use iroh_net::derp::DerpUrl; use iroh_net::magicsock::LocalEndpointsStream; +use iroh_net::relay::RelayUrl; use iroh_net::util::AbortingJoinHandle; use iroh_net::{ key::{PublicKey, SecretKey}, @@ -227,9 +227,9 @@ impl Node { self.inner.endpoint.my_addr().await } - /// Get the DERPer we are connected to. - pub fn my_derp(&self) -> Option { - self.inner.endpoint.my_derp() + /// Get the relay server we are connected to. + pub fn my_relay(&self) -> Option { + self.inner.endpoint.my_relay() } /// Aborts the node. diff --git a/iroh/src/node/builder.rs b/iroh/src/node/builder.rs index c27eabe5b0..6cc6de5a0a 100644 --- a/iroh/src/node/builder.rs +++ b/iroh/src/node/builder.rs @@ -15,7 +15,9 @@ use iroh_bytes::{ store::{GcMarkEvent, GcSweepEvent, Map, Store as BaoStore}, }; use iroh_gossip::net::{Gossip, GOSSIP_ALPN}; -use iroh_net::{derp::DerpMode, magic_endpoint::get_alpn, util::AbortingJoinHandle, MagicEndpoint}; +use iroh_net::{ + magic_endpoint::get_alpn, relay::RelayMode, util::AbortingJoinHandle, MagicEndpoint, +}; use iroh_sync::net::SYNC_ALPN; use quic_rpc::{ transport::{misc::DummyServerEndpoint, quinn::QuinnServerEndpoint}, @@ -77,7 +79,7 @@ where rpc_endpoint: E, blobs_store: D, keylog: bool, - derp_mode: DerpMode, + relay_mode: RelayMode, gc_policy: GcPolicy, docs_store: S, } @@ -99,7 +101,7 @@ impl Default for Builder Builder { secret_key: SecretKey::generate(), blobs_store, keylog: false, - derp_mode: DerpMode::Default, + relay_mode: RelayMode::Default, rpc_endpoint: Default::default(), gc_policy: GcPolicy::Disabled, docs_store, @@ -175,7 +177,7 @@ where blobs_store, keylog: self.keylog, rpc_endpoint: self.rpc_endpoint, - derp_mode: self.derp_mode, + relay_mode: self.relay_mode, gc_policy: self.gc_policy, docs_store, }) @@ -194,7 +196,7 @@ where blobs_store: self.blobs_store, keylog: self.keylog, rpc_endpoint: value, - derp_mode: self.derp_mode, + relay_mode: self.relay_mode, gc_policy: self.gc_policy, docs_store: self.docs_store, } @@ -217,7 +219,7 @@ where blobs_store: self.blobs_store, keylog: self.keylog, rpc_endpoint: ep, - derp_mode: self.derp_mode, + relay_mode: self.relay_mode, gc_policy: self.gc_policy, docs_store: self.docs_store, }) @@ -231,17 +233,17 @@ where self } - /// Sets the DERP servers to assist in establishing connectivity. + /// Sets the relay servers to assist in establishing connectivity. /// - /// DERP servers are used to discover other nodes by `PublicKey` and also help + /// Relay servers are used to discover other nodes by `PublicKey` and also help /// establish connections between peers by being an initial relay for traffic while /// assisting in holepunching to establish a direct connection between peers. /// - /// When using [DerpMode::Custom], the provided `derp_map` must contain at least one - /// configured derp node. If an invalid [`iroh_net::derp::DerpMap`] + /// When using [RelayMode::Custom], the provided `relay_map` must contain at least one + /// configured relay node. If an invalid [`iroh_net::relay::RelayMode`] /// is provided [`Self::spawn`] will result in an error. - pub fn derp_mode(mut self, dm: DerpMode) -> Self { - self.derp_mode = dm; + pub fn relay_mode(mut self, dm: RelayMode) -> Self { + self.relay_mode = dm; self } @@ -298,7 +300,7 @@ where .keylog(self.keylog) .transport_config(transport_config) .concurrent_connections(MAX_CONNECTIONS) - .derp_mode(self.derp_mode); + .relay_mode(self.relay_mode); let endpoint = match self.storage { StorageConfig::Persistent(ref root) => { let peers_data_path = IrohPaths::PeerData.with_root(root); diff --git a/iroh/src/ticket/doc.rs b/iroh/src/ticket/doc.rs index 1467e6c240..d289761033 100644 --- a/iroh/src/ticket/doc.rs +++ b/iroh/src/ticket/doc.rs @@ -94,7 +94,7 @@ mod tests { ae58ff8833241ac82d6ff7611046ed67b5072d142c588d0063e942d9a75502b6 # namespace id, 32 bytes, see above 01 # one node ae58ff8833241ac82d6ff7611046ed67b5072d142c588d0063e942d9a75502b6 # node id, 32 bytes, see above - 00 # no derp url + 00 # no relay url 00 # no direct addresses ").unwrap(); assert_eq_hex!(base32, expected); diff --git a/iroh/tests/provide.rs b/iroh/tests/provide.rs index a745738e9e..a19e61f6bd 100644 --- a/iroh/tests/provide.rs +++ b/iroh/tests/provide.rs @@ -120,17 +120,17 @@ async fn empty_files() -> Result<()> { /// Create new get options with the given node id and addresses, using a /// randomly generated secret key. fn get_options(node_id: NodeId, addrs: Vec) -> iroh::dial::Options { - let derp_map = iroh_net::defaults::default_derp_map(); + let relay_map = iroh_net::defaults::default_relay_map(); let peer = iroh_net::NodeAddr::from_parts( node_id, - derp_map.nodes().next().map(|n| n.url.clone()), + relay_map.nodes().next().map(|n| n.url.clone()), addrs, ); iroh::dial::Options { secret_key: SecretKey::generate(), peer, keylog: false, - derp_map: Some(derp_map), + relay_map: Some(relay_map), } } @@ -495,7 +495,7 @@ async fn test_run_ticket() { secret_key: SecretKey::generate(), peer: ticket.node_addr().clone(), keylog: false, - derp_map: Some(iroh_net::defaults::default_derp_map()), + relay_map: Some(iroh_net::defaults::default_relay_map()), }, request, ) diff --git a/iroh/tests/sync.rs b/iroh/tests/sync.rs index eef00215ea..24ba60a73e 100644 --- a/iroh/tests/sync.rs +++ b/iroh/tests/sync.rs @@ -20,7 +20,7 @@ use tracing::{debug, info}; use tracing_subscriber::{prelude::*, EnvFilter}; use iroh_bytes::Hash; -use iroh_net::derp::DerpMode; +use iroh_net::relay::RelayMode; use iroh_sync::{ store::{self, DownloadPolicy, FilterKind, Query}, AuthorId, ContentStatus, @@ -33,7 +33,7 @@ fn test_node( ) -> Builder { Node::memory() .secret_key(secret_key) - .derp_mode(DerpMode::Disabled) + .relay_mode(RelayMode::Disabled) } // The function is not `async fn` so that we can take a `&mut` borrow on the `rng` without