LCOV - code coverage report
Current view: top level - source3/utils - net_util.c (source / functions) Hit Total Coverage
Test: coverage report for support-claim-type-attributes 6b5c566e Lines: 76 296 25.7 %
Date: 2023-11-21 12:31:41 Functions: 10 17 58.8 %

          Line data    Source code
       1             : /*
       2             :  *  Unix SMB/CIFS implementation.
       3             :  *  Helper routines for net
       4             :  *  Copyright (C) Volker Lendecke 2006
       5             :  *  Copyright (C) Kai Blin 2008
       6             :  *
       7             :  *  This program is free software; you can redistribute it and/or modify
       8             :  *  it under the terms of the GNU General Public License as published by
       9             :  *  the Free Software Foundation; either version 3 of the License, or
      10             :  *  (at your option) any later version.
      11             :  *
      12             :  *  This program is distributed in the hope that it will be useful,
      13             :  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
      14             :  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      15             :  *  GNU General Public License for more details.
      16             :  *
      17             :  *  You should have received a copy of the GNU General Public License
      18             :  *  along with this program; if not, see <http://www.gnu.org/licenses/>.
      19             :  */
      20             : 
      21             : 
      22             : #include "includes.h"
      23             : #include "utils/net.h"
      24             : #include "libsmb/namequery.h"
      25             : #include "rpc_client/cli_pipe.h"
      26             : #include "../librpc/gen_ndr/ndr_lsa_c.h"
      27             : #include "rpc_client/cli_lsarpc.h"
      28             : #include "../librpc/gen_ndr/ndr_dssetup_c.h"
      29             : #include "secrets.h"
      30             : #include "../libcli/security/security.h"
      31             : #include "libsmb/libsmb.h"
      32             : #include "lib/param/param.h"
      33             : #include "auth/gensec/gensec.h"
      34             : #include "libcli/auth/netlogon_creds_cli.h"
      35             : #include "lib/cmdline/cmdline.h"
      36             : 
      37           0 : NTSTATUS net_rpc_lookup_name(struct net_context *c,
      38             :                              TALLOC_CTX *mem_ctx, struct cli_state *cli,
      39             :                              const char *name, const char **ret_domain,
      40             :                              const char **ret_name, struct dom_sid *ret_sid,
      41             :                              enum lsa_SidType *ret_type)
      42             : {
      43           0 :         struct rpc_pipe_client *lsa_pipe = NULL;
      44           0 :         struct policy_handle pol;
      45           0 :         NTSTATUS status, result;
      46           0 :         const char **dom_names;
      47           0 :         struct dom_sid *sids;
      48           0 :         enum lsa_SidType *types;
      49           0 :         struct dcerpc_binding_handle *b;
      50             : 
      51           0 :         ZERO_STRUCT(pol);
      52             : 
      53           0 :         status = cli_rpc_pipe_open_noauth(cli, &ndr_table_lsarpc,
      54             :                                           &lsa_pipe);
      55           0 :         if (!NT_STATUS_IS_OK(status)) {
      56           0 :                 d_fprintf(stderr, _("Could not initialise lsa pipe\n"));
      57           0 :                 return status;
      58             :         }
      59             : 
      60           0 :         b = lsa_pipe->binding_handle;
      61             : 
      62           0 :         status = rpccli_lsa_open_policy(lsa_pipe, mem_ctx, false,
      63             :                                         SEC_FLAG_MAXIMUM_ALLOWED,
      64             :                                         &pol);
      65           0 :         if (!NT_STATUS_IS_OK(status)) {
      66           0 :                 d_fprintf(stderr, "open_policy %s: %s\n", _("failed"),
      67             :                           nt_errstr(status));
      68           0 :                 return status;
      69             :         }
      70             : 
      71           0 :         status = rpccli_lsa_lookup_names(lsa_pipe, mem_ctx, &pol, 1,
      72             :                                          &name, &dom_names, 1, &sids, &types);
      73             : 
      74           0 :         if (!NT_STATUS_IS_OK(status)) {
      75             :                 /* This can happen easily, don't log an error */
      76           0 :                 goto done;
      77             :         }
      78             : 
      79           0 :         if (ret_domain != NULL) {
      80           0 :                 *ret_domain = dom_names[0];
      81             :         }
      82           0 :         if (ret_name != NULL) {
      83           0 :                 *ret_name = talloc_strdup(mem_ctx, name);
      84             :         }
      85           0 :         if (ret_sid != NULL) {
      86           0 :                 sid_copy(ret_sid, &sids[0]);
      87             :         }
      88           0 :         if (ret_type != NULL) {
      89           0 :                 *ret_type = types[0];
      90             :         }
      91             : 
      92           0 :  done:
      93           0 :         if (is_valid_policy_hnd(&pol)) {
      94           0 :                 dcerpc_lsa_Close(b, mem_ctx, &pol, &result);
      95             :         }
      96           0 :         TALLOC_FREE(lsa_pipe);
      97             : 
      98           0 :         return status;
      99             : }
     100             : 
     101             : /****************************************************************************
     102             :  Connect to \\server\service.
     103             : ****************************************************************************/
     104             : 
     105         868 : NTSTATUS connect_to_service(struct net_context *c,
     106             :                             struct cli_state **cli_ctx,
     107             :                             const struct sockaddr_storage *server_ss,
     108             :                             const char *server_name,
     109             :                             const char *service_name,
     110             :                             const char *service_type)
     111             : {
     112           0 :         NTSTATUS nt_status;
     113         868 :         int flags = 0;
     114             : 
     115         868 :         if (strequal(service_type, "IPC")) {
     116         868 :                 flags |= CLI_FULL_CONNECTION_IPC;
     117             :         }
     118             : 
     119         868 :         nt_status = cli_full_connection_creds(cli_ctx, NULL, server_name,
     120             :                                         server_ss, c->opt_port,
     121             :                                         service_name, service_type,
     122             :                                         c->creds,
     123             :                                         flags);
     124         868 :         if (!NT_STATUS_IS_OK(nt_status)) {
     125           0 :                 d_fprintf(stderr, _("Could not connect to server %s\n"),
     126             :                           server_name);
     127             : 
     128             :                 /* Display a nicer message depending on the result */
     129             : 
     130           0 :                 if (NT_STATUS_V(nt_status) ==
     131           0 :                     NT_STATUS_V(NT_STATUS_LOGON_FAILURE))
     132           0 :                         d_fprintf(stderr,
     133           0 :                                   _("The username or password was not "
     134             :                                     "correct.\n"));
     135             : 
     136           0 :                 if (NT_STATUS_V(nt_status) ==
     137           0 :                     NT_STATUS_V(NT_STATUS_ACCOUNT_LOCKED_OUT))
     138           0 :                         d_fprintf(stderr, _("The account was locked out.\n"));
     139             : 
     140           0 :                 if (NT_STATUS_V(nt_status) ==
     141           0 :                     NT_STATUS_V(NT_STATUS_ACCOUNT_DISABLED))
     142           0 :                         d_fprintf(stderr, _("The account was disabled.\n"));
     143           0 :                 return nt_status;
     144             :         }
     145             : 
     146         868 :         return nt_status;
     147             : }
     148             : 
     149             : /****************************************************************************
     150             :  Connect to \\server\ipc$.
     151             : ****************************************************************************/
     152             : 
     153         868 : NTSTATUS connect_to_ipc(struct net_context *c,
     154             :                         struct cli_state **cli_ctx,
     155             :                         const struct sockaddr_storage *server_ss,
     156             :                         const char *server_name)
     157             : {
     158         868 :         return connect_to_service(c, cli_ctx, server_ss, server_name, "IPC$",
     159             :                                   "IPC");
     160             : }
     161             : 
     162             : /****************************************************************************
     163             :  Connect to \\server\ipc$ anonymously.
     164             : ****************************************************************************/
     165             : 
     166           6 : NTSTATUS connect_to_ipc_anonymous(struct net_context *c,
     167             :                                 struct cli_state **cli_ctx,
     168             :                                 const struct sockaddr_storage *server_ss,
     169             :                                 const char *server_name)
     170             : {
     171           0 :         NTSTATUS nt_status;
     172           6 :         struct cli_credentials *anon_creds = NULL;
     173             : 
     174           6 :         anon_creds = cli_credentials_init_anon(c);
     175           6 :         if (anon_creds == NULL) {
     176           0 :                 DBG_ERR("cli_credentials_init_anon() failed\n");
     177           0 :                 return NT_STATUS_NO_MEMORY;
     178             :         }
     179             : 
     180           6 :         nt_status = cli_full_connection_creds(cli_ctx, c->opt_requester_name,
     181             :                                         server_name, server_ss, c->opt_port,
     182             :                                         "IPC$", "IPC",
     183             :                                         anon_creds,
     184             :                                         CLI_FULL_CONNECTION_IPC);
     185             : 
     186           6 :         if (NT_STATUS_IS_OK(nt_status)) {
     187           6 :                 return nt_status;
     188             :         } else {
     189           0 :                 DEBUG(1,("Cannot connect to server (anonymously).  Error was %s\n", nt_errstr(nt_status)));
     190           0 :                 return nt_status;
     191             :         }
     192             : }
     193             : 
     194             : /**
     195             :  * Connect a server and open a given pipe
     196             :  *
     197             :  * @param cli_dst               A cli_state
     198             :  * @param pipe                  The pipe to open
     199             :  * @param got_pipe              boolean that stores if we got a pipe
     200             :  *
     201             :  * @return Normal NTSTATUS return.
     202             :  **/
     203           0 : NTSTATUS connect_dst_pipe(struct net_context *c, struct cli_state **cli_dst,
     204             :                           struct rpc_pipe_client **pp_pipe_hnd,
     205             :                           const struct ndr_interface_table *table)
     206             : {
     207           0 :         NTSTATUS nt_status;
     208           0 :         char *server_name = SMB_STRDUP("127.0.0.1");
     209           0 :         struct cli_state *cli_tmp = NULL;
     210           0 :         struct rpc_pipe_client *pipe_hnd = NULL;
     211             : 
     212           0 :         if (server_name == NULL) {
     213           0 :                 return NT_STATUS_NO_MEMORY;
     214             :         }
     215             : 
     216           0 :         if (c->opt_destination) {
     217           0 :                 SAFE_FREE(server_name);
     218           0 :                 if ((server_name = SMB_STRDUP(c->opt_destination)) == NULL) {
     219           0 :                         return NT_STATUS_NO_MEMORY;
     220             :                 }
     221             :         }
     222             : 
     223             :         /* make a connection to a named pipe */
     224           0 :         nt_status = connect_to_ipc(c, &cli_tmp, NULL, server_name);
     225           0 :         if (!NT_STATUS_IS_OK(nt_status)) {
     226           0 :                 SAFE_FREE(server_name);
     227           0 :                 return nt_status;
     228             :         }
     229             : 
     230           0 :         nt_status = cli_rpc_pipe_open_noauth(cli_tmp, table,
     231             :                                              &pipe_hnd);
     232           0 :         if (!NT_STATUS_IS_OK(nt_status)) {
     233           0 :                 DEBUG(0, ("couldn't not initialize pipe\n"));
     234           0 :                 cli_shutdown(cli_tmp);
     235           0 :                 SAFE_FREE(server_name);
     236           0 :                 return nt_status;
     237             :         }
     238             : 
     239           0 :         *cli_dst = cli_tmp;
     240           0 :         *pp_pipe_hnd = pipe_hnd;
     241           0 :         SAFE_FREE(server_name);
     242             : 
     243           0 :         return nt_status;
     244             : }
     245             : 
     246             : /****************************************************************************
     247             :  Use the local machine account (krb) and password for this session.
     248             : ****************************************************************************/
     249             : 
     250          40 : int net_use_krb_machine_account(struct net_context *c)
     251             : {
     252          40 :         char *user_name = NULL;
     253             : 
     254          40 :         if (!secrets_init()) {
     255           0 :                 d_fprintf(stderr,_("ERROR: Unable to open secrets database\n"));
     256           0 :                 exit(1);
     257             :         }
     258             : 
     259          40 :         c->opt_password = secrets_fetch_machine_password(
     260             :                                 c->opt_target_workgroup, NULL, NULL);
     261          40 :         if (asprintf(&user_name, "%s$@%s", lp_netbios_name(), lp_realm()) == -1) {
     262           0 :                 return -1;
     263             :         }
     264          40 :         c->opt_user_name = user_name;
     265          40 :         c->opt_user_specified = true;
     266             : 
     267          40 :         cli_credentials_set_machine_account(c->creds, c->lp_ctx);
     268          40 :         return 0;
     269             : }
     270             : 
     271         878 : bool net_find_server(struct net_context *c,
     272             :                         const char *domain,
     273             :                         unsigned flags,
     274             :                         struct sockaddr_storage *server_ss,
     275             :                         char **server_name)
     276             : {
     277         878 :         const char *d = domain ? domain : c->opt_target_workgroup;
     278             : 
     279         878 :         if (c->opt_host) {
     280         180 :                 *server_name = SMB_STRDUP(c->opt_host);
     281             :         }
     282             : 
     283         878 :         if (c->opt_have_ip) {
     284         698 :                 *server_ss = c->opt_dest_ip;
     285         698 :                 if (!*server_name) {
     286           0 :                         char addr[INET6_ADDRSTRLEN];
     287         698 :                         print_sockaddr(addr, sizeof(addr), &c->opt_dest_ip);
     288         698 :                         *server_name = SMB_STRDUP(addr);
     289             :                 }
     290         180 :         } else if (*server_name) {
     291             :                 /* resolve the IP address */
     292         180 :                 if (!resolve_name(*server_name, server_ss, 0x20, false))  {
     293           0 :                         DEBUG(1,("Unable to resolve server name\n"));
     294           0 :                         return false;
     295             :                 }
     296           0 :         } else if (flags & NET_FLAGS_PDC) {
     297           0 :                 fstring dc_name;
     298           0 :                 struct sockaddr_storage pdc_ss;
     299             : 
     300           0 :                 if (!get_pdc_ip(d, &pdc_ss)) {
     301           0 :                         DEBUG(1,("Unable to resolve PDC server address\n"));
     302           0 :                         return false;
     303             :                 }
     304             : 
     305           0 :                 if (is_zero_addr(&pdc_ss)) {
     306           0 :                         return false;
     307             :                 }
     308             : 
     309           0 :                 if (!name_status_find(d, 0x1b, 0x20, &pdc_ss, dc_name)) {
     310           0 :                         return false;
     311             :                 }
     312             : 
     313           0 :                 *server_name = SMB_STRDUP(dc_name);
     314           0 :                 *server_ss = pdc_ss;
     315           0 :         } else if (flags & NET_FLAGS_DMB) {
     316           0 :                 struct sockaddr_storage msbrow_ss;
     317           0 :                 char addr[INET6_ADDRSTRLEN];
     318             : 
     319             :                 /*  if (!resolve_name(MSBROWSE, &msbrow_ip, 1, false)) */
     320           0 :                 if (!resolve_name(d, &msbrow_ss, 0x1B, false))  {
     321           0 :                         DEBUG(1,("Unable to resolve domain browser via name lookup\n"));
     322           0 :                         return false;
     323             :                 }
     324           0 :                 *server_ss = msbrow_ss;
     325           0 :                 print_sockaddr(addr, sizeof(addr), server_ss);
     326           0 :                 *server_name = SMB_STRDUP(addr);
     327           0 :         } else if (flags & NET_FLAGS_MASTER) {
     328           0 :                 struct sockaddr_storage brow_ss;
     329           0 :                 char addr[INET6_ADDRSTRLEN];
     330           0 :                 if (!resolve_name(d, &brow_ss, 0x1D, false))  {
     331             :                                 /* go looking for workgroups */
     332           0 :                         DEBUG(1,("Unable to resolve master browser via name lookup\n"));
     333           0 :                         return false;
     334             :                 }
     335           0 :                 *server_ss = brow_ss;
     336           0 :                 print_sockaddr(addr, sizeof(addr), server_ss);
     337           0 :                 *server_name = SMB_STRDUP(addr);
     338           0 :         } else if (!(flags & NET_FLAGS_LOCALHOST_DEFAULT_INSANE)) {
     339           0 :                 if (!interpret_string_addr(server_ss,
     340             :                                         "127.0.0.1", AI_NUMERICHOST)) {
     341           0 :                         DEBUG(1,("Unable to resolve 127.0.0.1\n"));
     342           0 :                         return false;
     343             :                 }
     344           0 :                 *server_name = SMB_STRDUP("127.0.0.1");
     345             :         }
     346             : 
     347         878 :         if (!*server_name) {
     348           0 :                 DEBUG(1,("no server to connect to\n"));
     349           0 :                 return false;
     350             :         }
     351             : 
     352         878 :         return true;
     353             : }
     354             : 
     355           0 : bool net_find_pdc(struct sockaddr_storage *server_ss,
     356             :                 fstring server_name,
     357             :                 const char *domain_name)
     358             : {
     359           0 :         if (!get_pdc_ip(domain_name, server_ss)) {
     360           0 :                 return false;
     361             :         }
     362           0 :         if (is_zero_addr(server_ss)) {
     363           0 :                 return false;
     364             :         }
     365             : 
     366           0 :         if (!name_status_find(domain_name, 0x1b, 0x20, server_ss, server_name)) {
     367           0 :                 return false;
     368             :         }
     369             : 
     370           0 :         return true;
     371             : }
     372             : 
     373         874 : NTSTATUS net_make_ipc_connection(struct net_context *c, unsigned flags,
     374             :                                  struct cli_state **pcli)
     375             : {
     376         874 :         return net_make_ipc_connection_ex(c, c->opt_workgroup, NULL, NULL, flags, pcli);
     377             : }
     378             : 
     379         874 : NTSTATUS net_make_ipc_connection_ex(struct net_context *c ,const char *domain,
     380             :                                     const char *server,
     381             :                                     const struct sockaddr_storage *pss,
     382             :                                     unsigned flags, struct cli_state **pcli)
     383             : {
     384         874 :         char *server_name = NULL;
     385           0 :         struct sockaddr_storage server_ss;
     386         874 :         struct cli_state *cli = NULL;
     387           0 :         NTSTATUS nt_status;
     388             : 
     389         874 :         if ( !server || !pss ) {
     390         874 :                 if (!net_find_server(c, domain, flags, &server_ss,
     391             :                                      &server_name)) {
     392           0 :                         d_fprintf(stderr, _("Unable to find a suitable server "
     393             :                                 "for domain %s\n"), domain);
     394           0 :                         nt_status = NT_STATUS_UNSUCCESSFUL;
     395           0 :                         goto done;
     396             :                 }
     397             :         } else {
     398           0 :                 server_name = SMB_STRDUP( server );
     399           0 :                 server_ss = *pss;
     400             :         }
     401             : 
     402         874 :         if (flags & NET_FLAGS_ANONYMOUS) {
     403           6 :                 nt_status = connect_to_ipc_anonymous(c, &cli, &server_ss,
     404             :                                                      server_name);
     405             :         } else {
     406         868 :                 nt_status = connect_to_ipc(c, &cli, &server_ss,
     407             :                                            server_name);
     408             :         }
     409             : 
     410             :         /* store the server in the affinity cache if it was a PDC */
     411             : 
     412         874 :         if ( (flags & NET_FLAGS_PDC) && NT_STATUS_IS_OK(nt_status) )
     413           6 :                 saf_store(cli->server_domain, server_name);
     414             : 
     415         874 :         SAFE_FREE(server_name);
     416         874 :         if (!NT_STATUS_IS_OK(nt_status)) {
     417           0 :                 d_fprintf(stderr, _("Connection failed: %s\n"),
     418             :                           nt_errstr(nt_status));
     419           0 :                 cli = NULL;
     420         874 :         } else if (c->opt_request_timeout) {
     421           0 :                 cli_set_timeout(cli, c->opt_request_timeout * 1000);
     422             :         }
     423             : 
     424         874 : done:
     425         874 :         if (pcli != NULL) {
     426         874 :                 *pcli = cli;
     427             :         }
     428         874 :         return nt_status;
     429             : }
     430             : 
     431             : /****************************************************************************
     432             : ****************************************************************************/
     433             : 
     434             : /* TODO FIXME: Pass cli_creds via net_context and get rid of this function. */
     435         199 : const char *net_prompt_pass(struct net_context *c, const char *user)
     436             : {
     437         199 :         struct cli_credentials *creds = samba_cmdline_get_creds();
     438             : 
     439         199 :         if (c->opt_password == NULL) {
     440         199 :                 c->opt_password = cli_credentials_get_password(creds);
     441             :         }
     442             : 
     443         199 :         return c->opt_password;
     444             : }
     445             : 
     446        7159 : int net_run_function(struct net_context *c, int argc, const char **argv,
     447             :                       const char *whoami, struct functable *table)
     448             : {
     449           5 :         int i;
     450             : 
     451        7159 :         if (argc != 0) {
     452       95149 :                 for (i=0; table[i].funcname != NULL; i++) {
     453       95149 :                         if (strcasecmp_m(argv[0], table[i].funcname) == 0)
     454        7159 :                                 return table[i].fn(c, argc-1, argv+1);
     455             :                 }
     456             :         }
     457             : 
     458           0 :         if (c->display_usage == false) {
     459           0 :                 d_fprintf(stderr, _("Invalid command: %s %s\n"), whoami,
     460             :                           (argc > 0)?argv[0]:"");
     461             :         }
     462           0 :         d_printf(_("Usage:\n"));
     463           0 :         for (i=0; table[i].funcname != NULL; i++) {
     464           0 :                 if(c->display_usage == false)
     465           0 :                         d_printf("%s %-15s %s\n", whoami, table[i].funcname,
     466           0 :                                  _(table[i].description));
     467             :                 else
     468           0 :                         d_printf("%s\n", _(table[i].usage));
     469             :         }
     470             : 
     471           0 :         return c->display_usage?0:-1;
     472             : }
     473             : 
     474           0 : void net_display_usage_from_functable(struct functable *table)
     475             : {
     476           0 :         int i;
     477           0 :         for (i=0; table[i].funcname != NULL; i++) {
     478           0 :                 d_printf("%s\n", _(table[i].usage));
     479             :         }
     480           0 : }
     481             : 
     482         238 : void net_warn_member_options(void)
     483             : {
     484         238 :         TALLOC_CTX *frame = talloc_stackframe();
     485         238 :         struct loadparm_context *lp_ctx = NULL;
     486             : 
     487         238 :         lp_ctx = loadparm_init_s3(frame, loadparm_s3_helpers());
     488         238 :         if (lp_ctx != NULL) {
     489         238 :                 netlogon_creds_cli_warn_options(lp_ctx);
     490             :         }
     491             : 
     492         238 :         TALLOC_FREE(frame);
     493         238 : }
     494             : 
     495           0 : const char *net_share_type_str(int num_type)
     496             : {
     497           0 :         switch(num_type) {
     498           0 :                 case 0: return _("Disk");
     499           0 :                 case 1: return _("Print");
     500           0 :                 case 2: return _("Dev");
     501           0 :                 case 3: return _("IPC");
     502           0 :                 default: return _("Unknown");
     503             :         }
     504             : }
     505             : 
     506           0 : static NTSTATUS net_scan_dc_noad(struct net_context *c,
     507             :                                  struct cli_state *cli,
     508             :                                  struct net_dc_info *dc_info)
     509             : {
     510           0 :         TALLOC_CTX *mem_ctx = talloc_tos();
     511           0 :         struct rpc_pipe_client *pipe_hnd = NULL;
     512           0 :         struct dcerpc_binding_handle *b;
     513           0 :         NTSTATUS status, result;
     514           0 :         struct policy_handle pol;
     515           0 :         union lsa_PolicyInformation *info;
     516             : 
     517           0 :         ZERO_STRUCTP(dc_info);
     518           0 :         ZERO_STRUCT(pol);
     519             : 
     520           0 :         status = cli_rpc_pipe_open_noauth(cli, &ndr_table_lsarpc,
     521             :                                           &pipe_hnd);
     522           0 :         if (!NT_STATUS_IS_OK(status)) {
     523           0 :                 return status;
     524             :         }
     525             : 
     526           0 :         b = pipe_hnd->binding_handle;
     527             : 
     528           0 :         status = dcerpc_lsa_open_policy(b, mem_ctx,
     529             :                                         false,
     530             :                                         SEC_FLAG_MAXIMUM_ALLOWED,
     531             :                                         &pol,
     532             :                                         &result);
     533           0 :         if (!NT_STATUS_IS_OK(status)) {
     534           0 :                 goto done;
     535             :         }
     536           0 :         if (!NT_STATUS_IS_OK(result)) {
     537           0 :                 status = result;
     538           0 :                 goto done;
     539             :         }
     540             : 
     541           0 :         status = dcerpc_lsa_QueryInfoPolicy(b, mem_ctx,
     542             :                                             &pol,
     543             :                                             LSA_POLICY_INFO_ACCOUNT_DOMAIN,
     544             :                                             &info,
     545             :                                             &result);
     546           0 :         if (!NT_STATUS_IS_OK(status)) {
     547           0 :                 goto done;
     548             :         }
     549           0 :         if (!NT_STATUS_IS_OK(result)) {
     550           0 :                 status = result;
     551           0 :                 goto done;
     552             :         }
     553             : 
     554           0 :         dc_info->netbios_domain_name = talloc_strdup(mem_ctx, info->account_domain.name.string);
     555           0 :         if (dc_info->netbios_domain_name == NULL) {
     556           0 :                 status = NT_STATUS_NO_MEMORY;
     557           0 :                 goto done;
     558             :         }
     559             : 
     560           0 :  done:
     561           0 :         if (is_valid_policy_hnd(&pol)) {
     562           0 :                 dcerpc_lsa_Close(b, mem_ctx, &pol, &result);
     563             :         }
     564             : 
     565           0 :         TALLOC_FREE(pipe_hnd);
     566             : 
     567           0 :         return status;
     568             : }
     569             : 
     570           0 : NTSTATUS net_scan_dc(struct net_context *c,
     571             :                      struct cli_state *cli,
     572             :                      struct net_dc_info *dc_info)
     573             : {
     574           0 :         TALLOC_CTX *mem_ctx = talloc_tos();
     575           0 :         struct rpc_pipe_client *dssetup_pipe = NULL;
     576           0 :         struct dcerpc_binding_handle *dssetup_handle = NULL;
     577           0 :         union dssetup_DsRoleInfo info;
     578           0 :         NTSTATUS status;
     579           0 :         WERROR werr;
     580             : 
     581           0 :         ZERO_STRUCTP(dc_info);
     582             : 
     583           0 :         status = cli_rpc_pipe_open_noauth(cli, &ndr_table_dssetup,
     584             :                                           &dssetup_pipe);
     585           0 :         if (!NT_STATUS_IS_OK(status)) {
     586           0 :                 DEBUG(10,("net_scan_dc: failed to open dssetup pipe with %s, "
     587             :                         "retrying with lsa pipe\n", nt_errstr(status)));
     588           0 :                 return net_scan_dc_noad(c, cli, dc_info);
     589             :         }
     590           0 :         dssetup_handle = dssetup_pipe->binding_handle;
     591             : 
     592           0 :         status = dcerpc_dssetup_DsRoleGetPrimaryDomainInformation(dssetup_handle, mem_ctx,
     593             :                                                                   DS_ROLE_BASIC_INFORMATION,
     594             :                                                                   &info,
     595             :                                                                   &werr);
     596           0 :         TALLOC_FREE(dssetup_pipe);
     597             : 
     598           0 :         if (NT_STATUS_IS_OK(status)) {
     599           0 :                 status = werror_to_ntstatus(werr);
     600             :         }
     601           0 :         if (!NT_STATUS_IS_OK(status)) {
     602           0 :                 return status;
     603             :         }
     604             : 
     605           0 :         dc_info->is_dc       = (info.basic.role & (DS_ROLE_PRIMARY_DC|DS_ROLE_BACKUP_DC));
     606           0 :         dc_info->is_pdc      = (info.basic.role & DS_ROLE_PRIMARY_DC);
     607           0 :         dc_info->is_ad       = (info.basic.flags & DS_ROLE_PRIMARY_DS_RUNNING);
     608           0 :         dc_info->is_mixed_mode = (info.basic.flags & DS_ROLE_PRIMARY_DS_MIXED_MODE);
     609           0 :         dc_info->netbios_domain_name = talloc_strdup(mem_ctx, info.basic.domain);
     610           0 :         dc_info->dns_domain_name = talloc_strdup(mem_ctx, info.basic.dns_domain);
     611           0 :         dc_info->forest_name = talloc_strdup(mem_ctx, info.basic.forest);
     612             : 
     613           0 :         return NT_STATUS_OK;
     614             : }

Generated by: LCOV version 1.14