diff options
author | 2024-04-24 05:49:53 -0400 | |
---|---|---|
committer | 2024-04-24 05:49:53 -0400 | |
commit | 9d3ec1cffb76141b4706bb289beced8b04ecac4a (patch) | |
tree | 0a8f3462b82f24e87151a4c77d39d4ece8bf6e08 | |
parent | 4e2c9c065a06bf9cb5d7dd46e3b29f62a1c20057 (diff) | |
download | bytes-9d3ec1cffb76141b4706bb289beced8b04ecac4a.tar.gz bytes-9d3ec1cffb76141b4706bb289beced8b04ecac4a.tar.zst bytes-9d3ec1cffb76141b4706bb289beced8b04ecac4a.zip |
Resize refactor (#696)
* use checked_sub
* return when additional == 0
* move safe operation out of unsafe block
* use spare_capacity_mut instead of chunk_mut
We don't need to check capacity because it's already been reserved
above.
* Add safety comments
* refactor to use guard clauses
This would be better written with let-else, but we won't get that until
`MSRV >= 1.65.x`.
* use if-let instead of unwrap
* reduce scope of unsafe blocks
Co-authored-by: Alice Ryhl <aliceryhl@google.com>
---------
Co-authored-by: Alice Ryhl <aliceryhl@google.com>
-rw-r--r-- | src/bytes_mut.rs | 26 |
1 files changed, 17 insertions, 9 deletions
diff --git a/src/bytes_mut.rs b/src/bytes_mut.rs index 0248df8..0ea0272 100644 --- a/src/bytes_mut.rs +++ b/src/bytes_mut.rs @@ -468,18 +468,26 @@ impl BytesMut { /// assert_eq!(&buf[..], &[0x1, 0x1, 0x3, 0x3]); /// ``` pub fn resize(&mut self, new_len: usize, value: u8) { - let len = self.len(); - if new_len > len { - let additional = new_len - len; - self.reserve(additional); - unsafe { - let dst = self.chunk_mut().as_mut_ptr(); - ptr::write_bytes(dst, value, additional); - self.set_len(new_len); - } + let additional = if let Some(additional) = new_len.checked_sub(self.len()) { + additional } else { self.truncate(new_len); + return; + }; + + if additional == 0 { + return; } + + self.reserve(additional); + let dst = self.spare_capacity_mut().as_mut_ptr(); + // SAFETY: `spare_capacity_mut` returns a valid, properly aligned pointer and we've + // reserved enough space to write `additional` bytes. + unsafe { ptr::write_bytes(dst, value, additional) }; + + // SAFETY: There are at least `new_len` initialized bytes in the buffer so no + // uninitialized bytes are being exposed. + unsafe { self.set_len(new_len) }; } /// Sets the length of the buffer. |