int add_home_service(const char *service, const char *username, const char *homedir) { int iHomeService; if (!service || !homedir || homedir[0] == '\0') return -1; if ((iHomeService = lp_servicenumber(HOMES_NAME)) < 0) return -1; /* * If this is a winbindd provided username, remove * the domain component before adding the service. * Log a warning if the "path=" parameter does not * include any macros. */ { const char *p = strchr(service,*lp_winbind_separator()); /* We only want the 'user' part of the string */ if (p) { service = p + 1; } } if (!lp_add_home(service, iHomeService, username, homedir)) { return -1; } return lp_servicenumber(service); }
static int register_homes_share(const char *username) { int result; struct passwd *pwd; result = lp_servicenumber(username); if (result != -1) { DEBUG(3, ("Using static (or previously created) service for " "user '%s'; path = '%s'\n", username, lp_pathname(result))); return result; } pwd = getpwnam_alloc(talloc_tos(), username); if ((pwd == NULL) || (pwd->pw_dir[0] == '\0')) { DEBUG(3, ("No home directory defined for user '%s'\n", username)); TALLOC_FREE(pwd); return -1; } DEBUG(3, ("Adding homes service for user '%s' using home directory: " "'%s'\n", username, pwd->pw_dir)); result = add_home_service(username, username, pwd->pw_dir); TALLOC_FREE(pwd); return result; }
int print_queue_snum(const char *qname) { int snum = lp_servicenumber(qname); if (snum == -1 || !lp_print_ok(snum)) return -1; return snum; }
uint16 DosNetShareGetInfo(PCONN_HND phnd, SMBCHR pszNetName, uint16 sLevel, RCVBUF pbBuffer, RCVBUFLEN cbBuffer, uint16 *pcTotalAvail) { int snum = lp_servicenumber(pszNetName); *pcTotalAvail = 0; DEBUG(10,("DosNetShareGetInfo: %s [%d]\n", pszNetName ? pszNetName : "", snum)); if (pszNetName == 0 || snum < 0) return ERRnosuchshare; switch (sLevel) { case 1: { SHARE_INFO_1 *sh1 = (SHARE_INFO_1*)pbBuffer; if (cbBuffer < sizeof(SHARE_INFO_1)) { *pcTotalAvail = sizeof(SHARE_INFO_1); return ERRmoredata; } fill_share_1(sh1, snum); return ERRsuccess; } } return ERRunknownlevel; }
void reload_printers(void) { int snum; int n_services = lp_numservices(); int pnum = lp_servicenumber(PRINTERS_NAME); const char *pname; pcap_cache_reload(); /* remove stale printers */ for (snum = 0; snum < n_services; snum++) { /* avoid removing PRINTERS_NAME or non-autoloaded printers */ if (snum == pnum || !(lp_snum_ok(snum) && lp_print_ok(snum) && lp_autoloaded(snum))) continue; pname = lp_printername(snum); if (!pcap_printername_ok(pname)) { DEBUG(3, ("removing stale printer %s\n", pname)); if (is_printer_published(NULL, snum, NULL)) nt_printer_publish(NULL, snum, SPOOL_DS_UNPUBLISH); del_a_printer(pname); lp_killservice(snum); } } load_printers(); }
/*************************************************************************** load automatic printer services ***************************************************************************/ void load_printers(void) { if (!pcap_cache_loaded()) pcap_cache_reload(); add_auto_printers(); /* load all printcap printers */ if (lp_load_printers() && lp_servicenumber(PRINTERS_NAME) >= 0) pcap_printer_fn(lp_add_one_printer, NULL); }
static void process_requests(void) { char *req = cgi_variable("request"); char *newvalue = cgi_variable("newvalue"); char *parameter = cgi_variable("parameter"); char *service = cgi_variable("service"); int snum=0; if (!req) return; if (service) { /* work out what service it is */ if (strcmp(service,SGLOBAL) == 0) { snum = GLOBALS_SNUM; } else if (strcmp(service,SDEFAULTS) == 0) { snum = DEFAULTS_SNUM; } else { snum = lp_servicenumber(service); if (snum < 0) return; } } if (!newvalue) newvalue = ""; if (strcmp(req,"Change") == 0) { /* change the value of a parameter */ if (!parameter || !service) return; lp_do_parameter(snum, parameter, newvalue); } else if (strcmp(req,"Rename") == 0) { /* rename a service */ if (!newvalue || !service) return; lp_rename_service(snum, newvalue); } else if (strcmp(req,"Remove") == 0) { /* remove a service */ if (!service) return; lp_remove_service(snum); } else if (strcmp(req,"Copy") == 0) { /* copy a service */ if (!service || !newvalue) return; lp_copy_service(snum, newvalue); } save_reload(); }
/*************************************************************************** auto-load some homes and printer services ***************************************************************************/ static void add_auto_printers(void) { const char *p; int pnum = lp_servicenumber(PRINTERS_NAME); char *str; char *saveptr; if (pnum < 0) return; if ((str = SMB_STRDUP(lp_auto_services())) == NULL) return; for (p = strtok_r(str, LIST_SEP, &saveptr); p; p = strtok_r(NULL, LIST_SEP, &saveptr)) { if (lp_servicenumber(p) >= 0) continue; if (pcap_printername_ok(p)) lp_add_printer(p, pnum); } SAFE_FREE(str); }
static int load_registry_service(const char *servicename) { if (!lp_registry_shares()) { return -1; } if ((servicename == NULL) || (*servicename == '\0')) { return -1; } if (strequal(servicename, GLOBAL_NAME)) { return -2; } if (!process_registry_service(servicename)) { return -1; } return lp_servicenumber(servicename); }
/**************************************************************************** purge stale printers and reload from pre-populated pcap cache **************************************************************************/ void reload_printers(struct tevent_context *ev, struct messaging_context *msg_ctx) { int n_services; int pnum; int snum; const char *pname; n_services = lp_numservices(); pnum = lp_servicenumber(PRINTERS_NAME); DEBUG(10, ("reloading printer services from pcap cache\n")); /* * Add default config for printers added to smb.conf file and remove * stale printers */ for (snum = 0; snum < n_services; snum++) { /* avoid removing PRINTERS_NAME */ if (snum == pnum) { continue; } /* skip no-printer services */ if (!(lp_snum_ok(snum) && lp_print_ok(snum))) { continue; } pname = lp_printername(snum); /* check printer, but avoid removing non-autoloaded printers */ if (lp_autoloaded(snum) && !pcap_printername_ok(pname)) { DEBUG(3, ("removing stale printer %s\n", pname)); lp_killservice(snum); } } /* Make sure deleted printers are gone */ load_printers(ev, msg_ctx); }
/** * @brief Purge stale printer shares and reload from pre-populated pcap cache. * * This function should normally only be called as a callback on a successful * pcap_cache_reload(), or on client enumeration. * * @param[in] ev The event context. * * @param[in] msg_ctx The messaging context. */ void delete_and_reload_printers(struct tevent_context *ev, struct messaging_context *msg_ctx) { int n_services; int pnum; int snum; const char *pname; bool ok; time_t pcap_last_update; TALLOC_CTX *frame = talloc_stackframe(); ok = pcap_cache_loaded(&pcap_last_update); if (!ok) { DEBUG(1, ("pcap cache not loaded\n")); talloc_free(frame); return; } if (reload_last_pcap_time == pcap_last_update) { DEBUG(5, ("skipping printer reload, already up to date.\n")); talloc_free(frame); return; } reload_last_pcap_time = pcap_last_update; /* Get pcap printers updated */ load_printers(ev, msg_ctx); n_services = lp_numservices(); pnum = lp_servicenumber(PRINTERS_NAME); DEBUG(10, ("reloading printer services from pcap cache\n")); /* * Add default config for printers added to smb.conf file and remove * stale printers */ for (snum = 0; snum < n_services; snum++) { /* avoid removing PRINTERS_NAME */ if (snum == pnum) { continue; } /* skip no-printer services */ if (!snum_is_shared_printer(snum)) { continue; } pname = lp_printername(frame, snum); /* check printer, but avoid removing non-autoloaded printers */ if (lp_autoloaded(snum) && !pcap_printername_ok(pname)) { lp_killservice(snum); } } /* Make sure deleted printers are gone */ load_printers(ev, msg_ctx); talloc_free(frame); }
int register_vuid(auth_serversupplied_info *server_info, DATA_BLOB session_key, DATA_BLOB response_blob, const char *smb_name) { user_struct *vuser = NULL; /* Paranoia check. */ if(lp_security() == SEC_SHARE) { smb_panic("Tried to register uid in security=share\n"); } /* Limit allowed vuids to 16bits - VUID_OFFSET. */ if (num_validated_vuids >= 0xFFFF-VUID_OFFSET) { data_blob_free(&session_key); return UID_FIELD_INVALID; } if((vuser = SMB_MALLOC_P(user_struct)) == NULL) { DEBUG(0,("Failed to malloc users struct!\n")); data_blob_free(&session_key); return UID_FIELD_INVALID; } ZERO_STRUCTP(vuser); /* Allocate a free vuid. Yes this is a linear search... :-) */ while( get_valid_user_struct(next_vuid) != NULL ) { next_vuid++; /* Check for vuid wrap. */ if (next_vuid == UID_FIELD_INVALID) next_vuid = VUID_OFFSET; } DEBUG(10,("register_vuid: allocated vuid = %u\n", (unsigned int)next_vuid )); vuser->vuid = next_vuid; if (!server_info) { /* * This happens in an unfinished NTLMSSP session setup. We * need to allocate a vuid between the first and second calls * to NTLMSSP. */ next_vuid++; num_validated_vuids++; vuser->server_info = NULL; DLIST_ADD(validated_users, vuser); return vuser->vuid; } /* the next functions should be done by a SID mapping system (SMS) as * the new real sam db won't have reference to unix uids or gids */ vuser->uid = server_info->uid; vuser->gid = server_info->gid; vuser->n_groups = server_info->n_groups; if (vuser->n_groups) { if (!(vuser->groups = (gid_t *)memdup(server_info->groups, sizeof(gid_t) * vuser->n_groups))) { DEBUG(0,("register_vuid: failed to memdup " "vuser->groups\n")); data_blob_free(&session_key); free(vuser); TALLOC_FREE(server_info); return UID_FIELD_INVALID; } } vuser->guest = server_info->guest; fstrcpy(vuser->user.unix_name, server_info->unix_name); /* This is a potentially untrusted username */ alpha_strcpy(vuser->user.smb_name, smb_name, ". _-$", sizeof(vuser->user.smb_name)); fstrcpy(vuser->user.domain, pdb_get_domain(server_info->sam_account)); fstrcpy(vuser->user.full_name, pdb_get_fullname(server_info->sam_account)); { /* Keep the homedir handy */ const char *homedir = pdb_get_homedir(server_info->sam_account); const char *logon_script = pdb_get_logon_script(server_info->sam_account); if (!IS_SAM_DEFAULT(server_info->sam_account, PDB_UNIXHOMEDIR)) { const char *unix_homedir = pdb_get_unix_homedir(server_info->sam_account); if (unix_homedir) { vuser->unix_homedir = smb_xstrdup(unix_homedir); } } else { struct passwd *passwd = getpwnam_alloc(NULL, vuser->user.unix_name); if (passwd) { vuser->unix_homedir = smb_xstrdup(passwd->pw_dir); TALLOC_FREE(passwd); } } if (homedir) { vuser->homedir = smb_xstrdup(homedir); } if (logon_script) { vuser->logon_script = smb_xstrdup(logon_script); } } vuser->session_key = session_key; DEBUG(10,("register_vuid: (%u,%u) %s %s %s guest=%d\n", (unsigned int)vuser->uid, (unsigned int)vuser->gid, vuser->user.unix_name, vuser->user.smb_name, vuser->user.domain, vuser->guest )); DEBUG(3, ("User name: %s\tReal name: %s\n", vuser->user.unix_name, vuser->user.full_name)); if (server_info->ptok) { vuser->nt_user_token = dup_nt_token(NULL, server_info->ptok); } else { DEBUG(1, ("server_info does not contain a user_token - " "cannot continue\n")); TALLOC_FREE(server_info); data_blob_free(&session_key); SAFE_FREE(vuser->homedir); SAFE_FREE(vuser->unix_homedir); SAFE_FREE(vuser->logon_script); SAFE_FREE(vuser); return UID_FIELD_INVALID; } /* use this to keep tabs on all our info from the authentication */ vuser->server_info = server_info; DEBUG(3,("UNIX uid %d is UNIX user %s, and will be vuid %u\n", (int)vuser->uid,vuser->user.unix_name, vuser->vuid)); next_vuid++; num_validated_vuids++; DLIST_ADD(validated_users, vuser); if (!session_claim(vuser)) { DEBUG(1, ("Failed to claim session for vuid=%d\n", vuser->vuid)); invalidate_vuid(vuser->vuid); return UID_FIELD_INVALID; } /* Register a home dir service for this user iff (a) This is not a guest connection, (b) we have a home directory defined (c) there s not an existing static share by that name If a share exists by this name (autoloaded or not) reuse it . */ vuser->homes_snum = -1; if ( (!vuser->guest) && vuser->unix_homedir && *(vuser->unix_homedir)) { int servicenumber = lp_servicenumber(vuser->user.unix_name); if ( servicenumber == -1 ) { DEBUG(3, ("Adding homes service for user '%s' using " "home directory: '%s'\n", vuser->user.unix_name, vuser->unix_homedir)); vuser->homes_snum = add_home_service(vuser->user.unix_name, vuser->user.unix_name, vuser->unix_homedir); } else { DEBUG(3, ("Using static (or previously created) " "service for user '%s'; path = '%s'\n", vuser->user.unix_name, lp_pathname(servicenumber) )); vuser->homes_snum = servicenumber; } } if (srv_is_signing_negotiated() && !vuser->guest && !srv_signing_started()) { /* Try and turn on server signing on the first non-guest * sessionsetup. */ srv_set_signing(vuser->session_key, response_blob); } /* fill in the current_user_info struct */ set_current_user_info( &vuser->user ); return vuser->vuid; }
/**************************************************************************** find a service entry ****************************************************************************/ int find_service(char *service) { int iService; all_string_sub(service,"\\","/",0); iService = lp_servicenumber(service); /* now handle the special case of a home directory */ if (iService < 0) { int iHomeService; /* We check that the HOMES_NAME exists before calling expensive functions like get_user_home_dir */ if ((iHomeService = lp_servicenumber(HOMES_NAME)) >= 0) { char *phome_dir = get_user_home_dir(service); if(!phome_dir) { /* * Try mapping the servicename, it may * be a Windows to unix mapped user name. */ if(map_username(service)) phome_dir = get_user_home_dir(service); } DEBUG(3,("checking for home directory %s gave %s\n",service, phome_dir?phome_dir:"(NULL)")); if (phome_dir) { lp_add_home(service,iHomeService,phome_dir); iService = lp_servicenumber(service); } } } #ifdef PRINTING /* If we still don't have a service, attempt to add it as a printer. */ if (iService < 0) { int iPrinterService; if ((iPrinterService = lp_servicenumber(PRINTERS_NAME)) >= 0) { char *pszTemp; DEBUG(3,("checking whether %s is a valid printer name...\n", service)); pszTemp = PRINTCAP; if ((pszTemp != NULL) && pcap_printername_ok(service, pszTemp)) { DEBUG(3,("%s is a valid printer name\n", service)); DEBUG(3,("adding %s as a printer service\n", service)); lp_add_printer(service,iPrinterService); iService = lp_servicenumber(service); if (iService < 0) DEBUG(0,("failed to add %s as a printer service!\n", service)); } else DEBUG(3,("%s is not a valid printer name\n", service)); } } #endif /* just possibly it's a default service? */ if (iService < 0) { char *pdefservice = lp_defaultservice(); if (pdefservice && *pdefservice && !strequal(pdefservice,service) && !strstr(service,"..")) { /* * We need to do a local copy here as lp_defaultservice() * returns one of the rotating lp_string buffers that * could get overwritten by the recursive find_service() call * below. Fix from Josef Hinteregger <*****@*****.**>. */ pstring defservice; pstrcpy(defservice, pdefservice); iService = find_service(defservice); if (iService >= 0) { all_string_sub(service,"_","/",0); iService = lp_add_service(service,iService); } } } if (iService >= 0) if (!VALID_SNUM(iService)) { DEBUG(0,("Invalid snum %d for %s\n",iService,service)); iService = -1; } if (iService < 0) DEBUG(3,("find_service() failed to find service %s\n", service)); return (iService); }
/** * @brief Purge stale printers and reload from pre-populated pcap cache. * * This function should normally only be called as a callback on a successful * pcap_cache_reload(). * * This function can cause DELETION of printers and drivers from our registry, * so calling it on a failed pcap reload may REMOVE permanently all printers * and drivers. * * @param[in] ev The event context. * * @param[in] msg_ctx The messaging context. */ static void delete_and_reload_printers_full(struct tevent_context *ev, struct messaging_context *msg_ctx) { struct auth_session_info *session_info = NULL; struct spoolss_PrinterInfo2 *pinfo2 = NULL; int n_services; int pnum; int snum; const char *pname; const char *sname; NTSTATUS status; n_services = lp_numservices(); pnum = lp_servicenumber(PRINTERS_NAME); status = make_session_info_system(talloc_tos(), &session_info); if (!NT_STATUS_IS_OK(status)) { DEBUG(3, ("reload_printers: " "Could not create system session_info\n")); /* can't remove stale printers before we * are fully initilized */ return; } /* * Add default config for printers added to smb.conf file and remove * stale printers */ for (snum = 0; snum < n_services; snum++) { /* avoid removing PRINTERS_NAME */ if (snum == pnum) { continue; } /* skip no-printer services */ if (!snum_is_shared_printer(snum)) { continue; } sname = lp_const_servicename(snum); pname = lp_printername(session_info, snum); /* check printer, but avoid removing non-autoloaded printers */ if (lp_autoloaded(snum) && !pcap_printername_ok(pname)) { DEBUG(3, ("removing stale printer %s\n", pname)); if (is_printer_published(session_info, session_info, msg_ctx, NULL, lp_servicename(session_info, snum), &pinfo2)) { nt_printer_publish(session_info, session_info, msg_ctx, pinfo2, DSPRINT_UNPUBLISH); TALLOC_FREE(pinfo2); } nt_printer_remove(session_info, session_info, msg_ctx, pname); } else { DEBUG(8, ("Adding default registry entry for printer " "[%s], if it doesn't exist.\n", sname)); nt_printer_add(session_info, session_info, msg_ctx, sname); } } /* finally, purge old snums */ delete_and_reload_printers(); TALLOC_FREE(session_info); }
static uint32 _srv_SMBtcon_NT1(PSESS_HND sess_hnd, uint16 *conn_tid, Q_TCON_ANDX_4 *q4, Q_TCON_ANDX_D_4 *qd4, R_TCON_ANDX_3 *r3, R_TCON_ANDX_D_3 *rd3) { PCONN_HND conn_hnd = NULL; int snum = -1; SMBSTR *dir_path = NULL; const char *path = smbstrA(&qd4->path); const char *dev = smbstrA(&qd4->device); char *service; struct vfs_connection_struct *vfs_conn; struct smb_connection_struct *conn; BOOL is_ipc; BOOL is_print; uint32 err = NT_STATUS_NOPROBLEMO; conn_hnd = find_conn_hnd_by_index(sess_hnd, *conn_tid); if (conn_hnd != NULL) { DEBUG(10,("close connection %d\n", *conn_tid)); conn_close_hnd(conn_hnd); } if (path == NULL || dev == NULL) return ERRDOS|ERRnosuchshare; DEBUG(10,("path: [%s] device: [%s]\n", path, dev)); service = strchr(path+2, '\\') + 1; snum = lp_servicenumber(service); if (snum < 0) { err = ERRDOS|ERRnosuchshare; goto end; } if (!create_conn_hnd(sess_hnd, &conn_hnd, NULL) || conn_hnd == NULL || !get_conn_index(conn_hnd, conn_tid)) { err = NT_STATUS_INVALID_HANDLE; goto end; } is_ipc = strequal(dev, "IPC") || strequal(service, "IPC$"); is_print = strequal(dev, "LPT:"); vfs_conn = g_new(struct vfs_connection_struct, 1); if (vfs_conn == NULL) { err = NT_STATUS_NO_MEMORY; goto end; } conn = g_new(struct smb_connection_struct, 1); if (conn == NULL) { err = NT_STATUS_NO_MEMORY; goto end; } if (is_ipc) { rd3->service = "IPC"; smbstr_initA(&rd3->nativefs, "", 0); dir_path = NULL; vfs_init_ipc(vfs_conn, snum); smbvfs_init_ipc(conn, snum); } else if (is_print) { rd3->service = "LPT:"; smbstr_initA(&rd3->nativefs, "", 0); dir_path = smbstr_setA("", 0); vfs_init_print(vfs_conn, snum); smbvfs_init_print(conn, snum); } else { rd3->service = "A:"; smbstr_initA(&rd3->nativefs, lp_fstype(snum), 0); dir_path = smbstr_setA(lp_pathname(snum), 0); vfs_init_fs(vfs_conn, snum); smbvfs_init_fs(conn, snum); } vfs_conn->connectpath = smbstr_dup(dir_path); if (!set_conn_info(conn_hnd, vfs_conn, conn, smbstr_dup(&qd4->path), dir_path)) { err = NT_STATUS_INVALID_HANDLE; goto end; } DEBUG(10,("service: [%s] snum: [%d] tid: [%d]\n", dir_path ? smbstrA(dir_path) : "", snum, *conn_tid)); end: if (err) { DEBUG(10,("error:[%x]\n", err)); conn_close_hnd(conn_hnd); } return err; }
int main(int argc, const char *argv[]) { int opt; int retval = 0; enum acl_mode mode = SMB_ACL_SET; static char *the_acl = NULL; fstring sharename; bool force_acl = False; int snum; poptContext pc; bool initialize_sid = False; struct poptOption long_options[] = { POPT_AUTOHELP { "remove", 'r', POPT_ARG_STRING, &the_acl, 'r', "Delete an ACE", "ACL" }, { "modify", 'm', POPT_ARG_STRING, &the_acl, 'm', "Modify an acl", "ACL" }, { "add", 'a', POPT_ARG_STRING, &the_acl, 'a', "Add an ACE", "ACL" }, { "replace", 'R', POPT_ARG_STRING, &the_acl, 'R', "Set share mission ACL", "ACLS" }, { "view", 'v', POPT_ARG_NONE, NULL, 'v', "View current share permissions" }, { "machine-sid", 'M', POPT_ARG_NONE, NULL, 'M', "Initialize the machine SID" }, { "force", 'F', POPT_ARG_NONE, NULL, 'F', "Force storing the ACL", "ACLS" }, POPT_COMMON_SAMBA { NULL } }; if ( !(ctx = talloc_stackframe()) ) { fprintf( stderr, "Failed to initialize talloc context!\n"); return -1; } /* set default debug level to 1 regardless of what smb.conf sets */ setup_logging( "sharesec", True ); DEBUGLEVEL_CLASS[DBGC_ALL] = 1; dbf = x_stderr; x_setbuf( x_stderr, NULL ); pc = poptGetContext("sharesec", argc, argv, long_options, 0); poptSetOtherOptionHelp(pc, "sharename\n"); while ((opt = poptGetNextOpt(pc)) != -1) { switch (opt) { case 'r': the_acl = smb_xstrdup(poptGetOptArg(pc)); mode = SMB_ACL_DELETE; break; case 'm': the_acl = smb_xstrdup(poptGetOptArg(pc)); mode = SMB_ACL_MODIFY; break; case 'a': the_acl = smb_xstrdup(poptGetOptArg(pc)); mode = SMB_ACL_ADD; break; case 'R': the_acl = smb_xstrdup(poptGetOptArg(pc)); mode = SMB_ACL_SET; break; case 'v': mode = SMB_ACL_VIEW; break; case 'F': force_acl = True; break; case 'M': initialize_sid = True; break; } } setlinebuf(stdout); load_case_tables(); lp_load( get_dyn_CONFIGFILE(), False, False, False, True ); /* check for initializing secrets.tdb first */ if ( initialize_sid ) { DOM_SID *sid = get_global_sam_sid(); if ( !sid ) { fprintf( stderr, "Failed to retrieve Machine SID!\n"); return 3; } printf ("%s\n", sid_string_tos( sid ) ); return 0; } if ( mode == SMB_ACL_VIEW && force_acl ) { fprintf( stderr, "Invalid combination of -F and -v\n"); return -1; } /* get the sharename */ if(!poptPeekArg(pc)) { poptPrintUsage(pc, stderr, 0); return -1; } fstrcpy(sharename, poptGetArg(pc)); snum = lp_servicenumber( sharename ); if ( snum == -1 && !force_acl ) { fprintf( stderr, "Invalid sharename: %s\n", sharename); return -1; } retval = change_share_sec(ctx, sharename, the_acl, mode); talloc_destroy(ctx); return retval; }
int find_service(fstring service) { int iService; struct smbd_server_connection *sconn = smbd_server_conn; all_string_sub(service,"\\","/",0); iService = lp_servicenumber(service); /* now handle the special case of a home directory */ if (iService < 0) { char *phome_dir = get_user_home_dir(talloc_tos(), service); if(!phome_dir) { /* * Try mapping the servicename, it may * be a Windows to unix mapped user name. */ if(map_username(sconn, service)) phome_dir = get_user_home_dir( talloc_tos(), service); } DEBUG(3,("checking for home directory %s gave %s\n",service, phome_dir?phome_dir:"(NULL)")); iService = add_home_service(service,service /* 'username' */, phome_dir); } /* If we still don't have a service, attempt to add it as a printer. */ if (iService < 0) { int iPrinterService; if ((iPrinterService = lp_servicenumber(PRINTERS_NAME)) < 0) { iPrinterService = load_registry_service(PRINTERS_NAME); } if (iPrinterService) { DEBUG(3,("checking whether %s is a valid printer name...\n", service)); if (pcap_printername_ok(service)) { DEBUG(3,("%s is a valid printer name\n", service)); DEBUG(3,("adding %s as a printer service\n", service)); lp_add_printer(service, iPrinterService); iService = lp_servicenumber(service); if (iService < 0) { DEBUG(0,("failed to add %s as a printer service!\n", service)); } } else { DEBUG(3,("%s is not a valid printer name\n", service)); } } } /* Check for default vfs service? Unsure whether to implement this */ if (iService < 0) { } if (iService < 0) { iService = load_registry_service(service); } /* Is it a usershare service ? */ if (iService < 0 && *lp_usershare_path()) { /* Ensure the name is canonicalized. */ strlower_m(service); iService = load_usershare_service(service); } /* just possibly it's a default service? */ if (iService < 0) { char *pdefservice = lp_defaultservice(); if (pdefservice && *pdefservice && !strequal(pdefservice,service) && !strstr_m(service,"..")) { /* * We need to do a local copy here as lp_defaultservice() * returns one of the rotating lp_string buffers that * could get overwritten by the recursive find_service() call * below. Fix from Josef Hinteregger <*****@*****.**>. */ char *defservice = SMB_STRDUP(pdefservice); if (!defservice) { goto fail; } /* Disallow anything except explicit share names. */ if (strequal(defservice,HOMES_NAME) || strequal(defservice, PRINTERS_NAME) || strequal(defservice, "IPC$")) { SAFE_FREE(defservice); goto fail; } iService = find_service(defservice); if (iService >= 0) { all_string_sub(service, "_","/",0); iService = lp_add_service(service, iService); } SAFE_FREE(defservice); } } if (iService >= 0) { if (!VALID_SNUM(iService)) { DEBUG(0,("Invalid snum %d for %s\n",iService, service)); iService = -1; } } fail: if (iService < 0) DEBUG(3,("find_service() failed to find service %s\n", service)); return (iService); }
int main(int argc, const char *argv[]) { const char *config_file = get_dyn_CONFIGFILE(); int s; static int silent_mode = False; static int show_all_parameters = False; int ret = 0; poptContext pc; static char *parameter_name = NULL; static const char *section_name = NULL; const char *cname; const char *caddr; static int show_defaults; static int skip_logic_checks = 0; struct poptOption long_options[] = { POPT_AUTOHELP {"suppress-prompt", 's', POPT_ARG_VAL, &silent_mode, 1, "Suppress prompt for enter"}, {"verbose", 'v', POPT_ARG_NONE, &show_defaults, 1, "Show default options too"}, {"skip-logic-checks", 'l', POPT_ARG_NONE, &skip_logic_checks, 1, "Skip the global checks"}, {"show-all-parameters", '\0', POPT_ARG_VAL, &show_all_parameters, True, "Show the parameters, type, possible values" }, {"parameter-name", '\0', POPT_ARG_STRING, ¶meter_name, 0, "Limit testparm to a named parameter" }, {"section-name", '\0', POPT_ARG_STRING, §ion_name, 0, "Limit testparm to a named section" }, POPT_COMMON_VERSION POPT_COMMON_DEBUGLEVEL POPT_COMMON_OPTION POPT_TABLEEND }; TALLOC_CTX *frame = talloc_stackframe(); load_case_tables(); /* * Set the default debug level to 2. * Allow it to be overridden by the command line, * not by smb.conf. */ lp_set_cmdline("log level", "2"); pc = poptGetContext(NULL, argc, argv, long_options, POPT_CONTEXT_KEEP_FIRST); poptSetOtherOptionHelp(pc, "[OPTION...] <config-file> [host-name] [host-ip]"); while(poptGetNextOpt(pc) != -1); if (show_all_parameters) { show_parameter_list(); exit(0); } setup_logging(poptGetArg(pc), DEBUG_STDERR); if (poptPeekArg(pc)) config_file = poptGetArg(pc); cname = poptGetArg(pc); caddr = poptGetArg(pc); poptFreeContext(pc); if ( cname && ! caddr ) { printf ( "ERROR: You must specify both a machine name and an IP address.\n" ); ret = 1; goto done; } fprintf(stderr,"Load smb config files from %s\n",config_file); if (!lp_load_with_registry_shares(config_file,False,True,False,True)) { fprintf(stderr,"Error loading services.\n"); ret = 1; goto done; } fprintf(stderr,"Loaded services file OK.\n"); if (skip_logic_checks == 0) { ret = do_global_checks(); } for (s=0;s<1000;s++) { if (VALID_SNUM(s)) if (strlen(lp_servicename(talloc_tos(), s)) > 12) { fprintf(stderr, "WARNING: You have some share names that are longer than 12 characters.\n" ); fprintf(stderr, "These may not be accessible to some older clients.\n" ); fprintf(stderr, "(Eg. Windows9x, WindowsMe, and smbclient prior to Samba 3.0.)\n" ); break; } } for (s=0;s<1000;s++) { if (VALID_SNUM(s) && (skip_logic_checks == 0)) { do_per_share_checks(s); } } if (!section_name && !parameter_name) { fprintf(stderr, "Server role: %s\n\n", server_role_str(lp_server_role())); } if (!cname) { if (!silent_mode) { fprintf(stderr,"Press enter to see a dump of your service definitions\n"); fflush(stdout); getc(stdin); } if (parameter_name || section_name) { bool isGlobal = False; s = GLOBAL_SECTION_SNUM; if (!section_name) { section_name = GLOBAL_NAME; isGlobal = True; } else if ((isGlobal=!strwicmp(section_name, GLOBAL_NAME)) == 0 && (s=lp_servicenumber(section_name)) == -1) { fprintf(stderr,"Unknown section %s\n", section_name); ret = 1; goto done; } if (parameter_name) { if (!dump_a_parameter( s, parameter_name, stdout, isGlobal)) { fprintf(stderr,"Parameter %s unknown for section %s\n", parameter_name, section_name); ret = 1; goto done; } } else { if (isGlobal == True) lp_dump(stdout, show_defaults, 0); else lp_dump_one(stdout, show_defaults, s); } goto done; } lp_dump(stdout, show_defaults, lp_numservices()); } if(cname && caddr){ /* this is totally ugly, a real `quick' hack */ for (s=0;s<1000;s++) { if (VALID_SNUM(s)) { if (allow_access(lp_hosts_deny(-1), lp_hosts_allow(-1), cname, caddr) && allow_access(lp_hosts_deny(s), lp_hosts_allow(s), cname, caddr)) { fprintf(stderr,"Allow connection from %s (%s) to %s\n", cname,caddr,lp_servicename(talloc_tos(), s)); } else { fprintf(stderr,"Deny connection from %s (%s) to %s\n", cname,caddr,lp_servicename(talloc_tos(), s)); } } } } done: gfree_loadparm(); TALLOC_FREE(frame); return ret; }