diff options
author | nsylvain@chromium.org <nsylvain@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2008-10-27 14:41:51 +0000 |
---|---|---|
committer | nsylvain@chromium.org <nsylvain@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98> | 2008-10-27 14:41:51 +0000 |
commit | ce16adb506bee0650584c64575423e2d120c75bd (patch) | |
tree | bc6db25350ce984e233740cb0bf85f1a7bc39aeb /base | |
parent | b182a98a89152bce37b35be5727b7d1e988c4ccd (diff) | |
download | chromium_src-ce16adb506bee0650584c64575423e2d120c75bd.zip chromium_src-ce16adb506bee0650584c64575423e2d120c75bd.tar.gz chromium_src-ce16adb506bee0650584c64575423e2d120c75bd.tar.bz2 |
Make sure it's possible to download to a network share.
The function to move the file was failing to set the
security descriptor. Now we use SHFileOperation, which
has a flag to do everything we want.
Eventually we might want to display ui on errors and
use the ui features of SHFileOperation, but for the
1.0 build we want to stick to a smaller and less risky
change.
BUG: 984
Review URL: http://codereview.chromium.org/8128
git-svn-id: svn://svn.chromium.org/chrome/trunk/src@3996 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'base')
-rw-r--r-- | base/file_util.h | 4 | ||||
-rw-r--r-- | base/file_util_win.cc | 59 |
2 files changed, 20 insertions, 43 deletions
diff --git a/base/file_util.h b/base/file_util.h index 150b629..8594d28 100644 --- a/base/file_util.h +++ b/base/file_util.h @@ -346,8 +346,8 @@ class FileEnumerator { DISALLOW_EVIL_CONSTRUCTORS(FileEnumerator); }; -// Renames a file using the MoveFileEx API and ensures that the target file gets -// the correct security descriptor in the new path. +// Renames a file using the SHFileOperation API to ensure that the target file +// gets the correct default security descriptor in the new path. bool RenameFileAndResetSecurityDescriptor( const std::wstring& source_file_path, const std::wstring& target_file_path); diff --git a/base/file_util_win.cc b/base/file_util_win.cc index 9c34ab3..9d775f0 100644 --- a/base/file_util_win.cc +++ b/base/file_util_win.cc @@ -535,47 +535,24 @@ int WriteFile(const std::wstring& filename, const char* data, int size) { bool RenameFileAndResetSecurityDescriptor( const std::wstring& source_file_path, const std::wstring& target_file_path) { - // The MoveFile API does not reset the security descriptor on the target - // file. To ensure that the target file gets the correct security descriptor - // we create the target file initially in the target path, read its security - // descriptor and stamp this descriptor on the target file after the MoveFile - // API completes. - ScopedHandle temp_file_handle_for_security_desc( - CreateFileW(target_file_path.c_str(), GENERIC_READ | GENERIC_WRITE, - FILE_SHARE_READ, NULL, OPEN_ALWAYS, - FILE_ATTRIBUTE_NORMAL | FILE_FLAG_DELETE_ON_CLOSE, - NULL)); - if (!temp_file_handle_for_security_desc.IsValid()) - return false; - - // Check how much we should allocate for the security descriptor. - unsigned long security_descriptor_size_in_bytes = 0; - GetFileSecurity(target_file_path.c_str(), DACL_SECURITY_INFORMATION, NULL, 0, - &security_descriptor_size_in_bytes); - if (ERROR_INSUFFICIENT_BUFFER != GetLastError() || - security_descriptor_size_in_bytes == 0) - return false; - - scoped_array<char> security_descriptor( - new char[security_descriptor_size_in_bytes]); - - if (!GetFileSecurity(target_file_path.c_str(), DACL_SECURITY_INFORMATION, - security_descriptor.get(), - security_descriptor_size_in_bytes, - &security_descriptor_size_in_bytes)) { - return false; - } - - temp_file_handle_for_security_desc.Set(INVALID_HANDLE_VALUE); - - if (!MoveFileEx(source_file_path.c_str(), target_file_path.c_str(), - MOVEFILE_COPY_ALLOWED)) { - return false; - } - - return !!SetFileSecurity(target_file_path.c_str(), - DACL_SECURITY_INFORMATION, - security_descriptor.get()); + // The parameters to SHFileOperation must be terminated with 2 NULL chars. + std::wstring source = source_file_path; + std::wstring target = target_file_path; + + source.append(1, L'\0'); + target.append(1, L'\0'); + + SHFILEOPSTRUCT move_info = {0}; + move_info.wFunc = FO_MOVE; + move_info.pFrom = source.c_str(); + move_info.pTo = target.c_str(); + move_info.fFlags = FOF_SILENT | FOF_NOCONFIRMATION | FOF_NOERRORUI | + FOF_NOCONFIRMMKDIR | FOF_NOCOPYSECURITYATTRIBS; + + if (0 != SHFileOperation(&move_info)) + return false; + + return true; } // Gets the current working directory for the process. |