Skip to content

Commit 2e68130

Browse files
committed
cmp: avoid using advanced rust formatting for -l
Octal conversion and simple integer to string both show up in profiling. This change improves comparing ~36M completely different files wth both -l and -b by ~11-13%.
1 parent 5005741 commit 2e68130

File tree

3 files changed

+40
-8
lines changed

3 files changed

+40
-8
lines changed

Cargo.lock

Lines changed: 7 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ path = "src/main.rs"
1717
[dependencies]
1818
chrono = "0.4.38"
1919
diff = "0.1.13"
20+
itoa = "1.0.11"
2021
regex = "1.10.4"
2122
same-file = "1.0.6"
2223
unicode-width = "0.2.0"

src/cmp.rs

Lines changed: 32 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -483,6 +483,24 @@ fn is_ascii_printable(byte: u8) -> bool {
483483
c.is_ascii() && !c.is_ascii_control()
484484
}
485485

486+
#[inline]
487+
fn format_octal(byte: u8, buf: &mut [u8; 3]) -> &str {
488+
*buf = [b' ', b' ', b'0'];
489+
490+
let mut num = byte;
491+
let mut idx = 2; // Start at the last position in the buffer
492+
493+
// Generate octal digits
494+
while num > 0 {
495+
buf[idx] = b'0' + num % 8;
496+
num /= 8;
497+
idx = idx.saturating_sub(1);
498+
}
499+
500+
// SAFETY: the operations we do above always land within ascii range.
501+
unsafe { std::str::from_utf8_unchecked(&buf[..]) }
502+
}
503+
486504
#[inline]
487505
fn format_byte(byte: u8) -> String {
488506
let mut byte = byte;
@@ -520,15 +538,20 @@ fn report_verbose_diffs(diffs: Vec<(usize, u8, u8)>, params: &Params) -> Result<
520538
// Obtain the width of the first column from the last byte offset.
521539
let width = format!("{}", offset).len();
522540

541+
let mut at_byte_buf = itoa::Buffer::new();
542+
let mut from_oct = [0u8; 3]; // for octal conversions
543+
let mut to_oct = [0u8; 3];
544+
523545
if params.print_bytes {
524546
for (at_byte, from_byte, to_byte) in diffs {
547+
let at_byte_str = at_byte_buf.format(at_byte);
525548
writeln!(
526549
stdout,
527-
"{:>width$} {:>3o} {:4} {:>3o} {}",
528-
at_byte,
529-
from_byte,
550+
"{:>width$} {} {:4} {} {}",
551+
at_byte_str,
552+
format_octal(from_byte, &mut from_oct),
530553
format_byte(from_byte),
531-
to_byte,
554+
format_octal(to_byte, &mut to_oct),
532555
format_byte(to_byte),
533556
)
534557
.map_err(|e| {
@@ -540,12 +563,13 @@ fn report_verbose_diffs(diffs: Vec<(usize, u8, u8)>, params: &Params) -> Result<
540563
}
541564
} else {
542565
for (at_byte, from_byte, to_byte) in diffs {
566+
let at_byte_str = at_byte_buf.format(at_byte);
543567
writeln!(
544568
stdout,
545-
"{:>width$} {:>3o} {:>3o}",
546-
at_byte,
547-
from_byte,
548-
to_byte,
569+
"{:>width$} {} {}",
570+
at_byte_str,
571+
format_octal(from_byte, &mut from_oct),
572+
format_octal(to_byte, &mut to_oct),
549573
width = width
550574
)
551575
.map_err(|e| {

0 commit comments

Comments
 (0)