commit: 3452bf237ba357bcc76bfda0db4c90ccd5bd4403
parent 17b2f2278b39c9259505179d64c8ec38c1c64fb4
Author: Haelwenn (lanodan) Monnier <contact@hacktivis.me>
Date: Sat, 8 Nov 2025 19:37:43 +0100
libutils/mode: use `|=` instead of `=` for applying `g[-+=]s` mode
Diffstat:
3 files changed, 28 insertions(+), 12 deletions(-)
diff --git a/libutils/mode.c b/libutils/mode.c
@@ -155,14 +155,18 @@ new_mode(const char *mode, mode_t old, const char **errstr)
}
// ((^|,)[ugoa]*([+-=]|[ugo]|[rwxXst]+)+)+
- struct modes_meta meta = {.dest = WHO_RST,
- .op = OP_RST,
- .new_modes = {
- .set = (old & 07000) >> 9,
- .user = (old & 00700) >> 6,
- .group = (old & 00070) >> 3,
- .other = (old & 00007) >> 0,
- }};
+ // clang-format off
+ struct modes_meta meta = {
+ .dest = WHO_RST,
+ .op = OP_RST,
+ .new_modes = {
+ .set = (old & 07000) >> 9,
+ .user = (old & 00700) >> 6,
+ .group = (old & 00070) >> 3,
+ .other = (old & 00007) >> 0,
+ }
+ };
+ // clang-format on
for(size_t i = 0; i < mode_len; i++)
{
@@ -253,8 +257,9 @@ new_mode(const char *mode, mode_t old, const char **errstr)
*errstr = "perm 's' given without operator";
return 0;
}
- mode_t set_id = S_ISUID >> 9;
- if(FIELD_MATCH(meta.dest, WHO_GROUP)) set_id = S_ISGID >> 9;
+ mode_t set_id = 0;
+ if(meta.dest != WHO_GROUP) set_id = S_ISUID >> 9;
+ if(FIELD_MATCH(meta.dest, WHO_GROUP)) set_id |= S_ISGID >> 9;
switch(meta.op)
{
diff --git a/test-cmd/chmod.sh b/test-cmd/chmod.sh
@@ -2,7 +2,7 @@
# SPDX-FileCopyrightText: 2017 Haelwenn (lanodan) Monnier <contact+utils@hacktivis.me>
# SPDX-License-Identifier: MPL-2.0
-plans=15
+plans=17
WD="$(dirname "$0")/../"
target="${WD}/cmd/chmod"
. "${WD}/test-cmd/tap.sh"
@@ -46,6 +46,12 @@ t 'mode:+t' "-v +t $tmpfile" "chmod: Permissions changed from 00133/---x-wx-wx t
t 'mode:-t' "-v -t $tmpfile" "${dash_warn}chmod: Permissions changed from 01133/---x-wx-wt to 00133/---x-wx-wx for '${tmpfile}'
"
+t 'ugo+s' "-v ugo+s $tmpfile" "chmod: Permissions changed from 00133/---x-wx-wx to 06133/---s-ws-wx for '${tmpfile}'
+"
+
+t 'ugo-s' "-v ugo-s $tmpfile" "chmod: Permissions changed from 06133/---s-ws-wx to 00133/---x-wx-wx for '${tmpfile}'
+"
+
t '__mode:-x,+w' "-v -- -x,+w $tmpfile" "chmod: Permissions changed from 00133/---x-wx-wx to 00222/--w--w--w- for '${tmpfile}'
"
diff --git a/test-libutils/t_mode.c b/test-libutils/t_mode.c
@@ -288,7 +288,7 @@ non_symbolic(void)
int
main(void)
{
- int plan = 161;
+ int plan = 165;
printf("1..%d\n", plan);
t_mode(NULL, 0, 0);
@@ -308,6 +308,11 @@ main(void)
t_mode("g-s", 02544, 00544);
t_mode("-t", 01544, 00544);
+ t_mode("ugo+s", 00133, 06133);
+ t_mode("ug-s", 06133, 00133);
+ t_mode("go-s", 06133, 00133);
+ t_mode("ugo-s", 06133, 00133);
+
add_read();
set_read();
del_read();