aboutsummaryrefslogtreecommitdiffstats
path: root/src/daemon.rs
diff options
context:
space:
mode:
Diffstat (limited to 'src/daemon.rs')
-rw-r--r--src/daemon.rs36
1 files changed, 36 insertions, 0 deletions
diff --git a/src/daemon.rs b/src/daemon.rs
index 12757a3..4895a48 100644
--- a/src/daemon.rs
+++ b/src/daemon.rs
@@ -30,6 +30,9 @@ const REPUBLISH_INTERVAL: Duration = Duration::from_secs(1800);
/// How often to persist routing table and state (5 min).
const SAVE_INTERVAL: Duration = Duration::from_secs(300);
+/// How often to attempt re-join when the routing table is empty (60 s).
+const REJOIN_INTERVAL: Duration = Duration::from_secs(60);
+
/// How often to sync DHT-replicated values to local store (5 s).
const SYNC_INTERVAL: Duration = Duration::from_secs(5);
@@ -45,11 +48,13 @@ pub fn run_daemon(
store: &PasteStore,
rx: &mpsc::Receiver<DaemonRequest>,
shutdown: &AtomicBool,
+ bootstrap: &[String],
) {
let mut last_gc = Instant::now();
let mut last_republish = Instant::now() - REPUBLISH_INTERVAL;
let mut last_save = Instant::now();
let mut last_sync = Instant::now();
+ let mut last_rejoin = Instant::now();
log::info!("daemon main loop started");
@@ -65,6 +70,37 @@ pub fn run_daemon(
}
}
+ // Re-join bootstrap nodes when the routing table is empty
+ if node.routing_table_size() == 0
+ && !bootstrap.is_empty()
+ && last_rejoin.elapsed() >= REJOIN_INTERVAL
+ {
+ last_rejoin = Instant::now();
+ log::warn!("routing table empty, re-joining bootstrap nodes");
+ for peer in bootstrap {
+ let parts: Vec<&str> = peer.rsplitn(2, ':').collect();
+ if parts.len() != 2 {
+ continue;
+ }
+ let host = parts[1];
+ if let Ok(p) = parts[0].parse::<u16>() {
+ // Unban bootstrap addresses before re-joining
+ // so their replies are not silently dropped.
+ use std::net::ToSocketAddrs;
+ if let Ok(addrs) = format!("{host}:{p}").to_socket_addrs() {
+ for addr in addrs {
+ node.unban(&addr);
+ }
+ }
+ if let Err(e) = node.join(host, p) {
+ log::warn!("rejoin: failed to join {peer}: {e}");
+ } else {
+ log::info!("rejoin: sent join to {peer}");
+ }
+ }
+ }
+ }
+
if last_sync.elapsed() >= SYNC_INTERVAL {
last_sync = Instant::now();
sync_dht_to_store(node, store);