diff --git a/lib/db/set_test.go b/lib/db/set_test.go index 2716a301..5bf7bd9d 100644 --- a/lib/db/set_test.go +++ b/lib/db/set_test.go @@ -606,6 +606,7 @@ func TestGlobalNeedWithInvalid(t *testing.T) { protocol.FileInfo{Name: "a", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Blocks: genBlocks(4)}, protocol.FileInfo{Name: "b", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Invalid: true}, protocol.FileInfo{Name: "c", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Blocks: genBlocks(4)}, + protocol.FileInfo{Name: "d", Version: protocol.Vector{Counters: []protocol.Counter{{ID: remoteDevice0.Short(), Value: 1002}}}}, } replace(s, remoteDevice0, rem0) @@ -613,6 +614,7 @@ func TestGlobalNeedWithInvalid(t *testing.T) { protocol.FileInfo{Name: "a", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Blocks: genBlocks(4)}, protocol.FileInfo{Name: "b", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Blocks: genBlocks(4)}, protocol.FileInfo{Name: "c", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Invalid: true}, + protocol.FileInfo{Name: "d", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Invalid: true, ModifiedS: 10}, } replace(s, remoteDevice1, rem1) @@ -621,6 +623,8 @@ func TestGlobalNeedWithInvalid(t *testing.T) { protocol.FileInfo{Name: "a", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Blocks: genBlocks(4)}, protocol.FileInfo{Name: "b", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Blocks: genBlocks(4)}, protocol.FileInfo{Name: "c", Version: protocol.Vector{Counters: []protocol.Counter{{ID: myID, Value: 1002}}}, Blocks: genBlocks(4)}, + // in conflict and older, but still wins as the other is invalid + protocol.FileInfo{Name: "d", Version: protocol.Vector{Counters: []protocol.Counter{{ID: remoteDevice0.Short(), Value: 1002}}}}, } need := fileList(needList(s, protocol.LocalDeviceID)) diff --git a/lib/protocol/bep_extensions.go b/lib/protocol/bep_extensions.go index 2bd2e0e0..a3ed7d16 100644 --- a/lib/protocol/bep_extensions.go +++ b/lib/protocol/bep_extensions.go @@ -95,6 +95,11 @@ func (f FileInfo) SequenceNo() int64 { // WinsConflict returns true if "f" is the one to choose when it is in // conflict with "other". func (f FileInfo) WinsConflict(other FileInfo) bool { + // If only one of the files is invalid, that one loses + if f.IsInvalid() != other.IsInvalid() { + return !f.IsInvalid() + } + // If a modification is in conflict with a delete, we pick the // modification. if !f.IsDeleted() && other.IsDeleted() { diff --git a/lib/protocol/conflict_test.go b/lib/protocol/conflict_test.go index 848445b1..e3afb23d 100644 --- a/lib/protocol/conflict_test.go +++ b/lib/protocol/conflict_test.go @@ -9,6 +9,7 @@ func TestWinsConflict(t *testing.T) { // The first should always win over the second {{ModifiedS: 42}, {ModifiedS: 41}}, {{ModifiedS: 41}, {ModifiedS: 42, Deleted: true}}, + {{Deleted: true}, {ModifiedS: 10, Invalid: true}}, {{ModifiedS: 41, Version: Vector{[]Counter{{42, 2}, {43, 1}}}}, {ModifiedS: 41, Version: Vector{[]Counter{{42, 1}, {43, 2}}}}}, }