summaryrefslogtreecommitdiff
path: root/source3/smbd/dir.c
diff options
context:
space:
mode:
Diffstat (limited to 'source3/smbd/dir.c')
-rw-r--r--source3/smbd/dir.c96
1 files changed, 39 insertions, 57 deletions
diff --git a/source3/smbd/dir.c b/source3/smbd/dir.c
index 04e3167e77..ca6f8bfd8d 100644
--- a/source3/smbd/dir.c
+++ b/source3/smbd/dir.c
@@ -142,8 +142,7 @@ static void dptr_idle(struct dptr_struct *dptr)
{
if (dptr->dir_hnd) {
DEBUG(4,("Idling dptr dnum %d\n",dptr->dnum));
- CloseDir(dptr->dir_hnd);
- dptr->dir_hnd = NULL;
+ TALLOC_FREE(dptr->dir_hnd);
}
}
@@ -192,7 +191,9 @@ static struct dptr_struct *dptr_get(int key, bool forclose)
if (dirhandles_open >= MAX_OPEN_DIRECTORIES)
dptr_idleoldest();
DEBUG(4,("dptr_get: Reopening dptr key %d\n",key));
- if (!(dptr->dir_hnd = OpenDir(dptr->conn, dptr->path, dptr->wcard, dptr->attr))) {
+ if (!(dptr->dir_hnd = OpenDir(
+ NULL, dptr->conn, dptr->path,
+ dptr->wcard, dptr->attr))) {
DEBUG(4,("dptr_get: Failed to open %s (%s)\n",dptr->path,
strerror(errno)));
return False;
@@ -263,9 +264,7 @@ static void dptr_close_internal(struct dptr_struct *dptr)
bitmap_clear(dptr_bmap, dptr->dnum - 1);
- if (dptr->dir_hnd) {
- CloseDir(dptr->dir_hnd);
- }
+ TALLOC_FREE(dptr->dir_hnd);
/* Lanman 2 specific code */
SAFE_FREE(dptr->wcard);
@@ -411,7 +410,7 @@ NTSTATUS dptr_create(connection_struct *conn, const char *path, bool old_handle,
return status;
}
- dir_hnd = OpenDir(conn, path, wcard, attr);
+ dir_hnd = OpenDir(NULL, conn, path, wcard, attr);
if (!dir_hnd) {
return map_nt_error_from_unix(errno);
}
@@ -425,7 +424,7 @@ NTSTATUS dptr_create(connection_struct *conn, const char *path, bool old_handle,
dptr = SMB_MALLOC_P(struct dptr_struct);
if(!dptr) {
DEBUG(0,("malloc fail in dptr_create.\n"));
- CloseDir(dir_hnd);
+ TALLOC_FREE(dir_hnd);
return NT_STATUS_NO_MEMORY;
}
@@ -455,7 +454,7 @@ NTSTATUS dptr_create(connection_struct *conn, const char *path, bool old_handle,
if(dptr->dnum == -1 || dptr->dnum > 254) {
DEBUG(0,("dptr_create: returned %d: Error - all old dirptrs in use ?\n", dptr->dnum));
SAFE_FREE(dptr);
- CloseDir(dir_hnd);
+ TALLOC_FREE(dir_hnd);
return NT_STATUS_TOO_MANY_OPENED_FILES;
}
}
@@ -485,7 +484,7 @@ NTSTATUS dptr_create(connection_struct *conn, const char *path, bool old_handle,
if(dptr->dnum == -1 || dptr->dnum < 255) {
DEBUG(0,("dptr_create: returned %d: Error - all new dirptrs in use ?\n", dptr->dnum));
SAFE_FREE(dptr);
- CloseDir(dir_hnd);
+ TALLOC_FREE(dir_hnd);
return NT_STATUS_TOO_MANY_OPENED_FILES;
}
}
@@ -504,7 +503,7 @@ NTSTATUS dptr_create(connection_struct *conn, const char *path, bool old_handle,
if (!dptr->wcard) {
bitmap_clear(dptr_bmap, dptr->dnum - 1);
SAFE_FREE(dptr);
- CloseDir(dir_hnd);
+ TALLOC_FREE(dir_hnd);
return NT_STATUS_NO_MEMORY;
}
if (lp_posix_pathnames() || (wcard[0] == '.' && wcard[1] == 0)) {
@@ -533,7 +532,8 @@ NTSTATUS dptr_create(connection_struct *conn, const char *path, bool old_handle,
int dptr_CloseDir(struct dptr_struct *dptr)
{
DLIST_REMOVE(dirptrs, dptr);
- return CloseDir(dptr->dir_hnd);
+ TALLOC_FREE(dptr->dir_hnd);
+ return 0;
}
void dptr_SeekDir(struct dptr_struct *dptr, long offset)
@@ -1113,72 +1113,53 @@ bool is_visible_file(connection_struct *conn, const char *dir_path, const char *
return True;
}
+static int smb_Dir_destructor(struct smb_Dir *dirp)
+{
+ if (dirp->dir) {
+ SMB_VFS_CLOSEDIR(dirp->conn,dirp->dir);
+ }
+ dirhandles_open--;
+ return 0;
+}
+
/*******************************************************************
Open a directory.
********************************************************************/
-struct smb_Dir *OpenDir(connection_struct *conn, const char *name, const char *mask, uint32 attr)
+struct smb_Dir *OpenDir(TALLOC_CTX *mem_ctx, connection_struct *conn,
+ const char *name, const char *mask, uint32 attr)
{
- struct smb_Dir *dirp = SMB_MALLOC_P(struct smb_Dir);
+ struct smb_Dir *dirp = TALLOC_ZERO_P(mem_ctx, struct smb_Dir);
if (!dirp) {
return NULL;
}
- ZERO_STRUCTP(dirp);
dirp->conn = conn;
dirp->name_cache_size = lp_directory_name_cache_size(SNUM(conn));
- dirp->dir_path = SMB_STRDUP(name);
+ dirp->dir_path = talloc_strdup(dirp, name);
if (!dirp->dir_path) {
goto fail;
}
+
+ dirhandles_open++;
+ talloc_set_destructor(dirp, smb_Dir_destructor);
+
dirp->dir = SMB_VFS_OPENDIR(conn, dirp->dir_path, mask, attr);
if (!dirp->dir) {
- DEBUG(5,("OpenDir: Can't open %s. %s\n", dirp->dir_path, strerror(errno) ));
+ DEBUG(5,("OpenDir: Can't open %s. %s\n", dirp->dir_path,
+ strerror(errno) ));
goto fail;
}
- dirhandles_open++;
return dirp;
fail:
-
- if (dirp) {
- if (dirp->dir) {
- SMB_VFS_CLOSEDIR(conn,dirp->dir);
- }
- SAFE_FREE(dirp->dir_path);
- SAFE_FREE(dirp->name_cache);
- SAFE_FREE(dirp);
- }
+ TALLOC_FREE(dirp);
return NULL;
}
-
-/*******************************************************************
- Close a directory.
-********************************************************************/
-
-int CloseDir(struct smb_Dir *dirp)
-{
- int i, ret = 0;
-
- if (dirp->dir) {
- ret = SMB_VFS_CLOSEDIR(dirp->conn,dirp->dir);
- }
- SAFE_FREE(dirp->dir_path);
- if (dirp->name_cache) {
- for (i = 0; i < dirp->name_cache_size; i++) {
- SAFE_FREE(dirp->name_cache[i].name);
- }
- }
- SAFE_FREE(dirp->name_cache);
- SAFE_FREE(dirp);
- dirhandles_open--;
- return ret;
-}
-
/*******************************************************************
Read from a directory. Also return current offset.
Don't check for veto or invisible files.
@@ -1290,8 +1271,8 @@ void DirCacheAdd(struct smb_Dir *dirp, const char *name, long offset)
}
if (dirp->name_cache == NULL) {
- dirp->name_cache = SMB_CALLOC_ARRAY(struct name_cache_entry,
- dirp->name_cache_size);
+ dirp->name_cache = TALLOC_ZERO_ARRAY(
+ dirp, struct name_cache_entry, dirp->name_cache_size);
if (dirp->name_cache == NULL) {
return;
@@ -1301,8 +1282,8 @@ void DirCacheAdd(struct smb_Dir *dirp, const char *name, long offset)
dirp->name_cache_index = (dirp->name_cache_index+1) %
dirp->name_cache_size;
e = &dirp->name_cache[dirp->name_cache_index];
- SAFE_FREE(e->name);
- e->name = SMB_STRDUP(name);
+ TALLOC_FREE(e->name);
+ e->name = talloc_strdup(dirp, name);
e->offset = offset;
}
@@ -1359,7 +1340,8 @@ NTSTATUS can_delete_directory(struct connection_struct *conn,
NTSTATUS status = NT_STATUS_OK;
long dirpos = 0;
const char *dname;
- struct smb_Dir *dir_hnd = OpenDir(conn, dirname, NULL, 0);
+ struct smb_Dir *dir_hnd = OpenDir(talloc_tos(), conn, dirname,
+ NULL, 0);
if (!dir_hnd) {
return map_nt_error_from_unix(errno);
@@ -1383,7 +1365,7 @@ NTSTATUS can_delete_directory(struct connection_struct *conn,
status = NT_STATUS_DIRECTORY_NOT_EMPTY;
break;
}
- CloseDir(dir_hnd);
+ TALLOC_FREE(dir_hnd);
return status;
}