aboutsummaryrefslogtreecommitdiffstats
path: root/src/swarm
diff options
context:
space:
mode:
Diffstat (limited to 'src/swarm')
-rw-r--r--src/swarm/stats.rs9
-rw-r--r--src/swarm/sync.rs9
2 files changed, 17 insertions, 1 deletions
diff --git a/src/swarm/stats.rs b/src/swarm/stats.rs
index 31b6a3b..ba75d68 100644
--- a/src/swarm/stats.rs
+++ b/src/swarm/stats.rs
@@ -157,6 +157,10 @@ pub(crate) struct Relay {
pub(crate) carrying_bloom_bytes: u64,
pub(crate) nothing_new_change_bytes: u64,
pub(crate) nothing_new_bloom_bytes: u64,
+ /// Sync messages received that carried changes, none of them applied yet: they wait
+ /// for predecessors that didn't come (Automerge holds them back). Not counted with
+ /// `nothing_new`, which they aren't.
+ pub(crate) waiting: u64,
/// The changes new to us that sync messages brought (beside what they carried that
/// we had): with `carrying` less `nothing_new`, how many a message with news brings.
pub(crate) new_changes: u64,
@@ -314,6 +318,11 @@ impl NodeStats {
inner.relay.nothing_new_bloom_bytes += sizes.1 as u64;
}
+ /// A sync message carried changes that wait for predecessors (`Relay::waiting`).
+ pub(crate) fn waiting(&self) {
+ self.lock().relay.waiting += 1;
+ }
+
/// Changes from elsewhere were applied, `delays_ms` after they were committed, that
/// came not along a writer's tree.
pub(crate) fn off_tree(&self, delays_ms: &[i64]) {
diff --git a/src/swarm/sync.rs b/src/swarm/sync.rs
index 0edc277..5511ea2 100644
--- a/src/swarm/sync.rs
+++ b/src/swarm/sync.rs
@@ -574,6 +574,7 @@ pub(crate) async fn handle_sync(
peer_state.last_heads =
Some((epoch, transport::HeadsSummary::of(message.heads().to_vec())));
let heads_before = replica.heads().to_vec();
+ let said = message.heads().to_vec();
let sync = &mut peer_state.sync;
replica
@@ -617,7 +618,13 @@ pub(crate) async fn handle_sync(
stats.new_changes(new);
}
if carried && !changed {
- stats.nothing_new(payload_len, writer.is_some(), delivered, sizes);
+ // Its heads not ours yet: what it brought waits for predecessors, which
+ // isn't having come twice.
+ if !crate::document::changes::holds_all(&replica.doc, &said) {
+ stats.waiting();
+ } else {
+ stats.nothing_new(payload_len, writer.is_some(), delivered, sizes);
+ }
}
// Whose they are, to pass them on along their writers' trees, however they
// came (along a tree, with an answer, pulled).