r11420: Fix issue pointed out by Dina Fine <dina@exanet.com>. We can
authorJeremy Allison <jra@samba.org>
Mon, 31 Oct 2005 20:11:58 +0000 (20:11 +0000)
committerGerald (Jerry) Carter <jerry@samba.org>
Wed, 10 Oct 2007 16:05:15 +0000 (11:05 -0500)
only tell at parse time from the wire if an incoming name
has wildcards or not. If it's a mangled name and we demangle
the demangled name may contain wildcard characters. Ensure
these are ignored.
Jeremy.
(This used to be commit 4cd8e2a96b98ff711905e8c6f416b22440c16062)

source3/libsmb/clifile.c
source3/printing/nt_printing.c
source3/smbd/dir.c
source3/smbd/msdfs.c
source3/smbd/nttrans.c
source3/smbd/reply.c
source3/smbd/trans2.c
source3/torture/torture.c

index a7e6fbfe3f1858dc0202ad085ee2d389b9277682..ff42e6414376a9aab443c877004d048cd058f5ea 100644 (file)
@@ -1404,19 +1404,29 @@ static BOOL cli_set_ea(struct cli_state *cli, uint16 setup, char *param, unsigne
        char *p;
        size_t ea_namelen = strlen(ea_name);
 
-       data_len = 4 + 4 + ea_namelen + 1 + ea_len;
-       data = SMB_MALLOC(data_len);
-       if (!data) {
-               return False;
+       if (ea_namelen == 0 && ea_len == 0) {
+               data_len = 4;
+               data = SMB_MALLOC(data_len);
+               if (!data) {
+                       return False;
+               }
+               p = data;
+               SIVAL(p,0,data_len);
+       } else {
+               data_len = 4 + 4 + ea_namelen + 1 + ea_len;
+               data = SMB_MALLOC(data_len);
+               if (!data) {
+                       return False;
+               }
+               p = data;
+               SIVAL(p,0,data_len);
+               p += 4;
+               SCVAL(p, 0, 0); /* EA flags. */
+               SCVAL(p, 1, ea_namelen);
+               SSVAL(p, 2, ea_len);
+               memcpy(p+4, ea_name, ea_namelen+1); /* Copy in the name. */
+               memcpy(p+4+ea_namelen+1, ea_val, ea_len);
        }
-       p = data;
-       SIVAL(p,0,data_len);
-       p += 4;
-       SCVAL(p, 0, 0); /* EA flags. */
-       SCVAL(p, 1, ea_namelen);
-       SSVAL(p, 2, ea_len);
-       memcpy(p+4, ea_name, ea_namelen+1); /* Copy in the name. */
-       memcpy(p+4+ea_namelen+1, ea_val, ea_len);
 
        if (!cli_send_trans(cli, SMBtrans2,
                NULL,                        /* name */
index 8061842ad9ff4b1acb839b0f54519e4000a4dbb4..09775e60c8cf2bcc350f684b2dc39174eb2317fa 100644 (file)
@@ -4792,7 +4792,7 @@ static BOOL delete_driver_files( NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3, struct
                        pstrcpy( file, s );
                        driver_unix_convert(file, conn, NULL, &bad_path, &st);
                        DEBUG(10,("deleting driverfile [%s]\n", s));
-                       unlink_internals(conn, 0, file);
+                       unlink_internals(conn, 0, file, False);
                }
        }
                
@@ -4801,7 +4801,7 @@ static BOOL delete_driver_files( NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3, struct
                        pstrcpy( file, s );
                        driver_unix_convert(file, conn, NULL, &bad_path, &st);
                        DEBUG(10,("deleting configfile [%s]\n", s));
-                       unlink_internals(conn, 0, file);
+                       unlink_internals(conn, 0, file, False);
                }
        }
        
@@ -4810,7 +4810,7 @@ static BOOL delete_driver_files( NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3, struct
                        pstrcpy( file, s );
                        driver_unix_convert(file, conn, NULL, &bad_path, &st);
                        DEBUG(10,("deleting datafile [%s]\n", s));
-                       unlink_internals(conn, 0, file);
+                       unlink_internals(conn, 0, file, False);
                }
        }
        
@@ -4819,7 +4819,7 @@ static BOOL delete_driver_files( NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3, struct
                        pstrcpy( file, s );
                        driver_unix_convert(file, conn, NULL, &bad_path, &st);
                        DEBUG(10,("deleting helpfile [%s]\n", s));
-                       unlink_internals(conn, 0, file);
+                       unlink_internals(conn, 0, file, False);
                }
        }
        
@@ -4835,7 +4835,7 @@ static BOOL delete_driver_files( NT_PRINTER_DRIVER_INFO_LEVEL_3 *info_3, struct
                                pstrcpy( file, p );
                                driver_unix_convert(file, conn, NULL, &bad_path, &st);
                                DEBUG(10,("deleting dependent file [%s]\n", file));
-                               unlink_internals(conn, 0, file );
+                               unlink_internals(conn, 0, file, False);
                        }
                        
                        i++;
index 70a3b81ad69a3ffa50a093908f5bf4cd7b8f2f94..7ea97e69b01059d43b364dc14fd2672e103db618 100644 (file)
@@ -382,7 +382,7 @@ static void dptr_close_oldest(BOOL old)
 ****************************************************************************/
 
 int dptr_create(connection_struct *conn, pstring path, BOOL old_handle, BOOL expect_close,uint16 spid,
-               const char *wcard, uint32 attr)
+               const char *wcard, BOOL wcard_has_wild, uint32 attr)
 {
        struct dptr_struct *dptr = NULL;
        struct smb_Dir *dir_hnd;
@@ -500,7 +500,7 @@ int dptr_create(connection_struct *conn, pstring path, BOOL old_handle, BOOL exp
        if (lp_posix_pathnames() || (wcard[0] == '.' && wcard[1] == 0)) {
                dptr->has_wild = True;
        } else {
-               dptr->has_wild = ms_has_wild(wcard);
+               dptr->has_wild = wcard_has_wild;
        }
 
        dptr->attr = attr;
index 1e6306382aa754296d3a27d93da78c8e137bbdfd..a4f371b18ffa0a418ff88ccff1a694fe806d1929 100644 (file)
@@ -114,7 +114,8 @@ static BOOL parse_processed_dfs_path(char* pathname, struct dfs_path *pdp, BOOL
 
        /* rest is reqpath */
        if (allow_wcards) {
-               check_path_syntax_wcard(pdp->reqpath, p+1);
+               BOOL path_contains_wcard;
+               check_path_syntax_wcard(pdp->reqpath, p+1, &path_contains_wcard);
        } else {
                check_path_syntax(pdp->reqpath, p+1);
        }
index 3db55bad14d275da0adb908071a51daaa6069c80..91dcc933227ba6d34530a1fdf9d89b1711374f2d 100644 (file)
@@ -541,7 +541,7 @@ create_options = 0x%x root_dir_fid = 0x%x\n",
 
                if(!dir_fsp->is_directory) {
 
-                       srvstr_get_path(inbuf, fname, smb_buf(inbuf), sizeof(fname), 0, STR_TERMINATE, &status,False);
+                       srvstr_get_path(inbuf, fname, smb_buf(inbuf), sizeof(fname), 0, STR_TERMINATE, &status);
                        if (!NT_STATUS_IS_OK(status)) {
                                END_PROFILE(SMBntcreateX);
                                return ERROR_NT(status);
@@ -583,14 +583,14 @@ create_options = 0x%x root_dir_fid = 0x%x\n",
                        dir_name_len++;
                }
 
-               srvstr_get_path(inbuf, rel_fname, smb_buf(inbuf), sizeof(rel_fname), 0, STR_TERMINATE, &status,False);
+               srvstr_get_path(inbuf, rel_fname, smb_buf(inbuf), sizeof(rel_fname), 0, STR_TERMINATE, &status);
                if (!NT_STATUS_IS_OK(status)) {
                        END_PROFILE(SMBntcreateX);
                        return ERROR_NT(status);
                }
                pstrcat(fname, rel_fname);
        } else {
-               srvstr_get_path(inbuf, fname, smb_buf(inbuf), sizeof(fname), 0, STR_TERMINATE, &status,False);
+               srvstr_get_path(inbuf, fname, smb_buf(inbuf), sizeof(fname), 0, STR_TERMINATE, &status);
                if (!NT_STATUS_IS_OK(status)) {
                        END_PROFILE(SMBntcreateX);
                        return ERROR_NT(status);
@@ -939,7 +939,7 @@ static int do_nt_transact_create_pipe( connection_struct *conn, char *inbuf, cha
                return ERROR_DOS(ERRDOS,ERRnoaccess);
        }
 
-       srvstr_get_path(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                return ERROR_NT(status);
        }
@@ -1195,7 +1195,7 @@ static int call_nt_transact_create(connection_struct *conn, char *inbuf, char *o
                }
 
                if(!dir_fsp->is_directory) {
-                       srvstr_get_path(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE, &status, False);
+                       srvstr_get_path(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE, &status);
                        if (!NT_STATUS_IS_OK(status)) {
                                return ERROR_NT(status);
                        }
@@ -1229,14 +1229,14 @@ static int call_nt_transact_create(connection_struct *conn, char *inbuf, char *o
 
                {
                        pstring tmpname;
-                       srvstr_get_path(inbuf, tmpname, params+53, sizeof(tmpname), parameter_count-53, STR_TERMINATE, &status, False);
+                       srvstr_get_path(inbuf, tmpname, params+53, sizeof(tmpname), parameter_count-53, STR_TERMINATE, &status);
                        if (!NT_STATUS_IS_OK(status)) {
                                return ERROR_NT(status);
                        }
                        pstrcat(fname, tmpname);
                }
        } else {
-               srvstr_get_path(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE, &status, False);
+               srvstr_get_path(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE, &status);
                if (!NT_STATUS_IS_OK(status)) {
                        return ERROR_NT(status);
                }
@@ -1738,13 +1738,14 @@ int reply_ntrename(connection_struct *conn,
        pstring newname;
        char *p;
        NTSTATUS status;
+       BOOL path_contains_wcard = False;
        uint32 attrs = SVAL(inbuf,smb_vwv0);
        uint16 rename_type = SVAL(inbuf,smb_vwv1);
 
        START_PROFILE(SMBntrename);
 
        p = smb_buf(inbuf) + 1;
-       p += srvstr_get_path(inbuf, oldname, p, sizeof(oldname), 0, STR_TERMINATE, &status, True);
+       p += srvstr_get_path_wcard(inbuf, oldname, p, sizeof(oldname), 0, STR_TERMINATE, &status, &path_contains_wcard);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBntrename);
                return ERROR_NT(status);
@@ -1762,7 +1763,7 @@ int reply_ntrename(connection_struct *conn,
        }
 
        p++;
-       p += srvstr_get_path(inbuf, newname, p, sizeof(newname), 0, STR_TERMINATE, &status, False);
+       p += srvstr_get_path(inbuf, newname, p, sizeof(newname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBntrename);
                return ERROR_NT(status);
@@ -1775,13 +1776,18 @@ int reply_ntrename(connection_struct *conn,
        
        switch(rename_type) {
                case RENAME_FLAG_RENAME:
-                       status = rename_internals(conn, oldname, newname, attrs, False);
+                       status = rename_internals(conn, oldname, newname, attrs, False, path_contains_wcard);
                        break;
                case RENAME_FLAG_HARD_LINK:
                        status = hardlink_internals(conn, oldname, newname);
                        break;
                case RENAME_FLAG_COPY:
-                       status = copy_internals(conn, oldname, newname, attrs);
+                       if (path_contains_wcard) {
+                               /* No wildcards. */
+                               status = NT_STATUS_OBJECT_PATH_SYNTAX_BAD;
+                       } else {
+                               status = copy_internals(conn, oldname, newname, attrs);
+                       }
                        break;
                case RENAME_FLAG_MOVE_CLUSTER_INFORMATION:
                        status = NT_STATUS_INVALID_PARAMETER;
@@ -1878,6 +1884,7 @@ static int call_nt_transact_rename(connection_struct *conn, char *inbuf, char *o
        pstring new_name;
        files_struct *fsp = NULL;
        BOOL replace_if_exists = False;
+       BOOL path_contains_wcard = False;
        NTSTATUS status;
 
         if(parameter_count < 4) {
@@ -1887,13 +1894,13 @@ static int call_nt_transact_rename(connection_struct *conn, char *inbuf, char *o
        fsp = file_fsp(params, 0);
        replace_if_exists = (SVAL(params,2) & RENAME_REPLACE_IF_EXISTS) ? True : False;
        CHECK_FSP(fsp, conn);
-       srvstr_get_path(inbuf, new_name, params+4, sizeof(new_name), -1, STR_TERMINATE, &status, True);
+       srvstr_get_path_wcard(inbuf, new_name, params+4, sizeof(new_name), -1, STR_TERMINATE, &status, &path_contains_wcard);
        if (!NT_STATUS_IS_OK(status)) {
                return ERROR_NT(status);
        }
 
        status = rename_internals(conn, fsp->fsp_name,
-                                 new_name, 0, replace_if_exists);
+                                 new_name, 0, replace_if_exists, path_contains_wcard);
        if (!NT_STATUS_IS_OK(status))
                return ERROR_NT(status);
 
index beed90f9aa7ebe8cb8ea45d5d6d10076efd1a99c..f73eea3fa69df2ae239ffdfb5bf83c7b9fd84fa6 100644 (file)
@@ -172,7 +172,7 @@ NTSTATUS check_path_syntax(pstring destname, const pstring srcname)
  set.
 ****************************************************************************/
 
-NTSTATUS check_path_syntax_wcard(pstring destname, const pstring srcname)
+NTSTATUS check_path_syntax_wcard(pstring destname, const pstring srcname, BOOL *p_contains_wcard)
 {
        char *d = destname;
        const char *s = srcname;
@@ -180,6 +180,8 @@ NTSTATUS check_path_syntax_wcard(pstring destname, const pstring srcname)
        BOOL start_of_name_component = True;
        unsigned int num_bad_components = 0;
 
+       *p_contains_wcard = False;
+
        while (*s) {
                if (IS_DIRECTORY_SEP(*s)) {
                        /*
@@ -249,6 +251,19 @@ NTSTATUS check_path_syntax_wcard(pstring destname, const pstring srcname)
                        if (*s <= 0x1f) {
                                return NT_STATUS_OBJECT_NAME_INVALID;
                        }
+                       if (!*p_contains_wcard) {
+                               switch (*s) {
+                                       case '*':
+                                       case '?':
+                                       case '<':
+                                       case '>':
+                                       case '"':
+                                               *p_contains_wcard = True;
+                                               break;
+                                       default:
+                                               break;
+                               }
+                       }
                        *d++ = *s++;
                } else {
                        switch(next_mb_char_size(s)) {
@@ -379,11 +394,41 @@ NTSTATUS check_path_syntax_posix(pstring destname, const pstring srcname)
        return ret;
 }
 
+/****************************************************************************
+ Pull a string and check the path allowing a wilcard - provide for error return.
+****************************************************************************/
+
+size_t srvstr_get_path_wcard(char *inbuf, char *dest, const char *src, size_t dest_len, size_t src_len, int flags,
+                               NTSTATUS *err, BOOL *contains_wcard)
+{
+       pstring tmppath;
+       char *tmppath_ptr = tmppath;
+       size_t ret;
+#ifdef DEVELOPER
+       SMB_ASSERT(dest_len == sizeof(pstring));
+#endif
+
+       if (src_len == 0) {
+               ret = srvstr_pull_buf( inbuf, tmppath_ptr, src, dest_len, flags);
+       } else {
+               ret = srvstr_pull( inbuf, tmppath_ptr, src, dest_len, src_len, flags);
+       }
+
+       *contains_wcard = False;
+
+       if (lp_posix_pathnames()) {
+               *err = check_path_syntax_posix(dest, tmppath);
+       } else {
+               *err = check_path_syntax_wcard(dest, tmppath, contains_wcard);
+       }
+       return ret;
+}
+
 /****************************************************************************
  Pull a string and check the path - provide for error return.
 ****************************************************************************/
 
-size_t srvstr_get_path(char *inbuf, char *dest, const char *src, size_t dest_len, size_t src_len, int flags, NTSTATUS *err, BOOL allow_wcard_names)
+size_t srvstr_get_path(char *inbuf, char *dest, const char *src, size_t dest_len, size_t src_len, int flags, NTSTATUS *err)
 {
        pstring tmppath;
        char *tmppath_ptr = tmppath;
@@ -399,8 +444,6 @@ size_t srvstr_get_path(char *inbuf, char *dest, const char *src, size_t dest_len
        }
        if (lp_posix_pathnames()) {
                *err = check_path_syntax_posix(dest, tmppath);
-       } else if (allow_wcard_names) {
-               *err = check_path_syntax_wcard(dest, tmppath);
        } else {
                *err = check_path_syntax(dest, tmppath);
        }
@@ -754,7 +797,7 @@ int reply_chkpth(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
 
        START_PROFILE(SMBchkpth);
 
-       srvstr_get_path(inbuf, name, smb_buf(inbuf) + 1, sizeof(name), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, name, smb_buf(inbuf) + 1, sizeof(name), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBchkpth);
                return ERROR_NT(status);
@@ -826,7 +869,7 @@ int reply_getatr(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
        START_PROFILE(SMBgetatr);
 
        p = smb_buf(inbuf) + 1;
-       p += srvstr_get_path(inbuf, fname, p, sizeof(fname), 0, STR_TERMINATE, &status, False);
+       p += srvstr_get_path(inbuf, fname, p, sizeof(fname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBgetatr);
                return ERROR_NT(status);
@@ -905,7 +948,7 @@ int reply_setatr(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
        START_PROFILE(SMBsetatr);
 
        p = smb_buf(inbuf) + 1;
-       p += srvstr_get_path(inbuf, fname, p, sizeof(fname), 0, STR_TERMINATE, &status, False);
+       p += srvstr_get_path(inbuf, fname, p, sizeof(fname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBsetatr);
                return ERROR_NT(status);
@@ -1031,6 +1074,7 @@ int reply_search(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
        BOOL can_open = True;
        BOOL bad_path = False;
        NTSTATUS nt_status;
+       BOOL mask_contains_wcard = False;
        BOOL allow_long_path_components = (SVAL(inbuf,smb_flg2) & FLAGS2_LONG_PATH_COMPONENTS) ? True : False;
 
        if (lp_posix_pathnames()) {
@@ -1049,7 +1093,7 @@ int reply_search(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
        maxentries = SVAL(inbuf,smb_vwv0); 
        dirtype = SVAL(inbuf,smb_vwv1);
        p = smb_buf(inbuf) + 1;
-       p += srvstr_get_path(inbuf, path, p, sizeof(path), 0, STR_TERMINATE, &nt_status, True);
+       p += srvstr_get_path_wcard(inbuf, path, p, sizeof(path), 0, STR_TERMINATE, &nt_status, &mask_contains_wcard);
        if (!NT_STATUS_IS_OK(nt_status)) {
                END_PROFILE(SMBsearch);
                return ERROR_NT(nt_status);
@@ -1114,7 +1158,7 @@ int reply_search(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
                ok = True;
      
                if (status_len == 0) {
-                       dptr_num = dptr_create(conn,directory,True,expect_close,SVAL(inbuf,smb_pid), mask, dirtype);
+                       dptr_num = dptr_create(conn,directory,True,expect_close,SVAL(inbuf,smb_pid), mask, mask_contains_wcard, dirtype);
                        if (dptr_num < 0) {
                                if(dptr_num == -2) {
                                        END_PROFILE(SMBsearch);
@@ -1185,7 +1229,7 @@ int reply_search(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
                dptr_close(&dptr_num);
        }
 
-       if ((numentries == 0) && !ms_has_wild(mask)) {
+       if ((numentries == 0) && !mask_contains_wcard) {
                return ERROR_BOTH(STATUS_NO_MORE_FILES,ERRDOS,ERRnofiles);
        }
 
@@ -1230,6 +1274,7 @@ int reply_fclose(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
        int dptr_num= -2;
        char *p;
        NTSTATUS err;
+       BOOL path_contains_wcard = False;
 
        if (lp_posix_pathnames()) {
                return reply_unknown(inbuf, outbuf);
@@ -1239,7 +1284,7 @@ int reply_fclose(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
 
        outsize = set_message(outbuf,1,0,True);
        p = smb_buf(inbuf) + 1;
-       p += srvstr_get_path(inbuf, path, p, sizeof(path), 0, STR_TERMINATE, &err, True);
+       p += srvstr_get_path_wcard(inbuf, path, p, sizeof(path), 0, STR_TERMINATE, &err, &path_contains_wcard);
        if (!NT_STATUS_IS_OK(err)) {
                END_PROFILE(SMBfclose);
                return ERROR_NT(err);
@@ -1295,7 +1340,7 @@ int reply_open(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
  
        deny_mode = SVAL(inbuf,smb_vwv0);
 
-       srvstr_get_path(inbuf, fname, smb_buf(inbuf)+1, sizeof(fname), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, fname, smb_buf(inbuf)+1, sizeof(fname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBopen);
                return ERROR_NT(status);
@@ -1415,7 +1460,7 @@ int reply_open_and_X(connection_struct *conn, char *inbuf,char *outbuf,int lengt
        }
 
        /* XXXX we need to handle passed times, sattr and flags */
-       srvstr_get_path(inbuf, fname, smb_buf(inbuf), sizeof(fname), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, fname, smb_buf(inbuf), sizeof(fname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBopenX);
                return ERROR_NT(status);
@@ -1586,7 +1631,7 @@ int reply_mknew(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
  
        com = SVAL(inbuf,smb_com);
 
-       srvstr_get_path(inbuf, fname, smb_buf(inbuf) + 1, sizeof(fname), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, fname, smb_buf(inbuf) + 1, sizeof(fname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBcreate);
                return ERROR_NT(status);
@@ -1669,7 +1714,7 @@ int reply_ctemp(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
 
        START_PROFILE(SMBctemp);
 
-       srvstr_get_path(inbuf, fname, smb_buf(inbuf)+1, sizeof(fname), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, fname, smb_buf(inbuf)+1, sizeof(fname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBctemp);
                return ERROR_NT(status);
@@ -1889,30 +1934,19 @@ NTSTATUS can_delete(connection_struct *conn, char *fname, uint32 dirtype, BOOL b
  code.
 ****************************************************************************/
 
-NTSTATUS unlink_internals(connection_struct *conn, uint32 dirtype, char *name)
+NTSTATUS unlink_internals(connection_struct *conn, uint32 dirtype, char *name, BOOL has_wild)
 {
        pstring directory;
        pstring mask;
        char *p;
        int count=0;
        NTSTATUS error = NT_STATUS_OK;
-       BOOL has_wild;
        BOOL bad_path = False;
        BOOL rc = True;
        SMB_STRUCT_STAT sbuf;
        
        *directory = *mask = 0;
        
-       /* We must check for wildcards in the name given
-        * directly by the client - before any unmangling.
-        * This prevents an unmangling of a UNIX name containing
-        * a DOS wildcard like '*' or '?' from unmangling into
-        * a wildcard delete which was not intended.
-        * FIX for #226. JRA.
-        */
-
-       has_wild = ms_has_wild(name);
-
        rc = unix_convert(name,conn,0,&bad_path,&sbuf);
        
        p = strrchr_m(name,'/');
@@ -2029,10 +2063,11 @@ int reply_unlink(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
        uint32 dirtype;
        NTSTATUS status;
        START_PROFILE(SMBunlink);
-       
+       BOOL path_contains_wcard = False;
+
        dirtype = SVAL(inbuf,smb_vwv0);
        
-       srvstr_get_path(inbuf, name, smb_buf(inbuf) + 1, sizeof(name), 0, STR_TERMINATE, &status, True);
+       srvstr_get_path_wcard(inbuf, name, smb_buf(inbuf) + 1, sizeof(name), 0, STR_TERMINATE, &status, &path_contains_wcard);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBunlink);
                return ERROR_NT(status);
@@ -2042,7 +2077,7 @@ int reply_unlink(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
        
        DEBUG(3,("reply_unlink : %s\n",name));
        
-       status = unlink_internals(conn, dirtype, name);
+       status = unlink_internals(conn, dirtype, name, path_contains_wcard);
        if (!NT_STATUS_IS_OK(status)) {
                if (open_was_deferred(SVAL(inbuf,smb_mid))) {
                        /* We have re-scheduled this call. */
@@ -3721,7 +3756,7 @@ int reply_mkdir(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
 
        START_PROFILE(SMBmkdir);
  
-       srvstr_get_path(inbuf, directory, smb_buf(inbuf) + 1, sizeof(directory), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, directory, smb_buf(inbuf) + 1, sizeof(directory), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBmkdir);
                return ERROR_NT(status);
@@ -3925,7 +3960,7 @@ int reply_rmdir(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
        NTSTATUS status;
        START_PROFILE(SMBrmdir);
 
-       srvstr_get_path(inbuf, directory, smb_buf(inbuf) + 1, sizeof(directory), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, directory, smb_buf(inbuf) + 1, sizeof(directory), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBrmdir);
                return ERROR_NT(status);
@@ -4216,14 +4251,13 @@ NTSTATUS rename_internals_fsp(connection_struct *conn, files_struct *fsp, char *
  code. 
 ****************************************************************************/
 
-NTSTATUS rename_internals(connection_struct *conn, char *name, char *newname, uint32 attrs, BOOL replace_if_exists)
+NTSTATUS rename_internals(connection_struct *conn, char *name, char *newname, uint32 attrs, BOOL replace_if_exists, BOOL has_wild)
 {
        pstring directory;
        pstring mask;
        pstring last_component_src;
        pstring last_component_dest;
        char *p;
-       BOOL has_wild;
        BOOL bad_path_src = False;
        BOOL bad_path_dest = False;
        int count=0;
@@ -4292,8 +4326,6 @@ NTSTATUS rename_internals(connection_struct *conn, char *name, char *newname, ui
        if (!rc && mangle_is_mangled(mask,SNUM(conn)))
                mangle_check_cache( mask, sizeof(pstring)-1, SNUM(conn));
 
-       has_wild = ms_has_wild(mask);
-
        if (!has_wild) {
                /*
                 * No wildcards - just process the one file.
@@ -4559,17 +4591,18 @@ int reply_mv(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
        char *p;
        uint32 attrs = SVAL(inbuf,smb_vwv0);
        NTSTATUS status;
+       BOOL path_contains_wcard = False;
 
        START_PROFILE(SMBmv);
 
        p = smb_buf(inbuf) + 1;
-       p += srvstr_get_path(inbuf, name, p, sizeof(name), 0, STR_TERMINATE, &status, True);
+       p += srvstr_get_path_wcard(inbuf, name, p, sizeof(name), 0, STR_TERMINATE, &status, &path_contains_wcard);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBmv);
                return ERROR_NT(status);
        }
        p++;
-       p += srvstr_get_path(inbuf, newname, p, sizeof(newname), 0, STR_TERMINATE, &status, True);
+       p += srvstr_get_path(inbuf, newname, p, sizeof(newname), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBmv);
                return ERROR_NT(status);
@@ -4580,7 +4613,7 @@ int reply_mv(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
        
        DEBUG(3,("reply_mv : %s -> %s\n",name,newname));
        
-       status = rename_internals(conn, name, newname, attrs, False);
+       status = rename_internals(conn, name, newname, attrs, False, path_contains_wcard);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBmv);
                if (open_was_deferred(SVAL(inbuf,smb_mid))) {
@@ -4727,21 +4760,22 @@ int reply_copy(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
        BOOL target_is_directory=False;
        BOOL bad_path1 = False;
        BOOL bad_path2 = False;
+       BOOL path_contains_wcard1 = False;
+       BOOL path_contains_wcard2 = False;
        BOOL rc = True;
        SMB_STRUCT_STAT sbuf1, sbuf2;
        NTSTATUS status;
-
        START_PROFILE(SMBcopy);
 
        *directory = *mask = 0;
 
        p = smb_buf(inbuf);
-       p += srvstr_get_path(inbuf, name, p, sizeof(name), 0, STR_TERMINATE, &status, True);
+       p += srvstr_get_path_wcard(inbuf, name, p, sizeof(name), 0, STR_TERMINATE, &status, &path_contains_wcard1);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBcopy);
                return ERROR_NT(status);
        }
-       p += srvstr_get_path(inbuf, newname, p, sizeof(newname), 0, STR_TERMINATE, &status, True);
+       p += srvstr_get_path_wcard(inbuf, newname, p, sizeof(newname), 0, STR_TERMINATE, &status, &path_contains_wcard2);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(SMBcopy);
                return ERROR_NT(status);
@@ -4803,7 +4837,7 @@ int reply_copy(connection_struct *conn, char *inbuf,char *outbuf, int dum_size,
        if (!rc && mangle_is_mangled(mask, SNUM(conn)))
                mangle_check_cache( mask, sizeof(pstring)-1, SNUM(conn));
 
-       has_wild = ms_has_wild(mask);
+       has_wild = path_contains_wcard1;
 
        if (!has_wild) {
                pstrcat(directory,"/");
@@ -4904,7 +4938,7 @@ int reply_setdir(connection_struct *conn, char *inbuf,char *outbuf, int dum_size
                return ERROR_DOS(ERRDOS,ERRnoaccess);
        }
 
-       srvstr_get_path(inbuf, newdir, smb_buf(inbuf) + 1, sizeof(newdir), 0, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, newdir, smb_buf(inbuf) + 1, sizeof(newdir), 0, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                END_PROFILE(pathworks_setdir);
                return ERROR_NT(status);
index f04e6c78f05ef5bb9f518c43bf7c1458841d3d83..a9b67cc48437f86f9749064d720d69ba8e44f632 100644 (file)
@@ -775,7 +775,7 @@ static int call_trans2open(connection_struct *conn, char *inbuf, char *outbuf, i
                return(ERROR_DOS(ERRSRV,ERRaccess));
        }
 
-       srvstr_get_path(inbuf, fname, pname, sizeof(fname), -1, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, fname, pname, sizeof(fname), -1, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                return ERROR_NT(status);
        }
@@ -1614,6 +1614,7 @@ static int call_trans2findfirst(connection_struct *conn, char *inbuf, char *outb
        BOOL out_of_space = False;
        int space_remaining;
        BOOL bad_path = False;
+       BOOL mask_contains_wcard = False;
        SMB_STRUCT_STAT sbuf;
        TALLOC_CTX *ea_ctx = NULL;
        struct ea_list *ea_list = NULL;
@@ -1654,7 +1655,7 @@ close_if_end = %d requires_resume_key = %d level = 0x%x, max_data_bytes = %d\n",
                        return(ERROR_DOS(ERRDOS,ERRunknownlevel));
        }
 
-       srvstr_get_path(inbuf, directory, params+12, sizeof(directory), -1, STR_TERMINATE, &ntstatus, True);
+       srvstr_get_path_wcard(inbuf, directory, params+12, sizeof(directory), -1, STR_TERMINATE, &ntstatus, &mask_contains_wcard);
        if (!NT_STATUS_IS_OK(ntstatus)) {
                return ERROR_NT(ntstatus);
        }
@@ -1672,10 +1673,12 @@ close_if_end = %d requires_resume_key = %d level = 0x%x, max_data_bytes = %d\n",
        p = strrchr_m(directory,'/');
        if(p == NULL) {
                /* Windows and OS/2 systems treat search on the root '\' as if it were '\*' */
-               if((directory[0] == '.') && (directory[1] == '\0'))
+               if((directory[0] == '.') && (directory[1] == '\0')) {
                        pstrcpy(mask,"*");
-               else
+                       mask_contains_wcard = True;
+               } else {
                        pstrcpy(mask,directory);
+               }
                pstrcpy(directory,"./");
        } else {
                pstrcpy(mask,p+1);
@@ -1733,7 +1736,7 @@ total_data=%u (should be %u)\n", (unsigned int)total_data, (unsigned int)IVAL(pd
        /* Save the wildcard match and attribs we are using on this directory - 
                needed as lanman2 assumes these are being saved between calls */
 
-       dptr_num = dptr_create(conn,directory, False, True ,SVAL(inbuf,smb_pid), mask, dirtype);
+       dptr_num = dptr_create(conn,directory, False, True ,SVAL(inbuf,smb_pid), mask, mask_contains_wcard, dirtype);
        if (dptr_num < 0) {
                talloc_destroy(ea_ctx);
                return(UNIXERROR(ERRDOS,ERRbadfile));
@@ -1868,6 +1871,7 @@ static int call_trans2findnext(connection_struct *conn, char *inbuf, char *outbu
        BOOL close_if_end = (findnext_flags & FLAG_TRANS2_FIND_CLOSE_IF_END);
        BOOL requires_resume_key = (findnext_flags & FLAG_TRANS2_FIND_REQUIRE_RESUME);
        BOOL continue_bit = (findnext_flags & FLAG_TRANS2_FIND_CONTINUE);
+       BOOL mask_contains_wcard = False;
        pstring resume_name;
        pstring mask;
        pstring directory;
@@ -1889,7 +1893,7 @@ static int call_trans2findnext(connection_struct *conn, char *inbuf, char *outbu
 
        *mask = *directory = *resume_name = 0;
 
-       srvstr_get_path(inbuf, resume_name, params+12, sizeof(resume_name), -1, STR_TERMINATE, &ntstatus, True);
+       srvstr_get_path_wcard(inbuf, resume_name, params+12, sizeof(resume_name), -1, STR_TERMINATE, &ntstatus, &mask_contains_wcard);
        if (!NT_STATUS_IS_OK(ntstatus)) {
                /* Win9x or OS/2 can send a resume name of ".." or ".". This will cause the parser to
                   complain (it thinks we're asking for the directory above the shared
@@ -2854,7 +2858,7 @@ static int call_trans2qfilepathinfo(connection_struct *conn, char *inbuf, char *
 
                DEBUG(3,("call_trans2qfilepathinfo: TRANSACT2_QPATHINFO: level = %d\n", info_level));
 
-               srvstr_get_path(inbuf, fname, &params[6], sizeof(fname), -1, STR_TERMINATE, &status, False);
+               srvstr_get_path(inbuf, fname, &params[6], sizeof(fname), -1, STR_TERMINATE, &status);
                if (!NT_STATUS_IS_OK(status)) {
                        return ERROR_NT(status);
                }
@@ -3659,7 +3663,7 @@ static int call_trans2setfilepathinfo(connection_struct *conn, char *inbuf, char
                }
 
                info_level = SVAL(params,0);    
-               srvstr_get_path(inbuf, fname, &params[6], sizeof(fname), -1, STR_TERMINATE, &status, False);
+               srvstr_get_path(inbuf, fname, &params[6], sizeof(fname), -1, STR_TERMINATE, &status);
                if (!NT_STATUS_IS_OK(status)) {
                        return ERROR_NT(status);
                }
@@ -4217,7 +4221,7 @@ size = %.0f, uid = %u, gid = %u, raw perms = 0%o\n",
                        char *newname = fname;
 
                        /* Set a hard link. */
-                       srvstr_get_path(inbuf, oldname, pdata, sizeof(oldname), -1, STR_TERMINATE, &status, False);
+                       srvstr_get_path(inbuf, oldname, pdata, sizeof(oldname), -1, STR_TERMINATE, &status);
                        if (!NT_STATUS_IS_OK(status)) {
                                return ERROR_NT(status);
                        }
@@ -4251,7 +4255,7 @@ size = %.0f, uid = %u, gid = %u, raw perms = 0%o\n",
                        overwrite = (CVAL(pdata,0) ? True : False);
                        root_fid = IVAL(pdata,4);
                        len = IVAL(pdata,8);
-                       srvstr_get_path(inbuf, newname, &pdata[12], sizeof(newname), len, 0, &status, False);
+                       srvstr_get_path(inbuf, newname, &pdata[12], sizeof(newname), len, 0, &status);
                        if (!NT_STATUS_IS_OK(status)) {
                                return ERROR_NT(status);
                        }
@@ -4278,7 +4282,7 @@ size = %.0f, uid = %u, gid = %u, raw perms = 0%o\n",
                        } else {
                                DEBUG(10,("call_trans2setfilepathinfo: SMB_FILE_RENAME_INFORMATION %s -> %s\n",
                                        fname, newname ));
-                               status = rename_internals(conn, fname, base_name, 0, overwrite);
+                               status = rename_internals(conn, fname, base_name, 0, overwrite, False);
                        }
                        if (!NT_STATUS_IS_OK(status)) {
                                return ERROR_NT(status);
@@ -4489,7 +4493,7 @@ static int call_trans2mkdir(connection_struct *conn, char *inbuf, char *outbuf,
                return ERROR_NT(NT_STATUS_INVALID_PARAMETER);
        }
 
-       srvstr_get_path(inbuf, directory, &params[4], sizeof(directory), -1, STR_TERMINATE, &status, False);
+       srvstr_get_path(inbuf, directory, &params[4], sizeof(directory), -1, STR_TERMINATE, &status);
        if (!NT_STATUS_IS_OK(status)) {
                return ERROR_NT(status);
        }
index 8ad567f17781c79682298d1317346afe43c2b3a7..0bd9aa1728b264c973237cf69334daa3c59cfae2 100644 (file)
@@ -4424,6 +4424,9 @@ static BOOL run_eatest(int dummy)
        /* Setting EA's to zero length deletes them. Test this */
        printf("Now deleting all EA's - case indepenent....\n");
 
+#if 1
+       cli_set_ea_path(cli, fname, "", "", 0);
+#else
        for (i = 0; i < 20; i++) {
                fstring ea_name;
                slprintf(ea_name, sizeof(ea_name), "ea_%d", i);
@@ -4432,7 +4435,8 @@ static BOOL run_eatest(int dummy)
                        return False;
                }
        }
-       
+#endif
+
        if (!cli_get_ea_list_path(cli, fname, mem_ctx, &num_eas, &ea_list)) {
                printf("ea_get list failed - %s\n", cli_errstr(cli));
                correct = False;