blob: 736cbf5e4261795bdb4ec2249d59f0e96e0070d4 [file] [log] [blame]
// Copyright 2018 The Go Authors. All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
package filebuf
import (
"bytes"
"io"
)
// implement a Buf version from an io.Reader
type rbuf struct {
buf []byte // contents
pos int64
seeks, reads int // number of calls. 0 seems right.
}
func (r *rbuf) Stats() Stat {
return Stat{r.seeks, r.reads, int64(len(r.buf))}
}
func (r *rbuf) Size() int64 {
return int64(len(r.buf))
}
// FromReader creates a Buf by copying the contents of an io.Reader
func FromReader(rd io.Reader) (Buf, error) {
r := &rbuf{}
x := bytes.NewBuffer(r.buf)
_, err := io.Copy(x, rd)
r.buf = x.Bytes()
if err != nil {
return nil, err
}
return r, nil
}
func (r *rbuf) Close() error {
return nil
}
func (r *rbuf) Read(p []byte) (int, error) {
n := copy(p, r.buf[r.pos:])
r.pos += int64(n)
if n == 0 || n < len(p) {
return n, io.EOF
}
return n, nil
}
func (r *rbuf) Seek(offset int64, whence int) (int64, error) {
seekpos := offset
switch whence {
case io.SeekCurrent:
seekpos += int64(r.pos)
case io.SeekEnd:
seekpos += int64(len(r.buf))
}
if seekpos < 0 || seekpos > int64(len(r.buf)) {
if seekpos < 0 {
r.pos = 0
return 0, nil
}
r.pos = int64(len(r.buf))
return r.pos, nil
}
r.pos = seekpos
return seekpos, nil
}