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

lost data from mark/reset? #78

Closed
stevengj opened this issue Jul 12, 2023 · 2 comments · Fixed by #79
Closed

lost data from mark/reset? #78

stevengj opened this issue Jul 12, 2023 · 2 comments · Fixed by #79
Labels

Comments

@stevengj
Copy link
Member

stevengj commented Jul 12, 2023

I noticed this when rewriting peek in #77. Running peek (which calls mark and reset) sometimes seems to screw up the buffer so that the subsequent read fails:

julia> io = BufferedInputStream(IOBuffer("α∆"), 1)
BufferedInputStream{IOBuffer}(<1 B buffer, 0% filled>)

julia> read(io, Char)
'α': Unicode U+03B1 (category Ll: Letter, lowercase)

julia> peek(io, Char)
'': Unicode U+2206 (category Sm: Symbol, math)

julia> read(io, Char)
ERROR: EOFError: read end of file
Stacktrace:
 [1] read
   @ ~/.julia/packages/BufferedStreams/0mu59/src/bufferedinputstream.jl:186 [inlined]
 [2] read(io::BufferedInputStream{IOBuffer}, #unused#::Type{Char})
   @ Base ./io.jl:789
 [3] top-level scope
   @ REPL[72]:1

PR #77 avoids this problem specifically for peek(io, Char) since it adds an optimized implementation of that function, but it would be good to identify and solve the underlying problem.

@stevengj
Copy link
Member Author

stevengj commented Jul 12, 2023

Here is some more detailed debugging data for a byte-by-byte read (not using peek), showing that the anchored data from the mark has not actually been preserved — we are only saving the last byte of :

julia> io = BufferedInputStream(IOBuffer("α∆"), 1)
BufferedInputStream{IOBuffer}(<1 B buffer, 0% filled>)

julia> read(io, Char)
'α': Unicode U+03B1 (category Ll: Letter, lowercase)

julia> mark(io)
2

julia> @show io.buffer, io.position, io.available, io.anchor
(io.buffer, io.position, io.available, io.anchor) = (UInt8[0xb1], 2, 1, 2)
(UInt8[0xb1], 2, 1, 2)

julia> read(io, UInt8)
0xe2

julia> @show io.buffer, io.position, io.available, io.anchor
(io.buffer, io.position, io.available, io.anchor) = (UInt8[0xe2], 2, 1, 2)
(UInt8[0xe2], 2, 1, 2)

julia> read(io, UInt8)
0x88

julia> @show io.buffer, io.position, io.available, io.anchor
(io.buffer, io.position, io.available, io.anchor) = (UInt8[0x88], 2, 1, 2)
(UInt8[0x88], 2, 1, 2)

julia> read(io, UInt8)
0x86

julia> @show io.buffer, io.position, io.available, io.anchor
(io.buffer, io.position, io.available, io.anchor) = (UInt8[0x86], 2, 1, 2)
(UInt8[0x86], 2, 1, 2)

julia> reset(io)
2

julia> @show io.buffer, io.position, io.available, io.anchor
(io.buffer, io.position, io.available, io.anchor) = (UInt8[0x86], 2, 1, 0)
(UInt8[0x86], 2, 1, 0)

My understanding was that fillbuffer! is supposed to resize! the buffer as needed to preserve the anchored data?

@stevengj
Copy link
Member Author

Could be related to #63, although I can't reproduce @feanor12's example in that issue.

@stevengj stevengj changed the title bug in peek(io::BufferedInputStream, Char) lost data from mark/reset? Jul 12, 2023
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant