Skip to content

Commit e252e6c

Browse files
authored
Merge pull request #24847 from squeek502/zstd-partial-magic
zstd.Decompress: Treat a partial magic number as a failure
2 parents 2761cc8 + 353cf1f commit e252e6c

File tree

2 files changed

+18
-3
lines changed

2 files changed

+18
-3
lines changed

lib/std/compress/zstd.zig

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,12 @@ test Decompress {
121121
try testExpectDecompress(uncompressed, compressed19);
122122
}
123123

124+
test "partial magic number" {
125+
const input_raw =
126+
"\x28\xb5\x2f"; // 3 bytes of the 4-byte zstandard frame magic number
127+
try testExpectDecompressError(error.BadMagic, input_raw);
128+
}
129+
124130
test "zero sized raw block" {
125131
const input_raw =
126132
"\x28\xb5\x2f\xfd" ++ // zstandard frame magic number

lib/std/compress/zstd/Decompress.zig

Lines changed: 12 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,6 @@ const State = union(enum) {
1717
new_frame,
1818
in_frame: InFrame,
1919
skipping_frame: usize,
20-
end,
2120

2221
const InFrame = struct {
2322
frame: Frame,
@@ -158,7 +157,18 @@ fn stream(r: *Reader, w: *Writer, limit: Limit) Reader.StreamError!usize {
158157

159158
switch (d.state) {
160159
.new_frame => {
161-
// Allow error.EndOfStream only on the frame magic.
160+
// Only return EndOfStream when there are exactly 0 bytes remaining on the
161+
// frame magic. Any partial magic bytes should be considered a failure.
162+
in.fill(@sizeOf(Frame.Magic)) catch |err| switch (err) {
163+
error.EndOfStream => {
164+
if (in.bufferedLen() != 0) {
165+
d.err = error.BadMagic;
166+
return error.ReadFailed;
167+
}
168+
return err;
169+
},
170+
else => |e| return e,
171+
};
162172
const magic = try in.takeEnumNonexhaustive(Frame.Magic, .little);
163173
initFrame(d, w.buffer.len, magic) catch |err| {
164174
d.err = err;
@@ -192,7 +202,6 @@ fn stream(r: *Reader, w: *Writer, limit: Limit) Reader.StreamError!usize {
192202
if (remaining.* == 0) d.state = .new_frame;
193203
return 0;
194204
},
195-
.end => return error.EndOfStream,
196205
}
197206
}
198207

0 commit comments

Comments
 (0)