Skip to content

Commit

Permalink
lib/readers: add mutex to RepeatableReader - fixes #2572
Browse files Browse the repository at this point in the history
  • Loading branch information
ncw committed Nov 12, 2018
1 parent 9b3c951 commit ee700ec
Showing 1 changed file with 11 additions and 3 deletions.
14 changes: 11 additions & 3 deletions lib/readers/repeatable.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package readers

import (
"io"
"sync"

"github.com/pkg/errors"
)
Expand All @@ -10,9 +11,10 @@ import (
// back and forth within the reader but will only read data from the internal Reader as necessary
// and will play nicely with the Account and io.LimitedReader to reflect current speed
type RepeatableReader struct {
in io.Reader // Input reader
i int64 // current reading index
b []byte // internal cache buffer
mu sync.Mutex // protect against concurrent use
in io.Reader // Input reader
i int64 // current reading index
b []byte // internal cache buffer
}

var _ io.ReadSeeker = (*RepeatableReader)(nil)
Expand All @@ -21,6 +23,9 @@ var _ io.ReadSeeker = (*RepeatableReader)(nil)
// If seek position is passed the cache buffer length the function will return
// the maximum offset that can be used and "fs.RepeatableReader.Seek: offset is unavailable" Error
func (r *RepeatableReader) Seek(offset int64, whence int) (int64, error) {
r.mu.Lock()
defer r.mu.Unlock()

var abs int64
cacheLen := int64(len(r.b))
switch whence {
Expand All @@ -46,6 +51,9 @@ func (r *RepeatableReader) Seek(offset int64, whence int) (int64, error) {
// Read data from original Reader into bytes
// Data is either served from the underlying Reader or from cache if was already read
func (r *RepeatableReader) Read(b []byte) (n int, err error) {
r.mu.Lock()
defer r.mu.Unlock()

cacheLen := int64(len(r.b))
if r.i == cacheLen {
n, err = r.in.Read(b)
Expand Down

0 comments on commit ee700ec

Please sign in to comment.