github.com/hirochachacha/plua@v0.0.0-20170217012138-c82f520cc725/internal/file/rofile.go (about) 1 package file 2 3 import ( 4 "bufio" 5 "errors" 6 "os" 7 ) 8 9 type rofile struct { 10 *os.File 11 br *bufio.Reader 12 off int64 13 closed bool 14 std bool 15 } 16 17 func (ro *rofile) IsClosed() bool { 18 return ro.closed 19 } 20 21 func (ro *rofile) Close() error { 22 if ro.std { 23 return errors.New("cannot close standard file") 24 } 25 26 if err := ro.File.Close(); err != nil { 27 return err 28 } 29 30 ro.closed = true 31 32 return nil 33 } 34 35 func (ro *rofile) Flush() error { 36 return os.ErrInvalid 37 } 38 39 func (ro *rofile) UnreadByte() error { 40 err := ro.br.UnreadByte() 41 if err == nil { 42 ro.off-- 43 } 44 return err 45 } 46 47 func (ro *rofile) ReadByte() (c byte, err error) { 48 c, err = ro.br.ReadByte() 49 if err == nil { 50 ro.off++ 51 } 52 return c, err 53 } 54 55 func (ro *rofile) Read(p []byte) (n int, err error) { 56 n, err = ro.br.Read(p) 57 ro.off += int64(n) 58 return n, err 59 } 60 61 func (ro *rofile) ReadBytes(delim byte) (line []byte, err error) { 62 line, err = ro.br.ReadBytes(delim) 63 ro.off += int64(len(line)) 64 return line, err 65 } 66 67 func (ro *rofile) Seek(offset int64, whence int) (n int64, err error) { 68 switch whence { 69 case 0: 70 if ro.off <= offset && offset <= ro.off+int64(ro.br.Buffered()) { 71 ro.br.Discard(int(offset - ro.off)) 72 ro.off = offset 73 } else { 74 ro.off, err = ro.File.Seek(offset, 0) 75 ro.br.Reset(ro.File) 76 } 77 case 1: 78 if 0 <= offset && offset <= int64(ro.br.Buffered()) { 79 ro.br.Discard(int(offset)) 80 ro.off += offset 81 } else { 82 ro.off, err = ro.File.Seek(ro.off+offset, 0) 83 ro.br.Reset(ro.File) 84 } 85 case 2: 86 ro.off, err = ro.File.Seek(offset, 2) 87 ro.br.Reset(ro.File) 88 } 89 90 n = ro.off 91 92 return 93 } 94 95 func (ro *rofile) Setvbuf(mode int, size int) (err error) { 96 _, err = ro.File.Seek(ro.off, 0) 97 98 if size > 0 { 99 ro.br = bufio.NewReaderSize(ro.File, size) 100 } 101 102 return 103 }