Handle unlinking in-use files on virtual drives
* path.cc (path_conv::set_nt_native_path): New function. * path.h (path_conv::set_nt_native_path): Add prototype. * syscall.cc (try_to_bin): Handle moving files to the recycler accessed via a local virtual drive (subst). Fix a problem renaming the file to the unique replacement name on Samba. Align comment. Signed-off-by: Corinna Vinschen <corinna@vinschen.de>
This commit is contained in:
parent
4e99630cfd
commit
5abb0ed13c
|
@ -1,3 +1,11 @@
|
||||||
|
2015-04-23 Corinna Vinschen <corinna@vinschen.de>
|
||||||
|
|
||||||
|
* path.cc (path_conv::set_nt_native_path): New function.
|
||||||
|
* path.h (path_conv::set_nt_native_path): Add prototype.
|
||||||
|
* syscall.cc (try_to_bin): Handle moving files to the recycler
|
||||||
|
accessed via a local virtual drive (subst). Fix a problem renaming
|
||||||
|
the file to the unique replacement name on Samba. Align comment.
|
||||||
|
|
||||||
2015-04-22 Corinna Vinschen <corinna@vinschen.de>
|
2015-04-22 Corinna Vinschen <corinna@vinschen.de>
|
||||||
|
|
||||||
* fhandler_tty.cc (fhandler_pty_slave::fch_close_handles): Don't close
|
* fhandler_tty.cc (fhandler_pty_slave::fch_close_handles): Don't close
|
||||||
|
|
|
@ -486,6 +486,18 @@ get_nt_native_path (const char *path, UNICODE_STRING& upath, bool dos)
|
||||||
return &upath;
|
return &upath;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* Handle with extrem care! Only used in a certain instance in try_to_bin.
|
||||||
|
Every other usage needs a careful check. */
|
||||||
|
void
|
||||||
|
path_conv::set_nt_native_path (PUNICODE_STRING new_path)
|
||||||
|
{
|
||||||
|
wide_path = (PWCHAR) crealloc_abort (wide_path, new_path->MaximumLength);
|
||||||
|
memcpy (wide_path, new_path->Buffer, new_path->Length);
|
||||||
|
uni_path.Length = new_path->Length;
|
||||||
|
uni_path.MaximumLength = new_path->MaximumLength;
|
||||||
|
uni_path.Buffer = wide_path;
|
||||||
|
}
|
||||||
|
|
||||||
PUNICODE_STRING
|
PUNICODE_STRING
|
||||||
path_conv::get_nt_native_path ()
|
path_conv::get_nt_native_path ()
|
||||||
{
|
{
|
||||||
|
|
|
@ -270,6 +270,7 @@ class path_conv
|
||||||
|
|
||||||
~path_conv ();
|
~path_conv ();
|
||||||
inline const char *get_win32 () const { return path; }
|
inline const char *get_win32 () const { return path; }
|
||||||
|
void set_nt_native_path (PUNICODE_STRING);
|
||||||
PUNICODE_STRING get_nt_native_path ();
|
PUNICODE_STRING get_nt_native_path ();
|
||||||
inline POBJECT_ATTRIBUTES get_object_attr (OBJECT_ATTRIBUTES &attr,
|
inline POBJECT_ATTRIBUTES get_object_attr (OBJECT_ATTRIBUTES &attr,
|
||||||
SECURITY_ATTRIBUTES &sa)
|
SECURITY_ATTRIBUTES &sa)
|
||||||
|
|
|
@ -314,15 +314,35 @@ try_to_bin (path_conv &pc, HANDLE &fh, ACCESS_MASK access, ULONG flags)
|
||||||
RtlAppendUnicodeToString (&recycler, L"\\Recycled\\");
|
RtlAppendUnicodeToString (&recycler, L"\\Recycled\\");
|
||||||
else
|
else
|
||||||
goto out;
|
goto out;
|
||||||
/* Is the file a subdir of the recycler? */
|
|
||||||
RtlInitCountedUnicodeString(&fname, pfni->FileName, pfni->FileNameLength);
|
RtlInitCountedUnicodeString(&fname, pfni->FileName, pfni->FileNameLength);
|
||||||
|
/* Is the file a subdir of the recycler? */
|
||||||
if (RtlEqualUnicodePathPrefix (&fname, &recycler, TRUE))
|
if (RtlEqualUnicodePathPrefix (&fname, &recycler, TRUE))
|
||||||
goto out;
|
goto out;
|
||||||
/* Is fname the recycler? Temporarily hide trailing backslash. */
|
/* Is fname the recycler? Temporarily hide trailing backslash. */
|
||||||
recycler.Length -= sizeof (WCHAR);
|
recycler.Length -= sizeof (WCHAR);
|
||||||
if (RtlEqualUnicodeString (&fname, &recycler, TRUE))
|
if (RtlEqualUnicodeString (&fname, &recycler, TRUE))
|
||||||
goto out;
|
goto out;
|
||||||
|
/* Is fname really a subcomponent of the full path? If not, there's
|
||||||
|
a high probability we're acessing the file via a virtual drive
|
||||||
|
created with "subst". Check and accommodate it. Note that we
|
||||||
|
ony get here if the virtual drive is really pointing to a local
|
||||||
|
drive. Otherwise pc.isremote () returns "true". */
|
||||||
|
if (!RtlEqualUnicodePathSuffix (pc.get_nt_native_path (), &fname, TRUE))
|
||||||
|
{
|
||||||
|
WCHAR drive[3] = { pc.get_nt_native_path ()->Buffer[4], ':', '\0' };
|
||||||
|
PWCHAR tgt = tp.w_get ();
|
||||||
|
|
||||||
|
if (QueryDosDeviceW (drive, tgt, NT_MAX_PATH)
|
||||||
|
&& !wcsncmp (tgt, L"\\??\\", 4))
|
||||||
|
{
|
||||||
|
UNICODE_STRING new_path;
|
||||||
|
|
||||||
|
wcsncpy (tgt + 6, fname.Buffer, fname.Length / sizeof (WCHAR));
|
||||||
|
RtlInitCountedUnicodeString(&new_path, tgt,
|
||||||
|
6 * sizeof (WCHAR) + fname.Length);
|
||||||
|
pc.set_nt_native_path (&new_path);
|
||||||
|
}
|
||||||
|
}
|
||||||
/* Create root dir path from file name information. */
|
/* Create root dir path from file name information. */
|
||||||
RtlSplitUnicodePath (&fname, &fname, NULL);
|
RtlSplitUnicodePath (&fname, &fname, NULL);
|
||||||
RtlSplitUnicodePath (pc.get_nt_native_path (), &root, NULL);
|
RtlSplitUnicodePath (pc.get_nt_native_path (), &root, NULL);
|
||||||
|
@ -367,9 +387,11 @@ try_to_bin (path_conv &pc, HANDLE &fh, ACCESS_MASK access, ULONG flags)
|
||||||
starting at U+dc00. Use plain ASCII chars on filesystems not supporting
|
starting at U+dc00. Use plain ASCII chars on filesystems not supporting
|
||||||
Unicode. The rest of the filename is the inode number in hex encoding
|
Unicode. The rest of the filename is the inode number in hex encoding
|
||||||
and a hash of the full NT path in hex. The combination allows to remove
|
and a hash of the full NT path in hex. The combination allows to remove
|
||||||
multiple hardlinks to the same file. */
|
multiple hardlinks to the same file. Samba doesn't like the transposed
|
||||||
|
names. */
|
||||||
RtlAppendUnicodeToString (&recycler,
|
RtlAppendUnicodeToString (&recycler,
|
||||||
pc.fs_flags () & FILE_UNICODE_ON_DISK
|
(pc.fs_flags () & FILE_UNICODE_ON_DISK
|
||||||
|
&& !pc.fs_is_samba ())
|
||||||
? L".\xdc63\xdc79\xdc67" : L".cyg");
|
? L".\xdc63\xdc79\xdc67" : L".cyg");
|
||||||
pfii = (PFILE_INTERNAL_INFORMATION) infobuf;
|
pfii = (PFILE_INTERNAL_INFORMATION) infobuf;
|
||||||
/* Note: Modern Samba versions apparently don't like buffer sizes of more
|
/* Note: Modern Samba versions apparently don't like buffer sizes of more
|
||||||
|
|
Loading…
Reference in New Issue