Ignore:
Timestamp:
Sep 30, 2007, 3:42:50 AM (18 years ago)
Author:
Paul Smedley
Message:

Update trunk to 3.2.0pre1

File:
1 edited

Legend:

Unmodified
Added
Removed
  • trunk/samba/source/smbd/dir.c

    r71 r77  
    1 /* 
     1/*
    22   Unix SMB/CIFS implementation.
    33   Directory handling routines
    44   Copyright (C) Andrew Tridgell 1992-1998
    5    
     5   Copyright (C) Jeremy Allison 2007
     6
    67   This program is free software; you can redistribute it and/or modify
    78   it under the terms of the GNU General Public License as published by
    8    the Free Software Foundation; either version 2 of the License, or
     9   the Free Software Foundation; either version 3 of the License, or
    910   (at your option) any later version.
    10    
     11
    1112   This program is distributed in the hope that it will be useful,
    1213   but WITHOUT ANY WARRANTY; without even the implied warranty of
    1314   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    1415   GNU General Public License for more details.
    15    
     16
    1617   You should have received a copy of the GNU General Public License
    17    along with this program; if not, write to the Free Software
    18    Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
     18   along with this program.  If not, see <http://www.gnu.org/licenses/>.
    1919*/
    2020
     
    7474****************************************************************************/
    7575
    76 void make_dir_struct(char *buf, const char *mask, const char *fname,SMB_OFF_T size,uint32 mode,time_t date, BOOL uc)
    77 
     76BOOL make_dir_struct(TALLOC_CTX *ctx,
     77                        char *buf,
     78                        const char *mask,
     79                        const char *fname,
     80                        SMB_OFF_T size,
     81                        uint32 mode,
     82                        time_t date,
     83                        BOOL uc)
     84{
    7885        char *p;
    79         pstring mask2;
    80 
    81         pstrcpy(mask2,mask);
    82 
    83         if ((mode & aDIR) != 0)
     86        char *mask2 = talloc_strdup(ctx, mask);
     87
     88        if (!mask2) {
     89                return False;
     90        }
     91
     92        if ((mode & aDIR) != 0) {
    8493                size = 0;
     94        }
    8595
    8696        memset(buf+1,' ',11);
     
    90100                push_ascii(buf+9,p+1,3, 0);
    91101                *p = '.';
    92         } else
     102        } else {
    93103                push_ascii(buf+1,mask2,11, 0);
     104        }
    94105
    95106        memset(buf+21,'\0',DIR_STRUCT_SIZE-21);
     
    102113        push_ascii(buf+30,fname,12, uc ? STR_UPPER : 0);
    103114        DEBUG(8,("put name [%s] from [%s] into dir struct\n",buf+30, fname));
     115        return True;
    104116}
    105117
     
    240252        DLIST_REMOVE(dirptrs, dptr);
    241253
    242         /* 
     254        /*
    243255         * Free the dnum in the bitmap. Remember the dnum value is always
    244256         * biased by one with respect to the bitmap.
     
    382394****************************************************************************/
    383395
    384 NTSTATUS dptr_create(connection_struct *conn, pstring path, BOOL old_handle, BOOL expect_close,uint16 spid,
     396NTSTATUS dptr_create(connection_struct *conn, const char *path, BOOL old_handle, BOOL expect_close,uint16 spid,
    385397                const char *wcard, BOOL wcard_has_wild, uint32 attr, struct dptr_struct **dptr_ret)
    386398{
    387399        struct dptr_struct *dptr = NULL;
    388400        struct smb_Dir *dir_hnd;
    389         const char *dir2;
    390401        NTSTATUS status;
    391402
     
    401412        }
    402413
    403         /* use a const pointer from here on */
    404         dir2 = path;
    405         if (!*dir2)
    406                 dir2 = ".";
    407 
    408         dir_hnd = OpenDir(conn, dir2, wcard, attr);
     414        dir_hnd = OpenDir(conn, path, wcard, attr);
    409415        if (!dir_hnd) {
    410416                return map_nt_error_from_unix(errno);
    411417        }
    412418
    413         string_set(&conn->dirpath,dir2);
     419        string_set(&conn->dirpath,path);
    414420
    415421        if (dirhandles_open >= MAX_OPEN_DIRECTORIES) {
     
    490496        dptr->dnum += 1; /* Always bias the dnum by one - no zero dnums allowed. */
    491497
    492         string_set(&dptr->path,dir2);
     498        string_set(&dptr->path,path);
    493499        dptr->conn = conn;
    494500        dptr->dir_hnd = dir_hnd;
     
    571577****************************************************************************/
    572578
    573 const char *dptr_ReadDirName(struct dptr_struct *dptr, long *poffset, SMB_STRUCT_STAT *pst)
     579const char *dptr_ReadDirName(TALLOC_CTX *ctx,
     580                        struct dptr_struct *dptr,
     581                        long *poffset,
     582                        SMB_STRUCT_STAT *pst)
    574583{
    575584        SET_STAT_INVALID(*pst);
     
    586595
    587596        if (!dptr->did_stat) {
    588                 pstring pathreal;
     597                char *pathreal = NULL;
    589598
    590599                /* We know the stored wcard contains no wildcard characters. See if we can match
     
    610619                }
    611620
    612                 pstrcpy(pathreal,dptr->path);
    613                 pstrcat(pathreal,"/");
    614                 pstrcat(pathreal,dptr->wcard);
     621                pathreal = talloc_asprintf(ctx,
     622                                        "%s/%s",
     623                                        dptr->path,
     624                                        dptr->wcard);
     625                if (!pathreal) {
     626                        return NULL;
     627                }
    615628
    616629                if (SMB_VFS_STAT(dptr->conn,pathreal,pst) == 0) {
     
    618631                           this function is usually called with the output from TellDir. */
    619632                        dptr->dir_hnd->offset = *poffset = END_OF_DIRECTORY_OFFSET;
     633                        TALLOC_FREE(pathreal);
    620634                        return dptr->wcard;
    621635                } else {
     
    626640                                   this function is usually called with the output from TellDir. */
    627641                                dptr->dir_hnd->offset = *poffset = END_OF_DIRECTORY_OFFSET;
     642                                TALLOC_FREE(pathreal);
    628643                                return dptr->wcard;
    629644                        }
    630645                }
     646
     647                TALLOC_FREE(pathreal);
    631648
    632649                /* In case sensitive mode we don't search - we know if it doesn't exist
     
    760777}
    761778
    762 static BOOL mangle_mask_match(connection_struct *conn, fstring filename, char *mask)
    763 {
    764         mangle_map(filename,True,False,conn->params);
    765         return mask_match_search(filename,mask,False);
     779static BOOL mangle_mask_match(connection_struct *conn,
     780                const char *filename,
     781                const char *mask)
     782{
     783        char mname[13];
     784
     785        if (!name_to_8_3(filename,mname,False,conn->params)) {
     786                return False;
     787        }
     788        return mask_match_search(mname,mask,False);
    766789}
    767790
     
    770793****************************************************************************/
    771794
    772 BOOL get_dir_entry(connection_struct *conn,char *mask,uint32 dirtype, pstring fname,
    773                    SMB_OFF_T *size,uint32 *mode,time_t *date,BOOL check_descend)
    774 {
    775         const char *dname;
     795BOOL get_dir_entry(TALLOC_CTX *ctx,
     796                connection_struct *conn,
     797                const char *mask,
     798                uint32 dirtype,
     799                char **pp_fname_out,
     800                SMB_OFF_T *size,
     801                uint32 *mode,
     802                time_t *date,
     803                BOOL check_descend)
     804{
     805        const char *dname = NULL;
    776806        BOOL found = False;
    777807        SMB_STRUCT_STAT sbuf;
    778         pstring path;
    779         pstring pathreal;
    780         pstring filename;
     808        char *pathreal = NULL;
     809        const char *filename = NULL;
    781810        BOOL needslash;
    782811
    783         *path = *pathreal = *filename = 0;
     812        *pp_fname_out = NULL;
    784813
    785814        needslash = ( conn->dirpath[strlen(conn->dirpath) -1] != '/');
    786815
    787         if (!conn->dirptr)
     816        if (!conn->dirptr) {
    788817                return(False);
     818        }
    789819
    790820        while (!found) {
    791821                long curoff = dptr_TellDir(conn->dirptr);
    792                 dname = dptr_ReadDirName(conn->dirptr, &curoff, &sbuf);
     822                dname = dptr_ReadDirName(ctx, conn->dirptr, &curoff, &sbuf);
    793823
    794824                DEBUG(6,("readdir on dirptr 0x%lx now at offset %ld\n",
    795825                        (long)conn->dirptr,TellDir(conn->dirptr->dir_hnd)));
    796      
    797                 if (dname == NULL)
     826
     827                if (dname == NULL) {
    798828                        return(False);
    799      
    800                 pstrcpy(filename,dname);     
     829                }
     830
     831                filename = dname;
    801832
    802833                /* notice the special *.* handling. This appears to be the only difference
     
    807838                    mask_match_search(filename,mask,False) ||
    808839                    mangle_mask_match(conn,filename,mask)) {
    809 
    810                         if (!mangle_is_8_3(filename, False, conn->params))
    811                                 mangle_map(filename,True,False,
    812                                            conn->params);
    813 
    814                         pstrcpy(fname,filename);
    815                         *path = 0;
    816                         pstrcpy(path,conn->dirpath);
    817                         if(needslash)
    818                                 pstrcat(path,"/");
    819                         pstrcpy(pathreal,path);
    820                         pstrcat(path,fname);
    821                         pstrcat(pathreal,dname);
     840                        char mname[13];
     841
     842                        if (!mangle_is_8_3(filename, False, conn->params)) {
     843                                if (!name_to_8_3(filename,mname,False,
     844                                           conn->params)) {
     845                                        continue;
     846                                }
     847                                filename = mname;
     848                        }
     849
     850                        if (needslash) {
     851                                pathreal = talloc_asprintf(ctx,
     852                                                "%s/%s",
     853                                                conn->dirpath,
     854                                                dname);
     855                        } else {
     856                                pathreal = talloc_asprintf(ctx,
     857                                                "%s%s",
     858                                                conn->dirpath,
     859                                                dname);
     860                        }
     861                        if (!pathreal) {
     862                                return False;
     863                        }
     864
    822865                        if (!VALID_STAT(sbuf) && (SMB_VFS_STAT(conn, pathreal, &sbuf)) != 0) {
    823                                 DEBUG(5,("Couldn't stat 1 [%s]. Error = %s\n",path, strerror(errno) ));
     866                                DEBUG(5,("Couldn't stat 1 [%s]. Error = %s\n",
     867                                        pathreal, strerror(errno) ));
     868                                TALLOC_FREE(pathreal);
    824869                                continue;
    825870                        }
    826          
     871
    827872                        *mode = dos_mode(conn,pathreal,&sbuf);
    828873
    829874                        if (!dir_check_ftype(conn,*mode,dirtype)) {
    830875                                DEBUG(5,("[%s] attribs 0x%x didn't match 0x%x\n",filename,(unsigned int)*mode,(unsigned int)dirtype));
     876                                TALLOC_FREE(pathreal);
    831877                                continue;
    832878                        }
     
    835881                        *date = sbuf.st_mtime;
    836882
    837                         DEBUG(3,("get_dir_entry mask=[%s] found %s fname=%s\n",mask, pathreal,fname));
     883                        DEBUG(3,("get_dir_entry mask=[%s] found %s "
     884                                "fname=%s (%s)\n",
     885                                mask,
     886                                pathreal,
     887                                dname,
     888                                filename));
    838889
    839890                        found = True;
    840891
     892                        *pp_fname_out = talloc_strdup(ctx, filename);
     893                        if (!*pp_fname_out) {
     894                                return False;
     895                        }
     896
    841897                        DirCacheAdd(conn->dirptr->dir_hnd, dname, curoff);
     898                        TALLOC_FREE(pathreal);
    842899                }
    843900        }
     
    879936
    880937        if(S_ISDIR(pst->st_mode)) {
    881                  status = open_directory(conn, name, pst,
     938                 status = open_directory(conn, NULL, name, pst,
    882939                        READ_CONTROL_ACCESS,
    883940                        FILE_SHARE_READ|FILE_SHARE_WRITE,
     
    887944                        NULL, &fsp);
    888945        } else {
    889                 status = open_file_stat(conn, name, pst, &fsp);
     946                status = open_file_stat(conn, NULL, name, pst, &fsp);
    890947        }
    891948
     
    9431000                return True;
    9441001        } else {
    945                 status = open_file_ntcreate(conn, name, pst,
     1002                status = open_file_ntcreate(conn, NULL, name, pst,
    9461003                        FILE_WRITE_ATTRIBUTES,
    9471004                        FILE_SHARE_READ|FILE_SHARE_WRITE,
     
    10171074
    10181075        if (hide_unreadable || hide_unwriteable || hide_special) {
    1019                 pstring link_target;
    10201076                char *entry = NULL;
    10211077
     
    10271083                if (lp_host_msdfs() &&
    10281084                                lp_msdfs_root(SNUM(conn)) &&
    1029                                 is_msdfs_link(conn, entry, link_target, NULL)) {
     1085                                is_msdfs_link(conn, entry, NULL)) {
    10301086                        SAFE_FREE(entry);
    10311087                        return True;
     
    11961252                if (offset == START_OF_DIRECTORY_OFFSET) {
    11971253                        RewindDir(dirp, &offset);
    1198                         /* 
     1254                        /*
    11991255                         * Ok we should really set the file number here
    12001256                         * to 1 to enable ".." to be returned next. Trouble
Note: See TracChangeset for help on using the changeset viewer.