diff --git a/ircd/privilege.c b/ircd/privilege.c index 2f2c1cde..6ac27ada 100644 --- a/ircd/privilege.c +++ b/ircd/privilege.c @@ -91,11 +91,10 @@ privilegeset_index(struct PrivilegeSet *set) set->privs[set->size] = NULL; } -static void +void privilegeset_add_privs(struct PrivilegeSet *dst, const char *privs) { - size_t alloc_size; - size_t n; + size_t alloc_size, old_stored_size; if (dst->priv_storage == NULL) { @@ -107,6 +106,7 @@ privilegeset_add_privs(struct PrivilegeSet *dst, const char *privs) alloc_size = dst->allocated_size; } + old_stored_size = dst->stored_size; dst->stored_size += strlen(privs) + 1; while (alloc_size < dst->stored_size) @@ -119,14 +119,17 @@ privilegeset_add_privs(struct PrivilegeSet *dst, const char *privs) const char *s; char *d; - for (s = privs, d = dst->priv_storage; s < privs + strlen(privs); s += n , d += n) - { - const char *e = strchr(s, ' '); - /* up to space if there is one, else up to end of string */ - n = 1 + (e != NULL ? e - s : strlen(s)); - rb_strlcpy(d, s, n); - dst->size += 1; + for (s = privs, d = dst->priv_storage + old_stored_size; + s <= privs + strlen(privs); + s++, d++) + { + *d = *s; + if (*d == ' ' || *d == '\0') + { + *d = '\0'; + if (s > privs) dst->size += 1; + } } privilegeset_index(dst); diff --git a/tests/privilege1.c b/tests/privilege1.c index 38209673..a04cb6bb 100644 --- a/tests/privilege1.c +++ b/tests/privilege1.c @@ -28,6 +28,8 @@ #define MSG "%s:%d (%s)", __FILE__, __LINE__, __FUNCTION__ +void privilegeset_add_privs(struct PrivilegeSet *dst, const char *privs); + struct Client me; static void cleanup(void) @@ -48,6 +50,21 @@ static void test_privset_membership(void) cleanup(); } +static void test_privset_add(void) +{ + struct PrivilegeSet *set = privilegeset_set_new("test", "foo bar", 0); + privilegeset_add_privs(set, "baz qux"); + + is_bool(true, privilegeset_in_set(set, "foo"), MSG); + is_bool(true, privilegeset_in_set(set, "bar"), MSG); + is_bool(true, privilegeset_in_set(set, "baz"), MSG); + is_bool(true, privilegeset_in_set(set, "qux"), MSG); + + is_bool(false, privilegeset_in_set(set, "frob"), MSG); + + cleanup(); +} + static void test_privset_extend(void) { struct PrivilegeSet *parent = privilegeset_set_new("parent", "foo bar", 0); @@ -147,6 +164,7 @@ int main(int argc, char *argv[]) plan_lazy(); test_privset_membership(); + test_privset_add(); test_privset_extend(); test_privset_persistence(); test_privset_diff();