mirror of
https://github.com/rclone/rclone.git
synced 2024-11-29 11:55:01 +01:00
vfs: make writeback heap sort in insertion order if expiry times equal
This makes the tests 100% consistent on platforms which have a lower resolution timer like Windows.
This commit is contained in:
parent
746c41f527
commit
ef2d036884
@ -30,6 +30,7 @@ type writeBack struct {
|
|||||||
timer *time.Timer // next scheduled time for the uploader
|
timer *time.Timer // next scheduled time for the uploader
|
||||||
expiry time.Time // time the next item exires or IsZero
|
expiry time.Time // time the next item exires or IsZero
|
||||||
uploads int // number of uploads in progress
|
uploads int // number of uploads in progress
|
||||||
|
id uint64 // id of the last writeBackItem created
|
||||||
}
|
}
|
||||||
|
|
||||||
// make a new writeBack
|
// make a new writeBack
|
||||||
@ -55,6 +56,7 @@ func newWriteBack(ctx context.Context, opt *vfscommon.Options) *writeBack {
|
|||||||
// writeBack.mu must be held to manipulate this
|
// writeBack.mu must be held to manipulate this
|
||||||
type writeBackItem struct {
|
type writeBackItem struct {
|
||||||
name string // name of the item so we don't have to read it from item
|
name string // name of the item so we don't have to read it from item
|
||||||
|
id uint64 // id of the item
|
||||||
index int // index into the priority queue for update
|
index int // index into the priority queue for update
|
||||||
item *Item // Item that needs writeback
|
item *Item // Item that needs writeback
|
||||||
expiry time.Time // When this expires we will write it back
|
expiry time.Time // When this expires we will write it back
|
||||||
@ -74,7 +76,12 @@ type writeBackItems []*writeBackItem
|
|||||||
func (ws writeBackItems) Len() int { return len(ws) }
|
func (ws writeBackItems) Len() int { return len(ws) }
|
||||||
|
|
||||||
func (ws writeBackItems) Less(i, j int) bool {
|
func (ws writeBackItems) Less(i, j int) bool {
|
||||||
return ws[i].expiry.Sub(ws[j].expiry) < 0
|
a, b := ws[i], ws[j]
|
||||||
|
// If times are equal then use ID to disambiguate
|
||||||
|
if a.expiry.Equal(b.expiry) {
|
||||||
|
return a.id < b.id
|
||||||
|
}
|
||||||
|
return a.expiry.Before(b.expiry)
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ws writeBackItems) Swap(i, j int) {
|
func (ws writeBackItems) Swap(i, j int) {
|
||||||
@ -116,6 +123,7 @@ func (wb *writeBack) _newExpiry() time.Time {
|
|||||||
if wb.opt.WriteBack > 0 {
|
if wb.opt.WriteBack > 0 {
|
||||||
expiry = expiry.Add(wb.opt.WriteBack)
|
expiry = expiry.Add(wb.opt.WriteBack)
|
||||||
}
|
}
|
||||||
|
// expiry = expiry.Round(time.Millisecond)
|
||||||
return expiry
|
return expiry
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -123,11 +131,13 @@ func (wb *writeBack) _newExpiry() time.Time {
|
|||||||
//
|
//
|
||||||
// call with the lock held
|
// call with the lock held
|
||||||
func (wb *writeBack) _newItem(item *Item, name string) *writeBackItem {
|
func (wb *writeBack) _newItem(item *Item, name string) *writeBackItem {
|
||||||
|
wb.id++
|
||||||
wbItem := &writeBackItem{
|
wbItem := &writeBackItem{
|
||||||
name: name,
|
name: name,
|
||||||
item: item,
|
item: item,
|
||||||
expiry: wb._newExpiry(),
|
expiry: wb._newExpiry(),
|
||||||
delay: wb.opt.WriteBack,
|
delay: wb.opt.WriteBack,
|
||||||
|
id: wb.id,
|
||||||
}
|
}
|
||||||
wb._addItem(wbItem)
|
wb._addItem(wbItem)
|
||||||
wb._pushItem(wbItem)
|
wb._pushItem(wbItem)
|
||||||
|
@ -72,6 +72,12 @@ func TestWriteBackItems(t *testing.T) {
|
|||||||
|
|
||||||
wb.items._update(&wbItem1, now.Add(5*time.Second))
|
wb.items._update(&wbItem1, now.Add(5*time.Second))
|
||||||
assert.Equal(t, "two,three,one", wb.string(t))
|
assert.Equal(t, "two,three,one", wb.string(t))
|
||||||
|
|
||||||
|
// Set all times the same - should sort in insertion order
|
||||||
|
wb.items._update(&wbItem1, now)
|
||||||
|
wb.items._update(&wbItem2, now)
|
||||||
|
wb.items._update(&wbItem3, now)
|
||||||
|
assert.Equal(t, "one,two,three", wb.string(t))
|
||||||
}
|
}
|
||||||
|
|
||||||
func checkOnHeap(t *testing.T, wb *writeBack, wbItem *writeBackItem) {
|
func checkOnHeap(t *testing.T, wb *writeBack, wbItem *writeBackItem) {
|
||||||
|
Loading…
Reference in New Issue
Block a user