[SCM] Samba Shared Repository - branch v4-14-test updated
Karolin Seeger
kseeger at samba.org
Tue Aug 17 10:08:01 UTC 2021
The branch, v4-14-test has been updated
via 3228383d8ae vfs_shadow_copy2: ensure we call convert_sbuf() in shadow_copy2_*stat() on already converted paths with absolute path
via 8222ff1110c vfs_streams_xattr: ensure fstat calls NEXT fstat
via 262d09c511a selftest: add a test for shadow:fixinodes
via 9d6d585ca00 selftest: simplify snapshot directory creation in test_shadow_copy_torture.sh
via 5ae4300a36b selftest: enable "shadow:fixinodes" in "shadow_write" share
via a2ac4ee3d71 selftest: pass smbclient arg to samba3.blackbox.shadow_copy_torture test
via 93383852f0d smbd: update smb_fname statinfo from fsp
via e12c92d0175 smbd: canonicalize SMB_VFS_FSTAT() stat buffer
via 46995a8b146 smbd: return correct timestamps for quota fake file
via b53968656ee smbd: handle fake file handles in fdos_mode()
via 7e1d4a4b138 smbd: add dosmode_from_fake_filehandle()
via 8abd1abca64 smbtorture: verify attributes on fake quota file handle
from 618fd6c2594 s3: smbd: For FSCTL calls that go async, add the outstanding tevent_reqs to the aio list on the file handle.
https://git.samba.org/?p=samba.git;a=shortlog;h=v4-14-test
- Log -----------------------------------------------------------------
commit 3228383d8ae56d53dd8d726eec8e81353b988624
Author: Ralph Boehme <slow at samba.org>
Date: Sat Jul 3 15:46:11 2021 +0200
vfs_shadow_copy2: ensure we call convert_sbuf() in shadow_copy2_*stat() on already converted paths with absolute path
shadow_copy2_strip_snapshot() will happily return without modifying the passed
timestamp=0 if the path is already converted and refers to an object in a
snapshot, eg (first debug line from extra debugging patch [1]):
[10 2021/07/02 08:19:28.811424 pid=738290 ../../source3/modules/vfs_shadow_copy2.c:1303 shadow_copy2_fstat]
shadow_copy2_fstat: fsp [test.txt {@GMT-2000.01.02-03.04.05}]
[10 2021/07/02 08:19:28.811449 pid=738290 ../../source3/modules/vfs_shadow_copy2.c:607 _shadow_copy2_strip_snapshot_internal]
_shadow_copy2_strip_snapshot_internal: [from shadow_copy2_fstat()] Path 'test.txt {@GMT-2000.01.02-03.04.05}'
[10 2021/07/02 08:19:28.811474 pid=738290 ../../source3/modules/vfs_shadow_copy2.c:619 _shadow_copy2_strip_snapshot_internal]
_shadow_copy2_strip_snapshot_internal: abs path '/gpfs0/smb_snapshots2/filesetone/.snapshots/@GMT-2000.01.02-03.04.05/test.txt'
[10 2021/07/02 08:19:28.811496 pid=738290 ../../source3/modules/vfs_shadow_copy2.c:1924 shadow_copy2_snapshot_to_gmt]
shadow_copy2_snapshot_to_gmt: match @GMT-%Y.%m.%d-%H.%M.%S: @GMT-2000.01.02-03.04.05
[10 2021/07/02 08:19:28.811536 pid=738290 ../../source3/modules/vfs_shadow_copy2.c:566 check_for_converted_path]
check_for_converted_path: path |/gpfs0/smb_snapshots2/filesetone/.snapshots/@GMT-2000.01.02-03.04.05/test.txt| is already converted. connect path = |/gpfs0/smb_snapshots2/filesetone/.snapshots/@GMT-2000.01.02-03.04.05|
As check_for_converted_path() detects an "already converted path",
_shadow_copy2_strip_snapshot_internal() just returns without modifying the value
of the timestamp.
By using shadow_copy2_strip_snapshot_converted() instead of
shadow_copy2_strip_snapshot() we can check if the path is in fact referring to a
VSS object by checking the "converted" bool.
An alternative way would have been directly checking fsp->fsp_name->twrp != 0,
but that would be a new semantic in the module, I'll leave this excersize for
the future when we clean up the usage of shadow_copy2_strip_snapshot() in the
whole module.
This change also switches to using the absolute paths in both place where
convert_sbuf() is called.
[1]
@@ -1309,8 +1348,16 @@ static int shadow_copy2_fstat(vfs_handle_struct *handle, files_struct *fsp,
saved_errno = errno;
}
+ DBG_DEBUG("fsp [%s]\n", fsp_str_dbg(fsp));
RN: vfs_shadow_copy2 fixinodes not correctly updating inode numbers
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit c7d6745858f2efdd24ed6fd353ec5ece898033fa)
Autobuild-User(v4-14-test): Karolin Seeger <kseeger at samba.org>
Autobuild-Date(v4-14-test): Tue Aug 17 10:07:42 UTC 2021 on sn-devel-184
commit 8222ff1110c3ff506e3153b3294f2979206cdbfd
Author: Ralph Boehme <slow at samba.org>
Date: Wed Jul 28 17:16:27 2021 +0200
vfs_streams_xattr: ensure fstat calls NEXT fstat
This ensures fstat behaves the same as stat by calling the NEXT VFS stat
function. This is required for matching path and handle based inode
numbers.
This bug is currently only exposed in a special case: a VSS snapshot of a
stream.
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
commit 262d09c511a66562f397af099cfdef588813d1ab
Author: Ralph Boehme <slow at samba.org>
Date: Tue Jul 6 07:24:00 2021 +0200
selftest: add a test for shadow:fixinodes
This will fail with
Failed to open file \@GMT-2015.10.31-19.40.30\subdir\hardlink. NT_STATUS_ACCESS_DENIED
The open is failing in openat_pathref_fsp():
[2021/07/06 04:58:17.677104, 10, pid=95070, effective(1000, 1000), real(1000, 0)] ../../source3/smbd/files.c:541(openat_pathref_fsp)
openat_pathref_fsp: file [subdir/hardlink {@GMT-2015.10.31-19.40.30}] - dev/ino mismatch. Old (dev=64770, ino=3826943444). New (dev=64770, ino=1746568660).
[2021/07/06 04:58:17.677114, 10, pid=95070, effective(1000, 1000), real(1000, 0)] ../../source3/smbd/files.c:568(openat_pathref_fsp)
openat_pathref_fsp: Opening pathref for [subdir/hardlink {@GMT-2015.10.31-19.40.30}] failed: NT_STATUS_ACCESS_DENIED
The reason is subtle:
shadow_copy2 calculates inode numbers of snapshot files based on the path of the
file. The result of that when doing a path based stat() from filename_convert()
was
[2021/07/06 04:58:17.676159, 10, pid=95070, effective(1000, 1000), real(1000, 0)] ../../source3/smbd/filename.c:1945(filename_convert_internal)
filename_convert_internal: XXX smb_fname [subdir/hardlink {@GMT-2015.10.31-19.40.30}] (dev=64770, ino=3826943444).
which is the "Old" inode shown above.
Later in the open code called from openat_pathref_fsp() -> fd_openat() ->
non_widelink_open() since 4.14 we call SMB_VFS_FSTAT() where fsp->fsp_name will
be set to the new relative *basename* of the file:
[2021/07/06 04:58:17.676917, 10, pid=95070, effective(1000, 1000), real(1000, 0), class=vfs] ../../source3/modules/vfs_default.c:1302(vfswrap_fstat)
vfswrap_fstat: XXX fsp [hardlink {@GMT-2015.10.31-19.40.30}] (dev=64770, ino=3826943444)
So for stat() the hash function in called with the full path relative to the share
root:
subdir/hardlink
while for fstat() the hash function will used
hardlink
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit 4a7e483c516cf2b9767919a764f05c43f4620cd7)
commit 9d6d585ca00f7d001932fab8fc16b6a72ec3ec89
Author: Ralph Boehme <slow at samba.org>
Date: Tue Jul 6 07:22:40 2021 +0200
selftest: simplify snapshot directory creation in test_shadow_copy_torture.sh
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit 3aabc9825ca108641c2becf322fa0bd90ea18424)
commit 5ae4300a36b63de302af174a8fc6bd29dbecac82
Author: Ralph Boehme <slow at samba.org>
Date: Tue Jul 6 07:20:15 2021 +0200
selftest: enable "shadow:fixinodes" in "shadow_write" share
The existing tests don't care and this will be used in a subsequent commit to
demonstrate that this option is currently broken.
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit 0a0b438b8ab534eeb552a58ad72a714988e84d89)
commit a2ac4ee3d71480b3fc15b6a2e6308bb467b14e6b
Author: Ralph Boehme <slow at samba.org>
Date: Tue Jul 6 07:19:36 2021 +0200
selftest: pass smbclient arg to samba3.blackbox.shadow_copy_torture test
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit 745ded9afe12fda6d45638097a32b01122748649)
commit 93383852f0dec537e2f9b062f113c6f5747a80b9
Author: Ralph Boehme <slow at samba.org>
Date: Wed Jul 7 12:40:05 2021 +0200
smbd: update smb_fname statinfo from fsp
fd_openat() has done an FSTAT on the handle so update the smb_fname stat info
with "truth". from the handle.
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit b32e56d6eb29bfb5f368602edbc10d4b8bc9b4f0)
commit e12c92d0175ea8a0057e9bc6b01ad65ce9153d84
Author: Ralph Boehme <slow at samba.org>
Date: Tue Jul 6 09:04:26 2021 +0200
smbd: canonicalize SMB_VFS_FSTAT() stat buffer
This helps code inside any module implementing fstat() looking at
fsp->fsp_name->st instead of the passed in stat buf.
I only ran afoul of this in a DEBUG message I added while debugging some inode
related problem.
No change in behaviour.
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14756
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit 18a30d939e6f7d49300f235385953412f9e971b9)
commit 46995a8b14675f30536a65ceeaf687fa7cbedd9e
Author: Ralph Boehme <slow at samba.org>
Date: Mon Jun 7 19:02:56 2021 +0200
smbd: return correct timestamps for quota fake file
Prior to 572d4e3a56eef00e29f93482daa21647af7310d0 it was sufficient to
initialize struct timespec to zero to return NTTIME 0 (ie not set) over
SMB.
This fixes the same problem from bug 14714 where the timestamps in an SMB2 CLOSE
response.
Windows of course does return *some* timestamps, but as it's neither documented
nor was I able to figure out where they would be coming from, as well as the
Windows client apparently doesn't care, I didn't bother with implementing some
sophisticated heuristic to return some timestamps.
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14731
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
Autobuild-User(master): Jeremy Allison <jra at samba.org>
Autobuild-Date(master): Wed Jun 9 20:38:02 UTC 2021 on sn-devel-184
(cherry picked from commit 52a421111218d94d2e5cb131648bcdf5411d910b)
commit b53968656eee6c57e281ee32bff1d4643b4292f0
Author: Ralph Boehme <slow at samba.org>
Date: Fri Jun 4 15:54:20 2021 +0200
smbd: handle fake file handles in fdos_mode()
This ensures SMB requests on the quote fake file "$Extend/$Quota" don't hit the
VFS, where specifically in vfs_gpfs we log an error message if we fail to read
the DOS attributes for a file with
vfs_gpfs_get_dos_attributes: Getting winattrs failed for $Extend/$Quota
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14731
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit e093eaed1046638193d973c39fa9df74e41148d3)
commit 7e1d4a4b1385b9bc75ce61531c8df77584bb9ead
Author: Ralph Boehme <slow at samba.org>
Date: Fri Jun 4 16:31:20 2021 +0200
smbd: add dosmode_from_fake_filehandle()
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14731
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit 51b0fd0c566ff6bf112ab9752d9b105a6bb786a8)
commit 8abd1abca64bd9034482498484310692a411b9dd
Author: Ralph Boehme <slow at samba.org>
Date: Mon Jun 7 19:03:05 2021 +0200
smbtorture: verify attributes on fake quota file handle
The expected DOS attributes are taken from a Windows 2016 server. The expected
timestamps are what Samba has returned before commit 572d4e3a56eef00e29f9348:
NTTIME(0), ie no value.
The upcoming fix will restore this behaviour. Windows of course does
return *some* timestamps, but as it's neither documented nor was I able to
figure out where they would be coming from, as well as the Windows client apparently
doesn't care, I didn't bother with implementing some sophisticated heuristic to
return some timestamps.
BUG: https://bugzilla.samba.org/show_bug.cgi?id=14731
Signed-off-by: Ralph Boehme <slow at samba.org>
Reviewed-by: Jeremy Allison <jra at samba.org>
(cherry picked from commit 1e338d51602a7dca6108e5e8704f5cdde4740713)
-----------------------------------------------------------------------
Summary of changes:
selftest/knownfail | 1 +
selftest/target/Samba3.pm | 1 +
source3/include/fake_file.h | 1 +
source3/modules/vfs_shadow_copy2.c | 180 +++++++++++++++++------
source3/modules/vfs_streams_xattr.c | 27 +---
source3/script/tests/test_shadow_copy_torture.sh | 32 +++-
source3/selftest/tests.py | 2 +-
source3/smbd/dosmode.c | 5 +
source3/smbd/fake_file.c | 15 ++
source3/smbd/filename.c | 5 +
source3/smbd/files.c | 7 +
source3/smbd/open.c | 4 +-
source4/torture/smb2/create.c | 63 ++++++++
13 files changed, 275 insertions(+), 68 deletions(-)
Changeset truncated at 500 lines:
diff --git a/selftest/knownfail b/selftest/knownfail
index 6c005d1f4de..ea72ea27620 100644
--- a/selftest/knownfail
+++ b/selftest/knownfail
@@ -144,6 +144,7 @@
^samba4.raw.acls.*.create_owner_file
^samba4.smb2.create.*.acldir
^samba4.smb2.create.*.impersonation
+^samba4.smb2.create.quota-fake-file\(ad_dc_ntvfs\) # not supported by the NTVFS
^samba4.smb2.acls.*.generic
^samba4.smb2.acls.*.inheritflags
^samba4.smb2.acls.*.owner
diff --git a/selftest/target/Samba3.pm b/selftest/target/Samba3.pm
index b0910433940..4afcc47b82b 100755
--- a/selftest/target/Samba3.pm
+++ b/selftest/target/Samba3.pm
@@ -2810,6 +2810,7 @@ sub provision($$)
aio write size = 0
error_inject:pwrite = EBADF
shadow:mountpoint = $shadow_tstdir
+ shadow:fixinodes = yes
[dfq]
path = $shrdir/dfree
diff --git a/source3/include/fake_file.h b/source3/include/fake_file.h
index 00ebc88f7a7..c267df25188 100644
--- a/source3/include/fake_file.h
+++ b/source3/include/fake_file.h
@@ -47,5 +47,6 @@ NTSTATUS open_fake_file(struct smb_request *req, connection_struct *conn,
uint32_t access_mask,
files_struct **result);
NTSTATUS close_fake_file(struct smb_request *req, files_struct *fsp);
+uint32_t dosmode_from_fake_filehandle(const struct fake_file_handle *ffh);
#endif /* _FAKE_FILE_H */
diff --git a/source3/modules/vfs_shadow_copy2.c b/source3/modules/vfs_shadow_copy2.c
index 227ac148260..e340382ff3c 100644
--- a/source3/modules/vfs_shadow_copy2.c
+++ b/source3/modules/vfs_shadow_copy2.c
@@ -1168,19 +1168,45 @@ static int shadow_copy2_linkat(vfs_handle_struct *handle,
static int shadow_copy2_stat(vfs_handle_struct *handle,
struct smb_filename *smb_fname)
{
+ struct shadow_copy2_private *priv = NULL;
time_t timestamp = 0;
char *stripped = NULL;
+ bool converted = false;
+ char *abspath = NULL;
char *tmp;
- int saved_errno = 0;
- int ret;
+ int ret = 0;
- if (!shadow_copy2_strip_snapshot(talloc_tos(), handle,
- smb_fname,
- ×tamp, &stripped)) {
+ SMB_VFS_HANDLE_GET_DATA(handle, priv, struct shadow_copy2_private,
+ return -1);
+
+ if (!shadow_copy2_strip_snapshot_converted(talloc_tos(),
+ handle,
+ smb_fname,
+ ×tamp,
+ &stripped,
+ &converted)) {
return -1;
}
if (timestamp == 0) {
- return SMB_VFS_NEXT_STAT(handle, smb_fname);
+ TALLOC_FREE(stripped);
+ ret = SMB_VFS_NEXT_STAT(handle, smb_fname);
+ if (ret != 0) {
+ return ret;
+ }
+ if (!converted) {
+ return 0;
+ }
+
+ abspath = make_path_absolute(talloc_tos(),
+ priv,
+ smb_fname->base_name);
+ if (abspath == NULL) {
+ return -1;
+ }
+
+ convert_sbuf(handle, abspath, &smb_fname->st);
+ TALLOC_FREE(abspath);
+ return 0;
}
tmp = smb_fname->base_name;
@@ -1194,38 +1220,70 @@ static int shadow_copy2_stat(vfs_handle_struct *handle,
}
ret = SMB_VFS_NEXT_STAT(handle, smb_fname);
- if (ret == -1) {
- saved_errno = errno;
+ if (ret != 0) {
+ goto out;
}
+ abspath = make_path_absolute(talloc_tos(),
+ priv,
+ smb_fname->base_name);
+ if (abspath == NULL) {
+ ret = -1;
+ goto out;
+ }
+
+ convert_sbuf(handle, abspath, &smb_fname->st);
+ TALLOC_FREE(abspath);
+
+out:
TALLOC_FREE(smb_fname->base_name);
smb_fname->base_name = tmp;
- if (ret == 0) {
- convert_sbuf(handle, smb_fname->base_name, &smb_fname->st);
- }
- if (saved_errno != 0) {
- errno = saved_errno;
- }
return ret;
}
static int shadow_copy2_lstat(vfs_handle_struct *handle,
struct smb_filename *smb_fname)
{
+ struct shadow_copy2_private *priv = NULL;
time_t timestamp = 0;
char *stripped = NULL;
+ bool converted = false;
+ char *abspath = NULL;
char *tmp;
- int saved_errno = 0;
- int ret;
+ int ret = 0;
- if (!shadow_copy2_strip_snapshot(talloc_tos(), handle,
- smb_fname,
- ×tamp, &stripped)) {
+ SMB_VFS_HANDLE_GET_DATA(handle, priv, struct shadow_copy2_private,
+ return -1);
+
+ if (!shadow_copy2_strip_snapshot_converted(talloc_tos(),
+ handle,
+ smb_fname,
+ ×tamp,
+ &stripped,
+ &converted)) {
return -1;
}
if (timestamp == 0) {
- return SMB_VFS_NEXT_LSTAT(handle, smb_fname);
+ TALLOC_FREE(stripped);
+ ret = SMB_VFS_NEXT_LSTAT(handle, smb_fname);
+ if (ret != 0) {
+ return ret;
+ }
+ if (!converted) {
+ return 0;
+ }
+
+ abspath = make_path_absolute(talloc_tos(),
+ priv,
+ smb_fname->base_name);
+ if (abspath == NULL) {
+ return -1;
+ }
+
+ convert_sbuf(handle, abspath, &smb_fname->st);
+ TALLOC_FREE(abspath);
+ return 0;
}
tmp = smb_fname->base_name;
@@ -1239,45 +1297,76 @@ static int shadow_copy2_lstat(vfs_handle_struct *handle,
}
ret = SMB_VFS_NEXT_LSTAT(handle, smb_fname);
- if (ret == -1) {
- saved_errno = errno;
+ if (ret != 0) {
+ goto out;
+ }
+
+ abspath = make_path_absolute(talloc_tos(),
+ priv,
+ smb_fname->base_name);
+ if (abspath == NULL) {
+ ret = -1;
+ goto out;
}
+ convert_sbuf(handle, abspath, &smb_fname->st);
+ TALLOC_FREE(abspath);
+
+out:
TALLOC_FREE(smb_fname->base_name);
smb_fname->base_name = tmp;
- if (ret == 0) {
- convert_sbuf(handle, smb_fname->base_name, &smb_fname->st);
- }
- if (saved_errno != 0) {
- errno = saved_errno;
- }
return ret;
}
static int shadow_copy2_fstat(vfs_handle_struct *handle, files_struct *fsp,
SMB_STRUCT_STAT *sbuf)
{
+ struct shadow_copy2_private *priv = NULL;
time_t timestamp = 0;
struct smb_filename *orig_smb_fname = NULL;
struct smb_filename vss_smb_fname;
struct smb_filename *orig_base_smb_fname = NULL;
struct smb_filename vss_base_smb_fname;
char *stripped = NULL;
- int saved_errno = 0;
+ char *abspath = NULL;
+ bool converted = false;
bool ok;
int ret;
- ok = shadow_copy2_strip_snapshot(talloc_tos(), handle,
- fsp->fsp_name,
- ×tamp, &stripped);
+ SMB_VFS_HANDLE_GET_DATA(handle, priv, struct shadow_copy2_private,
+ return -1);
+
+ ok = shadow_copy2_strip_snapshot_converted(talloc_tos(),
+ handle,
+ fsp->fsp_name,
+ ×tamp,
+ &stripped,
+ &converted);
if (!ok) {
return -1;
}
if (timestamp == 0) {
TALLOC_FREE(stripped);
- return SMB_VFS_NEXT_FSTAT(handle, fsp, sbuf);
+ ret = SMB_VFS_NEXT_FSTAT(handle, fsp, sbuf);
+ if (ret != 0) {
+ return ret;
+ }
+ if (!converted) {
+ return 0;
+ }
+
+ abspath = make_path_absolute(talloc_tos(),
+ priv,
+ fsp->fsp_name->base_name);
+ if (abspath == NULL) {
+ return -1;
+ }
+
+ convert_sbuf(handle, abspath, sbuf);
+ TALLOC_FREE(abspath);
+ return 0;
}
vss_smb_fname = *fsp->fsp_name;
@@ -1301,20 +1390,27 @@ static int shadow_copy2_fstat(vfs_handle_struct *handle, files_struct *fsp,
}
ret = SMB_VFS_NEXT_FSTAT(handle, fsp, sbuf);
+ if (ret != 0) {
+ goto out;
+ }
+
+ abspath = make_path_absolute(talloc_tos(),
+ priv,
+ fsp->fsp_name->base_name);
+ if (abspath == NULL) {
+ ret = -1;
+ goto out;
+ }
+
+ convert_sbuf(handle, abspath, sbuf);
+ TALLOC_FREE(abspath);
+
+out:
fsp->fsp_name = orig_smb_fname;
if (fsp->base_fsp != NULL) {
fsp->base_fsp->fsp_name = orig_base_smb_fname;
}
- if (ret == -1) {
- saved_errno = errno;
- }
- if (ret == 0) {
- convert_sbuf(handle, fsp->fsp_name->base_name, sbuf);
- }
- if (saved_errno != 0) {
- errno = saved_errno;
- }
return ret;
}
diff --git a/source3/modules/vfs_streams_xattr.c b/source3/modules/vfs_streams_xattr.c
index 72032824b93..743cbd2e8b6 100644
--- a/source3/modules/vfs_streams_xattr.c
+++ b/source3/modules/vfs_streams_xattr.c
@@ -199,7 +199,6 @@ static int streams_xattr_stat_base(vfs_handle_struct *handle,
static int streams_xattr_fstat(vfs_handle_struct *handle, files_struct *fsp,
SMB_STRUCT_STAT *sbuf)
{
- struct smb_filename *smb_fname_base = NULL;
int ret = -1;
struct stream_io *io = (struct stream_io *)
VFS_FETCH_FSP_EXTENSION(handle, fsp);
@@ -214,30 +213,19 @@ static int streams_xattr_fstat(vfs_handle_struct *handle, files_struct *fsp,
return -1;
}
- /* Create an smb_filename with stream_name == NULL. */
- smb_fname_base = synthetic_smb_fname(talloc_tos(),
- io->base,
- NULL,
- NULL,
- fsp->fsp_name->twrp,
- fsp->fsp_name->flags);
- if (smb_fname_base == NULL) {
- errno = ENOMEM;
- return -1;
- }
-
- ret = vfs_stat(handle->conn, smb_fname_base);
- *sbuf = smb_fname_base->st;
-
+ ret = streams_xattr_stat_base(
+ handle,
+ fsp->fsp_name,
+ fsp->fsp_name->flags & SMB_FILENAME_POSIX_PATH);
if (ret == -1) {
- TALLOC_FREE(smb_fname_base);
return -1;
}
+ *sbuf = fsp->fsp_name->st;
+
sbuf->st_ex_size = get_xattr_size(handle->conn,
- smb_fname_base, io->xattr_name);
+ fsp->fsp_name, io->xattr_name);
if (sbuf->st_ex_size == -1) {
- TALLOC_FREE(smb_fname_base);
SET_STAT_INVALID(*sbuf);
return -1;
}
@@ -250,7 +238,6 @@ static int streams_xattr_fstat(vfs_handle_struct *handle, files_struct *fsp,
sbuf->st_ex_mode |= S_IFREG;
sbuf->st_ex_blocks = sbuf->st_ex_size / STAT_ST_BLOCKSIZE + 1;
- TALLOC_FREE(smb_fname_base);
return 0;
}
diff --git a/source3/script/tests/test_shadow_copy_torture.sh b/source3/script/tests/test_shadow_copy_torture.sh
index 240a0083506..1185ad5da11 100755
--- a/source3/script/tests/test_shadow_copy_torture.sh
+++ b/source3/script/tests/test_shadow_copy_torture.sh
@@ -5,7 +5,7 @@
if [ $# -lt 7 ]; then
cat <<EOF
-Usage: test_shadow_copy SERVER SERVER_IP DOMAIN USERNAME PASSWORD WORKDIR SMBTORTURE
+Usage: test_shadow_copy SERVER SERVER_IP DOMAIN USERNAME PASSWORD WORKDIR SMBTORTURE SMBCLIENT
EOF
exit 1;
fi
@@ -17,6 +17,7 @@ USERNAME=${4}
PASSWORD=${5}
WORKDIR=${6}
SMBTORTURE="$VALGRIND ${7}"
+SMBCLIENT="$VALGRIND ${8}"
shift 7
incdir=`dirname $0`/../../../testprogs/blackbox
@@ -33,6 +34,9 @@ build_files()
destdir=$1
echo "$content" > $destdir/foo
+
+ mkdir -p $WORKDIR/subdir/
+ touch $WORKDIR/subdir/hardlink
}
# build a snapshots directory
@@ -42,10 +46,12 @@ build_snapshots()
snapdir=$WORKDIR/.snapshots
- mkdir -p $snapdir
- mkdir $snapdir/$SNAPSHOT
+ mkdir -p $snapdir/$SNAPSHOT
build_files $snapdir/$SNAPSHOT
+
+ mkdir -p $snapdir/$SNAPSHOT/subdir
+ ln "$WORKDIR"/subdir/hardlink "$snapdir"/$SNAPSHOT/subdir/hardlink
}
build_stream_on_snapshot()
@@ -124,6 +130,24 @@ test_shadow_copy_openroot()
failed=`expr $failed + 1`
}
+test_shadow_copy_fix_inodes()
+{
+ local msg
+
+ msg=$1
+
+ #delete snapshots from previous tests
+ find $WORKDIR -name ".snapshots" -exec rm -rf {} \; 1>/dev/null 2>&1
+ build_snapshots
+
+ out=$($SMBCLIENT \
+ -U $USERNAME%$PASSWORD \
+ "//$SERVER/shadow_write" \
+ -c "open $SNAPSHOT/subdir/hardlink") || failed=`expr $failed + 1`
+ echo $out
+ echo $out | grep "hardlink: for read/write fnum 1" || return 1
+}
+
build_files $WORKDIR
# test open for writing and write behaviour of snapshoted files
@@ -133,4 +157,6 @@ test_shadow_copy_stream "reading stream of snapshotted file"
test_shadow_copy_openroot "opening root of shadow copy share"
+testit "fix inodes with hardlink" test_shadow_copy_fix_inodes || failed=`expr $failed + 1`
+
exit $failed
diff --git a/source3/selftest/tests.py b/source3/selftest/tests.py
index fe2fee610e5..533b58d6d9c 100755
--- a/source3/selftest/tests.py
+++ b/source3/selftest/tests.py
@@ -454,7 +454,7 @@ for env in ["fileserver"]:
plantestsuite("samba3.blackbox.offline", env, [os.path.join(samba3srcdir, "script/tests/test_offline.sh"), '$SERVER', '$SERVER_IP', '$DOMAIN', '$USERNAME', '$PASSWORD', '$LOCAL_PATH/offline', smbclient3])
plantestsuite("samba3.blackbox.shadow_copy2.NT1", env + "_smb1_done", [os.path.join(samba3srcdir, "script/tests/test_shadow_copy.sh"), '$SERVER', '$SERVER_IP', '$DOMAIN', '$USERNAME', '$PASSWORD', '$LOCAL_PATH/shadow', smbclient3, '-m', 'NT1'])
plantestsuite("samba3.blackbox.shadow_copy2.SMB3", env, [os.path.join(samba3srcdir, "script/tests/test_shadow_copy.sh"), '$SERVER', '$SERVER_IP', '$DOMAIN', '$USERNAME', '$PASSWORD', '$LOCAL_PATH/shadow', smbclient3, '-m', 'SMB3'])
- plantestsuite("samba3.blackbox.shadow_copy_torture", env, [os.path.join(samba3srcdir, "script/tests/test_shadow_copy_torture.sh"), '$SERVER', '$SERVER_IP', '$DOMAIN', '$USERNAME', '$PASSWORD', '$LOCAL_PATH/shadow', smbtorture4])
+ plantestsuite("samba3.blackbox.shadow_copy_torture", env, [os.path.join(samba3srcdir, "script/tests/test_shadow_copy_torture.sh"), '$SERVER', '$SERVER_IP', '$DOMAIN', '$USERNAME', '$PASSWORD', '$LOCAL_PATH/shadow', smbtorture4, smbclient3])
plantestsuite("samba3.blackbox.smbclient.forceuser_validusers", env, [os.path.join(samba3srcdir, "script/tests/test_forceuser_validusers.sh"), '$SERVER', '$DOMAIN', '$USERNAME', '$PASSWORD', '$LOCAL_PATH', smbclient3])
plantestsuite("samba3.blackbox.smbget", env, [os.path.join(samba3srcdir, "script/tests/test_smbget.sh"), '$SERVER', '$SERVER_IP', '$DOMAIN', 'smbget_user', '$PASSWORD', '$LOCAL_PATH/smbget', smbget])
plantestsuite("samba3.blackbox.netshareenum", env, [os.path.join(samba3srcdir, "script/tests/test_shareenum.sh"), '$SERVER', '$USERNAME', '$PASSWORD', rpcclient])
diff --git a/source3/smbd/dosmode.c b/source3/smbd/dosmode.c
index 844f5efe389..79158007654 100644
--- a/source3/smbd/dosmode.c
+++ b/source3/smbd/dosmode.c
@@ -28,6 +28,7 @@
#include "lib/param/loadparm.h"
#include "lib/util/tevent_ntstatus.h"
#include "lib/util/string_wrappers.h"
+#include "fake_file.h"
static NTSTATUS get_file_handle_for_metadata(connection_struct *conn,
const struct smb_filename *smb_fname,
@@ -751,6 +752,10 @@ uint32_t fdos_mode(struct files_struct *fsp)
DBG_DEBUG("%s\n", fsp_str_dbg(fsp));
+ if (fsp->fake_file_handle != NULL) {
+ return dosmode_from_fake_filehandle(fsp->fake_file_handle);
+ }
+
if (!VALID_STAT(fsp->fsp_name->st)) {
return 0;
}
diff --git a/source3/smbd/fake_file.c b/source3/smbd/fake_file.c
index c4c81dd19f9..6f6d5b3778a 100644
--- a/source3/smbd/fake_file.c
+++ b/source3/smbd/fake_file.c
@@ -115,6 +115,21 @@ enum FAKE_FILE_TYPE is_fake_file(const struct smb_filename *smb_fname)
return ret;
}
+uint32_t dosmode_from_fake_filehandle(const struct fake_file_handle *ffh)
+{
+ if (ffh->type != FAKE_FILE_TYPE_QUOTA) {
+ DBG_ERR("Unexpected fake_file_handle: %d\n", ffh->type);
+ log_stack_trace();
+ return FILE_ATTRIBUTE_NORMAL;
+ }
+
+ /* This is what Windows 2016 returns */
+ return FILE_ATTRIBUTE_HIDDEN
+ | FILE_ATTRIBUTE_SYSTEM
+ | FILE_ATTRIBUTE_DIRECTORY
+ | FILE_ATTRIBUTE_ARCHIVE;
+}
+
/****************************************************************************
Open a fake quota file with a share mode.
--
Samba Shared Repository
More information about the samba-cvs
mailing list