Skip to content

Commit 8bc47e1

Browse files
committed
code review updates
1 parent d042f87 commit 8bc47e1

File tree

2 files changed

+35
-2
lines changed

2 files changed

+35
-2
lines changed

src/s3/http.rs

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -234,8 +234,8 @@ impl Default for BaseUrl {
234234
fn default() -> Self {
235235
Self {
236236
https: true,
237-
host: String::default(),
238-
port: u16::default(),
237+
host: "127.0.0.1".to_string(),
238+
port: 9000,
239239
region: "".to_string(),
240240
aws_s3_prefix: "".to_string(),
241241
aws_domain_suffix: "".to_string(),

src/s3/utils.rs

Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,39 @@ pub fn sha256_hash(data: &[u8]) -> String {
9595
}
9696
}
9797

98+
/// Hex-encode a byte slice into a lowercase ASCII string.
99+
///
100+
/// # Safety
101+
/// This implementation uses `unsafe` code for performance reasons:
102+
/// - We call [`String::as_mut_vec`] to get direct access to the
103+
/// underlying `Vec<u8>` backing the `String`.
104+
/// - We then use [`set_len`] to pre-allocate the final length without
105+
/// initializing the contents first.
106+
/// - Finally, we use [`get_unchecked`] and [`get_unchecked_mut`] to
107+
/// avoid bounds checking inside the tight encoding loop.
108+
///
109+
/// # Why unsafe is needed
110+
/// Normally, writing this function with safe Rust requires:
111+
/// - Pushing each hex digit one-by-one into the string (extra bounds checks).
112+
/// - Or allocating and copying temporary buffers.
113+
///
114+
/// Using `unsafe` avoids redundant checks and makes this implementation
115+
/// significantly faster, especially for large inputs.
116+
///
117+
/// # Why this is correct
118+
/// - `s` is allocated with exactly `len * 2` capacity, and we immediately
119+
/// set its length to that value. Every byte in the string buffer will be
120+
/// initialized before being read or used.
121+
/// - The loop index `i` is always in `0..len`, so `bytes.get_unchecked(i)`
122+
/// is safe.
123+
/// - Each write goes to positions `j` and `j + 1`, where `j = i * 2`.
124+
/// Since `i < len`, the maximum write index is `2*len - 1`, which is
125+
/// within the allocated range.
126+
/// - All written bytes come from the `LUT` table, which has exactly 16
127+
/// elements, and indices are masked into the 0–15 range.
128+
///
129+
/// Therefore, although `unsafe` is used to skip bounds checking,
130+
/// the logic ensures all memory accesses remain in-bounds and initialized.
98131
pub fn hex_encode(bytes: &[u8]) -> String {
99132
const LUT: &[u8; 16] = b"0123456789abcdef";
100133
let len = bytes.len();

0 commit comments

Comments
 (0)