summaryrefslogtreecommitdiff
path: root/source3/smbd
diff options
context:
space:
mode:
authorJeremy Allison <jra@samba.org>2010-11-09 15:07:49 -0800
committerJeremy Allison <jra@samba.org>2010-11-10 01:14:17 +0000
commitf0dcc90f726e1232a4e0b74a03784281ea9a7cdc (patch)
treef05f122e49e766b6267feb65dc1dc738d4fbd70f /source3/smbd
parent3878fa4c435140bd2e3c59f8bdb932fe19e4c13a (diff)
downloadsamba-f0dcc90f726e1232a4e0b74a03784281ea9a7cdc.tar.gz
samba-f0dcc90f726e1232a4e0b74a03784281ea9a7cdc.tar.bz2
samba-f0dcc90f726e1232a4e0b74a03784281ea9a7cdc.zip
Fix bug 7781 - Samba transforms ShareName to lowercase (sharename) when adding new share via MMC
Change the find_service() interface to not depend on fstring, and create a useable talloc-based interface. Jeremy.
Diffstat (limited to 'source3/smbd')
-rw-r--r--source3/smbd/lanman.c7
-rw-r--r--source3/smbd/msdfs.c8
-rw-r--r--source3/smbd/service.c110
-rw-r--r--source3/smbd/smb2_tcon.c12
4 files changed, 92 insertions, 45 deletions
diff --git a/source3/smbd/lanman.c b/source3/smbd/lanman.c
index e5527a5812..fd8b0c7928 100644
--- a/source3/smbd/lanman.c
+++ b/source3/smbd/lanman.c
@@ -1994,7 +1994,8 @@ static bool api_RNetShareGetInfo(struct smbd_server_connection *sconn,
{
char *str1 = get_safe_str_ptr(param,tpscnt,param,2);
char *str2 = skip_string(param,tpscnt,str1);
- char *netname = skip_string(param,tpscnt,str2);
+ char *netname_in = skip_string(param,tpscnt,str2);
+ char *netname = NULL;
char *p = skip_string(param,tpscnt,netname);
int uLevel = get_safe_SVAL(param,tpscnt,p,0,-1);
int snum;
@@ -2003,8 +2004,8 @@ static bool api_RNetShareGetInfo(struct smbd_server_connection *sconn,
return False;
}
- snum = find_service(netname);
- if (snum < 0) {
+ snum = find_service(talloc_tos(), netname_in, &netname);
+ if (snum < 0 || !netname) {
return False;
}
diff --git a/source3/smbd/msdfs.c b/source3/smbd/msdfs.c
index c005a2f3ab..165e802a82 100644
--- a/source3/smbd/msdfs.c
+++ b/source3/smbd/msdfs.c
@@ -833,11 +833,13 @@ NTSTATUS get_referred_path(TALLOC_CTX *ctx,
/* Verify the share is a dfs root */
snum = lp_servicenumber(jucn->service_name);
if(snum < 0) {
- fstring service_name;
- fstrcpy(service_name, jucn->service_name);
- if ((snum = find_service(service_name)) < 0) {
+ char *service_name = NULL;
+ if ((snum = find_service(ctx, jucn->service_name, &service_name)) < 0) {
return NT_STATUS_NOT_FOUND;
}
+ if (!service_name) {
+ return NT_STATUS_NO_MEMORY;
+ }
TALLOC_FREE(jucn->service_name);
jucn->service_name = talloc_strdup(ctx, service_name);
if (!jucn->service_name) {
diff --git a/source3/smbd/service.c b/source3/smbd/service.c
index efe68d7c3f..5b6d9087a3 100644
--- a/source3/smbd/service.c
+++ b/source3/smbd/service.c
@@ -305,39 +305,47 @@ int add_home_service(const char *service, const char *username, const char *home
* @param service is modified (to canonical form??)
**/
-int find_service(fstring service)
+int find_service(TALLOC_CTX *ctx, const char *service_in, char **p_service_out)
{
int iService;
- all_string_sub(service,"\\","/",0);
+ if (!service_in) {
+ return -1;
+ }
+
+ /* First make a copy. */
+ *p_service_out = talloc_strdup(ctx, service_in);
+ if (!*p_service_out) {
+ return -1;
+ }
- iService = lp_servicenumber(service);
+ all_string_sub(*p_service_out,"\\","/",0);
+
+ iService = lp_servicenumber(*p_service_out);
/* now handle the special case of a home directory */
if (iService < 0) {
- char *phome_dir = get_user_home_dir(talloc_tos(), service);
+ char *phome_dir = get_user_home_dir(ctx, *p_service_out);
if(!phome_dir) {
- char *service_out = NULL;
/*
* Try mapping the servicename, it may
* be a Windows to unix mapped user name.
*/
- if(map_username(talloc_tos(), service, &service_out)) {
- if (service_out == NULL) {
+ if(map_username(ctx, *p_service_out, p_service_out)) {
+ if (*p_service_out == NULL) {
/* Out of memory. */
return -1;
}
- fstrcpy(service, service_out);
phome_dir = get_user_home_dir(
- talloc_tos(), service);
+ ctx, *p_service_out);
}
}
- DEBUG(3,("checking for home directory %s gave %s\n",service,
+ DEBUG(3,("checking for home directory %s gave %s\n",*p_service_out,
phome_dir?phome_dir:"(NULL)"));
- iService = add_home_service(service,service /* 'username' */, phome_dir);
+ iService = add_home_service(*p_service_out,*p_service_out /* 'username' */, phome_dir);
}
/* If we still don't have a service, attempt to add it as a printer. */
@@ -348,17 +356,22 @@ int find_service(fstring service)
iPrinterService = load_registry_service(PRINTERS_NAME);
}
if (iPrinterService >= 0) {
- 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);
+ DEBUG(3,("checking whether %s is a valid printer name...\n",
+ *p_service_out));
+ if (pcap_printername_ok(*p_service_out)) {
+ DEBUG(3,("%s is a valid printer name\n",
+ *p_service_out));
+ DEBUG(3,("adding %s as a printer service\n",
+ *p_service_out));
+ lp_add_printer(*p_service_out, iPrinterService);
+ iService = lp_servicenumber(*p_service_out);
if (iService < 0) {
- DEBUG(0,("failed to add %s as a printer service!\n", service));
+ DEBUG(0,("failed to add %s as a printer service!\n",
+ *p_service_out));
}
} else {
- DEBUG(3,("%s is not a valid printer name\n", service));
+ DEBUG(3,("%s is not a valid printer name\n",
+ *p_service_out));
}
}
}
@@ -368,27 +381,30 @@ int find_service(fstring service)
}
if (iService < 0) {
- iService = load_registry_service(service);
+ iService = load_registry_service(*p_service_out);
}
/* Is it a usershare service ? */
if (iService < 0 && *lp_usershare_path()) {
/* Ensure the name is canonicalized. */
- strlower_m(service);
- iService = load_usershare_service(service);
+ strlower_m(*p_service_out);
+ iService = load_usershare_service(*p_service_out);
}
/* just possibly it's a default service? */
if (iService < 0) {
char *pdefservice = lp_defaultservice();
- if (pdefservice && *pdefservice && !strequal(pdefservice,service) && !strstr_m(service,"..")) {
+ if (pdefservice &&
+ *pdefservice &&
+ !strequal(pdefservice, *p_service_out)
+ && !strstr_m(*p_service_out,"..")) {
/*
* 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 <joehtg@joehtg.co.at>.
*/
- char *defservice = SMB_STRDUP(pdefservice);
+ char *defservice = talloc_strdup(ctx, pdefservice);
if (!defservice) {
goto fail;
@@ -398,30 +414,38 @@ int find_service(fstring service)
if (strequal(defservice,HOMES_NAME) ||
strequal(defservice, PRINTERS_NAME) ||
strequal(defservice, "IPC$")) {
- SAFE_FREE(defservice);
+ TALLOC_FREE(defservice);
goto fail;
}
- iService = find_service(defservice);
+ iService = find_service(ctx, defservice, p_service_out);
+ if (!*p_service_out) {
+ TALLOC_FREE(defservice);
+ iService = -1;
+ goto fail;
+ }
if (iService >= 0) {
- all_string_sub(service, "_","/",0);
- iService = lp_add_service(service, iService);
+ all_string_sub(*p_service_out, "_","/",0);
+ iService = lp_add_service(*p_service_out, iService);
}
- SAFE_FREE(defservice);
+ TALLOC_FREE(defservice);
}
}
if (iService >= 0) {
if (!VALID_SNUM(iService)) {
- DEBUG(0,("Invalid snum %d for %s\n",iService, service));
+ DEBUG(0,("Invalid snum %d for %s\n",iService,
+ *p_service_out));
iService = -1;
}
}
fail:
- if (iService < 0)
- DEBUG(3,("find_service() failed to find service %s\n", service));
+ if (iService < 0) {
+ DEBUG(3,("find_service() failed to find service %s\n",
+ *p_service_out));
+ }
return (iService);
}
@@ -1101,7 +1125,7 @@ connection_struct *make_connection(struct smbd_server_connection *sconn,
{
uid_t euid;
user_struct *vuser = NULL;
- fstring service;
+ char *service = NULL;
fstring dev;
int snum = -1;
@@ -1164,7 +1188,13 @@ connection_struct *make_connection(struct smbd_server_connection *sconn,
(void)map_username(talloc_tos(),
current_user_info.smb_name,
&unix_username);
- snum = find_service(unix_username);
+ snum = find_service(talloc_tos(),
+ unix_username,
+ &unix_username);
+ if (!unix_username) {
+ *status = NT_STATUS_NO_MEMORY;
+ }
+ return NULL;
}
if (snum != -1) {
DEBUG(5, ("making a connection to 'homes' "
@@ -1188,11 +1218,19 @@ connection_struct *make_connection(struct smbd_server_connection *sconn,
dev, status);
}
- fstrcpy(service, service_in);
+ service = talloc_strdup(talloc_tos(), service_in);
+ if (!service) {
+ *status = NT_STATUS_NO_MEMORY;
+ return NULL;
+ }
strlower_m(service);
- snum = find_service(service);
+ snum = find_service(talloc_tos(), service, &service);
+ if (!service) {
+ *status = NT_STATUS_NO_MEMORY;
+ return NULL;
+ }
if (snum < 0) {
if (strequal(service,"IPC$") ||
diff --git a/source3/smbd/smb2_tcon.c b/source3/smbd/smb2_tcon.c
index 203325e71a..82d9a28084 100644
--- a/source3/smbd/smb2_tcon.c
+++ b/source3/smbd/smb2_tcon.c
@@ -151,7 +151,7 @@ static NTSTATUS smbd_smb2_tree_connect(struct smbd_smb2_request *req,
uint32_t *out_tree_id)
{
const char *share = in_path;
- fstring service;
+ char *service = NULL;
int snum = -1;
struct smbd_smb2_tcon *tcon;
connection_struct *compat_conn = NULL;
@@ -169,7 +169,10 @@ static NTSTATUS smbd_smb2_tree_connect(struct smbd_smb2_request *req,
DEBUG(10,("smbd_smb2_tree_connect: path[%s] share[%s]\n",
in_path, share));
- fstrcpy(service, share);
+ service = talloc_strdup(talloc_tos(), share);
+ if(!service) {
+ return NT_STATUS_NO_MEMORY;
+ }
strlower_m(service);
@@ -189,7 +192,10 @@ static NTSTATUS smbd_smb2_tree_connect(struct smbd_smb2_request *req,
lp_servicename(compat_vuser->homes_snum))) {
snum = compat_vuser->homes_snum;
} else {
- snum = find_service(service);
+ snum = find_service(talloc_tos(), service, &service);
+ if (!service) {
+ return NT_STATUS_NO_MEMORY;
+ }
}
if (snum < 0) {