root/source3/lib/netapi/cm.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. libnetapi_open_ipc_connection
  2. libnetapi_shutdown_cm
  3. pipe_cm_find
  4. pipe_cm_connect
  5. pipe_cm_open
  6. libnetapi_open_pipe

   1 /*
   2  *  Unix SMB/CIFS implementation.
   3  *  NetApi Support
   4  *  Copyright (C) Guenther Deschner 2008
   5  *
   6  *  This program is free software; you can redistribute it and/or modify
   7  *  it under the terms of the GNU General Public License as published by
   8  *  the Free Software Foundation; either version 3 of the License, or
   9  *  (at your option) any later version.
  10  *
  11  *  This program is distributed in the hope that it will be useful,
  12  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
  13  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  14  *  GNU General Public License for more details.
  15  *
  16  *  You should have received a copy of the GNU General Public License
  17  *  along with this program; if not, see <http://www.gnu.org/licenses/>.
  18  */
  19 
  20 #include "includes.h"
  21 
  22 #include "lib/netapi/netapi.h"
  23 #include "lib/netapi/netapi_private.h"
  24 
  25 /********************************************************************
  26 ********************************************************************/
  27 
  28 static WERROR libnetapi_open_ipc_connection(struct libnetapi_ctx *ctx,
     /* [<][>][^][v][top][bottom][index][help] */
  29                                             const char *server_name,
  30                                             struct cli_state **cli)
  31 {
  32         struct user_auth_info *auth_info = NULL;
  33         struct cli_state *cli_ipc = NULL;
  34 
  35         if (!ctx || !cli || !server_name) {
  36                 return WERR_INVALID_PARAM;
  37         }
  38 
  39         auth_info = user_auth_info_init(NULL);
  40         if (!auth_info) {
  41                 return WERR_NOMEM;
  42         }
  43         auth_info->signing_state = Undefined;
  44         set_cmdline_auth_info_use_kerberos(auth_info, ctx->use_kerberos);
  45         set_cmdline_auth_info_username(auth_info, ctx->username);
  46         if (ctx->password) {
  47                 set_cmdline_auth_info_password(auth_info, ctx->password);
  48         } else {
  49                 set_cmdline_auth_info_getpass(auth_info);
  50         }
  51 
  52         if (ctx->username && ctx->username[0] &&
  53             ctx->password && ctx->password[0] &&
  54             ctx->use_kerberos) {
  55                 set_cmdline_auth_info_fallback_after_kerberos(auth_info, true);
  56         }
  57 
  58         cli_ipc = cli_cm_open(ctx, NULL,
  59                                 server_name, "IPC$",
  60                                 auth_info,
  61                                 false, false,
  62                                 PROTOCOL_NT1,
  63                                 0, 0x20);
  64         if (cli_ipc) {
  65                 cli_set_username(cli_ipc, ctx->username);
  66                 cli_set_password(cli_ipc, ctx->password);
  67                 cli_set_domain(cli_ipc, ctx->workgroup);
  68         }
  69         TALLOC_FREE(auth_info);
  70 
  71         if (!cli_ipc) {
  72                 libnetapi_set_error_string(ctx,
  73                         "Failed to connect to IPC$ share on %s", server_name);
  74                 return WERR_CAN_NOT_COMPLETE;
  75         }
  76 
  77         *cli = cli_ipc;
  78 
  79         return WERR_OK;
  80 }
  81 
  82 /********************************************************************
  83 ********************************************************************/
  84 
  85 struct client_pipe_connection {
  86         struct client_pipe_connection *prev, *next;
  87         struct rpc_pipe_client *pipe;
  88         struct cli_state *cli;
  89 };
  90 
  91 static struct client_pipe_connection *pipe_connections;
  92 
  93 /********************************************************************
  94 ********************************************************************/
  95 
  96 WERROR libnetapi_shutdown_cm(struct libnetapi_ctx *ctx)
     /* [<][>][^][v][top][bottom][index][help] */
  97 {
  98         struct client_pipe_connection *p;
  99 
 100         for (p = pipe_connections; p; p = p->next) {
 101                 cli_shutdown(p->cli);
 102         }
 103 
 104         return WERR_OK;
 105 }
 106 
 107 /********************************************************************
 108 ********************************************************************/
 109 
 110 static NTSTATUS pipe_cm_find(struct cli_state *cli,
     /* [<][>][^][v][top][bottom][index][help] */
 111                              const struct ndr_syntax_id *interface,
 112                              struct rpc_pipe_client **presult)
 113 {
 114         struct client_pipe_connection *p;
 115 
 116         for (p = pipe_connections; p; p = p->next) {
 117 
 118                 if (!rpc_pipe_np_smb_conn(p->pipe)) {
 119                         return NT_STATUS_PIPE_EMPTY;
 120                 }
 121 
 122                 if (strequal(cli->desthost, p->pipe->desthost)
 123                     && ndr_syntax_id_equal(&p->pipe->abstract_syntax,
 124                                            interface)) {
 125                         *presult = p->pipe;
 126                         return NT_STATUS_OK;
 127                 }
 128         }
 129 
 130         return NT_STATUS_PIPE_NOT_AVAILABLE;
 131 }
 132 
 133 /********************************************************************
 134 ********************************************************************/
 135 
 136 static NTSTATUS pipe_cm_connect(TALLOC_CTX *mem_ctx,
     /* [<][>][^][v][top][bottom][index][help] */
 137                                 struct cli_state *cli,
 138                                 const struct ndr_syntax_id *interface,
 139                                 struct rpc_pipe_client **presult)
 140 {
 141         struct client_pipe_connection *p;
 142         NTSTATUS status;
 143 
 144         p = TALLOC_ZERO_ARRAY(mem_ctx, struct client_pipe_connection, 1);
 145         if (!p) {
 146                 return NT_STATUS_NO_MEMORY;
 147         }
 148 
 149         status = cli_rpc_pipe_open_noauth(cli, interface, &p->pipe);
 150         if (!NT_STATUS_IS_OK(status)) {
 151                 TALLOC_FREE(p);
 152                 return status;
 153         }
 154 
 155         p->cli = cli;
 156         DLIST_ADD(pipe_connections, p);
 157 
 158         *presult = p->pipe;
 159         return NT_STATUS_OK;
 160 }
 161 
 162 /********************************************************************
 163 ********************************************************************/
 164 
 165 static NTSTATUS pipe_cm_open(TALLOC_CTX *ctx,
     /* [<][>][^][v][top][bottom][index][help] */
 166                              struct cli_state *cli,
 167                              const struct ndr_syntax_id *interface,
 168                              struct rpc_pipe_client **presult)
 169 {
 170         if (NT_STATUS_IS_OK(pipe_cm_find(cli, interface, presult))) {
 171                 return NT_STATUS_OK;
 172         }
 173 
 174         return pipe_cm_connect(ctx, cli, interface, presult);
 175 }
 176 
 177 /********************************************************************
 178 ********************************************************************/
 179 
 180 WERROR libnetapi_open_pipe(struct libnetapi_ctx *ctx,
     /* [<][>][^][v][top][bottom][index][help] */
 181                            const char *server_name,
 182                            const struct ndr_syntax_id *interface,
 183                            struct rpc_pipe_client **presult)
 184 {
 185         struct rpc_pipe_client *result = NULL;
 186         NTSTATUS status;
 187         WERROR werr;
 188         struct cli_state *cli = NULL;
 189 
 190         if (!presult) {
 191                 return WERR_INVALID_PARAM;
 192         }
 193 
 194         werr = libnetapi_open_ipc_connection(ctx, server_name, &cli);
 195         if (!W_ERROR_IS_OK(werr)) {
 196                 return werr;
 197         }
 198 
 199         status = pipe_cm_open(ctx, cli, interface, &result);
 200         if (!NT_STATUS_IS_OK(status)) {
 201                 libnetapi_set_error_string(ctx, "failed to open PIPE %s: %s",
 202                         get_pipe_name_from_iface(interface),
 203                         get_friendly_nt_error_msg(status));
 204                 return WERR_DEST_NOT_FOUND;
 205         }
 206 
 207         *presult = result;
 208 
 209         return WERR_OK;
 210 }

/* [<][>][^][v][top][bottom][index][help] */