authorgravatar for igor.anic@gmail.comIgor Anić <igor.anic@gmail.com> 2024-07-11 17:01:39+02:00
committergravatar for andrew@ziglang.orgAndrew Kelley <andrew@ziglang.org> 2024-07-12 03:07:15-04:00
logca752c61c08eaa06458bdc6fa3cc724c09a62f77
treec24949196cded72c8aba71800fb95b0702e96560
parent80d7e260d78400b841f15e3350473650b87931a5

tls.Client: fix out of bounds panic

When calculating how much ciphertext from the stream can fit into user and internal buffers we should also take into account ciphertext data which are already in internal buffer. Fixes: 15226 Tested with [this](https://github.com/ziglang/zig/issues/15226#issuecomment-2218809140). Using client with different read buffers until I, hopefully, understood what is happening. Not relevant to this fix, but this [part](https://github.com/ziglang/zig/blob/95d9292a7a09ed883e65510ec054619747315c48/lib/std/crypto/tls/Client.zig#L988-L991) is still mystery to me. Why we don't use free_size in buf_cap calculation. Seems like rudiment from previous implementation without iovec.

1 files changed, 1 insertions(+), 1 deletions(-)

lib/std/crypto/tls/Client.zig+1-1
...@@ -1012,7 +1012,7 @@ pub fn readvAdvanced(c: *Client, stream: anytype, iovecs: []const std.posix.iove...@@ -1012,7 +1012,7 @@ pub fn readvAdvanced(c: *Client, stream: anytype, iovecs: []const std.posix.iove
1012 // Cleartext capacity of output buffer, in records. Minimum one full record.1012 // Cleartext capacity of output buffer, in records. Minimum one full record.
1013 const buf_cap = @max(cleartext_buf_len / max_ciphertext_len, 1);1013 const buf_cap = @max(cleartext_buf_len / max_ciphertext_len, 1);
1014 const wanted_read_len = buf_cap * (max_ciphertext_len + tls.record_header_len);1014 const wanted_read_len = buf_cap * (max_ciphertext_len + tls.record_header_len);
1015 const ask_len = @max(wanted_read_len, cleartext_stack_buffer.len);1015 const ask_len = @max(wanted_read_len, cleartext_stack_buffer.len) - c.partial_ciphertext_end;
1016 const ask_iovecs = limitVecs(&ask_iovecs_buf, ask_len);1016 const ask_iovecs = limitVecs(&ask_iovecs_buf, ask_len);
1017 const actual_read_len = try stream.readv(ask_iovecs);1017 const actual_read_len = try stream.readv(ask_iovecs);
1018 if (actual_read_len == 0) {1018 if (actual_read_len == 0) {