From 4caa150e15c581cd8c88614a9cc6cc7113cf2199 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 14:52:02 -0700 Subject: [PATCH 01/19] s4: torture: Add regression test for re-opening a durable handle after calling SMB2 setinfo (end of file). This is an implementation of a test written by Apple for their client. Currently fails to reconnect due to btime being overwritten incorrectly in the SMB2 setinfo path. Add knownfail.d/durable-v2-setinfo BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 0036617a5c76e6003e3c9a5039c325d77d897709) --- selftest/knownfail.d/durable-v2-setinfo | 1 + source4/torture/smb2/durable_v2_open.c | 140 ++++++++++++++++++++++++ 2 files changed, 141 insertions(+) create mode 100644 selftest/knownfail.d/durable-v2-setinfo diff --git a/selftest/knownfail.d/durable-v2-setinfo b/selftest/knownfail.d/durable-v2-setinfo new file mode 100644 index 00000000000..e47580922fc --- /dev/null +++ b/selftest/knownfail.d/durable-v2-setinfo @@ -0,0 +1 @@ +^samba3.smb2.durable-v2-open.durable-v2-setinfo\(nt4_dc\) diff --git a/source4/torture/smb2/durable_v2_open.c b/source4/torture/smb2/durable_v2_open.c index 8efa2622444..9b9af11124c 100644 --- a/source4/torture/smb2/durable_v2_open.c +++ b/source4/torture/smb2/durable_v2_open.c @@ -2010,6 +2010,145 @@ bool test_persistent_open_lease(struct torture_context *tctx, return ret; } +/** + * setfileinfo test for doing a durable open + * create the file with lease and durable handle, + * write to it (via set end-of-file), tcp disconnect, + * reconnect, do a durable reopen - should succeed. + * + * BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 + */ +bool test_durable_v2_setinfo(struct torture_context *tctx, + struct smb2_tree *tree) +{ + NTSTATUS status; + TALLOC_CTX *mem_ctx = talloc_new(tctx); + char fname[256]; + struct smb2_handle _h; + struct smb2_handle *h = NULL; + struct smb2_create io; + union smb_setfileinfo si; + struct GUID create_guid = GUID_random(); + struct smb2_lease ls; + uint64_t lease_key; + bool ret = true; + struct smbcli_options options; + uint32_t caps; + + caps = smb2cli_conn_server_capabilities(tree->session->transport->conn); + if (!(caps & SMB2_CAP_LEASING)) { + torture_skip(tctx, "leases are not supported"); + } + + options = tree->session->transport->options; + + smb2_deltree(tree, __func__); + status = torture_smb2_testdir(tree, __func__, &_h); + torture_assert_ntstatus_ok_goto(tctx, status, ret, done, + "torture_smb2_testdir failed\n"); + smb2_util_close(tree, _h); + + /* Choose a random name in case the state is left a little funky. */ + snprintf(fname, 256, "%s\\durable_v2_setinfo%s.dat", + __func__, generate_random_str(tctx, 8)); + + smb2_util_unlink(tree, fname); + + lease_key = random(); + smb2_lease_v2_create(&io, &ls, false /* dir */, fname, + lease_key, 0, /* parent lease key */ + smb2_util_lease_state("RWH"), 0 /* lease epoch */); + io.in.durable_open = false; + io.in.durable_open_v2 = true; + io.in.persistent_open = false; + io.in.create_guid = create_guid; + io.in.timeout = UINT32_MAX; + + status = smb2_create(tree, mem_ctx, &io); + CHECK_STATUS(status, NT_STATUS_OK); + _h = io.out.file.handle; + h = &_h; + CHECK_CREATED(&io, CREATED, FILE_ATTRIBUTE_ARCHIVE); + CHECK_VAL(io.out.durable_open, false); + CHECK_VAL(io.out.durable_open_v2, true); + CHECK_VAL(io.out.persistent_open, false); + CHECK_VAL(io.out.timeout, 300*1000); + CHECK_VAL(io.out.oplock_level, SMB2_OPLOCK_LEVEL_LEASE); + CHECK_VAL(io.out.lease_response_v2.lease_key.data[0], lease_key); + CHECK_VAL(io.out.lease_response_v2.lease_key.data[1], ~lease_key); + + /* + * Set EOF to 0x100000. + * Mimics an Apple client test, but most importantly + * causes the mtime timestamp on disk to be updated. + */ + ZERO_STRUCT(si); + si.generic.level = SMB_SFILEINFO_END_OF_FILE_INFORMATION; + si.generic.in.file.handle = io.out.file.handle; + si.end_of_file_info.in.size = 0x100000; + status = smb2_setinfo_file(tree, &si); + CHECK_STATUS(status, NT_STATUS_OK); + + /* disconnect, reconnect and then do durable reopen */ + TALLOC_FREE(tree); + + if (!torture_smb2_connection_ext(tctx, 0, &options, &tree)) { + torture_warning(tctx, "couldn't reconnect, bailing\n"); + ret = false; + goto done; + } + + /* + * Now for a succeeding reconnect: + */ + + ZERO_STRUCT(io); + io.in.fname = fname; + io.in.durable_open_v2 = false; + io.in.durable_handle_v2 = h; + io.in.create_guid = create_guid; + io.in.lease_request_v2 = &ls; + io.in.oplock_level = SMB2_OPLOCK_LEVEL_LEASE; + + /* the requested lease state is irrelevant */ + ls.lease_state = smb2_util_lease_state(""); + + h = NULL; + + status = smb2_create(tree, mem_ctx, &io); + CHECK_STATUS(status, NT_STATUS_OK); + + CHECK_VAL(io.out.create_action, NTCREATEX_ACTION_EXISTED); + CHECK_VAL(io.out.size, 0x100000); \ + CHECK_VAL(io.out.durable_open, false); + CHECK_VAL(io.out.durable_open_v2, false); /* no dh2q response blob */ + CHECK_VAL(io.out.persistent_open, false); + CHECK_VAL(io.out.oplock_level, SMB2_OPLOCK_LEVEL_LEASE); + CHECK_VAL(io.out.lease_response_v2.lease_key.data[0], lease_key); + CHECK_VAL(io.out.lease_response_v2.lease_key.data[1], ~lease_key); + CHECK_VAL(io.out.lease_response_v2.lease_state, + smb2_util_lease_state("RWH")); + CHECK_VAL(io.out.lease_response_v2.lease_flags, 0); + CHECK_VAL(io.out.lease_response_v2.lease_duration, 0); + _h = io.out.file.handle; + h = &_h; + +done: + + if (h != NULL) { + smb2_util_close(tree, *h); + } + + smb2_util_unlink(tree, fname); + smb2_deltree(tree, __func__); + + talloc_free(tree); + + talloc_free(mem_ctx); + + return ret; +} + struct torture_suite *torture_smb2_durable_v2_open_init(TALLOC_CTX *ctx) { struct torture_suite *suite = @@ -2026,6 +2165,7 @@ struct torture_suite *torture_smb2_durable_v2_open_init(TALLOC_CTX *ctx) torture_suite_add_1smb2_test(suite, "reopen2c", test_durable_v2_open_reopen2c); torture_suite_add_1smb2_test(suite, "reopen2-lease", test_durable_v2_open_reopen2_lease); torture_suite_add_1smb2_test(suite, "reopen2-lease-v2", test_durable_v2_open_reopen2_lease_v2); + torture_suite_add_1smb2_test(suite, "durable-v2-setinfo", test_durable_v2_setinfo); torture_suite_add_2smb2_test(suite, "app-instance", test_durable_v2_open_app_instance); torture_suite_add_1smb2_test(suite, "persistent-open-oplock", test_persistent_open_oplock); torture_suite_add_1smb2_test(suite, "persistent-open-lease", test_persistent_open_lease); -- 2.32.0 From 49c795f34de5bea58dd24411b2326f6af700617f Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 11:40:04 -0700 Subject: [PATCH 02/19] s3: smbd: In set_ea_dos_attribute() cause root fallback code to exit via the same place. We're going to add another action on success next. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 9f62a149f12e899dbc2a7bac9458e7a375bf6608) --- source3/smbd/dosmode.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/source3/smbd/dosmode.c b/source3/smbd/dosmode.c index c0208ffa0a5..14737287860 100644 --- a/source3/smbd/dosmode.c +++ b/source3/smbd/dosmode.c @@ -521,7 +521,9 @@ NTSTATUS set_ea_dos_attribute(connection_struct *conn, status = NT_STATUS_OK; } unbecome_root(); - return status; + if (!NT_STATUS_IS_OK(status)) { + return status; + } } DEBUG(10,("set_ea_dos_attribute: set EA 0x%x on file %s\n", (unsigned int)dosmode, -- 2.32.0 From 0eeeb3a63d184cb1cfadcc8f31c7a319646c26c2 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 11:41:48 -0700 Subject: [PATCH 03/19] s3: smbd: In set_ea_dos_attribute(), if we've stored btime and set XATTR_DOSINFO_CREATE_TIME successfully, we need to clear ST_EX_IFLAG_CALCULATED_BTIME. This is no longer a calculated field, every call to fdos_mode() will set it as non-calculated. https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 2fc0820afcd375594b1d99edcd651420bea6ac91) --- source3/smbd/dosmode.c | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/source3/smbd/dosmode.c b/source3/smbd/dosmode.c index 14737287860..31e3da32edc 100644 --- a/source3/smbd/dosmode.c +++ b/source3/smbd/dosmode.c @@ -525,6 +525,17 @@ NTSTATUS set_ea_dos_attribute(connection_struct *conn, return status; } } + + /* + * We correctly stored the create time. + * We *always* set XATTR_DOSINFO_CREATE_TIME, + * so now it can no longer be considered + * calculated. + */ + update_stat_ex_create_time( + &smb_fname->fsp->fsp_name->st, + smb_fname->st.st_ex_btime); + DEBUG(10,("set_ea_dos_attribute: set EA 0x%x on file %s\n", (unsigned int)dosmode, smb_fname_str_dbg(smb_fname))); -- 2.32.0 From bdc2d93fdf9cf6b3459d86d8d659cc6d481dd836 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 11:51:00 -0700 Subject: [PATCH 04/19] s3: VFS: vxfs: All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit d460118be3ad2a3100bb3458f6f0223df12f7c3f) --- source3/modules/vfs_vxfs.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/source3/modules/vfs_vxfs.c b/source3/modules/vfs_vxfs.c index 75945cc476c..ddd34ba812a 100644 --- a/source3/modules/vfs_vxfs.c +++ b/source3/modules/vfs_vxfs.c @@ -407,6 +407,7 @@ static bool vxfs_compare(struct files_struct *fsp, TALLOC_CTX *mem_ctx = talloc_tos(); char *existing_buf = NULL, *new_buf = NULL, *compact_buf = NULL; int status; + NTSTATUS ntstatus; DEBUG(10, ("vfs_vxfs: Getting existing ACL for %s\n", fsp_str_dbg(fsp))); @@ -424,9 +425,10 @@ static bool vxfs_compare(struct files_struct *fsp, goto out; } - status = SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st); - if (status == -1) { + ntstatus = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(ntstatus)) { DEBUG(10, ("vfs_vxfs: stat failed!\n")); + errno = map_errno_from_nt_status(ntstatus); goto out; } -- 2.32.0 From 8017b95b67490a29e541ca8acd599bf12a4b0d43 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 11:56:53 -0700 Subject: [PATCH 05/19] s3: smbd: mdssvc: All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 2b246dbf687cbb6ef1e31e22fd64a95bdca8f4e9) --- source3/rpc_server/mdssvc/mdssvc.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/source3/rpc_server/mdssvc/mdssvc.c b/source3/rpc_server/mdssvc/mdssvc.c index fa31b55a183..956e097eaf4 100644 --- a/source3/rpc_server/mdssvc/mdssvc.c +++ b/source3/rpc_server/mdssvc/mdssvc.c @@ -1354,13 +1354,13 @@ static bool slrpc_fetch_attributes(struct mds_ctx *mds_ctx, return true; } - result = SMB_VFS_FSTAT(smb_fname->fsp, &smb_fname->st); - if (result != 0) { + status = vfs_stat_fsp(smb_fname->fsp); + if (!NT_STATUS_IS_OK(status)) { TALLOC_FREE(smb_fname); return true; } - sp = &smb_fname->st; + sp = &smb_fname->fsp->fsp_name->st; } ok = add_filemeta(mds_ctx, reqinfo, fm_array, path, sp); -- 2.32.0 From bd828fb064a9c584b432450167b9aadc0ed6e2bd Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:00:15 -0700 Subject: [PATCH 06/19] s3: smbd: open_internal_dirfsp() add missing file_free() in error path. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit ec2fb9d22842332992b8f667a8218f7aaa1be7c4) --- source3/smbd/files.c | 1 + 1 file changed, 1 insertion(+) diff --git a/source3/smbd/files.c b/source3/smbd/files.c index 677b600d0a6..a1788c2b822 100644 --- a/source3/smbd/files.c +++ b/source3/smbd/files.c @@ -266,6 +266,7 @@ NTSTATUS open_internal_dirfsp(connection_struct *conn, ret = SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st); if (ret != 0) { + file_free(NULL, fsp); return map_nt_error_from_unix(errno); } -- 2.32.0 From c02d0708311df88c35e05b4a3037550e5e8b0be3 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:02:35 -0700 Subject: [PATCH 07/19] s3: smbd: open_internal_dirfsp(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit a604dd02ffb468ba472ac4dd64f06d30ecdcc810) --- source3/smbd/files.c | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-) diff --git a/source3/smbd/files.c b/source3/smbd/files.c index a1788c2b822..704d3d84316 100644 --- a/source3/smbd/files.c +++ b/source3/smbd/files.c @@ -245,7 +245,6 @@ NTSTATUS open_internal_dirfsp(connection_struct *conn, { struct files_struct *fsp = NULL; NTSTATUS status; - int ret; status = create_internal_dirfsp(conn, smb_dname, &fsp); if (!NT_STATUS_IS_OK(status)) { @@ -264,10 +263,10 @@ NTSTATUS open_internal_dirfsp(connection_struct *conn, return status; } - ret = SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st); - if (ret != 0) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { file_free(NULL, fsp); - return map_nt_error_from_unix(errno); + return status; } if (!S_ISDIR(fsp->fsp_name->st.st_ex_mode)) { -- 2.32.0 From e873c4a78c0c901e321cd7ecf97e8119bb80ac9a Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:09:43 -0700 Subject: [PATCH 08/19] s3: smbd: non_widelink_open(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 18694c81cc3c3d94dc99e3b11878021052279eb6) --- source3/smbd/open.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/source3/smbd/open.c b/source3/smbd/open.c index 5a3ac2c064a..a17ce956198 100644 --- a/source3/smbd/open.c +++ b/source3/smbd/open.c @@ -779,9 +779,8 @@ static NTSTATUS non_widelink_open(const struct files_struct *dirfsp, fsp_set_fd(fsp, fd); if (fd != -1) { - ret = SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st); - if (ret != 0) { - status = map_nt_error_from_unix(errno); + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { goto out; } orig_fsp_name->st = fsp->fsp_name->st; -- 2.32.0 From c192b8bcf84dbd6756eed881e7ddf0957d351f99 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:11:23 -0700 Subject: [PATCH 09/19] s3: smbd: open_file(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit cfadecca802600fa9a01fa9781e4df9a0b71fa3c) --- source3/smbd/open.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/source3/smbd/open.c b/source3/smbd/open.c index a17ce956198..39af2b1fd3e 100644 --- a/source3/smbd/open.c +++ b/source3/smbd/open.c @@ -1498,12 +1498,11 @@ static NTSTATUS open_file(files_struct *fsp, } if (need_re_stat) { - ret = SMB_VFS_FSTAT(fsp, &smb_fname->st); + status = vfs_stat_fsp(fsp); /* * If we have an fd, this stat should succeed. */ - if (ret == -1) { - status = map_nt_error_from_unix(errno); + if (!NT_STATUS_IS_OK(status)) { DBG_ERR("Error doing fstat on open " "file %s (%s)\n", smb_fname_str_dbg(smb_fname), -- 2.32.0 From ae9bf260e16c6fa7fd813700072d7ea945369e01 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:19:44 -0700 Subject: [PATCH 10/19] s3: smbd: mkdir_internal(). 1 of 2. All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 064c5770deb4307272c60f0b08f6bc137df4b227) --- source3/smbd/open.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/source3/smbd/open.c b/source3/smbd/open.c index 39af2b1fd3e..31689d3853d 100644 --- a/source3/smbd/open.c +++ b/source3/smbd/open.c @@ -4302,10 +4302,11 @@ static NTSTATUS mkdir_internal(connection_struct *conn, /* Ensure we're checking for a symlink here.... */ /* We don't want to get caught by a symlink racer. */ - if (SMB_VFS_FSTAT(fsp, &smb_dname->st) == -1) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { DEBUG(2, ("Could not stat directory '%s' just created: %s\n", - smb_fname_str_dbg(smb_dname), strerror(errno))); - return map_nt_error_from_unix(errno); + smb_fname_str_dbg(smb_dname), nt_errstr(status))); + return status; } if (!S_ISDIR(smb_dname->st.st_ex_mode)) { -- 2.32.0 From a6b184b893139b412b84bac227765dfd927c8749 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:22:26 -0700 Subject: [PATCH 11/19] s3: smbd: mkdir_internal(). 2 of 2. All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 7f5c484804c87f37493e1f79d5c7e1738a4e0113) --- source3/smbd/open.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/source3/smbd/open.c b/source3/smbd/open.c index 31689d3853d..32df203e5ae 100644 --- a/source3/smbd/open.c +++ b/source3/smbd/open.c @@ -4363,10 +4363,11 @@ static NTSTATUS mkdir_internal(connection_struct *conn, } if (need_re_stat) { - if (SMB_VFS_FSTAT(fsp, &smb_dname->st) == -1) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { DEBUG(2, ("Could not stat directory '%s' just created: %s\n", - smb_fname_str_dbg(smb_dname), strerror(errno))); - return map_nt_error_from_unix(errno); + smb_fname_str_dbg(smb_dname), nt_errstr(status))); + return status; } } -- 2.32.0 From d3e8e4371286783ba3d53cccd666974c2a2fa872 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:24:27 -0700 Subject: [PATCH 12/19] s3: smbd: rename_internals_fsp(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit b53a69f4ffcaa5ec9b8660152802f5a7b2effc1f) --- source3/smbd/reply.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/source3/smbd/reply.c b/source3/smbd/reply.c index 50730baecc7..9b6ebb029fa 100644 --- a/source3/smbd/reply.c +++ b/source3/smbd/reply.c @@ -7497,8 +7497,8 @@ NTSTATUS rename_internals_fsp(connection_struct *conn, * We must set the archive bit on the newly renamed * file. */ - ret = SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st); - if (ret == 0) { + status = vfs_stat_fsp(fsp); + if (NT_STATUS_IS_OK(status)) { uint32_t old_dosmode; old_dosmode = fdos_mode(fsp); /* -- 2.32.0 From def2c4a2fb681ae0fa2f1dfe9c3a1e97e24a7539 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:26:27 -0700 Subject: [PATCH 13/19] s3: smbd: call_trans2qfilepathinfo(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 8d3812daa5b0c9eb534515d37498d0d6e1a40ec8) --- source3/smbd/trans2.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/source3/smbd/trans2.c b/source3/smbd/trans2.c index 7e075ce21c0..e79f78a5412 100644 --- a/source3/smbd/trans2.c +++ b/source3/smbd/trans2.c @@ -6031,11 +6031,11 @@ static void call_trans2qfilepathinfo(connection_struct *conn, /* * Original code - this is an open file. */ - if (SMB_VFS_FSTAT(fsp, &smb_fname->st) != 0) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { DEBUG(3, ("fstat of %s failed (%s)\n", - fsp_fnum_dbg(fsp), strerror(errno))); - reply_nterror(req, - map_nt_error_from_unix(errno)); + fsp_fnum_dbg(fsp), nt_errstr(status))); + reply_nterror(req, status); return; } if (lp_smbd_getinfo_ask_sharemode(SNUM(conn))) { -- 2.32.0 From 6705f3093d2b6fa5869805d21a1c199a4fe938d5 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:27:53 -0700 Subject: [PATCH 14/19] s3: smbd: call_trans2setfilepathinfo(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 6a25b6997ff9f99fde309db1e163d16cd70ca5f5) --- source3/smbd/trans2.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/source3/smbd/trans2.c b/source3/smbd/trans2.c index e79f78a5412..272136a4716 100644 --- a/source3/smbd/trans2.c +++ b/source3/smbd/trans2.c @@ -9333,11 +9333,12 @@ static void call_trans2setfilepathinfo(connection_struct *conn, /* * Original code - this is an open file. */ - if (SMB_VFS_FSTAT(fsp, &smb_fname->st) != 0) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { DEBUG(3,("call_trans2setfilepathinfo: fstat " "of %s failed (%s)\n", fsp_fnum_dbg(fsp), - strerror(errno))); - reply_nterror(req, map_nt_error_from_unix(errno)); + nt_errstr(status))); + reply_nterror(req, status); return; } } -- 2.32.0 From 5b4b7ac054b2ee5f1ce29a26d0d7794231d0a0f6 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 14:57:13 -0700 Subject: [PATCH 15/19] s3: pysmbd.c: init_files_struct(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit c4193f11d1871051d4cce4521b1f444a083c9189) --- source3/smbd/pysmbd.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/source3/smbd/pysmbd.c b/source3/smbd/pysmbd.c index 17a27e8cb35..92c4037b493 100644 --- a/source3/smbd/pysmbd.c +++ b/source3/smbd/pysmbd.c @@ -176,7 +176,6 @@ static NTSTATUS init_files_struct(TALLOC_CTX *mem_ctx, { struct smb_filename *smb_fname = NULL; int fd; - int ret; mode_t saved_umask; struct files_struct *fsp; struct files_struct *fspcwd = NULL; @@ -230,13 +229,13 @@ static NTSTATUS init_files_struct(TALLOC_CTX *mem_ctx, } fsp_set_fd(fsp, fd); - ret = SMB_VFS_FSTAT(fsp, &smb_fname->st); - if (ret == -1) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { /* If we have an fd, this stat should succeed. */ DEBUG(0,("Error doing fstat on open file %s (%s)\n", smb_fname_str_dbg(smb_fname), - strerror(errno) )); - return map_nt_error_from_unix(errno); + nt_errstr(status) )); + return status; } fsp->file_id = vfs_file_id_from_sbuf(conn, &smb_fname->st); -- 2.32.0 From dbac141f3775ff204d2f184333be205fb20b1965 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 15:01:52 -0700 Subject: [PATCH 16/19] s3: cmd_vfs: cmd_open(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit fbc6cdfbeda4086851dfb0f91fd23b4fd541e174) --- source3/torture/cmd_vfs.c | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/source3/torture/cmd_vfs.c b/source3/torture/cmd_vfs.c index 4be5719e94e..1499bd0046f 100644 --- a/source3/torture/cmd_vfs.c +++ b/source3/torture/cmd_vfs.c @@ -297,7 +297,6 @@ static NTSTATUS cmd_open(struct vfs_state *vfs, TALLOC_CTX *mem_ctx, int argc, c struct files_struct *fspcwd = NULL; struct smb_filename *smb_fname = NULL; NTSTATUS status; - int ret; int fd; mode = 00400; @@ -414,15 +413,13 @@ static NTSTATUS cmd_open(struct vfs_state *vfs, TALLOC_CTX *mem_ctx, int argc, c } fsp_set_fd(fsp, fd); - status = NT_STATUS_OK; - ret = SMB_VFS_FSTAT(fsp, &smb_fname->st); - if (ret == -1) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { /* If we have an fd, this stat should succeed. */ DEBUG(0,("Error doing fstat on open file %s " "(%s)\n", smb_fname_str_dbg(smb_fname), - strerror(errno) )); - status = map_nt_error_from_unix(errno); + nt_errstr(status) )); } else if (S_ISDIR(smb_fname->st.st_ex_mode)) { errno = EISDIR; status = NT_STATUS_FILE_IS_A_DIRECTORY; -- 2.32.0 From 3ec8414526f2b0cad270d00f7abab1ac062909bc Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 15:04:34 -0700 Subject: [PATCH 17/19] s3: cmd_vfs: cmd_set_nt_acl(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 23d5c909286d438534f1a7defb2faacd1877fea1) --- source3/torture/cmd_vfs.c | 12 +++--------- 1 file changed, 3 insertions(+), 9 deletions(-) diff --git a/source3/torture/cmd_vfs.c b/source3/torture/cmd_vfs.c index 1499bd0046f..b8d8b8d3acd 100644 --- a/source3/torture/cmd_vfs.c +++ b/source3/torture/cmd_vfs.c @@ -1702,7 +1702,6 @@ static NTSTATUS cmd_fset_nt_acl(struct vfs_state *vfs, TALLOC_CTX *mem_ctx, static NTSTATUS cmd_set_nt_acl(struct vfs_state *vfs, TALLOC_CTX *mem_ctx, int argc, const char **argv) { int flags; - int ret; mode_t mode; files_struct *fsp; struct files_struct *fspcwd = NULL; @@ -1773,18 +1772,13 @@ static NTSTATUS cmd_set_nt_acl(struct vfs_state *vfs, TALLOC_CTX *mem_ctx, int a } fsp_set_fd(fsp, fd); - status = NT_STATUS_OK; - ret = SMB_VFS_FSTAT(fsp, &smb_fname->st); - if (ret == -1) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { /* If we have an fd, this stat should succeed. */ DEBUG(0,("Error doing fstat on open file %s " "(%s)\n", smb_fname_str_dbg(smb_fname), - strerror(errno) )); - status = map_nt_error_from_unix(errno); - } - - if (!NT_STATUS_IS_OK(status)) { + nt_errstr(status) )); goto out; } -- 2.32.0 From d62739a0226f914ccb8ecddbf8b90a42755028f1 Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 11:45:50 -0700 Subject: [PATCH 18/19] s3: smbd: smbd_smb2_getinfo_send(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme (cherry picked from commit 7fb2038faca256c03c2bd7d982f39f5b1a57f784) --- source3/smbd/smb2_getinfo.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/source3/smbd/smb2_getinfo.c b/source3/smbd/smb2_getinfo.c index a918cc03385..0320dcc5fde 100644 --- a/source3/smbd/smb2_getinfo.c +++ b/source3/smbd/smb2_getinfo.c @@ -362,11 +362,11 @@ static struct tevent_req *smbd_smb2_getinfo_send(TALLOC_CTX *mem_ctx, * Original code - this is an open file. */ - if (SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) != 0) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { DEBUG(3, ("smbd_smb2_getinfo_send: " "fstat of %s failed (%s)\n", - fsp_fnum_dbg(fsp), strerror(errno))); - status = map_nt_error_from_unix(errno); + fsp_fnum_dbg(fsp), nt_errstr(status))); tevent_req_nterror(req, status); return tevent_req_post(req, ev); } -- 2.32.0 From 1d22835fdc54cbc5863a320070fbf6222249c1df Mon Sep 17 00:00:00 2001 From: Jeremy Allison Date: Fri, 18 Mar 2022 12:30:27 -0700 Subject: [PATCH 19/19] s3: smbd: smbd_smb2_setinfo_send(). All calls to SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) clobber fsp->fsp_name->st.st_ex_iflags. If doing an SMB_VFS_FSTAT() returning onto the stat struct stored in the fsp, we must call vfs_stat_fsp() as this preserves the iflags. This is the last SMB_VFS_FSTAT that uses fsp->fsp_name->st, so remove knownfail.d/durable-v2-setinfo BUG: https://bugzilla.samba.org/show_bug.cgi?id=15022 Signed-off-by: Jeremy Allison Reviewed-by: Ralph Boehme Autobuild-User(master): Jeremy Allison Autobuild-Date(master): Thu Mar 24 17:21:29 UTC 2022 on sn-devel-184 (cherry picked from commit c4f9c372405bea8a7d9c6b39e04cebefa3322a19) --- selftest/knownfail.d/durable-v2-setinfo | 1 - source3/smbd/smb2_setinfo.c | 6 +++--- 2 files changed, 3 insertions(+), 4 deletions(-) delete mode 100644 selftest/knownfail.d/durable-v2-setinfo diff --git a/selftest/knownfail.d/durable-v2-setinfo b/selftest/knownfail.d/durable-v2-setinfo deleted file mode 100644 index e47580922fc..00000000000 --- a/selftest/knownfail.d/durable-v2-setinfo +++ /dev/null @@ -1 +0,0 @@ -^samba3.smb2.durable-v2-open.durable-v2-setinfo\(nt4_dc\) diff --git a/source3/smbd/smb2_setinfo.c b/source3/smbd/smb2_setinfo.c index e490596a2e0..d3c3ba63d6b 100644 --- a/source3/smbd/smb2_setinfo.c +++ b/source3/smbd/smb2_setinfo.c @@ -458,12 +458,12 @@ static struct tevent_req *smbd_smb2_setinfo_send(TALLOC_CTX *mem_ctx, * Original code - this is an open file. */ - if (SMB_VFS_FSTAT(fsp, &fsp->fsp_name->st) != 0) { + status = vfs_stat_fsp(fsp); + if (!NT_STATUS_IS_OK(status)) { DEBUG(3,("smbd_smb2_setinfo_send: fstat " "of %s failed (%s)\n", fsp_fnum_dbg(fsp), - strerror(errno))); - status = map_nt_error_from_unix(errno); + nt_errstr(status))); tevent_req_nterror(req, status); return tevent_req_post(req, ev); } -- 2.32.0