lib: Add a few required includes
[samba4-gss.git] / source3 / utils / net.c
blobc432ebe991f7848bbd010d5767acbb7a23848bef
1 /*
2 Samba Unix/Linux SMB client library
3 Distributed SMB/CIFS Server Management Utility
4 Copyright (C) 2001 Steve French (sfrench@us.ibm.com)
5 Copyright (C) 2001 Jim McDonough (jmcd@us.ibm.com)
6 Copyright (C) 2001 Andrew Tridgell (tridge@samba.org)
7 Copyright (C) 2001 Andrew Bartlett (abartlet@samba.org)
8 Copyright (C) 2008 Kai Blin (kai@samba.org)
10 Originally written by Steve and Jim. Largely rewritten by tridge in
11 November 2001.
13 Reworked again by abartlet in December 2001
15 Another overhaul, moving functionality into plug-ins loaded on demand by Kai
16 in May 2008.
18 This program is free software; you can redistribute it and/or modify
19 it under the terms of the GNU General Public License as published by
20 the Free Software Foundation; either version 3 of the License, or
21 (at your option) any later version.
23 This program is distributed in the hope that it will be useful,
24 but WITHOUT ANY WARRANTY; without even the implied warranty of
25 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
26 GNU General Public License for more details.
28 You should have received a copy of the GNU General Public License
29 along with this program. If not, see <http://www.gnu.org/licenses/>. */
31 /*****************************************************/
32 /* */
33 /* Distributed SMB/CIFS Server Management Utility */
34 /* */
35 /* The intent was to make the syntax similar */
36 /* to the NET utility (first developed in DOS */
37 /* with additional interesting & useful functions */
38 /* added in later SMB server network operating */
39 /* systems). */
40 /* */
41 /*****************************************************/
43 #include "includes.h"
44 #include "lib/cmdline/cmdline.h"
45 #include "utils/net.h"
46 #include "secrets.h"
47 #include "lib/netapi/netapi.h"
48 #include "../libcli/security/security.h"
49 #include "passdb.h"
50 #include "messages.h"
51 #include "cmdline_contexts.h"
52 #include "lib/gencache.h"
53 #include "auth/credentials/credentials.h"
54 #include "source3/utils/passwd_proto.h"
55 #include "auth/gensec/gensec.h"
56 #include "lib/param/param.h"
58 #ifdef WITH_FAKE_KASERVER
59 #include "utils/net_afs.h"
60 #endif
62 /***********************************************************************/
63 /* end of internationalization section */
64 /***********************************************************************/
66 enum netr_SchannelType get_sec_channel_type(const char *param)
68 if (!(param && *param)) {
69 return get_default_sec_channel();
70 } else {
71 if (strequal(param, "PDC")) {
72 return SEC_CHAN_BDC;
73 } else if (strequal(param, "BDC")) {
74 return SEC_CHAN_BDC;
75 } else if (strequal(param, "MEMBER")) {
76 return SEC_CHAN_WKSTA;
77 #if 0
78 } else if (strequal(param, "DOMAIN")) {
79 return SEC_CHAN_DOMAIN;
80 #endif
81 } else {
82 return get_default_sec_channel();
87 static int net_changetrustpw(struct net_context *c, int argc, const char **argv)
89 net_warn_member_options();
91 if (net_ads_check_our_domain(c) == 0)
92 return net_ads_changetrustpw(c, argc, argv);
94 return net_rpc_changetrustpw(c, argc, argv);
97 static void set_line_buffering(FILE *f)
99 setvbuf(f, NULL, _IOLBF, 0);
102 static int net_primarytrust_dumpinfo(struct net_context *c, int argc,
103 const char **argv)
105 int role = lp_server_role();
106 const char *domain = lp_workgroup();
107 struct secrets_domain_info1 *info = NULL;
108 bool include_secrets = c->opt_force;
109 char *str = NULL;
110 NTSTATUS status;
112 if (role >= ROLE_ACTIVE_DIRECTORY_DC) {
113 d_printf(_("net primarytrust dumpinfo is only supported "
114 "on a DOMAIN_MEMBER for now.\n"));
115 return 1;
118 net_warn_member_options();
120 if (c->opt_stdin) {
121 set_line_buffering(stdin);
122 set_line_buffering(stdout);
123 set_line_buffering(stderr);
126 status = secrets_fetch_or_upgrade_domain_info(domain,
127 talloc_tos(),
128 &info);
129 if (!NT_STATUS_IS_OK(status)) {
130 d_fprintf(stderr,
131 _("Unable to fetch the information for domain[%s] "
132 "in the secrets database.\n"),
133 domain);
134 return 1;
137 str = secrets_domain_info_string(info, info, domain, include_secrets);
138 if (str == NULL) {
139 d_fprintf(stderr, "secrets_domain_info_string() failed.\n");
140 return 1;
143 d_printf("%s", str);
144 if (!c->opt_force) {
145 d_printf(_("The password values are only included using "
146 "-f flag.\n"));
149 TALLOC_FREE(info);
150 return 0;
154 * Entrypoint for 'net primarytrust' code.
156 * @param argc Standard argc.
157 * @param argv Standard argv without initial components.
159 * @return Integer status (0 means success).
162 static int net_primarytrust(struct net_context *c, int argc, const char **argv)
164 struct functable func[] = {
166 .funcname = "dumpinfo",
167 .fn = net_primarytrust_dumpinfo,
168 .valid_transports = NET_TRANSPORT_LOCAL,
169 .description = N_("Dump the details of the "
170 "workstation trust"),
171 .usage = N_(" net [options] primarytrust "
172 "dumpinfo'\n"
173 " Dump the details of the "
174 "workstation trust in "
175 "secrets.tdb.\n"
176 " Requires the -f flag to "
177 "include the password values."),
180 .funcname = NULL,
184 return net_run_function(c, argc, argv, "net primarytrust", func);
187 static int net_changesecretpw(struct net_context *c, int argc,
188 const char **argv)
190 char *trust_pw;
191 int role = lp_server_role();
193 if (role != ROLE_DOMAIN_MEMBER) {
194 d_printf(_("Machine account password change only supported on a DOMAIN_MEMBER.\n"
195 "Do NOT use this function unless you know what it does!\n"
196 "This function will change the ADS Domain member "
197 "machine account password in the secrets.tdb file!\n"));
198 return 1;
201 net_warn_member_options();
203 if(c->opt_force) {
204 struct secrets_domain_info1 *info = NULL;
205 struct secrets_domain_info1_change *prev = NULL;
206 NTSTATUS status;
207 struct timeval tv = timeval_current();
208 NTTIME now = timeval_to_nttime(&tv);
210 #ifdef HAVE_ADS
211 if (USE_KERBEROS_KEYTAB) {
212 if (lp_sync_machine_password_to_keytab() == NULL) {
213 lp_do_parameter(-1, "sync machine password to keytab", "disabled");
216 #endif
218 if (c->opt_stdin) {
219 set_line_buffering(stdin);
220 set_line_buffering(stdout);
221 set_line_buffering(stderr);
224 trust_pw = get_pass(_("Enter machine password: "), c->opt_stdin);
225 if (trust_pw == NULL) {
226 d_fprintf(stderr,
227 _("Error in reading machine password\n"));
228 return 1;
231 status = secrets_prepare_password_change(lp_workgroup(),
232 "localhost",
233 trust_pw,
234 talloc_tos(),
235 &info,
236 &prev,
237 #ifdef HAVE_ADS
238 sync_pw2keytabs);
239 #else
240 NULL);
241 #endif
242 if (!NT_STATUS_IS_OK(status)) {
243 d_fprintf(stderr,
244 _("Unable to write the machine account password in the secrets database"));
245 return 1;
247 if (prev != NULL) {
248 d_fprintf(stderr,
249 _("Pending machine account password change found - aborting."));
250 status = secrets_failed_password_change("localhost",
251 NT_STATUS_REQUEST_NOT_ACCEPTED,
252 NT_STATUS_NOT_COMMITTED,
253 info);
254 if (!NT_STATUS_IS_OK(status)) {
255 d_fprintf(stderr,
256 _("Failed to abort machine account password change"));
258 return 1;
260 status = secrets_finish_password_change("localhost",
261 now,
262 info,
263 #ifdef HAVE_ADS
264 sync_pw2keytabs);
265 #else
266 NULL);
267 #endif
268 if (!NT_STATUS_IS_OK(status)) {
269 d_fprintf(stderr,
270 _("Unable to write the machine account password in the secrets database"));
271 return 1;
274 d_printf(_("Modified trust account password in secrets database\n"));
276 else {
277 d_printf(_("Machine account password change requires the -f flag.\n"
278 "Do NOT use this function unless you know what it does!\n"
279 "This function will change the ADS Domain member "
280 "machine account password in the secrets.tdb file!\n"));
283 return 0;
287 * @brief Set the authorised user for winbindd access in secrets.tdb
289 static int net_setauthuser(struct net_context *c, int argc, const char **argv)
291 const char *password = NULL;
292 bool ok;
294 if (!secrets_init()) {
295 d_fprintf(stderr, _("Failed to open secrets.tdb.\n"));
296 return 1;
299 /* Delete the settings. */
300 if (argc >= 1) {
301 if (strncmp(argv[0], "delete", 6) != 0) {
302 d_fprintf(stderr,_("Usage:\n"));
303 d_fprintf(stderr,
304 _(" net setauthuser -U user[%%password] \n"
305 " Set the auth user account to user"
306 "password. Prompt for password if not "
307 "specified.\n"));
308 d_fprintf(stderr,
309 _(" net setauthuser delete\n"
310 " Delete the auth user setting.\n"));
311 return 1;
313 secrets_delete_entry(SECRETS_AUTH_USER);
314 secrets_delete_entry(SECRETS_AUTH_DOMAIN);
315 secrets_delete_entry(SECRETS_AUTH_PASSWORD);
316 return 0;
319 if (!c->explicit_credentials) {
320 d_fprintf(stderr, _("Usage:\n"));
321 d_fprintf(stderr,
322 _(" net setauthuser -U user[%%password]\n"
323 " Set the auth user account to user"
324 "password. Prompt for password if not "
325 "specified.\n"));
326 d_fprintf(stderr,
327 _(" net setauthuser delete\n"
328 " Delete the auth user setting.\n"));
329 return 1;
332 password = cli_credentials_get_password(c->creds);
333 if (password == NULL) {
334 d_fprintf(stderr,_("Failed to get the auth users password.\n"));
335 return 1;
338 ok = secrets_store_creds(c->creds);
339 if (!ok) {
340 d_fprintf(stderr, _("Failed storing auth user credentials\n"));
341 return 1;
344 return 0;
348 * @brief Get the auth user settings
350 static int net_getauthuser(struct net_context *c, int argc, const char **argv)
352 char *user, *domain, *password;
354 /* Lift data from secrets file */
356 secrets_fetch_ipc_userpass(&user, &domain, &password);
358 if ((!user || !*user) && (!domain || !*domain ) &&
359 (!password || !*password)){
361 SAFE_FREE(user);
362 SAFE_FREE(domain);
363 BURN_FREE_STR(password);
364 d_printf(_("No authorised user configured\n"));
365 return 0;
368 /* Pretty print authorised user info */
370 d_printf("%s%s%s%s%s\n", domain ? domain : "",
371 domain ? lp_winbind_separator(): "", user,
372 password ? "%" : "", password ? password : "");
374 SAFE_FREE(user);
375 SAFE_FREE(domain);
376 BURN_FREE_STR(password);
378 return 0;
381 Retrieve our local SID or the SID for the specified name
383 static int net_getlocalsid(struct net_context *c, int argc, const char **argv)
385 struct dom_sid sid;
386 const char *name;
387 struct dom_sid_buf sid_str;
389 if (argc >= 1) {
390 name = argv[0];
392 else {
393 name = lp_netbios_name();
396 if(!initialize_password_db(false, NULL)) {
397 d_fprintf(stderr, _("WARNING: Could not open passdb\n"));
398 return 1;
401 /* first check to see if we can even access secrets, so we don't
402 panic when we can't. */
404 if (!secrets_init()) {
405 d_fprintf(stderr,
406 _("Unable to open secrets.tdb. Can't fetch domain "
407 "SID for name: %s\n"), name);
408 return 1;
411 /* Generate one, if it doesn't exist */
412 get_global_sam_sid();
414 if (!secrets_fetch_domain_sid(name, &sid)) {
415 DEBUG(0, ("Can't fetch domain SID for name: %s\n", name));
416 return 1;
418 d_printf(_("SID for domain %s is: %s\n"),
419 name,
420 dom_sid_str_buf(&sid, &sid_str));
421 return 0;
424 static int net_setlocalsid(struct net_context *c, int argc, const char **argv)
426 struct dom_sid sid;
428 if ( (argc != 1)
429 || (strncmp(argv[0], "S-1-5-21-", strlen("S-1-5-21-")) != 0)
430 || (!string_to_sid(&sid, argv[0]))
431 || (sid.num_auths != 4)) {
432 d_printf(_("Usage:"));
433 d_printf(" net setlocalsid S-1-5-21-x-y-z\n");
434 return 1;
437 if (!secrets_store_domain_sid(lp_netbios_name(), &sid)) {
438 DEBUG(0,("Can't store domain SID as a pdc/bdc.\n"));
439 return 1;
442 return 0;
445 static int net_setdomainsid(struct net_context *c, int argc, const char **argv)
447 struct dom_sid sid;
449 if ( (argc != 1)
450 || (strncmp(argv[0], "S-1-5-21-", strlen("S-1-5-21-")) != 0)
451 || (!string_to_sid(&sid, argv[0]))
452 || (sid.num_auths != 4)) {
453 d_printf(_("Usage:"));
454 d_printf(" net setdomainsid S-1-5-21-x-y-z\n");
455 return 1;
458 if (!secrets_store_domain_sid(lp_workgroup(), &sid)) {
459 DEBUG(0,("Can't store domain SID.\n"));
460 return 1;
463 return 0;
466 static int net_getdomainsid(struct net_context *c, int argc, const char **argv)
468 struct dom_sid domain_sid;
469 struct dom_sid_buf sid_str;
471 if (argc > 0) {
472 d_printf(_("Usage:"));
473 d_printf(" net getdomainsid\n");
474 return 1;
477 if(!initialize_password_db(false, NULL)) {
478 d_fprintf(stderr, _("WARNING: Could not open passdb\n"));
479 return 1;
482 /* first check to see if we can even access secrets, so we don't
483 panic when we can't. */
485 if (!secrets_init()) {
486 d_fprintf(stderr, _("Unable to open secrets.tdb. Can't fetch "
487 "domain SID for name: %s\n"),
488 get_global_sam_name());
489 return 1;
492 /* Generate one, if it doesn't exist */
493 get_global_sam_sid();
495 if (!IS_DC) {
496 if (!secrets_fetch_domain_sid(lp_netbios_name(), &domain_sid)) {
497 d_fprintf(stderr, _("Could not fetch local SID\n"));
498 return 1;
500 d_printf(_("SID for local machine %s is: %s\n"),
501 lp_netbios_name(),
502 dom_sid_str_buf(&domain_sid, &sid_str));
504 if (!secrets_fetch_domain_sid(c->opt_workgroup, &domain_sid)) {
505 d_fprintf(stderr, _("Could not fetch domain SID\n"));
506 return 1;
509 d_printf(_("SID for domain %s is: %s\n"),
510 c->opt_workgroup,
511 dom_sid_str_buf(&domain_sid, &sid_str));
513 return 0;
516 static bool search_maxrid(struct pdb_search *search, const char *type,
517 uint32_t *max_rid)
519 struct samr_displayentry *entries;
520 uint32_t i, num_entries;
522 if (search == NULL) {
523 d_fprintf(stderr, _("get_maxrid: Could not search %s\n"), type);
524 return false;
527 num_entries = pdb_search_entries(search, 0, 0xffffffff, &entries);
528 for (i=0; i<num_entries; i++)
529 *max_rid = MAX(*max_rid, entries[i].rid);
530 TALLOC_FREE(search);
531 return true;
534 static uint32_t get_maxrid(void)
536 uint32_t max_rid = 0;
538 if (!search_maxrid(pdb_search_users(talloc_tos(), 0), "users", &max_rid))
539 return 0;
541 if (!search_maxrid(pdb_search_groups(talloc_tos()), "groups", &max_rid))
542 return 0;
544 if (!search_maxrid(pdb_search_aliases(talloc_tos(),
545 get_global_sam_sid()),
546 "aliases", &max_rid))
547 return 0;
549 return max_rid;
552 static int net_maxrid(struct net_context *c, int argc, const char **argv)
554 uint32_t rid;
556 if (argc != 0) {
557 d_fprintf(stderr, "%s net maxrid\n", _("Usage:"));
558 return 1;
561 if ((rid = get_maxrid()) == 0) {
562 d_fprintf(stderr, _("can't get current maximum rid\n"));
563 return 1;
566 d_printf(_("Currently used maximum rid: %d\n"), rid);
568 return 0;
571 /* main function table */
572 static struct functable net_func[] = {
574 "rpc",
575 net_rpc,
576 NET_TRANSPORT_RPC,
577 N_("Run functions using RPC transport"),
578 N_(" Use 'net help rpc' to get more extensive information "
579 "about 'net rpc' commands.")
582 "rap",
583 net_rap,
584 NET_TRANSPORT_RAP,
585 N_("Run functions using RAP transport"),
586 N_(" Use 'net help rap' to get more extensive information "
587 "about 'net rap' commands.")
590 "ads",
591 net_ads,
592 NET_TRANSPORT_ADS,
593 N_("Run functions using ADS transport"),
594 N_(" Use 'net help ads' to get more extensive information "
595 "about 'net ads' commands.")
598 /* eventually these should auto-choose the transport ... */
600 "file",
601 net_file,
602 NET_TRANSPORT_RPC | NET_TRANSPORT_RAP,
603 N_("Functions on remote opened files"),
604 N_(" Use 'net help file' to get more information about 'net "
605 "file' commands.")
608 "share",
609 net_share,
610 NET_TRANSPORT_RPC | NET_TRANSPORT_RAP,
611 N_("Functions on shares"),
612 N_(" Use 'net help share' to get more information about 'net "
613 "share' commands.")
616 "session",
617 net_rap_session,
618 NET_TRANSPORT_RAP,
619 N_("Manage sessions"),
620 N_(" Use 'net help session' to get more information about "
621 "'net session' commands.")
624 "server",
625 net_rap_server,
626 NET_TRANSPORT_RAP,
627 N_("List servers in workgroup"),
628 N_(" Use 'net help server' to get more information about 'net "
629 "server' commands.")
632 "domain",
633 net_rap_domain,
634 NET_TRANSPORT_RAP,
635 N_("List domains/workgroups on network"),
636 N_(" Use 'net help domain' to get more information about 'net "
637 "domain' commands.")
640 "printq",
641 net_rap_printq,
642 NET_TRANSPORT_RAP,
643 N_("Modify printer queue"),
644 N_(" Use 'net help printq' to get more information about 'net "
645 "printq' commands.")
648 "user",
649 net_user,
650 NET_TRANSPORT_ADS | NET_TRANSPORT_RPC | NET_TRANSPORT_RAP,
651 N_("Manage users"),
652 N_(" Use 'net help user' to get more information about 'net "
653 "user' commands.")
656 "group",
657 net_group,
658 NET_TRANSPORT_ADS | NET_TRANSPORT_RPC | NET_TRANSPORT_RAP,
659 N_("Manage groups"),
660 N_(" Use 'net help group' to get more information about 'net "
661 "group' commands.")
664 "groupmap",
665 net_groupmap,
666 NET_TRANSPORT_LOCAL,
667 N_("Manage group mappings"),
668 N_(" Use 'net help groupmap' to get more information about "
669 "'net groupmap' commands.")
672 "sam",
673 net_sam,
674 NET_TRANSPORT_LOCAL,
675 N_("Functions on the SAM database"),
676 N_(" Use 'net help sam' to get more information about 'net "
677 "sam' commands.")
680 "validate",
681 net_rap_validate,
682 NET_TRANSPORT_RAP,
683 N_("Validate username and password"),
684 N_(" Use 'net help validate' to get more information about "
685 "'net validate' commands.")
688 "groupmember",
689 net_rap_groupmember,
690 NET_TRANSPORT_RAP,
691 N_("Modify group memberships"),
692 N_(" Use 'net help groupmember' to get more information about "
693 "'net groupmember' commands.")
695 { "admin",
696 net_rap_admin,
697 NET_TRANSPORT_RAP,
698 N_("Execute remote command on a remote OS/2 server"),
699 N_(" Use 'net help admin' to get more information about 'net "
700 "admin' commands.")
702 { "service",
703 net_rap_service,
704 NET_TRANSPORT_RAP,
705 N_("List/modify running services"),
706 N_(" Use 'net help service' to get more information about "
707 "'net service' commands.")
710 "password",
711 net_rap_password,
712 NET_TRANSPORT_RAP,
713 N_("Change user password on target server"),
714 N_(" Use 'net help password' to get more information about "
715 "'net password' commands.")
718 "primarytrust",
719 net_primarytrust,
720 NET_TRANSPORT_RPC,
721 N_("Run functions related to the primary workstation trust."),
722 N_(" Use 'net help primarytrust' to get more extensive information "
723 "about 'net primarytrust' commands.")
725 { "changetrustpw",
726 net_changetrustpw,
727 NET_TRANSPORT_ADS | NET_TRANSPORT_RPC,
728 N_("Change the trust password"),
729 N_(" Use 'net help changetrustpw' to get more information "
730 "about 'net changetrustpw'.")
732 { "changesecretpw",
733 net_changesecretpw,
734 NET_TRANSPORT_LOCAL,
735 N_("Change the secret password"),
736 N_(" net [options] changesecretpw\n"
737 " Change the ADS domain member machine account password "
738 "in secrets.tdb.\n"
739 " Do NOT use this function unless you know what it does.\n"
740 " Requires the -f flag to work.")
743 "setauthuser",
744 net_setauthuser,
745 NET_TRANSPORT_LOCAL,
746 N_("Set the winbind auth user"),
747 N_(" net -U user[%%password] [-W domain] setauthuser\n"
748 " Set the auth user, password (and optionally domain\n"
749 " Will prompt for password if not given.\n"
750 " net setauthuser delete\n"
751 " Delete the existing auth user settings.")
754 "getauthuser",
755 net_getauthuser,
756 NET_TRANSPORT_LOCAL,
757 N_("Get the winbind auth user settings"),
758 N_(" net getauthuser\n"
759 " Get the current winbind auth user settings.")
761 { "time",
762 net_time,
763 NET_TRANSPORT_LOCAL,
764 N_("Show/set time"),
765 N_(" Use 'net help time' to get more information about 'net "
766 "time' commands.")
768 { "lookup",
769 net_lookup,
770 NET_TRANSPORT_LOCAL,
771 N_("Look up host names/IP addresses"),
772 N_(" Use 'net help lookup' to get more information about 'net "
773 "lookup' commands.")
775 { "g_lock",
776 net_g_lock,
777 NET_TRANSPORT_LOCAL,
778 N_("Manipulate the global lock table"),
779 N_(" Use 'net help g_lock' to get more information about "
780 "'net g_lock' commands.")
782 { "join",
783 net_join,
784 NET_TRANSPORT_ADS | NET_TRANSPORT_RPC,
785 N_("Join a domain/AD"),
786 N_(" Use 'net help join' to get more information about 'net "
787 "join'.")
789 { "offlinejoin",
790 net_offlinejoin,
791 NET_TRANSPORT_ADS | NET_TRANSPORT_RPC,
792 N_("Perform offline domain join"),
793 N_(" Use 'net help offlinejoin' to get more information about 'net "
794 "offlinejoin'.")
796 { "dom",
797 net_dom,
798 NET_TRANSPORT_LOCAL,
799 N_("Join/unjoin (remote) machines to/from a domain/AD"),
800 N_(" Use 'net help dom' to get more information about 'net "
801 "dom' commands.")
803 { "cache",
804 net_cache,
805 NET_TRANSPORT_LOCAL,
806 N_("Operate on the cache tdb file"),
807 N_(" Use 'net help cache' to get more information about 'net "
808 "cache' commands.")
810 { "getlocalsid",
811 net_getlocalsid,
812 NET_TRANSPORT_LOCAL,
813 N_("Get the SID for the local domain"),
814 N_(" net getlocalsid")
816 { "setlocalsid",
817 net_setlocalsid,
818 NET_TRANSPORT_LOCAL,
819 N_("Set the SID for the local domain"),
820 N_(" net setlocalsid S-1-5-21-x-y-z")
822 { "setdomainsid",
823 net_setdomainsid,
824 NET_TRANSPORT_LOCAL,
825 N_("Set domain SID on member servers"),
826 N_(" net setdomainsid S-1-5-21-x-y-z")
828 { "getdomainsid",
829 net_getdomainsid,
830 NET_TRANSPORT_LOCAL,
831 N_("Get domain SID on member servers"),
832 N_(" net getdomainsid")
834 { "maxrid",
835 net_maxrid,
836 NET_TRANSPORT_LOCAL,
837 N_("Display the maximum RID currently used"),
838 N_(" net maxrid")
840 { "idmap",
841 net_idmap,
842 NET_TRANSPORT_LOCAL,
843 N_("IDmap functions"),
844 N_(" Use 'net help idmap to get more information about 'net "
845 "idmap' commands.")
847 { "status",
848 net_status,
849 NET_TRANSPORT_LOCAL,
850 N_("Display server status"),
851 N_(" Use 'net help status' to get more information about 'net "
852 "status' commands.")
854 { "usershare",
855 net_usershare,
856 NET_TRANSPORT_LOCAL,
857 N_("Manage user-modifiable shares"),
858 N_(" Use 'net help usershare to get more information about "
859 "'net usershare' commands.")
861 { "usersidlist",
862 net_usersidlist,
863 NET_TRANSPORT_RPC,
864 N_("Display list of all users with SID"),
865 N_(" Use 'net help usersidlist' to get more information about "
866 "'net usersidlist'.")
868 { "conf",
869 net_conf,
870 NET_TRANSPORT_LOCAL,
871 N_("Manage Samba registry based configuration"),
872 N_(" Use 'net help conf' to get more information about 'net "
873 "conf' commands.")
875 { "registry",
876 net_registry,
877 NET_TRANSPORT_LOCAL,
878 N_("Manage the Samba registry"),
879 N_(" Use 'net help registry' to get more information about "
880 "'net registry' commands.")
882 { "eventlog",
883 net_eventlog,
884 NET_TRANSPORT_LOCAL,
885 N_("Process Win32 *.evt eventlog files"),
886 N_(" Use 'net help eventlog' to get more information about "
887 "'net eventlog' commands.")
889 { "printing",
890 net_printing,
891 NET_TRANSPORT_LOCAL,
892 N_("Process tdb printer files"),
893 N_(" Use 'net help printing' to get more information about "
894 "'net printing' commands.")
897 { "serverid",
898 net_serverid,
899 NET_TRANSPORT_LOCAL,
900 N_("Manage the serverid tdb"),
901 N_(" Use 'net help serverid' to get more information about "
902 "'net serverid' commands.")
905 { "notify",
906 net_notify,
907 NET_TRANSPORT_LOCAL,
908 N_("notifyd client code"),
909 N_(" Use 'net help notify' to get more information about "
910 "'net notify' commands.")
913 { "tdb",
914 net_tdb,
915 NET_TRANSPORT_LOCAL,
916 N_("Show information from tdb records"),
917 N_(" Use 'net help tdb' to get more information about "
918 "'net tdb' commands.")
921 { "vfs",
922 net_vfs,
923 NET_TRANSPORT_LOCAL,
924 N_("Filesystem operation through the VFS stack"),
925 N_(" Use 'net help vfs' to get more information about "
926 "'net vfs' commands.")
929 { "witness",
930 net_witness,
931 NET_TRANSPORT_LOCAL,
932 N_("Manage witness registrations"),
933 N_(" Use 'net help witness' to get more information about "
934 "'net witness' commands.")
937 #ifdef WITH_FAKE_KASERVER
938 { "afs",
939 net_afs,
940 NET_TRANSPORT_LOCAL,
941 N_("Manage AFS tokens"),
942 N_(" Use 'net help afs' to get more information about 'net "
943 "afs' commands.")
945 #endif
947 { "help",
948 net_help,
949 NET_TRANSPORT_LOCAL,
950 N_("Print usage information"),
951 N_(" Use 'net help help' to list usage information for 'net' "
952 "commands.")
954 {NULL, NULL, 0, NULL, NULL}
958 /****************************************************************************
959 main program
960 ****************************************************************************/
961 int main(int argc, char **argv)
963 int opt,i;
964 int rc = 0;
965 int argc_new = 0;
966 const char ** argv_new;
967 const char **argv_const = discard_const_p(const char *, argv);
968 poptContext pc;
969 TALLOC_CTX *frame = talloc_stackframe();
970 struct net_context *c = talloc_zero(frame, struct net_context);
971 bool ok;
973 struct poptOption long_options[] = {
975 .longName = "help",
976 .shortName = 'h',
977 .argInfo = POPT_ARG_NONE,
978 .val = 'h',
981 .longName = "target-workgroup",
982 .shortName = 'w',
983 .argInfo = POPT_ARG_STRING,
984 .arg = &c->opt_target_workgroup,
987 .longName = "ipaddress",
988 .shortName = 'I',
989 .argInfo = POPT_ARG_STRING,
990 .arg = 0,
991 .val = 'I',
994 .longName = "port",
995 .shortName = 'p',
996 .argInfo = POPT_ARG_INT,
997 .arg = &c->opt_port,
1000 .longName = "myname",
1001 .shortName = 0,
1002 .argInfo = POPT_ARG_STRING,
1003 .arg = &c->opt_requester_name,
1006 .longName = "server",
1007 .shortName = 'S',
1008 .argInfo = POPT_ARG_STRING,
1009 .arg = &c->opt_host,
1012 .longName = "container",
1013 .shortName = 'c',
1014 .argInfo = POPT_ARG_STRING,
1015 .arg = &c->opt_container,
1018 .longName = "comment",
1019 .shortName = 'C',
1020 .argInfo = POPT_ARG_STRING,
1021 .arg = &c->opt_comment,
1024 .longName = "maxusers",
1025 .shortName = 'M',
1026 .argInfo = POPT_ARG_INT,
1027 .arg = &c->opt_maxusers,
1030 .longName = "flags",
1031 .shortName = 'F',
1032 .argInfo = POPT_ARG_INT,
1033 .arg = &c->opt_flags,
1036 .longName = "long",
1037 .argInfo = POPT_ARG_NONE,
1038 .arg = &c->opt_long_list_entries,
1041 .longName = "reboot",
1042 .shortName = 'r',
1043 .argInfo = POPT_ARG_NONE,
1044 .arg = &c->opt_reboot,
1047 .longName = "force",
1048 .shortName = 'f',
1049 .argInfo = POPT_ARG_NONE,
1050 .arg = &c->opt_force,
1053 .longName = "stdin",
1054 .shortName = 'i',
1055 .argInfo = POPT_ARG_NONE,
1056 .arg = &c->opt_stdin,
1059 .longName = "timeout",
1060 .shortName = 't',
1061 .argInfo = POPT_ARG_INT,
1062 .arg = &c->opt_timeout,
1065 .longName = "request-timeout",
1066 .shortName = 0,
1067 .argInfo = POPT_ARG_INT,
1068 .arg = &c->opt_request_timeout,
1071 /* legacy for --use-winbind-ccache */
1072 .longName = "use-ccache",
1073 .shortName = 0,
1074 .argInfo = POPT_ARG_NONE,
1075 .arg = &c->legacy_opt_ccache,
1078 .longName = "verbose",
1079 .shortName = 'v',
1080 .argInfo = POPT_ARG_NONE,
1081 .arg = &c->opt_verbose,
1084 .longName = "test",
1085 .shortName = 'T',
1086 .argInfo = POPT_ARG_NONE,
1087 .arg = &c->opt_testmode,
1089 /* Options for 'net groupmap set' */
1091 .longName = "local",
1092 .shortName = 'L',
1093 .argInfo = POPT_ARG_NONE,
1094 .arg = &c->opt_localgroup,
1097 .longName = "domain",
1098 .shortName = 'D',
1099 .argInfo = POPT_ARG_NONE,
1100 .arg = &c->opt_domaingroup,
1103 .longName = "ntname",
1104 .shortName = 0,
1105 .argInfo = POPT_ARG_STRING,
1106 .arg = &c->opt_newntname,
1109 .longName = "rid",
1110 .shortName = 0,
1111 .argInfo = POPT_ARG_INT,
1112 .arg = &c->opt_rid,
1114 /* Options for 'net rpc share migrate' */
1116 .longName = "acls",
1117 .shortName = 0,
1118 .argInfo = POPT_ARG_NONE,
1119 .arg = &c->opt_acls,
1122 .longName = "attrs",
1123 .shortName = 0,
1124 .argInfo = POPT_ARG_NONE,
1125 .arg = &c->opt_attrs,
1128 .longName = "timestamps",
1129 .shortName = 0,
1130 .argInfo = POPT_ARG_NONE,
1131 .arg = &c->opt_timestamps,
1134 .longName = "exclude",
1135 .shortName = 'X',
1136 .argInfo = POPT_ARG_STRING,
1137 .arg = &c->opt_exclude,
1140 .longName = "destination",
1141 .shortName = 0,
1142 .argInfo = POPT_ARG_STRING,
1143 .arg = &c->opt_destination,
1146 .longName = "tallocreport",
1147 .shortName = 0,
1148 .argInfo = POPT_ARG_NONE,
1149 .arg = &c->do_talloc_report,
1151 /* Options for 'net rpc vampire (keytab)' */
1153 .longName = "force-full-repl",
1154 .shortName = 0,
1155 .argInfo = POPT_ARG_NONE,
1156 .arg = &c->opt_force_full_repl,
1159 .longName = "single-obj-repl",
1160 .shortName = 0,
1161 .argInfo = POPT_ARG_NONE,
1162 .arg = &c->opt_single_obj_repl,
1165 .longName = "clean-old-entries",
1166 .shortName = 0,
1167 .argInfo = POPT_ARG_NONE,
1168 .arg = &c->opt_clean_old_entries,
1170 /* Options for 'net idmap'*/
1172 .longName = "db",
1173 .shortName = 0,
1174 .argInfo = POPT_ARG_STRING,
1175 .arg = &c->opt_db,
1178 .longName = "lock",
1179 .shortName = 0,
1180 .argInfo = POPT_ARG_NONE,
1181 .arg = &c->opt_lock,
1184 .longName = "auto",
1185 .shortName = 'a',
1186 .argInfo = POPT_ARG_NONE,
1187 .arg = &c->opt_auto,
1190 .longName = "repair",
1191 .shortName = 0,
1192 .argInfo = POPT_ARG_NONE,
1193 .arg = &c->opt_repair,
1195 /* Options for 'net registry check'*/
1197 .longName = "reg-version",
1198 .shortName = 0,
1199 .argInfo = POPT_ARG_INT,
1200 .arg = &c->opt_reg_version,
1203 .longName = "output",
1204 .shortName = 'o',
1205 .argInfo = POPT_ARG_STRING,
1206 .arg = &c->opt_output,
1209 .longName = "wipe",
1210 .shortName = 0,
1211 .argInfo = POPT_ARG_NONE,
1212 .arg = &c->opt_wipe,
1214 /* Options for 'net registry import' */
1216 .longName = "precheck",
1217 .shortName = 0,
1218 .argInfo = POPT_ARG_STRING,
1219 .arg = &c->opt_precheck,
1221 /* Options for 'net ads join or leave' */
1223 .longName = "no-dns-updates",
1224 .shortName = 0,
1225 .argInfo = POPT_ARG_NONE,
1226 .arg = &c->opt_no_dns_updates,
1229 .longName = "keep-account",
1230 .shortName = 0,
1231 .argInfo = POPT_ARG_NONE,
1232 .arg = &c->opt_keep_account,
1235 .longName = "json",
1236 .shortName = 0,
1237 .argInfo = POPT_ARG_NONE,
1238 .arg = &c->opt_json,
1240 /* Options for 'net vfs' */
1242 .longName = "continue",
1243 .argInfo = POPT_ARG_NONE,
1244 .arg = &c->opt_continue_on_error,
1245 .descrip = "Continue on errors",
1248 .longName = "recursive",
1249 .argInfo = POPT_ARG_NONE,
1250 .arg = &c->opt_recursive,
1251 .descrip = "Traverse directory hierarchy",
1254 .longName = "follow-symlinks",
1255 .argInfo = POPT_ARG_NONE,
1256 .arg = &c->opt_follow_symlink,
1257 .descrip = "follow symlinks",
1259 /* Options for 'net ads dns register' */
1261 .longName = "dns-ttl",
1262 .argInfo = POPT_ARG_INT,
1263 .arg = &c->opt_dns_ttl,
1264 .descrip = "TTL in seconds of DNS records",
1266 /* Options for 'net witness {list,...}' */
1268 .longName = "witness-registration",
1269 .shortName = 0,
1270 .argInfo = POPT_ARG_STRING,
1271 .arg = &c->opt_witness_registration,
1274 .longName = "witness-net-name",
1275 .shortName = 0,
1276 .argInfo = POPT_ARG_STRING,
1277 .arg = &c->opt_witness_net_name,
1280 .longName = "witness-share-name",
1281 .shortName = 0,
1282 .argInfo = POPT_ARG_STRING,
1283 .arg = &c->opt_witness_share_name,
1286 .longName = "witness-ip-address",
1287 .shortName = 0,
1288 .argInfo = POPT_ARG_STRING,
1289 .arg = &c->opt_witness_ip_address,
1292 .longName = "witness-client-computer-name",
1293 .shortName = 0,
1294 .argInfo = POPT_ARG_STRING,
1295 .arg = &c->opt_witness_client_computer_name,
1298 .longName = "witness-apply-to-all",
1299 .shortName = 0,
1300 .argInfo = POPT_ARG_NONE,
1301 .arg = &c->opt_witness_apply_to_all,
1304 .longName = "witness-new-ip",
1305 .shortName = 0,
1306 .argInfo = POPT_ARG_STRING,
1307 .arg = &c->opt_witness_new_ip,
1310 .longName = "witness-new-node",
1311 .shortName = 0,
1312 .argInfo = POPT_ARG_INT,
1313 .arg = &c->opt_witness_new_node,
1316 .longName = "witness-forced-response",
1317 .shortName = 0,
1318 .argInfo = POPT_ARG_STRING,
1319 .arg = &c->opt_witness_forced_response,
1321 POPT_COMMON_SAMBA
1322 POPT_COMMON_CONNECTION
1323 POPT_COMMON_CREDENTIALS
1324 POPT_COMMON_VERSION
1325 POPT_LEGACY_S3
1326 POPT_TABLEEND
1329 /* Ignore possible SIGPIPE upon ldap_unbind when over TLS */
1330 BlockSignals(True, SIGPIPE);
1332 zero_sockaddr(&c->opt_dest_ip);
1333 c->opt_witness_new_node = -2;
1335 smb_init_locale();
1337 setlocale(LC_ALL, "");
1338 #if defined(HAVE_BINDTEXTDOMAIN)
1339 bindtextdomain(MODULE_NAME, get_dyn_LOCALEDIR());
1340 #endif
1341 #if defined(HAVE_TEXTDOMAIN)
1342 textdomain(MODULE_NAME);
1343 #endif
1345 ok = samba_cmdline_init(frame,
1346 SAMBA_CMDLINE_CONFIG_CLIENT,
1347 false /* require_smbconf */);
1348 if (!ok) {
1349 DBG_ERR("Failed to init cmdline parser!\n");
1350 TALLOC_FREE(frame);
1351 exit(1);
1353 c->lp_ctx = samba_cmdline_get_lp_ctx();
1354 /* set default debug level to 0 regardless of what smb.conf sets */
1355 lpcfg_set_cmdline(c->lp_ctx, "log level", "0");
1356 c->private_data = net_func;
1358 pc = samba_popt_get_context(getprogname(),
1359 argc,
1360 argv_const,
1361 long_options,
1362 POPT_CONTEXT_KEEP_FIRST);
1363 if (pc == NULL) {
1364 DBG_ERR("Failed to setup popt context!\n");
1365 TALLOC_FREE(frame);
1366 exit(1);
1369 while((opt = poptGetNextOpt(pc)) != -1) {
1370 switch (opt) {
1371 case 'h':
1372 c->display_usage = true;
1373 break;
1374 case 'I':
1375 if (!interpret_string_addr(&c->opt_dest_ip,
1376 poptGetOptArg(pc), 0)) {
1377 d_fprintf(stderr, _("\nInvalid ip address specified\n"));
1378 } else {
1379 c->opt_have_ip = true;
1381 break;
1382 default:
1383 d_fprintf(stderr, _("\nInvalid option %s: %s\n"),
1384 poptBadOption(pc, 0), poptStrerror(opt));
1385 net_help(c, argc, argv_const);
1386 exit(1);
1390 c->creds = samba_cmdline_get_creds();
1393 enum credentials_obtained principal_obtained =
1394 cli_credentials_get_principal_obtained(c->creds);
1395 enum credentials_obtained password_obtained =
1396 cli_credentials_get_password_obtained(c->creds);
1398 if (principal_obtained == CRED_SPECIFIED) {
1399 c->explicit_credentials = true;
1401 if (password_obtained == CRED_SPECIFIED) {
1402 c->explicit_credentials = true;
1405 c->opt_workgroup = cli_credentials_get_domain(c->creds);
1407 if (c->legacy_opt_ccache) {
1408 cli_credentials_add_gensec_features(
1409 c->creds,
1410 GENSEC_FEATURE_NTLM_CCACHE,
1411 CRED_SPECIFIED);
1415 c->msg_ctx = cmdline_messaging_context(get_dyn_CONFIGFILE());
1417 #if defined(HAVE_BIND_TEXTDOMAIN_CODESET)
1418 /* Bind our gettext results to 'unix charset'
1420 This ensures that the translations and any embedded strings are in the
1421 same charset. It won't be the one from the user's locale (we no
1422 longer auto-detect that), but it will be self-consistent.
1424 bind_textdomain_codeset(MODULE_NAME, lp_unix_charset());
1425 #endif
1427 argv_new = (const char **)poptGetArgs(pc);
1429 argc_new = argc;
1430 for (i=0; i<argc; i++) {
1431 if (argv_new[i] == NULL) {
1432 argc_new = i;
1433 break;
1437 if (c->do_talloc_report) {
1438 talloc_enable_leak_report();
1441 if (c->opt_requester_name) {
1442 lpcfg_set_cmdline(c->lp_ctx, "netbios name", c->opt_requester_name);
1445 if (!c->opt_target_workgroup) {
1446 c->opt_target_workgroup = talloc_strdup(c, lp_workgroup());
1449 load_interfaces();
1451 /* this makes sure that when we do things like call scripts,
1452 that it won't assert because we are not root */
1453 sec_init();
1455 samba_cmdline_burn(argc, argv);
1457 rc = net_run_function(c, argc_new-1, argv_new+1, "net", net_func);
1459 DEBUG(2,("return code = %d\n", rc));
1461 libnetapi_free(c->netapi_ctx);
1463 poptFreeContext(pc);
1465 cmdline_messaging_context_free();
1467 gfree_all();
1469 TALLOC_FREE(frame);
1470 return rc;