From 5e29c60b26cf8fdbef9a733601667c3f6b664c92 Mon Sep 17 00:00:00 2001 From: Sylvestre Ledru Date: Fri, 19 Jan 2024 20:34:09 +0100 Subject: [PATCH] hashsum: when the filename contains some special chars, escape them Should fix tests/cksum/md5sum-newline.pl --- src/uu/hashsum/src/hashsum.rs | 14 +++++++++++++- tests/by-util/test_hashsum.rs | 15 +++++++++++++++ 2 files changed, 28 insertions(+), 1 deletion(-) diff --git a/src/uu/hashsum/src/hashsum.rs b/src/uu/hashsum/src/hashsum.rs index 22ef4152070..5e439853a58 100644 --- a/src/uu/hashsum/src/hashsum.rs +++ b/src/uu/hashsum/src/hashsum.rs @@ -756,7 +756,9 @@ where } else if options.zero { print!("{} {}{}\0", sum, binary_marker, filename.display()); } else { - println!("{} {}{}", sum, binary_marker, filename.display()); + let (filename, has_prefix) = escape_filename(filename); + let prefix = if has_prefix { "\\" } else { "" }; + println!("{}{} {}{}", prefix, sum, binary_marker, filename); } } } @@ -781,6 +783,16 @@ where Ok(()) } +fn escape_filename(filename: &Path) -> (String, bool) { + let original = filename.as_os_str().to_string_lossy(); + let escaped = original + .replace('\\', "\\\\") + .replace('\n', "\\n") + .replace('\r', "\\r"); + let has_changed = escaped != original; + (escaped, has_changed) +} + fn digest_reader( digest: &mut Box, reader: &mut BufReader, diff --git a/tests/by-util/test_hashsum.rs b/tests/by-util/test_hashsum.rs index 31471495b07..7edd387c326 100644 --- a/tests/by-util/test_hashsum.rs +++ b/tests/by-util/test_hashsum.rs @@ -371,3 +371,18 @@ fn test_tag() { "SHA256 (foobar) = 1f2ec52b774368781bed1d1fb140a92e0eb6348090619c9291f9a5a3c8e8d151\n", ); } + +#[test] +#[cfg(not(windows))] +fn test_with_escape_filename() { + let scene = TestScenario::new(util_name!()); + + let at = &scene.fixtures; + let filename = "a\nb"; + at.touch(filename); + let result = scene.ccmd("md5sum").arg("--text").arg(filename).succeeds(); + let stdout = result.stdout_str(); + println!("stdout {}", stdout); + assert!(stdout.starts_with('\\')); + assert!(stdout.trim().ends_with("a\\nb")); +}