Merge pull request #2499 from nspcc-dev/fix-concurrent-seek
core: avoid concurrent map iteration and map write during SeekAsync over private MemCachedStore
This commit is contained in:
commit
34e7d3e53c
2 changed files with 13 additions and 2 deletions
|
@ -195,7 +195,14 @@ func storageFind(ic *interop.Context) error {
|
|||
seekres := ic.DAO.SeekAsync(ctx, stc.ID, storage.SeekRange{Prefix: prefix})
|
||||
item := istorage.NewIterator(seekres, prefix, opts)
|
||||
ic.VM.Estack().PushItem(stackitem.NewInterop(item))
|
||||
ic.RegisterCancelFunc(cancel)
|
||||
ic.RegisterCancelFunc(func() {
|
||||
cancel()
|
||||
// Underlying persistent store is likely to be a private MemCachedStore. Thus,
|
||||
// to avoid concurrent map iteration and map write we need to wait until internal
|
||||
// seek goroutine is finished, because it can access underlying persistent store.
|
||||
for range seekres {
|
||||
}
|
||||
})
|
||||
|
||||
return nil
|
||||
}
|
||||
|
|
|
@ -969,7 +969,11 @@ func (n *NEO) getAllCandidatesCall(ic *interop.Context, _ []stackitem.Item) stac
|
|||
|
||||
opts := istorage.FindRemovePrefix | istorage.FindDeserialize | istorage.FindPick1
|
||||
item := istorage.NewIterator(filteredRes, prefix, int64(opts))
|
||||
ic.RegisterCancelFunc(cancel)
|
||||
ic.RegisterCancelFunc(func() {
|
||||
cancel()
|
||||
for range seekres {
|
||||
}
|
||||
})
|
||||
return stackitem.NewInterop(item)
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue