Merge pull request #13142 from mllken/gzip-safety
gzip: add missing header fields and bounds for header parsing
This commit is contained in:
commit
e361740669
|
@ -15,6 +15,8 @@ const FEXTRA = 1 << 2;
|
|||
const FNAME = 1 << 3;
|
||||
const FCOMMENT = 1 << 4;
|
||||
|
||||
const max_string_len = 1024;
|
||||
|
||||
pub fn GzipStream(comptime ReaderType: type) type {
|
||||
return struct {
|
||||
const Self = @This();
|
||||
|
@ -31,9 +33,11 @@ pub fn GzipStream(comptime ReaderType: type) type {
|
|||
read_amt: usize,
|
||||
|
||||
info: struct {
|
||||
extra: ?[]const u8,
|
||||
filename: ?[]const u8,
|
||||
comment: ?[]const u8,
|
||||
modification_time: u32,
|
||||
operating_system: u8,
|
||||
},
|
||||
|
||||
fn init(allocator: mem.Allocator, source: ReaderType) !Self {
|
||||
|
@ -57,33 +61,27 @@ pub fn GzipStream(comptime ReaderType: type) type {
|
|||
// Operating system where the compression took place
|
||||
const OS = header[9];
|
||||
_ = XFL;
|
||||
_ = OS;
|
||||
|
||||
if (FLG & FEXTRA != 0) {
|
||||
// Skip the extra data, we could read and expose it to the user
|
||||
// if somebody needs it.
|
||||
const extra = if (FLG & FEXTRA != 0) blk: {
|
||||
const len = try source.readIntLittle(u16);
|
||||
try source.skipBytes(len, .{});
|
||||
}
|
||||
const tmp_buf = try allocator.alloc(u8, len);
|
||||
errdefer allocator.free(tmp_buf);
|
||||
|
||||
var filename: ?[]const u8 = null;
|
||||
if (FLG & FNAME != 0) {
|
||||
filename = try source.readUntilDelimiterAlloc(
|
||||
allocator,
|
||||
0,
|
||||
std.math.maxInt(usize),
|
||||
);
|
||||
}
|
||||
try source.readNoEof(tmp_buf);
|
||||
break :blk tmp_buf;
|
||||
} else null;
|
||||
errdefer if (extra) |p| allocator.free(p);
|
||||
|
||||
const filename = if (FLG & FNAME != 0)
|
||||
try source.readUntilDelimiterAlloc(allocator, 0, max_string_len)
|
||||
else
|
||||
null;
|
||||
errdefer if (filename) |p| allocator.free(p);
|
||||
|
||||
var comment: ?[]const u8 = null;
|
||||
if (FLG & FCOMMENT != 0) {
|
||||
comment = try source.readUntilDelimiterAlloc(
|
||||
allocator,
|
||||
0,
|
||||
std.math.maxInt(usize),
|
||||
);
|
||||
}
|
||||
const comment = if (FLG & FCOMMENT != 0)
|
||||
try source.readUntilDelimiterAlloc(allocator, 0, max_string_len)
|
||||
else
|
||||
null;
|
||||
errdefer if (comment) |p| allocator.free(p);
|
||||
|
||||
if (FLG & FHCRC != 0) {
|
||||
|
@ -100,7 +98,9 @@ pub fn GzipStream(comptime ReaderType: type) type {
|
|||
.info = .{
|
||||
.filename = filename,
|
||||
.comment = comment,
|
||||
.extra = extra,
|
||||
.modification_time = MTIME,
|
||||
.operating_system = OS,
|
||||
},
|
||||
.read_amt = 0,
|
||||
};
|
||||
|
@ -108,6 +108,8 @@ pub fn GzipStream(comptime ReaderType: type) type {
|
|||
|
||||
pub fn deinit(self: *Self) void {
|
||||
self.inflater.deinit();
|
||||
if (self.info.extra) |extra|
|
||||
self.allocator.free(extra);
|
||||
if (self.info.filename) |filename|
|
||||
self.allocator.free(filename);
|
||||
if (self.info.comment) |comment|
|
||||
|
|
Loading…
Reference in New Issue
Block a user