]> git.ipfire.org Git - thirdparty/dovecot/core.git/commitdiff
lib-auth: Changed auth_master_user_lookup() API.
authorTimo Sirainen <tss@iki.fi>
Mon, 19 Oct 2009 19:02:04 +0000 (15:02 -0400)
committerTimo Sirainen <tss@iki.fi>
Mon, 19 Oct 2009 19:02:04 +0000 (15:02 -0400)
--HG--
branch : HEAD

src/doveadm/doveadm-auth.c
src/lib-auth/auth-master.c
src/lib-auth/auth-master.h
src/lib-storage/mail-storage-service.c
src/lib-storage/mail-user.c

index f52ec41831a99b4c1879ca11d60680a91e0e1177..2077b6e2bf5173566bb0059e20177c56c447ffb5 100644 (file)
@@ -26,9 +26,7 @@ cmd_user_input(const char *auth_socket_path, const struct authtest_input *input)
 {
        struct auth_master_connection *conn;
        pool_t pool;
-       struct auth_user_reply reply;
-       const char *const *fields;
-       unsigned int i, count;
+       const char *username, *const *fields, *p;
        int ret;
 
        if (auth_socket_path == NULL)
@@ -38,7 +36,7 @@ cmd_user_input(const char *auth_socket_path, const struct authtest_input *input)
 
        conn = auth_master_init(auth_socket_path, FALSE);
        ret = auth_master_user_lookup(conn, input->username, &input->info,
-                                     pool, &reply);
+                                     pool, &username, &fields);
        if (ret < 0)
                i_fatal("userdb lookup failed");
        else if (ret == 0) {
@@ -47,21 +45,14 @@ cmd_user_input(const char *auth_socket_path, const struct authtest_input *input)
        } else {
                printf("userdb: %s\n", input->username);
 
-               if (reply.uid != (uid_t)-1)
-                       printf("uid   : %s\n", dec2str(reply.uid));
-               if (reply.gid != (gid_t)-1)
-                       printf("gid   : %s\n", dec2str(reply.gid));
-               if (reply.user != NULL)
-                       printf("user  : %s\n", reply.user);
-               if (reply.home != NULL)
-                       printf("home  : %s\n", reply.home);
-               if (reply.chroot != NULL)
-                       printf("chroot: %s\n", reply.chroot);
-               fields = array_get(&reply.extra_fields, &count);
-               if (count > 0) {
-                       printf("extra fields:\n");
-                       for (i = 0; i < count; i++)
-                               printf("  %s\n", fields[i]);
+               for (; *fields; fields++) {
+                       p = strchr(*fields, '=');
+                       if (p == NULL)
+                               printf("  %-10s\n", *fields);
+                       else {
+                               printf("  %-10s: %s\n",
+                                      t_strcut(*fields, '='), p + 1);
+                       }
                }
        }
        auth_master_deinit(&conn);
index c4864aa81fa49ea01fdd9b1eb752d6294373d87a..042449128b337bc853a46fb159ea0f093229696a 100644 (file)
@@ -48,15 +48,9 @@ struct auth_master_connection {
        unsigned int aborted:1;
 };
 
-struct auth_master_user_lookup_ctx {
-       struct auth_master_connection *conn;
-       pool_t pool;
-       struct auth_user_reply *user_reply;
-       int return_value;
-};
-
-struct auth_master_pass_lookup_ctx {
+struct auth_master_lookup_ctx {
        struct auth_master_connection *conn;
+       const char *expected_reply;
        int return_value;
 
        pool_t pool;
@@ -117,36 +111,6 @@ static void auth_request_lookup_abort(struct auth_master_connection *conn)
        conn->aborted = TRUE;
 }
 
-static void auth_parse_input(struct auth_master_user_lookup_ctx *ctx,
-                            const char *const *args)
-{
-       struct auth_user_reply *reply = ctx->user_reply;
-
-       memset(reply, 0, sizeof(*reply));
-       reply->uid = (uid_t)-1;
-       reply->gid = (gid_t)-1;
-       p_array_init(&reply->extra_fields, ctx->pool, 64);
-
-       reply->user = p_strdup(ctx->pool, *args);
-       for (args++; *args != NULL; args++) {
-               if (ctx->conn->debug)
-                       i_debug("auth input: %s", *args);
-
-               if (strncmp(*args, "uid=", 4) == 0)
-                       reply->uid = strtoul(*args + 4, NULL, 10);
-               else if (strncmp(*args, "gid=", 4) == 0)
-                       reply->gid = strtoul(*args + 4, NULL, 10);
-               else if (strncmp(*args, "home=", 5) == 0)
-                       reply->home = p_strdup(ctx->pool, *args + 5);
-               else if (strncmp(*args, "chroot=", 7) == 0)
-                       reply->chroot = p_strdup(ctx->pool, *args + 7);
-               else {
-                       const char *field = p_strdup(ctx->pool, *args);
-                       array_append(&reply->extra_fields, &field, 1);
-               }
-       }
-}
-
 static int auth_input_handshake(struct auth_master_connection *conn)
 {
        const char *line, *const *tmp;
@@ -190,14 +154,24 @@ static int parse_reply(struct auth_master_connection *conn,
        return -1;
 }
 
-static bool auth_user_reply_callback(const char *cmd, const char *const *args,
-                                    void *context)
+static bool auth_lookup_reply_callback(const char *cmd, const char *const *args,
+                                      void *context)
 {
-       struct auth_master_user_lookup_ctx *ctx = context;
+       struct auth_master_lookup_ctx *ctx = context;
+       unsigned int i, len;
+
+       ctx->return_value =
+               parse_reply(ctx->conn, cmd, args, ctx->expected_reply);
+       if (ctx->return_value > 0) {
+               len = str_array_length(args);
+               ctx->fields = p_new(ctx->pool, const char *, len + 1);
+               for (i = 0; i < len; i++) {
+                       if (ctx->conn->debug)
+                               i_debug("auth input: %s", *args);
 
-       ctx->return_value = parse_reply(ctx->conn, cmd, args, "USER");
-       if (ctx->return_value > 0)
-               auth_parse_input(ctx, args);
+                       ctx->fields[i] = p_strdup(ctx->pool, args[i]);
+               }
+       }
        return TRUE;
 }
 
@@ -423,9 +397,10 @@ auth_user_info_export(string_t *str, const struct auth_user_info *info)
 
 int auth_master_user_lookup(struct auth_master_connection *conn,
                            const char *user, const struct auth_user_info *info,
-                           pool_t pool, struct auth_user_reply *reply_r)
+                           pool_t pool, const char **username_r,
+                           const char *const **fields_r)
 {
-       struct auth_master_user_lookup_ctx ctx;
+       struct auth_master_lookup_ctx ctx;
        string_t *str;
 
        if (!is_valid_string(user) || !is_valid_string(info->service)) {
@@ -437,9 +412,9 @@ int auth_master_user_lookup(struct auth_master_connection *conn,
        ctx.conn = conn;
        ctx.return_value = -1;
        ctx.pool = pool;
-       ctx.user_reply = reply_r;
+       ctx.expected_reply = "USER";
 
-       conn->reply_callback = auth_user_reply_callback;
+       conn->reply_callback = auth_lookup_reply_callback;
        conn->reply_context = &ctx;
 
        str = t_str_new(128);
@@ -452,30 +427,49 @@ int auth_master_user_lookup(struct auth_master_connection *conn,
        (void)auth_master_run_cmd(conn, str_c(str));
        conn->prefix = DEFAULT_USERDB_LOOKUP_PREFIX;
 
+       if (ctx.return_value <= 0 || ctx.fields[0] == NULL) {
+               *username_r = NULL;
+               *fields_r = NULL;
+               if (ctx.return_value > 0) {
+                       i_error("Userdb lookup didn't return username");
+                       ctx.return_value = -1;
+               }
+       } else {
+               *username_r = ctx.fields[0];
+               *fields_r = ctx.fields + 1;
+       }
        return ctx.return_value;
 }
 
-static bool auth_pass_reply_callback(const char *cmd, const char *const *args,
-                                    void *context)
+void auth_user_fields_parse(const char *const *fields, pool_t pool,
+                           struct auth_user_reply *reply_r)
 {
-       struct auth_master_pass_lookup_ctx *ctx = context;
-       unsigned int i, len;
-
-       ctx->return_value = parse_reply(ctx->conn, cmd, args, "PASS");
-       if (ctx->return_value > 0) {
-               len = str_array_length(args);
-               ctx->fields = p_new(ctx->pool, const char *, len + 1);
-               for (i = 0; i < len; i++)
-                       ctx->fields[i] = p_strdup(ctx->pool, args[i]);
+       memset(reply_r, 0, sizeof(*reply_r));
+       reply_r->uid = (uid_t)-1;
+       reply_r->gid = (gid_t)-1;
+       p_array_init(&reply_r->extra_fields, pool, 64);
+
+       for (; *fields != NULL; fields++) {
+               if (strncmp(*fields, "uid=", 4) == 0)
+                       reply_r->uid = strtoul(*fields + 4, NULL, 10);
+               else if (strncmp(*fields, "gid=", 4) == 0)
+                       reply_r->gid = strtoul(*fields + 4, NULL, 10);
+               else if (strncmp(*fields, "home=", 5) == 0)
+                       reply_r->home = p_strdup(pool, *fields + 5);
+               else if (strncmp(*fields, "chroot=", 7) == 0)
+                       reply_r->chroot = p_strdup(pool, *fields + 7);
+               else {
+                       const char *field = p_strdup(pool, *fields);
+                       array_append(&reply_r->extra_fields, &field, 1);
+               }
        }
-       return TRUE;
 }
 
 int auth_master_pass_lookup(struct auth_master_connection *conn,
                            const char *user, const struct auth_user_info *info,
                            pool_t pool, const char *const **fields_r)
 {
-       struct auth_master_pass_lookup_ctx ctx;
+       struct auth_master_lookup_ctx ctx;
        string_t *str;
 
        if (!is_valid_string(user) || !is_valid_string(info->service)) {
@@ -487,8 +481,9 @@ int auth_master_pass_lookup(struct auth_master_connection *conn,
        ctx.conn = conn;
        ctx.return_value = -1;
        ctx.pool = pool;
+       ctx.expected_reply = "PASS";
 
-       conn->reply_callback = auth_pass_reply_callback;
+       conn->reply_callback = auth_lookup_reply_callback;
        conn->reply_context = &ctx;
 
        str = t_str_new(128);
index b12043b9e19b81dc43dec8afaefe86769752ecf3..4eaf578b9707ea5bf0039dc5c0ad7488cee44b07 100644 (file)
@@ -12,7 +12,7 @@ struct auth_user_info {
 struct auth_user_reply {
        uid_t uid;
        gid_t gid;
-       const char *user, *home, *chroot;
+       const char *home, *chroot;
        ARRAY_TYPE(const_string) extra_fields;
 };
 
@@ -23,12 +23,17 @@ void auth_master_deinit(struct auth_master_connection **conn);
 /* Do a USER lookup. Returns -1 = error, 0 = user not found, 1 = ok */
 int auth_master_user_lookup(struct auth_master_connection *conn,
                            const char *user, const struct auth_user_info *info,
-                           pool_t pool, struct auth_user_reply *reply_r);
+                           pool_t pool, const char **username_r,
+                           const char *const **fields_r);
 /* Do a PASS lookup (the actual password isn't returned). */
 int auth_master_pass_lookup(struct auth_master_connection *conn,
                            const char *user, const struct auth_user_info *info,
                            pool_t pool, const char *const **fields_r);
 
+/* Parse userdb extra fields into auth_user_reply structure. */
+void auth_user_fields_parse(const char *const *fields, pool_t pool,
+                           struct auth_user_reply *reply_r);
+
 /* Iterate through all users. */
 struct auth_master_user_list_ctx *
 auth_master_user_list_init(struct auth_master_connection *conn);
index 94fec2b3469121bbab0fdd75346341b201d1c9ac..134d955f69664db19473f31370e4bc75dd3ec609 100644 (file)
@@ -159,6 +159,7 @@ service_auth_userdb_lookup(struct auth_master_connection *conn,
        struct auth_user_info info;
        struct auth_user_reply reply;
        const char *system_groups_user, *orig_user = *user;
+       const char *new_username, *const *fields;
        unsigned int len;
        pool_t pool;
        int ret;
@@ -169,11 +170,13 @@ service_auth_userdb_lookup(struct auth_master_connection *conn,
        info.remote_ip = input->remote_ip;
 
        pool = pool_alloconly_create("userdb lookup", 1024);
-       ret = auth_master_user_lookup(conn, *user, &info, pool, &reply);
+       ret = auth_master_user_lookup(conn, *user, &info, pool,
+                                     &new_username, &fields);
        if (ret > 0) {
+               auth_user_fields_parse(fields, pool, &reply);
                len = reply.chroot == NULL ? 0 : strlen(reply.chroot);
 
-               *user = t_strdup(reply.user);
+               *user = t_strdup(new_username);
                if (user_reply_handle(set_parser, user_set, &reply,
                                      &system_groups_user, error_r) < 0)
                        ret = -1;
index e9afeac1b7e4c0994aa2a73d1a36cbf8e431f8d0..013c85f4890de7e57a82d7576b6790b9cb1cead7 100644 (file)
@@ -244,6 +244,7 @@ int mail_user_get_home(struct mail_user *user, const char **home_r)
        struct auth_user_info info;
        struct auth_user_reply reply;
        pool_t userdb_pool;
+       const char *username, *const *fields;
        int ret;
 
        memset(&info, 0, sizeof(info));
@@ -260,10 +261,11 @@ int mail_user_get_home(struct mail_user *user, const char **home_r)
 
        userdb_pool = pool_alloconly_create("userdb lookup", 512);
        ret = auth_master_user_lookup(auth_master_conn, user->username,
-                                     &info, userdb_pool, &reply);
+                                     &info, userdb_pool, &username, &fields);
        if (ret < 0)
                *home_r = NULL;
        else {
+               auth_user_fields_parse(fields, userdb_pool, &reply);
                user->_home = ret == 0 ? NULL :
                        p_strdup(user->pool, reply.home);
                user->home_looked_up = TRUE;