LCOV - code coverage report
Current view: top level - source3/libsmb - libsmb_context.c (source / functions) Hit Total Coverage
Test: coverage report for recycleplus df22b230 Lines: 0 372 0.0 %
Date: 2024-02-14 10:14:15 Functions: 0 10 0.0 %

          Line data    Source code
       1             : /*
       2             :    Unix SMB/Netbios implementation.
       3             :    SMB client library implementation
       4             :    Copyright (C) Andrew Tridgell 1998
       5             :    Copyright (C) Richard Sharpe 2000, 2002
       6             :    Copyright (C) John Terpstra 2000
       7             :    Copyright (C) Tom Jansen (Ninja ISD) 2002
       8             :    Copyright (C) Derrell Lipman 2003-2008
       9             :    Copyright (C) Jeremy Allison 2007, 2008
      10             : 
      11             :    This program is free software; you can redistribute it and/or modify
      12             :    it under the terms of the GNU General Public License as published by
      13             :    the Free Software Foundation; either version 3 of the License, or
      14             :    (at your option) any later version.
      15             : 
      16             :    This program is distributed in the hope that it will be useful,
      17             :    but WITHOUT ANY WARRANTY; without even the implied warranty of
      18             :    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      19             :    GNU General Public License for more details.
      20             : 
      21             :    You should have received a copy of the GNU General Public License
      22             :    along with this program.  If not, see <http://www.gnu.org/licenses/>.
      23             : */
      24             : 
      25             : #include "includes.h"
      26             : #include "libsmb/libsmb.h"
      27             : #include "libsmbclient.h"
      28             : #include "libsmb_internal.h"
      29             : #include "secrets.h"
      30             : #include "../libcli/smb/smbXcli_base.h"
      31             : #include "auth/credentials/credentials.h"
      32             : #include "auth/gensec/gensec.h"
      33             : #include "lib/param/param.h"
      34             : #include "../lib/util/smb_threads.h"
      35             : #include "../lib/util/smb_threads_internal.h"
      36             : 
      37             : /*
      38             :  * Is the logging working / configfile read ?
      39             :  */
      40             : static bool SMBC_initialized = false;
      41             : static unsigned int initialized_ctx_count = 0;
      42             : static void *initialized_ctx_count_mutex = NULL;
      43             : 
      44             : /*
      45             :  * Do some module- and library-wide initializations
      46             :  */
      47             : static void
      48           0 : SMBC_module_init(void * punused)
      49             : {
      50           0 :         bool conf_loaded = False;
      51           0 :         char *home = NULL;
      52           0 :         TALLOC_CTX *frame = talloc_stackframe();
      53             : 
      54           0 :         setup_logging("libsmbclient", DEBUG_STDOUT);
      55             : 
      56             :         /* Here we would open the smb.conf file if needed ... */
      57             : 
      58           0 :         home = getenv("HOME");
      59           0 :         if (home) {
      60           0 :                 char *conf = NULL;
      61           0 :                 if (asprintf(&conf, "%s/.smb/smb.conf", home) > 0) {
      62           0 :                         if (lp_load_client(conf)) {
      63           0 :                                 conf_loaded = True;
      64             :                         } else {
      65           0 :                                 DEBUG(5, ("Could not load config file: %s\n",
      66             :                                           conf));
      67             :                         }
      68           0 :                         SAFE_FREE(conf);
      69             :                 }
      70             :         }
      71             : 
      72           0 :         if (!conf_loaded) {
      73             :                 /*
      74             :                  * Well, if that failed, try the get_dyn_CONFIGFILE
      75             :                  * Which points to the standard locn, and if that
      76             :                  * fails, silently ignore it and use the internal
      77             :                  * defaults ...
      78             :                  */
      79             : 
      80           0 :                 if (!lp_load_client(get_dyn_CONFIGFILE())) {
      81           0 :                         DEBUG(5, ("Could not load config file: %s\n",
      82             :                                   get_dyn_CONFIGFILE()));
      83           0 :                 } else if (home) {
      84             :                         char *conf;
      85             :                         /*
      86             :                          * We loaded the global config file.  Now lets
      87             :                          * load user-specific modifications to the
      88             :                          * global config.
      89             :                          */
      90           0 :                         if (asprintf(&conf,
      91             :                                      "%s/.smb/smb.conf.append",
      92             :                                      home) > 0) {
      93           0 :                                 if (!lp_load_client_no_reinit(conf)) {
      94           0 :                                         DEBUG(10,
      95             :                                               ("Could not append config file: "
      96             :                                                "%s\n",
      97             :                                                conf));
      98             :                                 }
      99           0 :                                 SAFE_FREE(conf);
     100             :                         }
     101             :                 }
     102             :         }
     103             : 
     104           0 :         load_interfaces();  /* Load the list of interfaces ... */
     105             : 
     106           0 :         reopen_logs();  /* Get logging working ... */
     107             : 
     108             :         /*
     109             :          * Block SIGPIPE (from lib/util_sock.c: write())
     110             :          * It is not needed and should not stop execution
     111             :          */
     112           0 :         BlockSignals(True, SIGPIPE);
     113             : 
     114             :         /* Create the mutex we'll use to protect initialized_ctx_count */
     115           0 :         if (SMB_THREAD_CREATE_MUTEX("initialized_ctx_count_mutex",
     116           0 :                                     initialized_ctx_count_mutex) != 0) {
     117           0 :                 smb_panic("SMBC_module_init: "
     118             :                           "failed to create 'initialized_ctx_count' mutex");
     119             :         }
     120             : 
     121           0 :         TALLOC_FREE(frame);
     122           0 : }
     123             : 
     124             : 
     125             : static void
     126           0 : SMBC_module_terminate(void)
     127             : {
     128           0 :         TALLOC_CTX *frame = talloc_stackframe();
     129           0 :         secrets_shutdown();
     130           0 :         gfree_all();
     131           0 :         SMBC_initialized = false;
     132           0 :         TALLOC_FREE(frame);
     133           0 : }
     134             : 
     135             : 
     136             : /*
     137             :  * Get a new empty handle to fill in with your own info
     138             :  */
     139             : SMBCCTX *
     140           0 : smbc_new_context(void)
     141             : {
     142             :         SMBCCTX *context;
     143           0 :         TALLOC_CTX *frame = talloc_stackframe();
     144             : 
     145             :         /* The first call to this function should initialize the module */
     146           0 :         SMB_THREAD_ONCE(&SMBC_initialized, SMBC_module_init, NULL);
     147             : 
     148             :         /*
     149             :          * All newly added context fields should be placed in
     150             :          * SMBC_internal_data, not directly in SMBCCTX.
     151             :          */
     152           0 :         context = SMB_MALLOC_P(SMBCCTX);
     153           0 :         if (!context) {
     154           0 :                 TALLOC_FREE(frame);
     155           0 :                 errno = ENOMEM;
     156           0 :                 return NULL;
     157             :         }
     158             : 
     159           0 :         ZERO_STRUCTP(context);
     160             : 
     161           0 :         context->internal = SMB_MALLOC_P(struct SMBC_internal_data);
     162           0 :         if (!context->internal) {
     163           0 :                 TALLOC_FREE(frame);
     164           0 :                 SAFE_FREE(context);
     165           0 :                 errno = ENOMEM;
     166           0 :                 return NULL;
     167             :         }
     168             : 
     169             :         /* Initialize the context and establish reasonable defaults */
     170           0 :         ZERO_STRUCTP(context->internal);
     171             : 
     172           0 :         smbc_setDebug(context, 0);
     173           0 :         smbc_setTimeout(context, 20000);
     174           0 :         smbc_setPort(context, 0);
     175             : 
     176           0 :         smbc_setOptionFullTimeNames(context, False);
     177           0 :         smbc_setOptionOpenShareMode(context, SMBC_SHAREMODE_DENY_NONE);
     178           0 :         smbc_setOptionSmbEncryptionLevel(context, SMBC_ENCRYPTLEVEL_DEFAULT);
     179           0 :         smbc_setOptionUseCCache(context, True);
     180           0 :         smbc_setOptionCaseSensitive(context, False);
     181           0 :         smbc_setOptionBrowseMaxLmbCount(context, 3);    /* # LMBs to query */
     182           0 :         smbc_setOptionUrlEncodeReaddirEntries(context, False);
     183           0 :         smbc_setOptionOneSharePerServer(context, False);
     184           0 :         if (getenv("LIBSMBCLIENT_NO_CCACHE") != NULL) {
     185           0 :                 smbc_setOptionUseCCache(context, false);
     186             :         }
     187             : 
     188           0 :         smbc_setFunctionAuthData(context, SMBC_get_auth_data);
     189           0 :         smbc_setFunctionCheckServer(context, SMBC_check_server);
     190           0 :         smbc_setFunctionRemoveUnusedServer(context, SMBC_remove_unused_server);
     191             : 
     192           0 :         smbc_setOptionUserData(context, NULL);
     193           0 :         smbc_setFunctionAddCachedServer(context, SMBC_add_cached_server);
     194           0 :         smbc_setFunctionGetCachedServer(context, SMBC_get_cached_server);
     195           0 :         smbc_setFunctionRemoveCachedServer(context, SMBC_remove_cached_server);
     196           0 :         smbc_setFunctionPurgeCachedServers(context, SMBC_purge_cached_servers);
     197             : 
     198           0 :         smbc_setFunctionOpen(context, SMBC_open_ctx);
     199           0 :         smbc_setFunctionCreat(context, SMBC_creat_ctx);
     200           0 :         smbc_setFunctionRead(context, SMBC_read_ctx);
     201           0 :         smbc_setFunctionSplice(context, SMBC_splice_ctx);
     202           0 :         smbc_setFunctionWrite(context, SMBC_write_ctx);
     203           0 :         smbc_setFunctionClose(context, SMBC_close_ctx);
     204           0 :         smbc_setFunctionUnlink(context, SMBC_unlink_ctx);
     205           0 :         smbc_setFunctionRename(context, SMBC_rename_ctx);
     206           0 :         smbc_setFunctionLseek(context, SMBC_lseek_ctx);
     207           0 :         smbc_setFunctionFtruncate(context, SMBC_ftruncate_ctx);
     208           0 :         smbc_setFunctionStat(context, SMBC_stat_ctx);
     209           0 :         smbc_setFunctionStatVFS(context, SMBC_statvfs_ctx);
     210           0 :         smbc_setFunctionFstatVFS(context, SMBC_fstatvfs_ctx);
     211           0 :         smbc_setFunctionFstat(context, SMBC_fstat_ctx);
     212           0 :         smbc_setFunctionOpendir(context, SMBC_opendir_ctx);
     213           0 :         smbc_setFunctionClosedir(context, SMBC_closedir_ctx);
     214           0 :         smbc_setFunctionReaddir(context, SMBC_readdir_ctx);
     215           0 :         smbc_setFunctionReaddirPlus(context, SMBC_readdirplus_ctx);
     216           0 :         smbc_setFunctionReaddirPlus2(context, SMBC_readdirplus2_ctx);
     217           0 :         smbc_setFunctionGetdents(context, SMBC_getdents_ctx);
     218           0 :         smbc_setFunctionMkdir(context, SMBC_mkdir_ctx);
     219           0 :         smbc_setFunctionRmdir(context, SMBC_rmdir_ctx);
     220           0 :         smbc_setFunctionTelldir(context, SMBC_telldir_ctx);
     221           0 :         smbc_setFunctionLseekdir(context, SMBC_lseekdir_ctx);
     222           0 :         smbc_setFunctionFstatdir(context, SMBC_fstatdir_ctx);
     223           0 :         smbc_setFunctionNotify(context, SMBC_notify_ctx);
     224           0 :         smbc_setFunctionChmod(context, SMBC_chmod_ctx);
     225           0 :         smbc_setFunctionUtimes(context, SMBC_utimes_ctx);
     226           0 :         smbc_setFunctionSetxattr(context, SMBC_setxattr_ctx);
     227           0 :         smbc_setFunctionGetxattr(context, SMBC_getxattr_ctx);
     228           0 :         smbc_setFunctionRemovexattr(context, SMBC_removexattr_ctx);
     229           0 :         smbc_setFunctionListxattr(context, SMBC_listxattr_ctx);
     230             : 
     231           0 :         smbc_setFunctionOpenPrintJob(context, SMBC_open_print_job_ctx);
     232           0 :         smbc_setFunctionPrintFile(context, SMBC_print_file_ctx);
     233           0 :         smbc_setFunctionListPrintJobs(context, SMBC_list_print_jobs_ctx);
     234           0 :         smbc_setFunctionUnlinkPrintJob(context, SMBC_unlink_print_job_ctx);
     235             : 
     236           0 :         TALLOC_FREE(frame);
     237           0 :         return context;
     238             : }
     239             : 
     240             : /*
     241             :  * Free a context
     242             :  *
     243             :  * Returns 0 on success. Otherwise returns 1, the SMBCCTX is _not_ freed
     244             :  * and thus you'll be leaking memory if not handled properly.
     245             :  *
     246             :  */
     247             : int
     248           0 : smbc_free_context(SMBCCTX *context,
     249             :                   int shutdown_ctx)
     250             : {
     251             :         TALLOC_CTX *frame;
     252           0 :         if (!context) {
     253           0 :                 errno = EBADF;
     254           0 :                 return 1;
     255             :         }
     256             : 
     257           0 :         frame = talloc_stackframe();
     258             : 
     259           0 :         if (shutdown_ctx) {
     260             :                 SMBCFILE * f;
     261           0 :                 DEBUG(1,("Performing aggressive shutdown.\n"));
     262             : 
     263           0 :                 f = context->internal->files;
     264           0 :                 while (f) {
     265           0 :                         SMBCFILE *next = f->next;
     266           0 :                         smbc_getFunctionClose(context)(context, f);
     267           0 :                         f = next;
     268             :                 }
     269           0 :                 context->internal->files = NULL;
     270             : 
     271             :                 /* First try to remove the servers the nice way. */
     272           0 :                 if (smbc_getFunctionPurgeCachedServers(context)(context)) {
     273             :                         SMBCSRV * s;
     274             :                         SMBCSRV * next;
     275           0 :                         DEBUG(1, ("Could not purge all servers, "
     276             :                                   "Nice way shutdown failed.\n"));
     277           0 :                         s = context->internal->servers;
     278           0 :                         while (s) {
     279           0 :                                 DEBUG(1, ("Forced shutdown: %p (cli=%p)\n",
     280             :                                           s, s->cli));
     281           0 :                                 cli_shutdown(s->cli);
     282           0 :                                 smbc_getFunctionRemoveCachedServer(context)(context,
     283             :                                                                          s);
     284           0 :                                 next = s->next;
     285           0 :                                 DLIST_REMOVE(context->internal->servers, s);
     286           0 :                                 SAFE_FREE(s);
     287           0 :                                 s = next;
     288             :                         }
     289           0 :                         context->internal->servers = NULL;
     290             :                 }
     291             :         }
     292             :         else {
     293             :                 /* This is the polite way */
     294           0 :                 if (smbc_getFunctionPurgeCachedServers(context)(context)) {
     295           0 :                         DEBUG(1, ("Could not purge all servers, "
     296             :                                   "free_context failed.\n"));
     297           0 :                         errno = EBUSY;
     298           0 :                         TALLOC_FREE(frame);
     299           0 :                         return 1;
     300             :                 }
     301           0 :                 if (context->internal->servers) {
     302           0 :                         DEBUG(1, ("Active servers in context, "
     303             :                                   "free_context failed.\n"));
     304           0 :                         errno = EBUSY;
     305           0 :                         TALLOC_FREE(frame);
     306           0 :                         return 1;
     307             :                 }
     308           0 :                 if (context->internal->files) {
     309           0 :                         DEBUG(1, ("Active files in context, "
     310             :                                   "free_context failed.\n"));
     311           0 :                         errno = EBUSY;
     312           0 :                         TALLOC_FREE(frame);
     313           0 :                         return 1;
     314             :                 }
     315             :         }
     316             : 
     317             :         /* Things we have to clean up */
     318           0 :         smbc_setWorkgroup(context, NULL);
     319           0 :         smbc_setNetbiosName(context, NULL);
     320           0 :         smbc_setUser(context, NULL);
     321             : 
     322           0 :         DEBUG(3, ("Context %p successfully freed\n", context));
     323             : 
     324             :         /* Free any DFS auth context. */
     325           0 :         TALLOC_FREE(context->internal->creds);
     326             : 
     327           0 :         SAFE_FREE(context->internal);
     328           0 :         SAFE_FREE(context);
     329             : 
     330             :         /* Protect access to the count of contexts in use */
     331           0 :         if (SMB_THREAD_LOCK(initialized_ctx_count_mutex) != 0) {
     332           0 :                 smb_panic("error locking 'initialized_ctx_count'");
     333             :         }
     334             : 
     335           0 :         if (initialized_ctx_count) {
     336           0 :                 initialized_ctx_count--;
     337             :         }
     338             : 
     339           0 :         if (initialized_ctx_count == 0) {
     340           0 :             SMBC_module_terminate();
     341             :         }
     342             : 
     343             :         /* Unlock the mutex */
     344           0 :         if (SMB_THREAD_UNLOCK(initialized_ctx_count_mutex) != 0) {
     345           0 :                 smb_panic("error unlocking 'initialized_ctx_count'");
     346             :         }
     347             : 
     348           0 :         TALLOC_FREE(frame);
     349           0 :         return 0;
     350             : }
     351             : 
     352             : 
     353             : /**
     354             :  * Deprecated interface.  Do not use.  Instead, use the various
     355             :  * smbc_setOption*() functions or smbc_setFunctionAuthDataWithContext().
     356             :  */
     357             : void
     358           0 : smbc_option_set(SMBCCTX *context,
     359             :                 char *option_name,
     360             :                 ... /* option_value */)
     361             : {
     362             :         va_list ap;
     363             :         union {
     364             :                 int i;
     365             :                 bool b;
     366             :                 smbc_get_auth_data_with_context_fn auth_fn;
     367             :                 void *v;
     368             :                 const char *s;
     369             :         } option_value;
     370             : 
     371           0 :         TALLOC_CTX *frame = talloc_stackframe();
     372             : 
     373           0 :         va_start(ap, option_name);
     374             : 
     375           0 :         if (strcmp(option_name, "debug_to_stderr") == 0) {
     376           0 :                 option_value.b = (bool) va_arg(ap, int);
     377           0 :                 smbc_setOptionDebugToStderr(context, option_value.b);
     378             : 
     379           0 :         } else if (strcmp(option_name, "full_time_names") == 0) {
     380           0 :                 option_value.b = (bool) va_arg(ap, int);
     381           0 :                 smbc_setOptionFullTimeNames(context, option_value.b);
     382             : 
     383           0 :         } else if (strcmp(option_name, "open_share_mode") == 0) {
     384           0 :                 option_value.i = va_arg(ap, int);
     385           0 :                 smbc_setOptionOpenShareMode(context, option_value.i);
     386             : 
     387           0 :         } else if (strcmp(option_name, "auth_function") == 0) {
     388           0 :                 option_value.auth_fn =
     389           0 :                         va_arg(ap, smbc_get_auth_data_with_context_fn);
     390           0 :                 smbc_setFunctionAuthDataWithContext(context, option_value.auth_fn);
     391             : 
     392           0 :         } else if (strcmp(option_name, "user_data") == 0) {
     393           0 :                 option_value.v = va_arg(ap, void *);
     394           0 :                 smbc_setOptionUserData(context, option_value.v);
     395             : 
     396           0 :         } else if (strcmp(option_name, "smb_encrypt_level") == 0) {
     397           0 :                 option_value.s = va_arg(ap, const char *);
     398           0 :                 if (strcmp(option_value.s, "none") == 0) {
     399           0 :                         smbc_setOptionSmbEncryptionLevel(context,
     400             :                                                          SMBC_ENCRYPTLEVEL_NONE);
     401           0 :                 } else if (strcmp(option_value.s, "request") == 0) {
     402           0 :                         smbc_setOptionSmbEncryptionLevel(context,
     403             :                                                          SMBC_ENCRYPTLEVEL_REQUEST);
     404           0 :                 } else if (strcmp(option_value.s, "require") == 0) {
     405           0 :                         smbc_setOptionSmbEncryptionLevel(context,
     406             :                                                          SMBC_ENCRYPTLEVEL_REQUIRE);
     407             :                 }
     408             : 
     409           0 :         } else if (strcmp(option_name, "browse_max_lmb_count") == 0) {
     410           0 :                 option_value.i = va_arg(ap, int);
     411           0 :                 smbc_setOptionBrowseMaxLmbCount(context, option_value.i);
     412             : 
     413           0 :         } else if (strcmp(option_name, "urlencode_readdir_entries") == 0) {
     414           0 :                 option_value.b = (bool) va_arg(ap, int);
     415           0 :                 smbc_setOptionUrlEncodeReaddirEntries(context, option_value.b);
     416             : 
     417           0 :         } else if (strcmp(option_name, "one_share_per_server") == 0) {
     418           0 :                 option_value.b = (bool) va_arg(ap, int);
     419           0 :                 smbc_setOptionOneSharePerServer(context, option_value.b);
     420             : 
     421           0 :         } else if (strcmp(option_name, "use_kerberos") == 0) {
     422           0 :                 option_value.b = (bool) va_arg(ap, int);
     423           0 :                 smbc_setOptionUseKerberos(context, option_value.b);
     424             : 
     425           0 :         } else if (strcmp(option_name, "fallback_after_kerberos") == 0) {
     426           0 :                 option_value.b = (bool) va_arg(ap, int);
     427           0 :                 smbc_setOptionFallbackAfterKerberos(context, option_value.b);
     428             : 
     429           0 :         } else if (strcmp(option_name, "use_ccache") == 0) {
     430           0 :                 option_value.b = (bool) va_arg(ap, int);
     431           0 :                 smbc_setOptionUseCCache(context, option_value.b);
     432             : 
     433           0 :         } else if (strcmp(option_name, "no_auto_anonymous_login") == 0) {
     434           0 :                 option_value.b = (bool) va_arg(ap, int);
     435           0 :                 smbc_setOptionNoAutoAnonymousLogin(context, option_value.b);
     436             :         }
     437             : 
     438           0 :         va_end(ap);
     439           0 :         TALLOC_FREE(frame);
     440           0 : }
     441             : 
     442             : 
     443             : /*
     444             :  * Deprecated interface.  Do not use.  Instead, use the various
     445             :  * smbc_getOption*() functions.
     446             :  */
     447             : void *
     448           0 : smbc_option_get(SMBCCTX *context,
     449             :                 char *option_name)
     450             : {
     451           0 :         if (strcmp(option_name, "debug_stderr") == 0) {
     452             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     453           0 :                 return (void *) (intptr_t) smbc_getOptionDebugToStderr(context);
     454             : #else
     455             :                 return (void *) smbc_getOptionDebugToStderr(context);
     456             : #endif
     457             : 
     458           0 :         } else if (strcmp(option_name, "full_time_names") == 0) {
     459             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     460           0 :                 return (void *) (intptr_t) smbc_getOptionFullTimeNames(context);
     461             : #else
     462             :                 return (void *) smbc_getOptionFullTimeNames(context);
     463             : #endif
     464             : 
     465           0 :         } else if (strcmp(option_name, "open_share_mode") == 0) {
     466             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     467           0 :                 return (void *) (intptr_t) smbc_getOptionOpenShareMode(context);
     468             : #else
     469             :                 return (void *) smbc_getOptionOpenShareMode(context);
     470             : #endif
     471             : 
     472           0 :         } else if (strcmp(option_name, "auth_function") == 0) {
     473           0 :                 return (void *) smbc_getFunctionAuthDataWithContext(context);
     474             : 
     475           0 :         } else if (strcmp(option_name, "user_data") == 0) {
     476           0 :                 return smbc_getOptionUserData(context);
     477             : 
     478           0 :         } else if (strcmp(option_name, "smb_encrypt_level") == 0) {
     479           0 :                 switch(smbc_getOptionSmbEncryptionLevel(context))
     480             :                 {
     481           0 :                 case SMBC_ENCRYPTLEVEL_DEFAULT:
     482           0 :                         return discard_const_p(void, "default");
     483           0 :                 case 0:
     484           0 :                         return discard_const_p(void, "none");
     485           0 :                 case 1:
     486           0 :                         return discard_const_p(void, "request");
     487           0 :                 case 2:
     488           0 :                         return discard_const_p(void, "require");
     489             :                 }
     490             : 
     491           0 :         } else if (strcmp(option_name, "smb_encrypt_on") == 0) {
     492             :                 SMBCSRV *s;
     493           0 :                 unsigned int num_servers = 0;
     494             : 
     495           0 :                 for (s = context->internal->servers; s; s = s->next) {
     496           0 :                         num_servers++;
     497           0 :                         if (!cli_state_is_encryption_on(s->cli)) {
     498           0 :                                 return (void *)false;
     499             :                         }
     500             :                 }
     501             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     502           0 :                 return (void *) (intptr_t) (bool) (num_servers > 0);
     503             : #else
     504             :                 return (void *) (bool) (num_servers > 0);
     505             : #endif
     506             : 
     507           0 :         } else if (strcmp(option_name, "browse_max_lmb_count") == 0) {
     508             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     509           0 :                 return (void *) (intptr_t) smbc_getOptionBrowseMaxLmbCount(context);
     510             : #else
     511             :                 return (void *) smbc_getOptionBrowseMaxLmbCount(context);
     512             : #endif
     513             : 
     514           0 :         } else if (strcmp(option_name, "urlencode_readdir_entries") == 0) {
     515             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     516           0 :                 return (void *)(intptr_t) smbc_getOptionUrlEncodeReaddirEntries(context);
     517             : #else
     518             :                 return (void *) (bool) smbc_getOptionUrlEncodeReaddirEntries(context);
     519             : #endif
     520             : 
     521           0 :         } else if (strcmp(option_name, "one_share_per_server") == 0) {
     522             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     523           0 :                 return (void *) (intptr_t) smbc_getOptionOneSharePerServer(context);
     524             : #else
     525             :                 return (void *) (bool) smbc_getOptionOneSharePerServer(context);
     526             : #endif
     527             : 
     528           0 :         } else if (strcmp(option_name, "use_kerberos") == 0) {
     529             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     530           0 :                 return (void *) (intptr_t) smbc_getOptionUseKerberos(context);
     531             : #else
     532             :                 return (void *) (bool) smbc_getOptionUseKerberos(context);
     533             : #endif
     534             : 
     535           0 :         } else if (strcmp(option_name, "fallback_after_kerberos") == 0) {
     536             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     537           0 :                 return (void *)(intptr_t) smbc_getOptionFallbackAfterKerberos(context);
     538             : #else
     539             :                 return (void *) (bool) smbc_getOptionFallbackAfterKerberos(context);
     540             : #endif
     541             : 
     542           0 :         } else if (strcmp(option_name, "use_ccache") == 0) {
     543             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     544           0 :                 return (void *) (intptr_t) smbc_getOptionUseCCache(context);
     545             : #else
     546             :                 return (void *) (bool) smbc_getOptionUseCCache(context);
     547             : #endif
     548             : 
     549           0 :         } else if (strcmp(option_name, "no_auto_anonymous_login") == 0) {
     550             : #if defined(__intptr_t_defined) || defined(HAVE_INTPTR_T)
     551           0 :                 return (void *) (intptr_t) smbc_getOptionNoAutoAnonymousLogin(context);
     552             : #else
     553             :                 return (void *) (bool) smbc_getOptionNoAutoAnonymousLogin(context);
     554             : #endif
     555             :         }
     556             : 
     557           0 :         return NULL;
     558             : }
     559             : 
     560             : 
     561             : /*
     562             :  * Initialize the library, etc.
     563             :  *
     564             :  * We accept a struct containing handle information.
     565             :  * valid values for info->debug from 0 to 100,
     566             :  * and insist that info->fn must be non-null.
     567             :  */
     568             : SMBCCTX *
     569           0 : smbc_init_context(SMBCCTX *context)
     570             : {
     571             :         int pid;
     572             :         TALLOC_CTX *frame;
     573             : 
     574           0 :         if (!context) {
     575           0 :                 errno = EBADF;
     576           0 :                 return NULL;
     577             :         }
     578             : 
     579             :         /* Do not initialise the same client twice */
     580           0 :         if (context->internal->initialized) {
     581           0 :                 return NULL;
     582             :         }
     583             : 
     584           0 :         frame = talloc_stackframe();
     585             : 
     586           0 :         if ((!smbc_getFunctionAuthData(context) &&
     587           0 :              !smbc_getFunctionAuthDataWithContext(context)) ||
     588           0 :             smbc_getDebug(context) < 0 ||
     589           0 :             smbc_getDebug(context) > 100) {
     590             : 
     591           0 :                 TALLOC_FREE(frame);
     592           0 :                 errno = EINVAL;
     593           0 :                 return NULL;
     594             : 
     595             :         }
     596             : 
     597           0 :         if (!smbc_getUser(context)) {
     598             :                 /*
     599             :                  * FIXME: Is this the best way to get the user info?
     600             :                  */
     601           0 :                 char *user = getenv("USER");
     602             :                 /* walk around as "guest" if no username can be found */
     603           0 :                 if (!user) {
     604           0 :                         user = SMB_STRDUP("guest");
     605             :                 } else {
     606           0 :                         user = SMB_STRDUP(user);
     607             :                 }
     608             : 
     609           0 :                 if (!user) {
     610           0 :                         TALLOC_FREE(frame);
     611           0 :                         errno = ENOMEM;
     612           0 :                         return NULL;
     613             :                 }
     614             : 
     615           0 :                 smbc_setUser(context, user);
     616           0 :                 SAFE_FREE(user);
     617             : 
     618           0 :                 if (!smbc_getUser(context)) {
     619           0 :                         TALLOC_FREE(frame);
     620           0 :                         errno = ENOMEM;
     621           0 :                         return NULL;
     622             :                 }
     623             :         }
     624             : 
     625           0 :         if (!smbc_getNetbiosName(context)) {
     626             :                 /*
     627             :                  * We try to get our netbios name from the config. If that
     628             :                  * fails we fall back on constructing our netbios name from
     629             :                  * our hostname etc
     630             :                  */
     631             :                 char *netbios_name;
     632           0 :                 if (lp_netbios_name()) {
     633           0 :                         netbios_name = SMB_STRDUP(lp_netbios_name());
     634             :                 } else {
     635             :                         /*
     636             :                          * Hmmm, I want to get hostname as well, but I am too
     637             :                          * lazy for the moment
     638             :                          */
     639           0 :                         pid = getpid();
     640           0 :                         netbios_name = (char *)SMB_MALLOC(17);
     641           0 :                         if (!netbios_name) {
     642           0 :                                 TALLOC_FREE(frame);
     643           0 :                                 errno = ENOMEM;
     644           0 :                                 return NULL;
     645             :                         }
     646           0 :                         slprintf(netbios_name, 16,
     647             :                                  "smbc%s%d", smbc_getUser(context), pid);
     648             :                 }
     649             : 
     650           0 :                 if (!netbios_name) {
     651           0 :                         TALLOC_FREE(frame);
     652           0 :                         errno = ENOMEM;
     653           0 :                         return NULL;
     654             :                 }
     655             : 
     656           0 :                 smbc_setNetbiosName(context, netbios_name);
     657           0 :                 SAFE_FREE(netbios_name);
     658             : 
     659           0 :                 if (!smbc_getNetbiosName(context)) {
     660           0 :                         TALLOC_FREE(frame);
     661           0 :                         errno = ENOMEM;
     662           0 :                         return NULL;
     663             :                 }
     664             :         }
     665             : 
     666           0 :         DEBUG(1, ("Using netbios name %s.\n", smbc_getNetbiosName(context)));
     667             : 
     668           0 :         if (!smbc_getWorkgroup(context)) {
     669             :                 const char *workgroup;
     670             : 
     671           0 :                 if (lp_workgroup()) {
     672           0 :                         workgroup = lp_workgroup();
     673             :                 } else {
     674             :                         /* TODO: Think about a decent default workgroup */
     675           0 :                         workgroup = "samba";
     676             :                 }
     677             : 
     678           0 :                 smbc_setWorkgroup(context, workgroup);
     679             : 
     680           0 :                 if (!smbc_getWorkgroup(context)) {
     681           0 :                         TALLOC_FREE(frame);
     682           0 :                         errno = ENOMEM;
     683           0 :                         return NULL;
     684             :                 }
     685             :         }
     686             : 
     687           0 :         DEBUG(1, ("Using workgroup %s.\n", smbc_getWorkgroup(context)));
     688             : 
     689             :         /* shortest timeout is 1 second */
     690           0 :         if (smbc_getTimeout(context) > 0 && smbc_getTimeout(context) < 1000)
     691           0 :                 smbc_setTimeout(context, 1000);
     692             : 
     693           0 :         context->internal->initialized = True;
     694             : 
     695             :         /* Protect access to the count of contexts in use */
     696           0 :         if (SMB_THREAD_LOCK(initialized_ctx_count_mutex) != 0) {
     697           0 :                 smb_panic("error locking 'initialized_ctx_count'");
     698             :         }
     699             : 
     700           0 :         initialized_ctx_count++;
     701             : 
     702             :         /* Unlock the mutex */
     703           0 :         if (SMB_THREAD_UNLOCK(initialized_ctx_count_mutex) != 0) {
     704           0 :                 smb_panic("error unlocking 'initialized_ctx_count'");
     705             :         }
     706             : 
     707           0 :         TALLOC_FREE(frame);
     708           0 :         return context;
     709             : }
     710             : 
     711             : 
     712             : /* Return the version of samba, and thus libsmbclient */
     713             : const char *
     714           0 : smbc_version(void)
     715             : {
     716           0 :         return samba_version_string();
     717             : }
     718             : 
     719             : /*
     720             :  * Set the credentials so DFS will work when following referrals.
     721             :  * This function is broken and must be removed. No SMBCCTX arg...
     722             :  * JRA.
     723             :  */
     724             : 
     725             : void
     726           0 : smbc_set_credentials(const char *workgroup,
     727             :                         const char *user,
     728             :                         const char *password,
     729             :                         smbc_bool use_kerberos,
     730             :                         const char *signing_state)
     731             : {
     732           0 :         d_printf("smbc_set_credentials is obsolete. Replace with smbc_set_credentials_with_fallback().\n");
     733           0 : }
     734             : 
     735           0 : void smbc_set_credentials_with_fallback(SMBCCTX *context,
     736             :                                         const char *workgroup,
     737             :                                         const char *user,
     738             :                                         const char *password)
     739             : {
     740           0 :         struct loadparm_context *lp_ctx = NULL;
     741           0 :         struct cli_credentials *creds = NULL;
     742           0 :         enum credentials_use_kerberos kerberos_state =
     743             :                 CRED_USE_KERBEROS_DISABLED;
     744             : 
     745           0 :         if (! context) {
     746             : 
     747           0 :                 return;
     748             :         }
     749             : 
     750           0 :         if (! workgroup || ! *workgroup) {
     751           0 :                 workgroup = smbc_getWorkgroup(context);
     752             :         }
     753             : 
     754           0 :         if (! user) {
     755           0 :                 user = smbc_getUser(context);
     756             :         }
     757             : 
     758           0 :         if (! password) {
     759           0 :                 password = "";
     760             :         }
     761             : 
     762           0 :         creds = cli_credentials_init(NULL);
     763           0 :         if (creds == NULL) {
     764           0 :                 DEBUG(0, ("smbc_set_credentials_with_fallback: allocation fail\n"));
     765           0 :                 return;
     766             :         }
     767             : 
     768           0 :         lp_ctx = loadparm_init_s3(creds, loadparm_s3_helpers());
     769           0 :         if (lp_ctx == NULL) {
     770           0 :                 TALLOC_FREE(creds);
     771           0 :                 return;
     772             :         }
     773             : 
     774           0 :         cli_credentials_set_conf(creds, lp_ctx);
     775             : 
     776           0 :         if (smbc_getOptionUseKerberos(context)) {
     777           0 :                 kerberos_state = CRED_USE_KERBEROS_REQUIRED;
     778             : 
     779           0 :                 if (smbc_getOptionFallbackAfterKerberos(context)) {
     780           0 :                         kerberos_state = CRED_USE_KERBEROS_DESIRED;
     781             :                 }
     782             :         }
     783             : 
     784           0 :         cli_credentials_set_username(creds, user, CRED_SPECIFIED);
     785           0 :         cli_credentials_set_password(creds, password, CRED_SPECIFIED);
     786           0 :         cli_credentials_set_domain(creds, workgroup, CRED_SPECIFIED);
     787           0 :         cli_credentials_set_kerberos_state(creds,
     788             :                                            kerberos_state,
     789             :                                            CRED_SPECIFIED);
     790           0 :         if (smbc_getOptionUseCCache(context)) {
     791             :                 uint32_t gensec_features;
     792             : 
     793           0 :                 gensec_features = cli_credentials_get_gensec_features(creds);
     794           0 :                 gensec_features |= GENSEC_FEATURE_NTLM_CCACHE;
     795           0 :                 cli_credentials_set_gensec_features(creds,
     796             :                                                     gensec_features,
     797             :                                                     CRED_SPECIFIED);
     798             :         }
     799             : 
     800           0 :         TALLOC_FREE(context->internal->creds);
     801           0 :         context->internal->creds = creds;
     802             : }

Generated by: LCOV version 1.14