Skip to content

Commit f80a75f

Browse files
authored
Merge pull request #78 from redraskal/fix/new-reader
fix: read enough header data on new reader
2 parents 617af6a + 4dbcf5b commit f80a75f

File tree

3 files changed

+430
-76
lines changed

3 files changed

+430
-76
lines changed

dissect/reader.go

Lines changed: 91 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -35,91 +35,22 @@ type Reader struct {
3535
// NewReader decompresses in using zstd and
3636
// validates the dissect header.
3737
func NewReader(in io.Reader) (r *Reader, err error) {
38-
internalReader := bufio.NewReader(in)
39-
chunkedCompression, err := testFileCompression(internalReader)
38+
br := bufio.NewReader(in)
39+
chunkedCompression, err := testFileCompression(br)
4040
if err != nil {
41-
return nil, err
41+
return r, err
4242
}
4343
log.Debug().Bool("chunkedCompression (>=Y8S4)", chunkedCompression).Send()
4444
r = &Reader{
4545
readPartial: false,
4646
}
4747
if chunkedCompression {
48-
log.Debug().Msg("creating header buffer")
49-
headerBuffer, err := internalReader.Peek(4000)
50-
if err != nil {
51-
return nil, err
52-
}
53-
r.b = headerBuffer
54-
log.Debug().Msg("reading header magic")
55-
if err = r.readHeaderMagic(); err != nil {
56-
return nil, err
57-
}
58-
log.Debug().Msg("reading header")
59-
h, err := r.readHeader()
60-
r.Header = h
61-
if err != nil {
62-
return nil, err
63-
}
64-
pattern := []byte{0x32, 0x30, 0x30, 0x56, 0x52, 0x50, 0x4D, 0x43}
65-
i := 0
66-
r.b = []byte{}
67-
zstdReader, _ := zstd.NewReader(bytes.NewReader([]byte{}))
68-
for !errors.Is(err, io.EOF) {
69-
log.Debug().Msg("scanning for dissect frame")
70-
for i != 8 {
71-
b, scanErr := internalReader.ReadByte()
72-
if errors.Is(scanErr, io.EOF) {
73-
err = scanErr
74-
break
75-
}
76-
if scanErr != nil {
77-
return nil, scanErr
78-
}
79-
if b == pattern[i] {
80-
i++
81-
} else {
82-
i = 0
83-
}
84-
}
85-
if errors.Is(err, io.EOF) {
86-
break
87-
}
88-
i = 0
89-
_, err := internalReader.Discard(8)
90-
if err != nil {
91-
return nil, err
92-
}
93-
log.Debug().Msg("reading zstd frame")
94-
if err = zstdReader.Reset(internalReader); err != nil {
95-
return nil, err
96-
}
97-
decompressed, err := io.ReadAll(zstdReader)
98-
if err != nil && !(len(decompressed) > 0 && errors.Is(err, zstd.ErrMagicMismatch)) {
99-
return nil, err
100-
}
101-
log.Debug().Msg("writing decompressed frame")
102-
for _, b := range decompressed {
103-
r.b = append(r.b, b)
104-
}
48+
if err = r.readChunkedData(br); err != nil {
49+
return r, err
10550
}
10651
} else {
107-
zstdReader, err := zstd.NewReader(internalReader)
108-
if err != nil {
109-
return nil, err
110-
}
111-
decompressed, err := io.ReadAll(zstdReader)
112-
if err != nil && !(len(decompressed) > 0 && errors.Is(err, zstd.ErrMagicMismatch)) {
113-
return nil, err
114-
}
115-
r.b = decompressed
116-
if err = r.readHeaderMagic(); err != nil {
117-
return nil, err
118-
}
119-
h, err := r.readHeader()
120-
r.Header = h
121-
if err != nil {
122-
return nil, err
52+
if err = r.readUnchunkedData(br); err != nil {
53+
return r, err
12354
}
12455
}
12556
log.Debug().Int("size", len(r.b)).Send()
@@ -137,6 +68,90 @@ func NewReader(in io.Reader) (r *Reader, err error) {
13768
return r, err
13869
}
13970

71+
func (r *Reader) readChunkedData(br *bufio.Reader) error {
72+
log.Debug().Msg("creating header buffer")
73+
r.b = make([]byte, 0)
74+
buf := make([]byte, 4096)
75+
for i := 0; i < 5; i++ {
76+
_, err := br.Read(buf)
77+
if err != nil {
78+
return err
79+
}
80+
r.b = append(r.b, buf...)
81+
}
82+
log.Debug().Msg("reading header magic")
83+
if err := r.readHeaderMagic(); err != nil {
84+
return err
85+
}
86+
log.Debug().Msg("reading header")
87+
h, err := r.readHeader()
88+
r.Header = h
89+
if err != nil {
90+
return err
91+
}
92+
pattern := []byte{0x32, 0x30, 0x30, 0x56, 0x52, 0x50, 0x4D, 0x43}
93+
i := 0
94+
r.b = []byte{}
95+
zstdReader, _ := zstd.NewReader(bytes.NewReader([]byte{}))
96+
for !errors.Is(err, io.EOF) {
97+
log.Debug().Msg("scanning for dissect frame")
98+
for i != 8 {
99+
b, scanErr := br.ReadByte()
100+
if errors.Is(scanErr, io.EOF) {
101+
err = scanErr
102+
break
103+
}
104+
if scanErr != nil {
105+
return scanErr
106+
}
107+
if b == pattern[i] {
108+
i++
109+
} else {
110+
i = 0
111+
}
112+
}
113+
if errors.Is(err, io.EOF) {
114+
break
115+
}
116+
i = 0
117+
_, err := br.Discard(8)
118+
if err != nil {
119+
return err
120+
}
121+
log.Debug().Msg("reading zstd frame")
122+
if err = zstdReader.Reset(br); err != nil {
123+
return err
124+
}
125+
decompressed, err := io.ReadAll(zstdReader)
126+
if err != nil && !(len(decompressed) > 0 && errors.Is(err, zstd.ErrMagicMismatch)) {
127+
return err
128+
}
129+
log.Debug().Msg("writing decompressed frame")
130+
for _, b := range decompressed {
131+
r.b = append(r.b, b)
132+
}
133+
}
134+
return nil
135+
}
136+
137+
func (r *Reader) readUnchunkedData(br *bufio.Reader) error {
138+
zstdReader, err := zstd.NewReader(br)
139+
if err != nil {
140+
return err
141+
}
142+
decompressed, err := io.ReadAll(zstdReader)
143+
if err != nil && !(len(decompressed) > 0 && errors.Is(err, zstd.ErrMagicMismatch)) {
144+
return err
145+
}
146+
r.b = decompressed
147+
if err = r.readHeaderMagic(); err != nil {
148+
return err
149+
}
150+
h, err := r.readHeader()
151+
r.Header = h
152+
return err
153+
}
154+
140155
type match struct {
141156
offset int
142157
listenerIndex int
16.4 MB
Binary file not shown.

0 commit comments

Comments
 (0)