Skip to content

Commit

Permalink
Add ExtSlice::escape_debug_into
Browse files Browse the repository at this point in the history
Add a method to the `ExtSlice` trait that supports writing the `BStr`
escaped representation into a `fmt::Write`. This enables extracting the
escaped `String` into a buffer without going through `fmt::Debug`.

The written `String` does not contain the surrounding quotes present in
the `fmt::Debug` implementation.

Fixes BurntSushiGH-34.
  • Loading branch information
lopopolo committed Feb 2, 2020
1 parent f8a6c70 commit 03fc158
Showing 1 changed file with 39 additions and 0 deletions.
39 changes: 39 additions & 0 deletions src/ext_slice.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ use std::borrow::Cow;
#[cfg(feature = "std")]
use std::ffi::OsStr;
#[cfg(feature = "std")]
use std::fmt;
#[cfg(feature = "std")]
use std::path::Path;

use core::cmp;
Expand Down Expand Up @@ -429,6 +431,43 @@ pub trait ByteSlice: Sealed {
}
}

/// Write a UTF-8 debug representation of a potentially UTF-8 invalid
/// sequence.
///
/// This method encodes a bytes slice into a UTF-8 valid representation by
/// writing invalid sequences as `\xXX` escape codes.
///
/// This method uses `char::escape_debug` which means UTF-8 valid characters
/// like `\n` and `\t` are also escaped.
///
/// # Examples
///
/// Basic usage:
///
/// ```
/// use bstr::ByteSlice;
///
/// let mut message = String::from("cannot load such file -- ");
/// let filename = b"utf8-invalid-name-\xFF";
/// filename.escape_debug_into(&mut message).unwrap();
/// assert_eq!(r"cannot load such file -- utf8-invalid-name-\xFF", message);
/// ```
#[cfg(feature = "std")]
#[inline]
fn escape_debug_into<T: fmt::Write>(&self, f: &mut T) -> fmt::Result {
let buf = self.as_bstr();
for (start, end, ch) in buf.char_indices() {
if ch == '\u{FFFD}' {
for byte in buf[start..end].as_bytes() {
write!(f, r"\x{:X}", byte)?;
}
} else {
write!(f, "{}", ch.escape_debug())?;
}
}
Ok(())
}

/// Create an OS string slice from this byte string.
///
/// On Unix, this always succeeds and is zero cost. On non-Unix systems,
Expand Down

0 comments on commit 03fc158

Please sign in to comment.