[SCM] Samba Shared Repository - branch master updated
Stefan Metzmacher
metze at samba.org
Thu Jan 14 12:41:01 UTC 2021
The branch, master has been updated
via da052dde8a9 s3:smbd: simplify the error handling in create_file_unixpath()
via 9c277b27dec s3:smbd: allow close_file() with a non-fsa fsp for {SHUTDOWN,ERROR}_CLOSE
via 20187c6f54c s3:smbd: make sure a SHUTDOWN_CLOSE applies to a stream fsp before its base fsp
via 930b6bb3b87 s3:smbd: make use of fsp_set_base_fsp() when changing fsp->base_fsp
via 928382f2700 s3:smbd: add fsp_set_base_fsp() helper
via 42c60703f2e s3:smbd: remove duplicate assignment of base_fsp in create_file_unixpath()
via 87b4a8f35a8 s3:smbd: fix the error cleanup in create_file_unixpath()
via 22bebaf8589 s3:smbd: split out create_internal_fsp() from create_internal_dirfsp()
via 7dc9a84bb5c s3:smbd: make fsp_free() static, it should only ever be called by file_free()
via 81b6931be0c s3:smbd: let vfs_default_durable_reconnect() use file_free()
via bcac1dab694 s3:smbd: close pathref fsp in call_trans2findfirst()
via eae7ce8a2e0 s3:smbd: turn assignment into assert check in call_trans2findfirst()
via e1a10b58171 s3:smbd: let call_trans2findfirst() use file_free() instead of fsp_free()
via 9b1dc2a4ca6 s3:smbd: make sure openat_pathref_fsp() calls fd_close(fsp->base_fsp);
via 8d79764ad3e s3:smbd: introduce a reopen_from_fsp() helper function
via 38ae1599a0c s3:smbd: don't pass an unused smb_fname to reopen_from_procfd()
via d6949f0f93f s3:smbd: let open_directory() also use fd_open_atomic() as reopen_from_procfd() fallback
via 30134630988 s3:smbd: let open_pathref_base_fsp() make use of smb_fname_fsp_unlink()
via c2e7256b1e0 s3:smbd: let openat_pathref_fsp() make use of fsp_attach_smb_fname()
via cff29e58ffa s3:smbd: let openat_pathref_fsp() allocate fsp->fsp_name directly on fsp
via 347edf7ee00 s3:smbd: split out a fsp_attach_smb_fname() helper function
via 1ab038b77a8 s3:smbd: let fsp_set_smb_fname() always link fsp to fsp->fsp_name->fsp
via 932c27e290e s3:smbd: let fsp_smb_fname_link() set both sides of the link
via 3fdfb79a12b s3:smbd: rearrange move_smb_fname_fsp_link a bit
from 4e624478dcd s4 auth ntlm: Fix integer overflow in authsam_password_check_and_record
https://git.samba.org/?p=samba.git;a=shortlog;h=master
- Log -----------------------------------------------------------------
commit da052dde8a9801063e74d036d15f516d079d3720
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Dec 21 16:49:03 2020 +0100
s3:smbd: simplify the error handling in create_file_unixpath()
We can just call close_file(req, fsp, ERROR_CLOSE), as it handles
non-fsa fsp's and base_fsp's just fine.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
Autobuild-User(master): Stefan Metzmacher <metze at samba.org>
Autobuild-Date(master): Thu Jan 14 12:40:56 UTC 2021 on sn-devel-184
commit 9c277b27dec568677c0b407497da6eb95ae7cb8d
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 23 12:10:37 2020 +0100
s3:smbd: allow close_file() with a non-fsa fsp for {SHUTDOWN,ERROR}_CLOSE
Such an fsp was typically created via create_internal_fsp() and
opened via fd_openat() without going through SMB_VFS_CREATE_FILE(),
so they should be closed via fd_close().
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 20187c6f54c85131bcdc7979a649d1a575d3a8e0
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 23 11:50:34 2020 +0100
s3:smbd: make sure a SHUTDOWN_CLOSE applies to a stream fsp before its base fsp
Before we had open_pathref_fsp() we had the stream fsp before the base
fsp in the linked list we traverse for SHUTDOWN_CLOSE.
Now the order has changed. I could have used some DLIST_PROMOTE()
hacks, but that's still fragile.
Now we reference both fsp's via ->base_fsp and ->stream_fsp.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 930b6bb3b87f600757266b34a9bb1ca3764177fd
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Dec 21 16:35:11 2020 +0100
s3:smbd: make use of fsp_set_base_fsp() when changing fsp->base_fsp
This allows us to add some more logic for bi-directional linking between
base and stream fsp in the next commits.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 928382f27000ce93aa29080f06cb7445b0b8c281
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Dec 21 15:44:22 2020 +0100
s3:smbd: add fsp_set_base_fsp() helper
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 42c60703f2e7417168774f7b5a0ff25299e3b6a2
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Jan 4 16:33:09 2021 +0100
s3:smbd: remove duplicate assignment of base_fsp in create_file_unixpath()
This has already been set a few lines above. The duplicate was the result of
restructuring create_file_unixpath() a few months ago, allocating fsp in
create_file_unixpath() instead of in the callees open_file_ntcreate() or
open_directory() respectively.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 87b4a8f35a8ab993eec806022986fdf860c8bbc7
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Dec 21 16:40:01 2020 +0100
s3:smbd: fix the error cleanup in create_file_unixpath()
We always need to cleanup the base_fsp!
Signed-off-by: Stefan Metzmacher <metze at samba.org>
commit 22bebaf8589ff6ff95fe59f14f632b3b90471920
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 23 11:50:34 2020 +0100
s3:smbd: split out create_internal_fsp() from create_internal_dirfsp()
That will be useful in other places as well.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 7dc9a84bb5c78235c4e77fde2b8297e9c8206862
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Dec 21 12:41:06 2020 +0100
s3:smbd: make fsp_free() static, it should only ever be called by file_free()
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 81b6931be0cd4adfcb233e1c03fb9ca898fee9b0
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Dec 21 12:18:44 2020 +0100
s3:smbd: let vfs_default_durable_reconnect() use file_free()
We should always go through file_free(), which calls fsp_free() at the end.
Most things in file_free() may not apply to all
vfs_default_durable_reconnect() cases, but we want fsp_free() to become
static to files.c
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit bcac1dab694be832c3f993356daacaee35c49f71
Author: Ralph Boehme <slow at samba.org>
Date: Tue Jan 12 12:50:43 2021 +0100
s3:smbd: close pathref fsp in call_trans2findfirst()
Before freeing the fsp we have to close the handle.
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Stefan Metzmacher <metze at samba.org>
commit eae7ce8a2e0e0982bba70fbd36f444954339abe3
Author: Ralph Boehme <slow at samba.org>
Date: Mon Jan 4 16:09:43 2021 +0100
s3:smbd: turn assignment into assert check in call_trans2findfirst()
The pathref fsp link destructor will set smb_dname->fsp to NULL. Turning this
into an assert to give a hint at readers of the code trying to understand the
mechanics.
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Stefan Metzmacher <metze at samba.org>
commit e1a10b58171ec5a1b41ab99962bc6eebb3b427e3
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 23 13:28:40 2020 +0100
s3:smbd: let call_trans2findfirst() use file_free() instead of fsp_free()
This makes sure we call vfs_remove_all_fsp_extensions() before
fsp_free() is called from within file_free(). And allows us to
make 'fsp_free()' static in the next commits.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 9b1dc2a4ca61aaa96c3e731a7a59da2a21aa522d
Author: Stefan Metzmacher <metze at samba.org>
Date: Mon Dec 21 15:31:25 2020 +0100
s3:smbd: make sure openat_pathref_fsp() calls fd_close(fsp->base_fsp);
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 8d79764ad3ed75cddec1568d74cbfd3d41e018be
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 23 15:48:36 2020 +0100
s3:smbd: introduce a reopen_from_fsp() helper function
In future we may move the reopen logic to the VFS,
but for now we just keep it in one place.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 38ae1599a0c7408a8a6abf9856ad2979c4c3aa81
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 23 16:03:37 2020 +0100
s3:smbd: don't pass an unused smb_fname to reopen_from_procfd()
Both callers pass in a helper variable that points to
fsp->fsp_name and it was only used for a debug message,
so we can simply use fsp_str_dgb() instead.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit d6949f0f93ff0a1f6292395fbbd9c07b12fe9336
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 23 15:38:03 2020 +0100
s3:smbd: let open_directory() also use fd_open_atomic() as reopen_from_procfd() fallback
Calling fd_open_atomic() without O_CREAT is the same as calling
fd_openat() directly, so we can also use it to open an existing
directory.
In the next step we'll move the reopen_from_procfd() fallback logic to
a single helper function.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 30134630988ca76545a8aee8516d44a0dc64bc8d
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 16 15:12:46 2020 +0100
s3:smbd: let open_pathref_base_fsp() make use of smb_fname_fsp_unlink()
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit c2e7256b1e092acc20daf58059c0e749e3a756e4
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 16 15:02:11 2020 +0100
s3:smbd: let openat_pathref_fsp() make use of fsp_attach_smb_fname()
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit cff29e58ffaa81785e89f240808af84d6db836c8
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 16 14:50:08 2020 +0100
s3:smbd: let openat_pathref_fsp() allocate fsp->fsp_name directly on fsp
Otherwise we'll always keep the current talloc_stackframe arround.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 347edf7ee00609782d6a5d1f4b0995424c831a00
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 16 15:01:38 2020 +0100
s3:smbd: split out a fsp_attach_smb_fname() helper function
It's useful to watch this using: git show --histogram
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 1ab038b77a89a7960fbd4cdb55565af6b2333574
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 16 14:15:11 2020 +0100
s3:smbd: let fsp_set_smb_fname() always link fsp to fsp->fsp_name->fsp
This was only done if fsp->fsp_name already existed, but not the first time.
This also makes sure we modify fsp->fsp_name and fsp->name_hash only on success.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 932c27e290ead0c2a98c57f2a9649aaf51d7233b
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Dec 16 14:03:36 2020 +0100
s3:smbd: let fsp_smb_fname_link() set both sides of the link
We also need to be sure both sides were not linked before.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
commit 3fdfb79a12bf21eb661a8dea00f46bf944ea9df0
Author: Stefan Metzmacher <metze at samba.org>
Date: Thu Dec 17 11:05:21 2020 +0100
s3:smbd: rearrange move_smb_fname_fsp_link a bit
We only modify smb_fname_src on success.
Signed-off-by: Stefan Metzmacher <metze at samba.org>
Reviewed-by: Volker Lendecke <vl at samba.org>
Reviewed-by: Ralph Boehme <slow at samba.org>
-----------------------------------------------------------------------
Summary of changes:
source3/include/vfs.h | 1 +
source3/smbd/close.c | 65 +++++++++++++++--
source3/smbd/durable.c | 35 ++++++----
source3/smbd/files.c | 184 ++++++++++++++++++++++++++++++++++---------------
source3/smbd/open.c | 128 +++++++++++++++++-----------------
source3/smbd/proto.h | 5 +-
source3/smbd/trans2.c | 14 +++-
7 files changed, 289 insertions(+), 143 deletions(-)
Changeset truncated at 500 lines:
diff --git a/source3/include/vfs.h b/source3/include/vfs.h
index 04c8c3e4c76..49726618c5c 100644
--- a/source3/include/vfs.h
+++ b/source3/include/vfs.h
@@ -446,6 +446,7 @@ typedef struct files_struct {
struct notify_change_buf *notify;
struct files_struct *base_fsp; /* placeholder for delete on close */
+ struct files_struct *stream_fsp; /* backlink from base_fsp */
/*
* Cache of share_mode_data->flags
diff --git a/source3/smbd/close.c b/source3/smbd/close.c
index 20f2ed8a172..97d13473082 100644
--- a/source3/smbd/close.c
+++ b/source3/smbd/close.c
@@ -1290,6 +1290,7 @@ NTSTATUS close_file(struct smb_request *req, files_struct *fsp,
{
NTSTATUS status;
struct files_struct *base_fsp = fsp->base_fsp;
+ bool close_base_fsp = false;
/*
* This fsp can never be an internal dirfsp. They must
@@ -1297,31 +1298,83 @@ NTSTATUS close_file(struct smb_request *req, files_struct *fsp,
*/
SMB_ASSERT(!fsp->fsp_flags.is_dirfsp);
- if (fsp->fsp_flags.is_directory) {
- status = close_directory(req, fsp, close_type);
- } else if (fsp->fake_file_handle != NULL) {
+ if (fsp->stream_fsp != NULL) {
+ /*
+ * fsp is the base for a stream.
+ *
+ * We're called with SHUTDOWN_CLOSE from files.c which walks the
+ * complete list of files.
+ *
+ * We need to wait until the stream is closed.
+ */
+ SMB_ASSERT(close_type == SHUTDOWN_CLOSE);
+ return NT_STATUS_OK;
+ }
+
+ if (base_fsp != NULL) {
+ /*
+ * We need to remove the link in order to
+ * recurse for the base fsp below.
+ */
+ SMB_ASSERT(base_fsp->base_fsp == NULL);
+ SMB_ASSERT(base_fsp->stream_fsp == fsp);
+ base_fsp->stream_fsp = NULL;
+
+ if (close_type == SHUTDOWN_CLOSE) {
+ /*
+ * We're called with SHUTDOWN_CLOSE from files.c
+ * which walks the complete list of files.
+ *
+ * We may need to defer the SHUTDOWN_CLOSE
+ * if it's the next in the linked list.
+ *
+ * So we only close if the base is *not* the
+ * next in the list.
+ */
+ close_base_fsp = (fsp->next != base_fsp);
+ } else {
+ close_base_fsp = true;
+ }
+ }
+
+ if (fsp->fake_file_handle != NULL) {
status = close_fake_file(req, fsp);
} else if (fsp->print_file != NULL) {
/* FIXME: return spool errors */
print_spool_end(fsp, close_type);
file_free(req, fsp);
status = NT_STATUS_OK;
+ } else if (!fsp->fsp_flags.is_fsa) {
+ if (close_type == NORMAL_CLOSE) {
+ DBG_ERR("unexpected NORMAL_CLOSE for [%s] "
+ "is_fsa[%u] is_pathref[%u] is_directory[%u]\n",
+ fsp_str_dbg(fsp),
+ fsp->fsp_flags.is_fsa,
+ fsp->fsp_flags.is_pathref,
+ fsp->fsp_flags.is_directory);
+ }
+ SMB_ASSERT(close_type != NORMAL_CLOSE);
+ fd_close(fsp);
+ file_free(req, fsp);
+ status = NT_STATUS_OK;
+ } else if (fsp->fsp_flags.is_directory) {
+ status = close_directory(req, fsp, close_type);
} else {
status = close_normal_file(req, fsp, close_type);
}
- if ((base_fsp != NULL) && (close_type != SHUTDOWN_CLOSE)) {
+ if (close_base_fsp) {
/*
* fsp was a stream, the base fsp can't be a stream as well
*
- * For SHUTDOWN_CLOSE this is not possible here, because
+ * For SHUTDOWN_CLOSE this is not possible here
+ * (if the base_fsp was the next in the linked list), because
* SHUTDOWN_CLOSE only happens from files.c which walks the
* complete list of files. If we mess with more than one fsp
* those loops will become confused.
*/
- SMB_ASSERT(base_fsp->base_fsp == NULL);
close_file(req, base_fsp, close_type);
}
diff --git a/source3/smbd/durable.c b/source3/smbd/durable.c
index 0580ae4adbf..c3f55d1bdff 100644
--- a/source3/smbd/durable.c
+++ b/source3/smbd/durable.c
@@ -719,7 +719,7 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
if (!GUID_equal(fsp_client_guid(fsp),
&e.client_guid)) {
TALLOC_FREE(lck);
- fsp_free(fsp);
+ file_free(smb1req, fsp);
return NT_STATUS_OBJECT_NAME_NOT_FOUND;
}
@@ -735,7 +735,7 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
&epoch); /* epoch */
if (!NT_STATUS_IS_OK(status)) {
TALLOC_FREE(lck);
- fsp_free(fsp);
+ file_free(smb1req, fsp);
return status;
}
@@ -747,7 +747,7 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
epoch);
if (fsp->lease == NULL) {
TALLOC_FREE(lck);
- fsp_free(fsp);
+ file_free(smb1req, fsp);
return NT_STATUS_NO_MEMORY;
}
}
@@ -765,7 +765,7 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
status = fsp_set_smb_fname(fsp, smb_fname);
if (!NT_STATUS_IS_OK(status)) {
TALLOC_FREE(lck);
- fsp_free(fsp);
+ file_free(smb1req, fsp);
DEBUG(0, ("vfs_default_durable_reconnect: "
"fsp_set_smb_fname failed: %s\n",
nt_errstr(status)));
@@ -786,7 +786,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
DBG_DEBUG("Could not set new share_mode_entry values\n");
TALLOC_FREE(lck);
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return NT_STATUS_INTERNAL_ERROR;
}
@@ -798,7 +799,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
nt_errstr(status)));
TALLOC_FREE(lck);
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return status;
}
@@ -819,7 +821,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
DEBUG(1, ("vfs_default_durable_reconnect: failed to open "
"file: %s\n", nt_errstr(status)));
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return status;
}
@@ -846,7 +849,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
}
TALLOC_FREE(lck);
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return status;
}
@@ -859,7 +863,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
}
TALLOC_FREE(lck);
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return NT_STATUS_OBJECT_NAME_NOT_FOUND;
}
@@ -873,7 +878,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
}
TALLOC_FREE(lck);
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return NT_STATUS_OBJECT_NAME_NOT_FOUND;
}
@@ -891,7 +897,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
}
TALLOC_FREE(lck);
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return NT_STATUS_OBJECT_NAME_NOT_FOUND;
}
@@ -907,7 +914,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
}
TALLOC_FREE(lck);
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return status;
}
@@ -918,7 +926,8 @@ NTSTATUS vfs_default_durable_reconnect(struct connection_struct *conn,
"vfs_default_durable_cookie - %s\n",
nt_errstr(status)));
op->compat = NULL;
- fsp_free(fsp);
+ fsp->op = NULL;
+ file_free(smb1req, fsp);
return status;
}
diff --git a/source3/smbd/files.c b/source3/smbd/files.c
index e19c11883eb..f60d5979f53 100644
--- a/source3/smbd/files.c
+++ b/source3/smbd/files.c
@@ -26,6 +26,9 @@
#define FILE_HANDLE_OFFSET 0x1000
+static NTSTATUS fsp_attach_smb_fname(struct files_struct *fsp,
+ struct smb_filename **_smb_fname);
+
/**
* create new fsp to be used for file_new or a durable handle reconnect
*/
@@ -183,6 +186,28 @@ NTSTATUS file_new(struct smb_request *req, connection_struct *conn,
return NT_STATUS_OK;
}
+NTSTATUS create_internal_fsp(connection_struct *conn,
+ const struct smb_filename *smb_fname,
+ struct files_struct **_fsp)
+{
+ struct files_struct *fsp = NULL;
+ NTSTATUS status;
+
+ status = file_new(NULL, conn, &fsp);
+ if (!NT_STATUS_IS_OK(status)) {
+ return status;
+ }
+
+ status = fsp_set_smb_fname(fsp, smb_fname);
+ if (!NT_STATUS_IS_OK(status)) {
+ file_free(NULL, fsp);
+ return status;
+ }
+
+ *_fsp = fsp;
+ return NT_STATUS_OK;
+}
+
/*
* Create an internal fsp for an *existing* directory.
*
@@ -196,17 +221,11 @@ NTSTATUS create_internal_dirfsp(connection_struct *conn,
struct files_struct *fsp = NULL;
NTSTATUS status;
- status = file_new(NULL, conn, &fsp);
+ status = create_internal_fsp(conn, smb_dname, &fsp);
if (!NT_STATUS_IS_OK(status)) {
return status;
}
- status = fsp_set_smb_fname(fsp, smb_dname);
- if (!NT_STATUS_IS_OK(status)) {
- file_free(NULL, fsp);
- return status;
- }
-
fsp->access_mask = FILE_LIST_DIRECTORY;
fsp->fsp_flags.is_directory = true;
fsp->fsp_flags.is_dirfsp = true;
@@ -299,6 +318,9 @@ static NTSTATUS fsp_smb_fname_link(struct files_struct *fsp,
{
struct fsp_smb_fname_link *link = NULL;
+ SMB_ASSERT(*smb_fname_link == NULL);
+ SMB_ASSERT(*smb_fname_fsp == NULL);
+
link = talloc_zero(fsp, struct fsp_smb_fname_link);
if (link == NULL) {
return NT_STATUS_NO_MEMORY;
@@ -307,6 +329,7 @@ static NTSTATUS fsp_smb_fname_link(struct files_struct *fsp,
link->smb_fname_link = smb_fname_link;
link->smb_fname_fsp = smb_fname_fsp;
*smb_fname_link = link;
+ *smb_fname_fsp = fsp;
talloc_set_destructor(link, fsp_smb_fname_link_destructor);
return NT_STATUS_OK;
@@ -343,10 +366,13 @@ static int smb_fname_fsp_destructor(struct smb_filename *smb_fname)
}
if (fsp->base_fsp != NULL) {
- status = fd_close(fsp->base_fsp);
+ struct files_struct *tmp_base_fsp = fsp->base_fsp;
+
+ fsp_set_base_fsp(fsp, NULL);
+
+ status = fd_close(tmp_base_fsp);
SMB_ASSERT(NT_STATUS_IS_OK(status));
- file_free(NULL, fsp->base_fsp);
- fsp->base_fsp = NULL;
+ file_free(NULL, tmp_base_fsp);
}
status = fd_close(fsp);
@@ -388,10 +414,8 @@ static NTSTATUS open_pathref_base_fsp(const struct files_struct *dirfsp,
return NT_STATUS_OBJECT_NAME_NOT_FOUND;
}
- fsp->base_fsp = smb_fname_base->fsp;
- smb_fname_base->fsp = NULL;
- talloc_set_destructor(smb_fname_base->fsp_link, NULL);
- talloc_set_destructor(smb_fname_base, NULL);
+ fsp_set_base_fsp(fsp, smb_fname_base->fsp);
+ smb_fname_fsp_unlink(smb_fname_base);
TALLOC_FREE(smb_fname_base);
return NT_STATUS_OK;
@@ -441,7 +465,7 @@ NTSTATUS openat_pathref_fsp(const struct files_struct *dirfsp,
open_flags |= O_DIRECTORY;
}
- full_fname = full_path_from_dirfsp_atname(talloc_tos(),
+ full_fname = full_path_from_dirfsp_atname(fsp,
dirfsp,
smb_fname);
if (full_fname == NULL) {
@@ -449,15 +473,11 @@ NTSTATUS openat_pathref_fsp(const struct files_struct *dirfsp,
goto fail;
}
- fsp->fsp_name = talloc_move(fsp, &full_fname);
-
- if (is_ntfs_default_stream_smb_fname(fsp->fsp_name)) {
- fsp->fsp_name->stream_name = NULL;
+ if (is_ntfs_default_stream_smb_fname(full_fname)) {
+ full_fname->stream_name = NULL;
}
- status = file_name_hash(fsp->conn,
- smb_fname_str_dbg(fsp->fsp_name),
- &fsp->name_hash);
+ status = fsp_attach_smb_fname(fsp, &full_fname);
if (!NT_STATUS_IS_OK(status)) {
goto fail;
}
@@ -478,10 +498,13 @@ NTSTATUS openat_pathref_fsp(const struct files_struct *dirfsp,
nt_errstr(status));
if (fsp->base_fsp != NULL) {
- file_free(NULL, fsp->base_fsp);
- fsp->base_fsp = NULL;
+ struct files_struct *tmp_base_fsp = fsp->base_fsp;
+
+ fsp_set_base_fsp(fsp, NULL);
+
+ fd_close(tmp_base_fsp);
+ file_free(NULL, tmp_base_fsp);
}
- fd_close(fsp);
file_free(NULL, fsp);
fsp = NULL;
@@ -525,9 +548,6 @@ NTSTATUS openat_pathref_fsp(const struct files_struct *dirfsp,
fsp->file_id = vfs_file_id_from_sbuf(conn, &fsp->fsp_name->st);
- fsp->fsp_name->fsp = fsp;
- smb_fname->fsp = fsp;
-
status = fsp_smb_fname_link(fsp,
&smb_fname->fsp_link,
&smb_fname->fsp);
@@ -535,13 +555,6 @@ NTSTATUS openat_pathref_fsp(const struct files_struct *dirfsp,
goto fail;
}
- status = fsp_smb_fname_link(fsp,
- &fsp->fsp_name->fsp_link,
- &fsp->fsp_name->fsp);
- if (!NT_STATUS_IS_OK(status)) {
- goto fail;
- }
-
DBG_DEBUG("fsp [%s]: OK\n", fsp_str_dbg(fsp));
talloc_set_destructor(smb_fname, smb_fname_fsp_destructor);
@@ -556,8 +569,12 @@ fail:
return status;
}
if (fsp->base_fsp != NULL) {
- file_free(NULL, fsp->base_fsp);
- fsp->base_fsp = NULL;
+ struct files_struct *tmp_base_fsp = fsp->base_fsp;
+
+ fsp_set_base_fsp(fsp, NULL);
+
+ fd_close(tmp_base_fsp);
+ file_free(NULL, tmp_base_fsp);
}
fd_close(fsp);
file_free(NULL, fsp);
@@ -581,22 +598,27 @@ NTSTATUS move_smb_fname_fsp_link(struct smb_filename *smb_fname_dst,
{
NTSTATUS status;
+ /*
+ * The target should always not be linked yet!
+ */
+ SMB_ASSERT(smb_fname_dst->fsp == NULL);
+ SMB_ASSERT(smb_fname_dst->fsp_link == NULL);
+
if (smb_fname_src->fsp == NULL) {
return NT_STATUS_OK;
}
- smb_fname_dst->fsp = smb_fname_src->fsp;
- talloc_set_destructor(smb_fname_dst, smb_fname_fsp_destructor);
-
- smb_fname_fsp_unlink(smb_fname_src);
-
- status = fsp_smb_fname_link(smb_fname_dst->fsp,
+ status = fsp_smb_fname_link(smb_fname_src->fsp,
&smb_fname_dst->fsp_link,
&smb_fname_dst->fsp);
if (!NT_STATUS_IS_OK(status)) {
return status;
}
+ talloc_set_destructor(smb_fname_dst, smb_fname_fsp_destructor);
+
+ smb_fname_fsp_unlink(smb_fname_src);
+
return NT_STATUS_OK;
}
@@ -918,7 +940,7 @@ bool file_find_subpath(files_struct *dir_fsp)
Free up a fsp.
****************************************************************************/
-void fsp_free(files_struct *fsp)
+static void fsp_free(files_struct *fsp)
{
struct smbd_server_connection *sconn = fsp->conn->sconn;
@@ -1223,13 +1245,47 @@ NTSTATUS file_name_hash(connection_struct *conn,
return NT_STATUS_OK;
}
+static NTSTATUS fsp_attach_smb_fname(struct files_struct *fsp,
+ struct smb_filename **_smb_fname)
+{
+ struct smb_filename *smb_fname_new = *_smb_fname;
+ const char *name_str = NULL;
+ uint32_t name_hash = 0;
+ NTSTATUS status;
+
+ name_str = smb_fname_str_dbg(smb_fname_new);
+ if (name_str == NULL) {
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ status = file_name_hash(fsp->conn,
+ name_str,
--
Samba Shared Repository
More information about the samba-cvs
mailing list