s3:popt_common: simplify popt_common_credentials handling
authorStefan Metzmacher <metze@samba.org>
Fri, 21 Oct 2016 15:22:03 +0000 (17:22 +0200)
committerAndreas Schneider <asn@cryptomilk.org>
Tue, 15 Nov 2016 10:00:26 +0000 (11:00 +0100)
This offers a global 'struct user_auth_info *cmdline_auth_info',
similar to the 'cmdline_credentials' we have in
source4/lib/cmdline/popt_common.c.

And we create that in the POPT_CALLBACK_REASON_PRE stage
and finalize it in the POPT_CALLBACK_REASON_POST stage.

That means much less boring work for the callers
and more freedom to change the user_auth_info internals
in future.

Signed-off-by: Stefan Metzmacher <metze@samba.org>
Reviewed-by: Andreas Schneider <asn@samba.org>
examples/fuse/smb2mount.c
source3/client/client.c
source3/include/popt_common.h
source3/lib/popt_common.c
source3/rpcclient/rpcclient.c
source3/utils/regedit.c
source3/utils/smbcacls.c
source3/utils/smbcquotas.c
source3/utils/smbtree.c

index 2c06ed563761df0bd8f30a3a81d359a74b891a11..b90e11510940428c72292182d9a0a22a18453222 100644 (file)
@@ -25,7 +25,7 @@
 #include "libsmb/proto.h"
 #include "clifuse.h"
 
-static struct cli_state *connect_one(struct user_auth_info *auth_info,
+static struct cli_state *connect_one(const struct user_auth_info *auth_info,
                                     const char *server, const char *share)
 {
        struct cli_state *c = NULL;
@@ -37,13 +37,6 @@ static struct cli_state *connect_one(struct user_auth_info *auth_info,
                         CLI_FULL_CONNECTION_FALLBACK_AFTER_KERBEROS;
        }
 
-       if (get_cmdline_auth_info_use_machine_account(auth_info) &&
-           !set_cmdline_auth_info_machine_account_creds(auth_info)) {
-               return NULL;
-       }
-
-       set_cmdline_auth_info_getpass(auth_info);
-
        nt_status = cli_full_connection(&c, lp_netbios_name(), server,
                                NULL, 0,
                                share, "?????",
@@ -78,7 +71,6 @@ int main(int argc, char *argv[])
 {
        const char **argv_const = discard_const_p(const char *, argv);
        TALLOC_CTX *frame = talloc_stackframe();
-       struct user_auth_info *auth_info;
        poptContext pc;
        int opt, ret;
        char *unc, *mountpoint, *server, *share;
@@ -96,12 +88,6 @@ int main(int argc, char *argv[])
        lp_set_cmdline("client min protocol", "SMB2");
        lp_set_cmdline("client max protocol", "SMB3_11");
 
-       auth_info = user_auth_info_init(frame);
-       if (auth_info == NULL) {
-               exit(1);
-       }
-       popt_common_set_auth_info(auth_info);
-
        lp_load_global(get_dyn_CONFIGFILE());
        load_interfaces();
 
@@ -151,7 +137,7 @@ int main(int argc, char *argv[])
        *share = 0;
        share++;
 
-       cli = connect_one(auth_info, server, share);
+       cli = connect_one(cmdline_auth_info, server, share);
        if (cli == NULL) {
                return -1;
        }
index ecfd27c72f37cd386619186a3972e20a6ee3a8e9..b7991e42002b095623f9e11599598946327355db 100644 (file)
@@ -5753,11 +5753,7 @@ int main(int argc,char *argv[])
 
        lp_set_cmdline("log level", "1");
 
-       auth_info = user_auth_info_init(frame);
-       if (auth_info == NULL) {
-               exit(1);
-       }
-       popt_common_set_auth_info(auth_info);
+       popt_common_credentials_set_delay_post();
 
        /* skip argv(0) */
        pc = poptGetContext("smbclient", argc, const_argv, long_options, 0);
@@ -5785,9 +5781,9 @@ int main(int argc,char *argv[])
 
                /* if the service has already been retrieved then check if we have also a password */
                if (service_opt
-                   && (!get_cmdline_auth_info_got_pass(auth_info))
+                   && (!get_cmdline_auth_info_got_pass(cmdline_auth_info))
                    && poptPeekArg(pc)) {
-                       set_cmdline_auth_info_password(auth_info,
+                       set_cmdline_auth_info_password(cmdline_auth_info,
                                                       poptGetArg(pc));
                }
 
@@ -5887,9 +5883,9 @@ int main(int argc,char *argv[])
 
        /* if the service has already been retrieved then check if we have also a password */
        if (service_opt
-           && !get_cmdline_auth_info_got_pass(auth_info)
+           && !get_cmdline_auth_info_got_pass(cmdline_auth_info)
            && poptPeekArg(pc)) {
-               set_cmdline_auth_info_password(auth_info,
+               set_cmdline_auth_info_password(cmdline_auth_info,
                                               poptGetArg(pc));
        }
 
@@ -5901,11 +5897,6 @@ int main(int argc,char *argv[])
                        argv[0], get_dyn_CONFIGFILE());
        }
 
-       if (get_cmdline_auth_info_use_machine_account(auth_info) &&
-           !set_cmdline_auth_info_machine_account_creds(auth_info)) {
-               exit(-1);
-       }
-
        load_interfaces();
 
        if (service_opt && service) {
@@ -5926,7 +5917,6 @@ int main(int argc,char *argv[])
                }
        }
 
-       smb_encrypt = get_cmdline_auth_info_smb_encrypt(auth_info);
        if (!init_names()) {
                fprintf(stderr, "init_names() failed\n");
                exit(1);
@@ -5946,7 +5936,9 @@ int main(int argc,char *argv[])
        DEBUG(3,("Client started (version %s).\n", samba_version_string()));
 
        /* Ensure we have a password (or equivalent). */
-       set_cmdline_auth_info_getpass(auth_info);
+       popt_common_credentials_post();
+       auth_info = cmdline_auth_info;
+       smb_encrypt = get_cmdline_auth_info_smb_encrypt(auth_info);
 
        max_protocol = lp_client_max_protocol();
 
index 5266f369dde8493d26e6cef7df3d895ba76d8a6b..ec7568c9fc3622073678fdcdff0cd3a96011b140 100644 (file)
@@ -48,7 +48,10 @@ extern const struct poptOption popt_common_dynconfig[];
 #define POPT_COMMON_DEBUGLEVEL { NULL, 0, POPT_ARG_INCLUDE_TABLE, popt_common_debuglevel, 0, "Common samba debugging:", NULL },
 #define POPT_COMMON_OPTION { NULL, 0, POPT_ARG_INCLUDE_TABLE, popt_common_option, 0, "Common samba commandline config:", NULL },
 
-void popt_common_set_auth_info(struct user_auth_info *auth_info);
+extern struct user_auth_info *cmdline_auth_info;
+
+void popt_common_credentials_set_delay_post(void);
+void popt_common_credentials_post(void);
 void popt_burn_cmdline_password(int argc, char *argv[]);
 
 #endif /* _POPT_COMMON_H */
index b685b65f7baef6cfa79785e3ed801a1d628ed243..6c1515bfcfc7e6cbf013f1b742e4e003a15e24c0 100644 (file)
@@ -347,19 +347,46 @@ static void get_credentials_file(struct user_auth_info *auth_info,
  *             -C --use-ccache
  */
 
+struct user_auth_info *cmdline_auth_info;
+static bool popt_common_credentials_delay_post;
+
+void popt_common_credentials_set_delay_post(void)
+{
+       popt_common_credentials_delay_post = true;
+}
+
+void popt_common_credentials_post(void)
+{
+       struct user_auth_info *auth_info = cmdline_auth_info;
+
+       if (get_cmdline_auth_info_use_machine_account(auth_info) &&
+           !set_cmdline_auth_info_machine_account_creds(auth_info))
+       {
+               fprintf(stderr,
+                       "Failed to use machine account credentials\n");
+               exit(1);
+       }
+
+       set_cmdline_auth_info_getpass(auth_info);
+}
 
 static void popt_common_credentials_callback(poptContext con,
                                        enum poptCallbackReason reason,
                                        const struct poptOption *opt,
                                        const char *arg, const void *data)
 {
-       const void **pp = discard_const(data);
-       void *p = discard_const(*pp);
-       struct user_auth_info *auth_info =
-               talloc_get_type_abort(p,
-               struct user_auth_info);
+       struct user_auth_info *auth_info = cmdline_auth_info;
 
        if (reason == POPT_CALLBACK_REASON_PRE) {
+               if (auth_info == NULL) {
+                       auth_info = user_auth_info_init(talloc_autofree_context());
+                       if (auth_info == NULL) {
+                               fprintf(stderr, "user_auth_info_init() failed\n");
+                               exit(1);
+                       }
+                       cmdline_auth_info = auth_info;
+               }
+
                set_cmdline_auth_info_username(auth_info, "GUEST");
 
                if (getenv("LOGNAME")) {
@@ -384,6 +411,15 @@ static void popt_common_credentials_callback(poptContext con,
                return;
        }
 
+       if (reason == POPT_CALLBACK_REASON_POST) {
+               if (popt_common_credentials_delay_post) {
+                       return;
+               }
+
+               popt_common_credentials_post();
+               return;
+       }
+
        switch(opt->val) {
        case 'U':
                {
@@ -444,13 +480,6 @@ static void popt_common_credentials_callback(poptContext con,
        }
 }
 
-static struct user_auth_info *global_auth_info;
-
-void popt_common_set_auth_info(struct user_auth_info *auth_info)
-{
-       global_auth_info = auth_info;
-}
-
 /**
  * @brief Burn the commandline password.
  *
@@ -499,9 +528,8 @@ void popt_burn_cmdline_password(int argc, char *argv[])
 }
 
 struct poptOption popt_common_credentials[] = {
-       { NULL, 0, POPT_ARG_CALLBACK|POPT_CBFLAG_PRE,
-         (void *)popt_common_credentials_callback, 0,
-         (const void *)&global_auth_info },
+       { NULL, 0, POPT_ARG_CALLBACK|POPT_CBFLAG_PRE|POPT_CBFLAG_POST,
+         (void *)popt_common_credentials_callback, 0, NULL },
        { "user", 'U', POPT_ARG_STRING, NULL, 'U', "Set the network username", "USERNAME" },
        { "no-pass", 'N', POPT_ARG_NONE, NULL, 'N', "Don't ask for a password" },
        { "kerberos", 'k', POPT_ARG_NONE, NULL, 'k', "Use kerberos (active directory) authentication" },
index 554620b0380b9afcdd68a990b86694f4ec17dbef..a38c141b425ac3b6c273325309f016df3cf642ec 100644 (file)
@@ -974,12 +974,6 @@ out_free:
        setup_logging("rpcclient", DEBUG_STDOUT);
        lp_set_cmdline("log level", "0");
 
-       rpcclient_auth_info = user_auth_info_init(frame);
-       if (rpcclient_auth_info == NULL) {
-               exit(1);
-       }
-       popt_common_set_auth_info(rpcclient_auth_info);
-
        /* Parse options */
 
        pc = poptGetContext("rpcclient", argc, const_argv,
@@ -1018,6 +1012,7 @@ out_free:
 
        poptFreeContext(pc);
        popt_burn_cmdline_password(argc, argv);
+       rpcclient_auth_info = cmdline_auth_info;
 
        /* Load smb.conf file */
 
@@ -1051,14 +1046,6 @@ out_free:
         * from stdin if necessary
         */
 
-       if (get_cmdline_auth_info_use_machine_account(rpcclient_auth_info) &&
-           !set_cmdline_auth_info_machine_account_creds(rpcclient_auth_info)) {
-               result = 1;
-               goto done;
-       }
-
-       set_cmdline_auth_info_getpass(rpcclient_auth_info);
-
        if ((server[0] == '/' && server[1] == '/') ||
                        (server[0] == '\\' && server[1] ==  '\\')) {
                server += 2;
index 88fd74c6c35d7bc41f8996218d02a81e703a9460..476897f4e780b23de3e9fc4320c7e9428ef8dd3b 100644 (file)
@@ -765,7 +765,6 @@ int main(int argc, const char **argv)
        };
        int opt;
        poptContext pc;
-       struct user_auth_info *auth_info;
        TALLOC_CTX *frame;
        struct registry_context *ctx;
        WERROR rv;
@@ -776,11 +775,6 @@ int main(int argc, const char **argv)
        lp_set_cmdline("log level", "0");
 
        /* process options */
-       auth_info = user_auth_info_init(frame);
-       if (auth_info == NULL) {
-               exit(1);
-       }
-       popt_common_set_auth_info(auth_info);
        pc = poptGetContext("regedit", argc, argv, long_options, 0);
 
        while ((opt = poptGetNextOpt(pc)) != -1) {
index 5cb707d2d7d7c581fe24f5d48d95ea9074adb9c5..8d775271617ac9569f2230831c02152b7fe2da49 100644 (file)
@@ -733,7 +733,7 @@ static int inherit(struct cli_state *cli, const char *filename,
 /*****************************************************
  Return a connection to a server.
 *******************************************************/
-static struct cli_state *connect_one(struct user_auth_info *auth_info,
+static struct cli_state *connect_one(const struct user_auth_info *auth_info,
                                     const char *server, const char *share)
 {
        struct cli_state *c = NULL;
@@ -745,13 +745,6 @@ static struct cli_state *connect_one(struct user_auth_info *auth_info,
                         CLI_FULL_CONNECTION_FALLBACK_AFTER_KERBEROS;
        }
 
-       if (get_cmdline_auth_info_use_machine_account(auth_info) &&
-           !set_cmdline_auth_info_machine_account_creds(auth_info)) {
-               return NULL;
-       }
-
-       set_cmdline_auth_info_getpass(auth_info);
-
        nt_status = cli_full_connection(&c, lp_netbios_name(), server,
                                NULL, 0,
                                share, "?????",
@@ -829,7 +822,6 @@ int main(int argc, char *argv[])
        TALLOC_CTX *frame = talloc_stackframe();
        const char *owner_username = "";
        char *server;
-       struct user_auth_info *auth_info;
 
        smb_init_locale();
 
@@ -839,13 +831,6 @@ int main(int argc, char *argv[])
 
        setlinebuf(stdout);
 
-
-       auth_info = user_auth_info_init(frame);
-       if (auth_info == NULL) {
-               exit(1);
-       }
-       popt_common_set_auth_info(auth_info);
-
        pc = poptGetContext("smbcacls", argc, argv_const, long_options, 0);
 
        poptSetOtherOptionHelp(pc, "//server1/share1 filename\nACLs look like: "
@@ -936,7 +921,7 @@ int main(int argc, char *argv[])
        share++;
 
        if (!test_args) {
-               cli = connect_one(auth_info, server, share);
+               cli = connect_one(cmdline_auth_info, server, share);
                if (!cli) {
                        exit(EXIT_FAILED);
                }
index 8ba3cc5f78f4a5c60e3faf3dc800c9810d387b11..ba80926580a779e1ee3a3d8f17b272ae0d1c7280 100644 (file)
@@ -523,19 +523,12 @@ static struct cli_state *connect_one(const char *share)
        NTSTATUS nt_status;
        uint32_t flags = 0;
 
-       if (get_cmdline_auth_info_use_machine_account(smbcquotas_auth_info) &&
-           !set_cmdline_auth_info_machine_account_creds(smbcquotas_auth_info)) {
-               return NULL;
-       }
-
        if (get_cmdline_auth_info_use_kerberos(smbcquotas_auth_info)) {
                flags |= CLI_FULL_CONNECTION_USE_KERBEROS |
                         CLI_FULL_CONNECTION_FALLBACK_AFTER_KERBEROS;
 
        }
 
-       set_cmdline_auth_info_getpass(smbcquotas_auth_info);
-
        nt_status = cli_full_connection(&c, lp_netbios_name(), server,
                                            NULL, 0,
                                            share, "?????",
@@ -618,12 +611,6 @@ FSQFLAGS:QUOTA_ENABLED/DENY_DISK/LOG_SOFTLIMIT/LOG_HARD_LIMIT", "SETSTRING" },
 
        fault_setup();
 
-       smbcquotas_auth_info = user_auth_info_init(frame);
-       if (smbcquotas_auth_info == NULL) {
-               exit(1);
-       }
-       popt_common_set_auth_info(smbcquotas_auth_info);
-
        pc = poptGetContext("smbcquotas", argc, argv_const, long_options, 0);
 
        poptSetOtherOptionHelp(pc, "//server1/share1");
@@ -689,6 +676,7 @@ FSQFLAGS:QUOTA_ENABLED/DENY_DISK/LOG_SOFTLIMIT/LOG_HARD_LIMIT", "SETSTRING" },
        if (todo == 0)
                todo = USER_QUOTA;
 
+       smbcquotas_auth_info = cmdline_auth_info;
        if (!fix_user) {
                username_str = talloc_strdup(
                        frame, get_cmdline_auth_info_username(smbcquotas_auth_info));
index 58410e86c4025223fe29381d9b5a76b79e329389..2f11dced12e667b8894f3136f8ffe7d9537644f5 100644 (file)
@@ -79,7 +79,7 @@ static void add_name(const char *machine_name, uint32_t server_type,
 /****************************************************************************
   display tree of smb workgroups, servers and shares
 ****************************************************************************/
-static bool get_workgroups(struct user_auth_info *user_info)
+static bool get_workgroups(const struct user_auth_info *user_info)
 {
         struct cli_state *cli;
         struct sockaddr_storage server_ss;
@@ -131,7 +131,7 @@ static bool get_workgroups(struct user_auth_info *user_info)
 
 /* Retrieve the list of servers for a given workgroup */
 
-static bool get_servers(char *workgroup, struct user_auth_info *user_info)
+static bool get_servers(char *workgroup, const struct user_auth_info *user_info)
 {
         struct cli_state *cli;
         struct sockaddr_storage server_ss;
@@ -220,7 +220,7 @@ static bool get_rpc_shares(struct cli_state *cli,
 }
 
 
-static bool get_shares(char *server_name, struct user_auth_info *user_info)
+static bool get_shares(char *server_name, const struct user_auth_info *user_info)
 {
         struct cli_state *cli;
 
@@ -236,7 +236,7 @@ static bool get_shares(char *server_name, struct user_auth_info *user_info)
         return True;
 }
 
-static bool print_tree(struct user_auth_info *user_info)
+static bool print_tree(const struct user_auth_info *user_info)
 {
         struct smb_name_list *wg, *sv, *sh;
 
@@ -289,7 +289,6 @@ int main(int argc, char *argv[])
 {
        TALLOC_CTX *frame = talloc_stackframe();
        const char **argv_const = discard_const_p(const char *, argv);
-       struct user_auth_info *auth_info;
        struct poptOption long_options[] = {
                POPT_AUTOHELP
                { "broadcast", 'b', POPT_ARG_VAL, &use_bcast, True, "Use broadcast instead of using the master browser" },
@@ -308,12 +307,6 @@ int main(int argc, char *argv[])
 
        setup_logging(argv[0], DEBUG_STDERR);
 
-       auth_info = user_auth_info_init(frame);
-       if (auth_info == NULL) {
-               exit(1);
-       }
-       popt_common_set_auth_info(auth_info);
-
        pc = poptGetContext("smbtree", argc, argv_const, long_options,
                            POPT_CONTEXT_KEEP_FIRST);
        while(poptGetNextOpt(pc) != -1);
@@ -323,19 +316,9 @@ int main(int argc, char *argv[])
        lp_load_global(get_dyn_CONFIGFILE());
        load_interfaces();
 
-       /* Parse command line args */
-
-       if (get_cmdline_auth_info_use_machine_account(auth_info) &&
-           !set_cmdline_auth_info_machine_account_creds(auth_info)) {
-               TALLOC_FREE(frame);
-               return 1;
-       }
-
-       set_cmdline_auth_info_getpass(auth_info);
-
        /* Now do our stuff */
 
-        if (!print_tree(auth_info)) {
+        if (!print_tree(cmdline_auth_info)) {
                TALLOC_FREE(frame);
                 return 1;
        }