From 1c30fb42d258e28d4335e34a9e0231058ed3bc89 Mon Sep 17 00:00:00 2001 From: Michael Debertol Date: Tue, 10 Aug 2021 23:31:42 +0200 Subject: [PATCH] chgrp: handle empty group --- src/uu/chgrp/src/chgrp.rs | 27 +++++++++++++-------------- src/uu/install/src/install.rs | 2 +- src/uucore/src/lib/features/perms.rs | 3 ++- tests/by-util/test_chgrp.rs | 7 +++++++ 4 files changed, 23 insertions(+), 16 deletions(-) diff --git a/src/uu/chgrp/src/chgrp.rs b/src/uu/chgrp/src/chgrp.rs index 489be59eb..d351eb2bb 100644 --- a/src/uu/chgrp/src/chgrp.rs +++ b/src/uu/chgrp/src/chgrp.rs @@ -161,12 +161,9 @@ pub fn uumain(args: impl uucore::Args) -> i32 { Verbosity::Normal }; - let dest_gid: u32; - if let Some(file) = matches.value_of(options::REFERENCE) { + let dest_gid = if let Some(file) = matches.value_of(options::REFERENCE) { match fs::metadata(&file) { - Ok(meta) => { - dest_gid = meta.gid(); - } + Ok(meta) => Some(meta.gid()), Err(e) => { show_error!("failed to get attributes of '{}': {}", file, e); return 1; @@ -174,16 +171,18 @@ pub fn uumain(args: impl uucore::Args) -> i32 { } } else { let group = matches.value_of(options::ARG_GROUP).unwrap_or_default(); - match entries::grp2gid(group) { - Ok(g) => { - dest_gid = g; - } - _ => { - show_error!("invalid group: {}", group); - return 1; + if group.is_empty() { + None + } else { + match entries::grp2gid(group) { + Ok(g) => Some(g), + _ => { + show_error!("invalid group: {}", group); + return 1; + } } } - } + }; let executor = Chgrper { bit_flag, @@ -278,7 +277,7 @@ pub fn uu_app() -> App<'static, 'static> { } struct Chgrper { - dest_gid: gid_t, + dest_gid: Option, bit_flag: u8, verbosity: Verbosity, files: Vec, diff --git a/src/uu/install/src/install.rs b/src/uu/install/src/install.rs index 8ce219f7a..df273405f 100644 --- a/src/uu/install/src/install.rs +++ b/src/uu/install/src/install.rs @@ -660,7 +660,7 @@ fn copy(from: &Path, to: &Path, b: &Behavior) -> UResult<()> { Ok(g) => g, _ => return Err(InstallError::NoSuchGroup(b.group.clone()).into()), }; - match wrap_chgrp(to, &meta, group_id, false, Verbosity::Normal) { + match wrap_chgrp(to, &meta, Some(group_id), false, Verbosity::Normal) { Ok(n) => { if !n.is_empty() { show_error!("{}", n); diff --git a/src/uucore/src/lib/features/perms.rs b/src/uucore/src/lib/features/perms.rs index 89c30b53b..69491c297 100644 --- a/src/uucore/src/lib/features/perms.rs +++ b/src/uucore/src/lib/features/perms.rs @@ -49,13 +49,14 @@ fn chgrp>(path: P, gid: gid_t, follow: bool) -> IOResult<()> { pub fn wrap_chgrp>( path: P, meta: &Metadata, - dest_gid: gid_t, + dest_gid: Option, follow: bool, verbosity: Verbosity, ) -> Result { use self::Verbosity::*; let path = path.as_ref(); let mut out: String = String::new(); + let dest_gid = dest_gid.unwrap_or_else(|| meta.gid()); if let Err(e) = chgrp(path, dest_gid, follow) { match verbosity { diff --git a/tests/by-util/test_chgrp.rs b/tests/by-util/test_chgrp.rs index 762e922c4..e887f659d 100644 --- a/tests/by-util/test_chgrp.rs +++ b/tests/by-util/test_chgrp.rs @@ -228,3 +228,10 @@ fn test_big_h() { ); } } + +#[test] +fn test_no_change() { + let (at, mut ucmd) = at_and_ucmd!(); + at.touch("file"); + ucmd.arg("").arg(at.plus("file")).succeeds(); +}