Merge pull request #7280 from leecannon/master

Add `readUntilDelimiterOrEofArrayList` & `readUntilDelimiterOrEofAlloc`
This commit is contained in:
Jakub Konka 2020-12-03 21:03:48 +01:00 committed by GitHub
commit a8e543bd6b
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23

View File

@ -64,7 +64,7 @@ pub fn Reader(
self: Self,
comptime alignment: ?u29,
array_list: *std.ArrayListAligned(u8, alignment),
max_append_size: usize
max_append_size: usize,
) !void {
try array_list.ensureCapacity(math.min(max_append_size, 4096));
const original_len = array_list.items.len;
@ -101,6 +101,35 @@ pub fn Reader(
return array_list.toOwnedSlice();
}
/// Replaces the `std.ArrayList` contents by reading from the stream until `delimiter` or end-of-stream is found.
/// Does not include the delimiter in the result.
/// If the `std.ArrayList` length would exceed `max_size`, `error.StreamTooLong` is returned and the
/// `std.ArrayList` is populated with `max_size` bytes from the stream.
pub fn readUntilDelimiterOrEofArrayList(
self: Self,
array_list: *std.ArrayList(u8),
delimiter: u8,
max_size: usize,
) !void {
array_list.shrink(0);
while (true) {
var byte: u8 = self.readByte() catch |err| switch (err) {
error.EndOfStream => return,
else => |e| return e,
};
if (byte == delimiter) {
return;
}
if (array_list.items.len == max_size) {
return error.StreamTooLong;
}
try array_list.append(byte);
}
}
/// Replaces the `std.ArrayList` contents by reading from the stream until `delimiter` is found.
/// Does not include the delimiter in the result.
/// If the `std.ArrayList` length would exceed `max_size`, `error.StreamTooLong` is returned and the
@ -143,6 +172,22 @@ pub fn Reader(
return array_list.toOwnedSlice();
}
/// Allocates enough memory to read until `delimiter` or end-of-stream.
/// If the allocated memory would be greater than `max_size`, returns `error.StreamTooLong`.
/// Caller owns returned memory.
/// If this function returns an error, the contents from the stream read so far are lost.
pub fn readUntilDelimiterOrEofAlloc(
self: Self,
allocator: *mem.Allocator,
delimiter: u8,
max_size: usize,
) ![]u8 {
var array_list = std.ArrayList(u8).init(allocator);
defer array_list.deinit();
try self.readUntilDelimiterOrEofArrayList(&array_list, delimiter, max_size);
return array_list.toOwnedSlice();
}
/// Reads from the stream until specified byte is found. If the buffer is not
/// large enough to hold the entire contents, `error.StreamTooLong` is returned.
/// If end-of-stream is found, returns the rest of the stream. If this