LCOV - code coverage report
Current view: top level - source4/libcli/raw - clisession.c (source / functions) Hit Total Coverage
Test: coverage report for v4-17-test 1498b464 Lines: 130 159 81.8 %
Date: 2024-06-13 04:01:37 Functions: 7 8 87.5 %

          Line data    Source code
       1             : /* 
       2             :    Unix SMB/CIFS implementation.
       3             :    SMB client session context management functions
       4             : 
       5             :    Copyright (C) Andrew Tridgell 1994-2005
       6             :    Copyright (C) James Myers 2003 <myersjj@samba.org>
       7             :    
       8             :    This program is free software; you can redistribute it and/or modify
       9             :    it under the terms of the GNU General Public License as published by
      10             :    the Free Software Foundation; either version 3 of the License, or
      11             :    (at your option) any later version.
      12             :    
      13             :    This program is distributed in the hope that it will be useful,
      14             :    but WITHOUT ANY WARRANTY; without even the implied warranty of
      15             :    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      16             :    GNU General Public License for more details.
      17             :    
      18             :    You should have received a copy of the GNU General Public License
      19             :    along with this program.  If not, see <http://www.gnu.org/licenses/>.
      20             : */
      21             : 
      22             : #include "includes.h"
      23             : #include "libcli/raw/libcliraw.h"
      24             : #include "libcli/raw/raw_proto.h"
      25             : #include "system/filesys.h"
      26             : #include "../libcli/smb/smbXcli_base.h"
      27             : 
      28             : #define SETUP_REQUEST_SESSION(cmd, wct, buflen) do { \
      29             :         req = smbcli_request_setup_session(session, cmd, wct, buflen); \
      30             :         if (!req) return NULL; \
      31             : } while (0)
      32             : 
      33             : 
      34             : /****************************************************************************
      35             :  Initialize the session context
      36             : ****************************************************************************/
      37         925 : struct smbcli_session *smbcli_session_init(struct smbcli_transport *transport, 
      38             :                                            TALLOC_CTX *parent_ctx, bool primary,
      39             :                                            struct smbcli_session_options options)
      40             : {
      41             :         struct smbcli_session *session;
      42             :         uint16_t flags2;
      43             :         uint32_t capabilities;
      44             : 
      45         925 :         session = talloc_zero(parent_ctx, struct smbcli_session);
      46         925 :         if (!session) {
      47           0 :                 return NULL;
      48             :         }
      49             : 
      50         925 :         if (primary) {
      51         894 :                 session->transport = talloc_steal(session, transport);
      52             :         } else {
      53          31 :                 session->transport = talloc_reference(session, transport);
      54             :         }
      55         925 :         session->pid = (uint32_t)getpid();
      56         925 :         session->vuid = UID_FIELD_INVALID;
      57         925 :         session->options = options;
      58             : 
      59             :         /*
      60             :          * for now session->vuid is still used by the callers, but we call:
      61             :          * smb1cli_session_set_id(session->smbXcli, session->vuid);
      62             :          * before using session->smbXcli, in future we should remove
      63             :          * session->vuid.
      64             :          */
      65         925 :         session->smbXcli = smbXcli_session_create(session, transport->conn);
      66         925 :         if (session->smbXcli == NULL) {
      67           0 :                 talloc_free(session);
      68           0 :                 return NULL;
      69             :         }
      70             : 
      71         925 :         capabilities = transport->negotiate.capabilities;
      72             : 
      73         925 :         flags2 = FLAGS2_LONG_PATH_COMPONENTS | FLAGS2_EXTENDED_ATTRIBUTES;
      74             : 
      75         925 :         if (capabilities & CAP_UNICODE) {
      76         921 :                 flags2 |= FLAGS2_UNICODE_STRINGS;
      77             :         }
      78         925 :         if (capabilities & CAP_STATUS32) {
      79         921 :                 flags2 |= FLAGS2_32_BIT_ERROR_CODES;
      80             :         }
      81         925 :         if (capabilities & CAP_EXTENDED_SECURITY) {
      82         917 :                 flags2 |= FLAGS2_EXTENDED_SECURITY;
      83             :         }
      84         925 :         if (smb1cli_conn_signing_is_active(session->transport->conn)) {
      85          31 :                 flags2 |= FLAGS2_SMB_SECURITY_SIGNATURES;
      86             :         }
      87             : 
      88         925 :         session->flags2 = flags2;
      89             : 
      90         925 :         return session;
      91             : }
      92             : 
      93             : /****************************************************************************
      94             :  Perform a session setup (async send)
      95             : ****************************************************************************/
      96        1034 : struct smbcli_request *smb_raw_sesssetup_send(struct smbcli_session *session, 
      97             :                                               union smb_sesssetup *parms) 
      98             : {
      99        1034 :         struct smbcli_request *req = NULL;
     100             : 
     101        1034 :         switch (parms->old.level) {
     102           4 :         case RAW_SESSSETUP_OLD:
     103           4 :                 SETUP_REQUEST_SESSION(SMBsesssetupX, 10, 0);
     104           4 :                 SSVAL(req->out.vwv, VWV(0), SMB_CHAIN_NONE);
     105           4 :                 SSVAL(req->out.vwv, VWV(1), 0);
     106           4 :                 SSVAL(req->out.vwv,VWV(2),parms->old.in.bufsize);
     107           4 :                 SSVAL(req->out.vwv,VWV(3),parms->old.in.mpx_max);
     108           4 :                 SSVAL(req->out.vwv,VWV(4),parms->old.in.vc_num);
     109           4 :                 SIVAL(req->out.vwv,VWV(5),parms->old.in.sesskey);
     110           4 :                 SSVAL(req->out.vwv,VWV(7),parms->old.in.password.length);
     111           4 :                 SIVAL(req->out.vwv,VWV(8), 0); /* reserved */
     112           4 :                 smbcli_req_append_blob(req, &parms->old.in.password);
     113           4 :                 smbcli_req_append_string(req, parms->old.in.user, STR_TERMINATE);
     114           4 :                 smbcli_req_append_string(req, parms->old.in.domain, STR_TERMINATE|STR_UPPER);
     115           4 :                 smbcli_req_append_string(req, parms->old.in.os, STR_TERMINATE);
     116           4 :                 smbcli_req_append_string(req, parms->old.in.lanman, STR_TERMINATE);
     117           4 :                 break;
     118             : 
     119           5 :         case RAW_SESSSETUP_NT1:
     120           5 :                 SETUP_REQUEST_SESSION(SMBsesssetupX, 13, 0);
     121           5 :                 SSVAL(req->out.vwv, VWV(0), SMB_CHAIN_NONE);
     122           5 :                 SSVAL(req->out.vwv, VWV(1), 0);
     123           5 :                 SSVAL(req->out.vwv, VWV(2), parms->nt1.in.bufsize);
     124           5 :                 SSVAL(req->out.vwv, VWV(3), parms->nt1.in.mpx_max);
     125           5 :                 SSVAL(req->out.vwv, VWV(4), parms->nt1.in.vc_num);
     126           5 :                 SIVAL(req->out.vwv, VWV(5), parms->nt1.in.sesskey);
     127           5 :                 SSVAL(req->out.vwv, VWV(7), parms->nt1.in.password1.length);
     128           5 :                 SSVAL(req->out.vwv, VWV(8), parms->nt1.in.password2.length);
     129           5 :                 SIVAL(req->out.vwv, VWV(9), 0); /* reserved */
     130           5 :                 SIVAL(req->out.vwv, VWV(11), parms->nt1.in.capabilities);
     131           5 :                 smbcli_req_append_blob(req, &parms->nt1.in.password1);
     132           5 :                 smbcli_req_append_blob(req, &parms->nt1.in.password2);
     133           5 :                 smbcli_req_append_string(req, parms->nt1.in.user, STR_TERMINATE);
     134           5 :                 smbcli_req_append_string(req, parms->nt1.in.domain, STR_TERMINATE|STR_UPPER);
     135           5 :                 smbcli_req_append_string(req, parms->nt1.in.os, STR_TERMINATE);
     136           5 :                 smbcli_req_append_string(req, parms->nt1.in.lanman, STR_TERMINATE);
     137           5 :                 break;
     138             : 
     139        1025 :         case RAW_SESSSETUP_SPNEGO:
     140        1025 :                 SETUP_REQUEST_SESSION(SMBsesssetupX, 12, 0);
     141        1025 :                 SSVAL(req->out.vwv, VWV(0), SMB_CHAIN_NONE);
     142        1025 :                 SSVAL(req->out.vwv, VWV(1), 0);
     143        1025 :                 SSVAL(req->out.vwv, VWV(2), parms->spnego.in.bufsize);
     144        1025 :                 SSVAL(req->out.vwv, VWV(3), parms->spnego.in.mpx_max);
     145        1025 :                 SSVAL(req->out.vwv, VWV(4), parms->spnego.in.vc_num);
     146        1025 :                 SIVAL(req->out.vwv, VWV(5), parms->spnego.in.sesskey);
     147        1025 :                 SSVAL(req->out.vwv, VWV(7), parms->spnego.in.secblob.length);
     148        1025 :                 SIVAL(req->out.vwv, VWV(8), 0); /* reserved */
     149        1025 :                 SIVAL(req->out.vwv, VWV(10), parms->spnego.in.capabilities);
     150        1025 :                 smbcli_req_append_blob(req, &parms->spnego.in.secblob);
     151        1025 :                 smbcli_req_append_string(req, parms->spnego.in.os, STR_TERMINATE);
     152        1025 :                 smbcli_req_append_string(req, parms->spnego.in.lanman, STR_TERMINATE);
     153        1025 :                 smbcli_req_append_string(req, parms->spnego.in.workgroup, STR_TERMINATE);
     154        1025 :                 break;
     155             : 
     156           0 :         case RAW_SESSSETUP_SMB2:
     157           0 :                 return NULL;
     158             :         }
     159             : 
     160        1034 :         if (!smbcli_request_send(req)) {
     161           0 :                 smbcli_request_destroy(req);
     162           0 :                 return NULL;
     163             :         }
     164             : 
     165        1034 :         return req;
     166             : }
     167             : 
     168             : 
     169             : /****************************************************************************
     170             :  Perform a session setup (async recv)
     171             : ****************************************************************************/
     172        1034 : NTSTATUS smb_raw_sesssetup_recv(struct smbcli_request *req, 
     173             :                                 TALLOC_CTX *mem_ctx, 
     174             :                                 union smb_sesssetup *parms) 
     175             : {
     176             :         uint16_t len;
     177             :         uint8_t *p;
     178             : 
     179        1034 :         if (!smbcli_request_receive(req)) {
     180           0 :                 return smbcli_request_destroy(req);
     181             :         }
     182             :         
     183        1106 :         if (!NT_STATUS_IS_OK(req->status) &&
     184         115 :             !NT_STATUS_EQUAL(req->status,NT_STATUS_MORE_PROCESSING_REQUIRED)) {
     185           7 :                 return smbcli_request_destroy(req);
     186             :         }
     187             : 
     188        1027 :         switch (parms->old.level) {
     189           0 :         case RAW_SESSSETUP_OLD:
     190           0 :                 SMBCLI_CHECK_WCT(req, 3);
     191           0 :                 ZERO_STRUCT(parms->old.out);
     192           0 :                 parms->old.out.vuid = SVAL(req->in.hdr, HDR_UID);
     193           0 :                 parms->old.out.action = SVAL(req->in.vwv, VWV(2));
     194           0 :                 p = req->in.data;
     195           0 :                 if (p) {
     196           0 :                         p += smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->old.out.os, p, -1, STR_TERMINATE);
     197           0 :                         p += smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->old.out.lanman, p, -1, STR_TERMINATE);
     198           0 :                         smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->old.out.domain, p, -1, STR_TERMINATE);
     199             :                 }
     200          83 :                 break;
     201             : 
     202           5 :         case RAW_SESSSETUP_NT1:
     203           5 :                 SMBCLI_CHECK_WCT(req, 3);
     204           5 :                 ZERO_STRUCT(parms->nt1.out);
     205           5 :                 parms->nt1.out.vuid   = SVAL(req->in.hdr, HDR_UID);
     206           5 :                 parms->nt1.out.action = SVAL(req->in.vwv, VWV(2));
     207           5 :                 p = req->in.data;
     208           5 :                 if (p) {
     209           5 :                         p += smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->nt1.out.os, p, -1, STR_TERMINATE);
     210           5 :                         p += smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->nt1.out.lanman, p, -1, STR_TERMINATE);
     211           5 :                         if (p < (req->in.data + req->in.data_size)) {
     212           5 :                                 smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->nt1.out.domain, p, -1, STR_TERMINATE);
     213             :                         }
     214             :                 }
     215           5 :                 break;
     216             : 
     217        1022 :         case RAW_SESSSETUP_SPNEGO:
     218        1022 :                 SMBCLI_CHECK_WCT(req, 4);
     219        1022 :                 ZERO_STRUCT(parms->spnego.out);
     220        1022 :                 parms->spnego.out.vuid   = SVAL(req->in.hdr, HDR_UID);
     221        1022 :                 parms->spnego.out.action = SVAL(req->in.vwv, VWV(2));
     222        1022 :                 len                      = SVAL(req->in.vwv, VWV(3));
     223        1022 :                 p = req->in.data;
     224        1022 :                 if (!p) {
     225           0 :                         break;
     226             :                 }
     227             : 
     228        1022 :                 parms->spnego.out.secblob = smbcli_req_pull_blob(&req->in.bufinfo, mem_ctx, p, len);
     229        1022 :                 p += parms->spnego.out.secblob.length;
     230        1022 :                 p += smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->spnego.out.os, p, -1, STR_TERMINATE);
     231        1022 :                 p += smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->spnego.out.lanman, p, -1, STR_TERMINATE);
     232        1022 :                 smbcli_req_pull_string(&req->in.bufinfo, mem_ctx, &parms->spnego.out.workgroup, p, -1, STR_TERMINATE);
     233        1022 :                 break;
     234             : 
     235           0 :         case RAW_SESSSETUP_SMB2:
     236           0 :                 req->status = NT_STATUS_INTERNAL_ERROR;
     237           0 :                 break;
     238             :         }
     239             : 
     240        1027 : failed:
     241        1027 :         return smbcli_request_destroy(req);
     242             : }
     243             : 
     244             : 
     245             : /*
     246             :  Perform a session setup (sync interface)
     247             : */
     248           0 : NTSTATUS smb_raw_sesssetup(struct smbcli_session *session, 
     249             :                            TALLOC_CTX *mem_ctx, union smb_sesssetup *parms) 
     250             : {
     251           0 :         struct smbcli_request *req = smb_raw_sesssetup_send(session, parms);
     252           0 :         return smb_raw_sesssetup_recv(req, mem_ctx, parms);
     253             : }
     254             : 
     255             : 
     256             : /****************************************************************************
     257             :  Send a ulogoff (async send)
     258             : *****************************************************************************/
     259          20 : struct smbcli_request *smb_raw_ulogoff_send(struct smbcli_session *session)
     260             : {
     261             :         struct smbcli_request *req;
     262             : 
     263          20 :         SETUP_REQUEST_SESSION(SMBulogoffX, 2, 0);
     264             : 
     265          20 :         SSVAL(req->out.vwv, VWV(0), SMB_CHAIN_NONE);
     266          20 :         SSVAL(req->out.vwv, VWV(1), 0);
     267             : 
     268          20 :         if (!smbcli_request_send(req)) {
     269           0 :                 smbcli_request_destroy(req);
     270           0 :                 return NULL;
     271             :         }
     272             : 
     273          20 :         return req;
     274             : }
     275             : 
     276             : /****************************************************************************
     277             :  Send a ulogoff (sync interface)
     278             : *****************************************************************************/
     279          20 : NTSTATUS smb_raw_ulogoff(struct smbcli_session *session)
     280             : {
     281          20 :         struct smbcli_request *req = smb_raw_ulogoff_send(session);
     282          20 :         return smbcli_request_simple_recv(req);
     283             : }
     284             : 
     285             : 
     286             : /****************************************************************************
     287             :  Send a exit (async send)
     288             : *****************************************************************************/
     289         613 : struct smbcli_request *smb_raw_exit_send(struct smbcli_session *session)
     290             : {
     291             :         struct smbcli_request *req;
     292             : 
     293         613 :         SETUP_REQUEST_SESSION(SMBexit, 0, 0);
     294             : 
     295         613 :         if (!smbcli_request_send(req)) {
     296           0 :                 smbcli_request_destroy(req);
     297           0 :                 return NULL;
     298             :         }
     299             : 
     300         613 :         return req;
     301             : }
     302             : 
     303             : /****************************************************************************
     304             :  Send a exit (sync interface)
     305             : *****************************************************************************/
     306         613 : _PUBLIC_ NTSTATUS smb_raw_exit(struct smbcli_session *session)
     307             : {
     308         613 :         struct smbcli_request *req = smb_raw_exit_send(session);
     309         613 :         return smbcli_request_simple_recv(req);
     310             : }

Generated by: LCOV version 1.13