From 908cbf0811b0932f97a2476f7926cbd9b212377d Mon Sep 17 00:00:00 2001 From: Coro Date: Mon, 17 Aug 2026 08:25:55 -0600 Subject: [PATCH] truncate: reject a size above i64::MAX instead of creating the file An absolute size above i64::MAX passed the size calculation and was only rejected later when opening the file, with a misleading error, after the file had been created. Check it against i64::MAX up front and report an invalid number, like GNU, so nothing is created. --- src/uu/truncate/src/truncate.rs | 15 +++++++++++++++ tests/by-util/test_truncate.rs | 10 ++++++++++ 2 files changed, 25 insertions(+) diff --git a/src/uu/truncate/src/truncate.rs b/src/uu/truncate/src/truncate.rs index 2fc9928cac..289da5ac37 100644 --- a/src/uu/truncate/src/truncate.rs +++ b/src/uu/truncate/src/truncate.rs @@ -279,6 +279,21 @@ fn file_truncate( } })?; + // A size above i64::MAX is not a valid file offset; reject it up front like + // GNU, instead of creating the file and failing when it is opened. + if truncate_size > i64::MAX as u64 { + let error = match size_argument { + None => translate!("truncate-error-value-too-large"), + Some(arg) => { + translate!("truncate-error-value-too-large-arg", "arg" => arg.quote()) + } + }; + return Err(USimpleError::new( + 1, + translate!("truncate-error-invalid-number", "error" => error), + )); + } + do_file_truncate(path, !no_create, truncate_size) } diff --git a/tests/by-util/test_truncate.rs b/tests/by-util/test_truncate.rs index 2a6eb18464..2ce100c562 100644 --- a/tests/by-util/test_truncate.rs +++ b/tests/by-util/test_truncate.rs @@ -38,6 +38,16 @@ fn test_increase_file_size_kb() { assert_eq!(expected, actual, "expected '{expected}' got '{actual}'"); } +#[test] +fn test_size_above_i64_max_is_rejected_without_creating_file() { + // A size above i64::MAX is rejected up front and the file is not created. + let (at, mut ucmd) = at_and_ucmd!(); + ucmd.args(&["-s", "9223372036854775808", "new-file"]) + .fails_with_code(1) + .stderr_contains("Value too large for defined data type"); + assert!(!at.file_exists("new-file")); +} + #[test] fn test_reference() { let expected = 5 * 1000;