]> granicus.if.org Git - sudo/commitdiff
Use an iterator instead of fragile pointer arithmetic to iterate
authorTodd C. Miller <Todd.Miller@sudo.ws>
Sat, 10 Feb 2018 05:06:56 +0000 (22:06 -0700)
committerTodd C. Miller <Todd.Miller@sudo.ws>
Sat, 10 Feb 2018 05:06:56 +0000 (22:06 -0700)
over value arrays in sudo_ldap_role_to_priv().

plugins/sudoers/ldap.c
plugins/sudoers/ldap_common.c
plugins/sudoers/sssd.c
plugins/sudoers/sudo_ldap.h

index a781635aa24ce1603487beb35d09c90dcb92482b..9498454f201a4fe5c039312edbdc7a9ece708fd9 100644 (file)
@@ -2311,6 +2311,16 @@ sudo_ldap_display_bound_defaults(struct sudo_nss *nss, struct passwd *pw,
     debug_return_int(0);
 }
 
+static char *
+berval_iter(void *base, void **save)
+{
+    struct berval **bv;
+
+    bv = *save ? *save : base;
+    *save = bv + 1;
+    return *bv ? (*bv)->bv_val : NULL;
+}
+
 static struct userspec_list *
 ldap_to_sudoers(LDAP *ld, struct ldap_result *lres)
 {
@@ -2368,8 +2378,7 @@ ldap_to_sudoers(LDAP *ld, struct ldap_result *lres)
 
        priv = sudo_ldap_role_to_priv(cn, runasusers, runasgroups,
            cmnds, opts, notbefore ? notbefore[0]->bv_val : NULL,
-           notafter ? notafter[0]->bv_val : NULL,
-           sizeof(struct berval *), offsetof(struct berval, bv_val));
+           notafter ? notafter[0]->bv_val : NULL, berval_iter);
 
        /* Cleanup */
        if (cn != NULL)
index fa14308c843dfc9e46176409db037ff451b9b59a..144d24e9124a266aa5f06252a145382f7cc3db72 100644 (file)
@@ -117,19 +117,19 @@ sudo_ldap_parse_option(char *optstr, char **varp, char **valp)
  * The caller is responsible for freeing the returned struct member_list.
  */
 static struct member_list *
-array_to_member_list(void *a, size_t ele_size, size_t str_off)
+array_to_member_list(void *a, sudo_ldap_iter_t iter)
 {
     struct member_list *members;
     struct member *m;
+    void *save = NULL;
+    char *val;
     debug_decl(bv_to_member_list, SUDOERS_DEBUG_LDAP)
 
     if ((members = calloc(1, sizeof(*members))) == NULL)
        return NULL;
     TAILQ_INIT(members);                      
 
-    for (;*((char **)a) != NULL; a = (char *)a + ele_size) {
-       char *val = *(char **)(*((char **)a) + str_off);
-
+    while ((val = iter(a, &save)) != NULL) {
        if ((m = calloc(1, sizeof(*m))) == NULL)
            goto bad;
 
@@ -173,13 +173,15 @@ bad:
 struct privilege *
 sudo_ldap_role_to_priv(const char *cn, void *runasusers, void *runasgroups,
     void *cmnds, void *opts, const char *notbefore,
-    const char *notafter, size_t ele_size, size_t str_off)
+    const char *notafter, sudo_ldap_iter_t iter)
 {
     struct cmndspec *cmndspec = NULL;
     struct cmndspec *prev_cmndspec = NULL;
     struct sudo_command *c;
     struct privilege *priv;
     struct member *m;
+    void *cmnds_save = NULL;
+    char *cmnd;
     debug_decl(sudo_ldap_role_to_priv, SUDOERS_DEBUG_LDAP)
 
     if ((priv = calloc(1, sizeof(*priv))) == NULL)
@@ -200,12 +202,8 @@ sudo_ldap_role_to_priv(const char *cn, void *runasusers, void *runasgroups,
 
     /*
      * Parse sudoCommands and add to cmndlist.
-     * The convoluted pointer arithmetic is to support passing in
-     * either a struct berval ** or a char ***.
-     * An interator would probably be better.
      */
-    for (;*((char **)cmnds) != NULL; cmnds = (char *)cmnds + ele_size) {
-       char *cmnd = *(char **)(*((char **)cmnds) + str_off);
+    while ((cmnd = iter(cmnds, &cmnds_save)) != NULL) {
        char *args;
 
        /* Allocate storage upfront. */
@@ -256,7 +254,7 @@ sudo_ldap_role_to_priv(const char *cn, void *runasusers, void *runasgroups,
            /* Parse sudoRunAsUser / sudoRunAs */
            if (runasusers != NULL) {
                cmndspec->runasuserlist =
-                   array_to_member_list(runasusers, ele_size, str_off);
+                   array_to_member_list(runasusers, iter);
                if (cmndspec->runasuserlist == NULL)
                    goto oom;
            }
@@ -264,7 +262,7 @@ sudo_ldap_role_to_priv(const char *cn, void *runasusers, void *runasgroups,
            /* Parse sudoRunAsGroup */
            if (runasgroups != NULL) {
                cmndspec->runasgrouplist =
-                   array_to_member_list(runasgroups, ele_size, str_off);
+                   array_to_member_list(runasgroups, iter);
                if (cmndspec->runasgrouplist == NULL)
                    goto oom;
            }
@@ -277,8 +275,10 @@ sudo_ldap_role_to_priv(const char *cn, void *runasusers, void *runasgroups,
 
            /* Parse sudoOptions. */
            if (opts != NULL) {
-               for (; *((char **)opts) != NULL; opts = (char *)opts + ele_size) {
-                   char *opt = *(char **)(*((char **)opts) + str_off);
+               void *opts_save = NULL;
+               char *opt;
+
+               while ((opt = iter(opts, &opts_save)) != NULL) {
                    char *var, *val;
                    int op;
 
index c1fd1ec9780e12edab518de74f59456e8c44e6a9..d932858b30d20212eefa061376ed11d80eab47b2 100644 (file)
@@ -1408,6 +1408,17 @@ sudo_sss_display_bound_defaults(struct sudo_nss *nss,
     debug_return_int(0);
 }
 
+static char *
+val_array_iter(void *base, void **save)
+{
+    char **val_array;
+
+    val_array = *save ? *save : base;
+    *save = val_array + 1;
+
+    return *val_array;
+}
+
 static struct userspec_list *
 sss_to_sudoers(struct sudo_sss_handle *handle, struct sss_sudo_result *sss_result)
 {
@@ -1466,10 +1477,9 @@ sss_to_sudoers(struct sudo_sss_handle *handle, struct sss_sudo_result *sss_resul
        /* Parse sudoOptions. */
        handle->fn_get_values(rule, "sudoOption", &opts);
 
-       priv = sudo_ldap_role_to_priv(cn, runasusers ? &runasusers : NULL,
-           runasgroups ? &runasgroups: NULL, &cmnds, opts ? &opts : NULL,
+       priv = sudo_ldap_role_to_priv(cn, runasusers, runasgroups, cmnds, opts,
            notbefore ? notbefore[0] : NULL, notafter ? notafter[0] : NULL,
-           sizeof(char **), 0);
+           val_array_iter);
 
        /* Cleanup */
        if (cn_array != NULL)
index 8904433f0af4009ab651d6a2f44e96ca37e7a155..1eb567943c5759c0cef302084356e89d9560c1ec 100644 (file)
 #ifndef SUDOERS_LDAP_H
 #define SUDOERS_LDAP_H
 
+typedef char * (*sudo_ldap_iter_t)(void *, void **);
+
 bool sudo_ldap_is_negated(char **valp);
 int sudo_ldap_parse_option(char *optstr, char **varp, char **valp);
-struct privilege *sudo_ldap_role_to_priv(const char *cn, void *runasusers, void *runasgroups, void *cmnds, void *opts, const char *notbefore, const char *notafter, size_t ele_size, size_t str_off);
+struct privilege *sudo_ldap_role_to_priv(const char *cn, void *runasusers, void *runasgroups, void *cmnds, void *opts, const char *notbefore, const char *notafter, sudo_ldap_iter_t iter);
 struct sudo_digest *sudo_ldap_extract_digest(char **cmnd, struct sudo_digest *digest);
 
 #endif /* SUDOERS_LDAP_H */