Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Panic in boundStringListItem.Get() #2643

Closed
macbutch opened this issue Nov 15, 2021 · 3 comments
Closed

Panic in boundStringListItem.Get() #2643

macbutch opened this issue Nov 15, 2021 · 3 comments
Labels
bug Something isn't working

Comments

@macbutch
Copy link

Describe the bug:

I believe this to be a race condition because it is not reproducible every time (sometimes it is apparently easy and sometimes it disappears completely). In my application I show the results of some processing in a list. I have a bound list created with binding.NewStringList().

When processing starts I reset it like this: dataList.Set([]string{}). Then I update it in the same way during processing. Items are added and removed during processing so I update the list like this:dataList.Set(sortedKeys).

Sometimes this panics like so (other indices are possible):

panic: runtime error: index out of range [7] with length 7

goroutine 57 [running]:
fyne.io/fyne/v2/data/binding.(*boundStringListItem).Get(0xc002762340, 0x0, 0x0, 0x0, 0x0)
	/Users/mark/go/pkg/mod/fyne.io/fyne/v2@v2.1.1/data/binding/bindlists.go:1039 +0xc9
fyne.io/fyne/v2/widget.(*Label).createListener.func1()
	/Users/mark/go/pkg/mod/fyne.io/fyne/v2@v2.1.1/widget/label.go:145 +0x48
fyne.io/fyne/v2/data/binding.(*listener).DataChanged(0xc0000b4088)
	/Users/mark/go/pkg/mod/fyne.io/fyne/v2@v2.1.1/data/binding/binding.go:55 +0x28
fyne.io/fyne/v2/data/binding.queueItem.func1.1()
	/Users/mark/go/pkg/mod/fyne.io/fyne/v2@v2.1.1/data/binding/queue.go:19 +0x4b
created by fyne.io/fyne/v2/data/binding.queueItem.func1
	/Users/mark/go/pkg/mod/fyne.io/fyne/v2@v2.1.1/data/binding/queue.go:17 +0x51

To Reproduce:

This is hard to reproduce reliably; it's almost certainly down to timing. Could be user error?

Example code:

Call this repeatedly:

someBoundStringArray.Set(someStringArray)

Very rarely you will get a panic (see above) which points to this code in bindlists.go:

func (b *boundStringListItem) Get() (string, error) {
	b.lock.Lock()
	defer b.lock.Unlock()

	return (*b.val)[b.index], nil // <--- panic here!
}

Adding the following appears results in a large number of errors logged to the console (but no panic):

func (b *boundStringListItem) Get() (string, error) {
	b.lock.Lock()
	defer b.lock.Unlock()

	if b.index < 0 || b.index >= len(*b.val) {
		return "", errOutOfBounds
	}

	return (*b.val)[b.index], nil
}

I don't think this is a good fix (probably there should be a check earlier so that we're not attempting to fetch items that have been removed) but this does seem to address the immediate problem.

Device:

  • OS: MacOS
  • Version: Mojava 10.14.6
  • Go version: go1.16.6 darwin/amd64
  • Fyne version: 2.1.1
@macbutch macbutch added the unverified A bug that has been reported but not verified label Nov 15, 2021
@andydotxyz andydotxyz added this to the Fixes (v2.1.x) milestone Nov 15, 2021
@macbutch
Copy link
Author

I believe there are other cases which aren't quite right. For example, here we should check the bounds after getting the lock:

func (l *boundFloatList) GetValue(i int) (float64, error) {
	if i < 0 || i >= l.Length() {
		return 0.0, errOutOfBounds
	}
	l.lock.RLock()
	defer l.lock.RUnlock()

	return (*l.val)[i], nil
}

If the underlying data changes between the bounds check and acquiring the lock then it could still be invalid (and panic).

@andydotxyz andydotxyz added bug Something isn't working and removed unverified A bug that has been reported but not verified labels Nov 29, 2021
andydotxyz added a commit to andydotxyz/fyne that referenced this issue Nov 29, 2021
@andydotxyz
Copy link
Member

Fixed on release/v2.1.x

@macbutch
Copy link
Author

Thanks @andydotxyz

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Projects
None yet
Development

No branches or pull requests

2 participants