summaryrefslogtreecommitdiff
path: root/source3
diff options
context:
space:
mode:
authorStefan Metzmacher <metze@samba.org>2020-12-16 14:15:11 +0100
committerStefan Metzmacher <metze@samba.org>2021-01-14 11:30:38 +0000
commit1ab038b77a89a7960fbd4cdb55565af6b2333574 (patch)
tree791cba2590c11efcca1ff2e011e1749a4344c0aa /source3
parent932c27e290ead0c2a98c57f2a9649aaf51d7233b (diff)
downloadsamba-1ab038b77a89a7960fbd4cdb55565af6b2333574.tar.gz
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@samba.org> Reviewed-by: Volker Lendecke <vl@samba.org> Reviewed-by: Ralph Boehme <slow@samba.org>
Diffstat (limited to 'source3')
-rw-r--r--source3/smbd/files.c41
-rw-r--r--source3/smbd/open.c1
2 files changed, 31 insertions, 11 deletions
diff --git a/source3/smbd/files.c b/source3/smbd/files.c
index 2076d13a4df..446cbec5251 100644
--- a/source3/smbd/files.c
+++ b/source3/smbd/files.c
@@ -1235,7 +1235,10 @@ NTSTATUS file_name_hash(connection_struct *conn,
NTSTATUS fsp_set_smb_fname(struct files_struct *fsp,
const struct smb_filename *smb_fname_in)
{
- struct smb_filename *smb_fname_new;
+ struct smb_filename *smb_fname_old = fsp->fsp_name;
+ struct smb_filename *smb_fname_new = NULL;
+ const char *name_str = NULL;
+ uint32_t name_hash = 0;
NTSTATUS status;
smb_fname_new = cp_smb_filename(fsp, smb_fname_in);
@@ -1243,19 +1246,37 @@ NTSTATUS fsp_set_smb_fname(struct files_struct *fsp,
return NT_STATUS_NO_MEMORY;
}
- if (fsp->fsp_name != NULL) {
- status = move_smb_fname_fsp_link(smb_fname_new, fsp->fsp_name);
- if (!NT_STATUS_IS_OK(status)) {
- return status;
- }
- TALLOC_FREE(fsp->fsp_name);
+ name_str = smb_fname_str_dbg(smb_fname_new);
+ if (name_str == NULL) {
+ TALLOC_FREE(smb_fname_new);
+ return NT_STATUS_NO_MEMORY;
+ }
+
+ status = file_name_hash(fsp->conn,
+ name_str,
+ &name_hash);
+ if (!NT_STATUS_IS_OK(status)) {
+ TALLOC_FREE(smb_fname_new);
+ return status;
}
+ status = fsp_smb_fname_link(fsp,
+ &smb_fname_new->fsp_link,
+ &smb_fname_new->fsp);
+ if (!NT_STATUS_IS_OK(status)) {
+ TALLOC_FREE(smb_fname_new);
+ return status;
+ }
+
+ fsp->name_hash = name_hash;
fsp->fsp_name = smb_fname_new;
- return file_name_hash(fsp->conn,
- smb_fname_str_dbg(fsp->fsp_name),
- &fsp->name_hash);
+ if (smb_fname_old != NULL) {
+ smb_fname_fsp_unlink(smb_fname_old);
+ TALLOC_FREE(smb_fname_old);
+ }
+
+ return NT_STATUS_OK;
}
size_t fsp_fullbasepath(struct files_struct *fsp, char *buf, size_t buflen)
diff --git a/source3/smbd/open.c b/source3/smbd/open.c
index 20f39ee2414..956230fdc4b 100644
--- a/source3/smbd/open.c
+++ b/source3/smbd/open.c
@@ -5831,7 +5831,6 @@ static NTSTATUS create_file_unixpath(connection_struct *conn,
if (!NT_STATUS_IS_OK(status)) {
goto fail;
}
- fsp->fsp_name->fsp = fsp;
}
if (base_fsp) {