Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 16 additions & 10 deletions lib/addgrps.c
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
#include "shadow/grp/agetgroups.h"
#include "shadowlog.h"
#include "string/strchr/strchrscnt.h"
#include "string/strcmp/streq.h"
#include "string/strerrno.h"


Expand All @@ -35,7 +36,7 @@
int
add_groups(const char *list)
{
char *g, *p, *dup;
char *dup;
FILE *shadow_logfd = log_get_logfd();
gid_t *gids;
size_t n;
Expand All @@ -48,20 +49,25 @@ add_groups(const char *list)
if (gids == NULL)
return -1;

p = dup = strdup(list);
dup = strdup(list);
if (dup == NULL)
goto free_gids;

while (NULL != (g = strsep(&p, ",:"))) {
struct group *grp;
if (!streq(dup, "")) {
char *g, *p;

grp = getgrnam(g); /* local, no need for xgetgrnam */
if (NULL == grp) {
fprintf(shadow_logfd, _("Warning: unknown group %s\n"), g);
continue;
}
p = dup;
while (NULL != (g = strsep(&p, ",:"))) {
struct group *grp;

grp = getgrnam(g); /* local, no need for xgetgrnam */
if (NULL == grp) {
fprintf(shadow_logfd, _("Warning: unknown group %s\n"), g);
continue;
}

LSEARCH(gid_t, &grp->gr_gid, gids, &n);
LSEARCH(gid_t, &grp->gr_gid, gids, &n);
}
}
free(dup);

Expand Down
3 changes: 2 additions & 1 deletion src/groupadd.c
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@
#include "shadow/gshadow/sgrp.h"
#include "shadowlog.h"
#include "string/memset/memzero.h"
#include "string/strcmp/streq.h"
#include "string/strerrno.h"
#include "string/strtok/stpsep.h"

Expand Down Expand Up @@ -217,7 +218,7 @@ grp_update(void)
}
#endif /* SHADOWGRP */

if (user_list) {
if (user_list && !streq(user_list, "")) {
char *u, *ul;

ul = user_list;
Expand Down
24 changes: 13 additions & 11 deletions src/groupmod.c
Original file line number Diff line number Diff line change
Expand Up @@ -259,8 +259,6 @@ grp_update(void)
}

if (user_list) {
char *u, *ul;

if (!aflg) {
// requested to replace the existing groups
grp.gr_mem = xmalloc_T(1, char *);
Expand All @@ -282,18 +280,22 @@ grp_update(void)
}
#endif /* SHADOWGRP */

ul = user_list;
while (NULL != (u = strsep(&ul, ","))) {
if (prefix_getpwnam(u) == NULL) {
fprintf(stderr, _("Invalid member username %s\n"), u);
exit (E_GRP_UPDATE);
}
if (!streq(user_list, "")) {
char *u, *ul;

grp.gr_mem = add_list(grp.gr_mem, u);
ul = user_list;
while (NULL != (u = strsep(&ul, ","))) {
if (prefix_getpwnam(u) == NULL) {
fprintf(stderr, _("Invalid member username %s\n"), u);
exit(E_GRP_UPDATE);
}

grp.gr_mem = add_list(grp.gr_mem, u);
#ifdef SHADOWGRP
if (NULL != osgrp)
sgrp.sg_mem = add_list(sgrp.sg_mem, u);
if (NULL != osgrp)
sgrp.sg_mem = add_list(sgrp.sg_mem, u);
#endif /* SHADOWGRP */
}
}
}

Expand Down
30 changes: 30 additions & 0 deletions tests/system/tests/test_groupadd.py
Original file line number Diff line number Diff line change
Expand Up @@ -36,3 +36,33 @@ def test_groupadd__add_group(shadow: Shadow):
assert gshadow_entry is not None, "Group should be found"
assert gshadow_entry.name == "tgroup", "Incorrect groupname"
assert gshadow_entry.password == "!", "Incorrect password"


@pytest.mark.topology(KnownTopology.Shadow)
def test_groupadd__u_option_empty_string_clears_members(shadow: Shadow):
"""
:title: Test groupadd -U option with empty user list
:setup:
1. None required
:steps:
1. Run groupadd with -U option and empty string parameter
2. Verify group exists after creation
3. Confirm group has no members
:expectedresults:
1. groupadd -U '' command completes successfully
2. Group entry is created and accessible
3. Group member list is empty (no users assigned to group)
:customerscenario: False
"""
shadow.groupadd("-U '' tgroup")

group_entry = shadow.tools.getent.group("tgroup")
assert group_entry is not None, "Group should be found"
assert group_entry.name == "tgroup", "Incorrect groupname"
assert not group_entry.members, "Group should have no members"

if shadow.host.features["gshadow"]:
gshadow_entry = shadow.tools.getent.gshadow("tgroup")
assert gshadow_entry is not None, "Group should be found"
assert gshadow_entry.name == "tgroup", "Incorrect groupname"
assert not gshadow_entry.members, "Group should have no members"
31 changes: 31 additions & 0 deletions tests/system/tests/test_groupmod.py
Original file line number Diff line number Diff line change
Expand Up @@ -38,3 +38,34 @@ def test_groupmod__change_gid(shadow: Shadow):
assert gshadow_entry is not None, "Group should be found"
assert gshadow_entry.name == "tgroup", "Incorrect groupname"
assert gshadow_entry.password == "!", "Incorrect password"


@pytest.mark.topology(KnownTopology.Shadow)
def test_groupmod__u_option_empty_string_clears_members(shadow: Shadow):
"""
:title: Test groupmod -U option with empty user list
:setup:
1. Create test group
:steps:
1. Run groupmod with -U option and empty string parameter
2. Verify group exists after operation
3. Confirm group has no members
:expectedresults:
1. groupmod -U '' command completes successfully
2. Group entry remains valid and accessible
3. Group member list is empty (no users assigned to group)
:customerscenario: False
"""
shadow.groupadd("tgroup")
shadow.groupmod("-U '' tgroup")

group_entry = shadow.tools.getent.group("tgroup")
assert group_entry is not None, "Group should be found"
assert group_entry.name == "tgroup", "Incorrect groupname"
assert not group_entry.members, "Group should have no members"

if shadow.host.features["gshadow"]:
gshadow_entry = shadow.tools.getent.gshadow("tgroup")
assert gshadow_entry is not None, "Group should be found"
assert gshadow_entry.name == "tgroup", "Incorrect groupname"
assert not gshadow_entry.members, "Group should have no members"
Loading