diff options
10 files changed, 196 insertions, 3 deletions
diff --git a/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.cc b/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.cc index 23b4e57..b14461d 100644 --- a/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.cc +++ b/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.cc @@ -189,6 +189,31 @@ void ReadBytesOnUIThread( task_helper->ReadBytes(request); } +// Renames |object_id| to |new_name|. +// +// |storage_name| specifies the name of the storage device. +// |read_only| specifies the mode of the storage device. +// |object_id| is an id of object to be renamed. +// |new_name| is new name of the object. +// |success_callback| is called when the object is renamed successfully. +// |error_callback| is called when it fails to rename the object. +// |success_callback| and |error_callback| runs on the IO thread. +void RenameObjectOnUIThread( + const std::string& storage_name, + const bool read_only, + const uint32 object_id, + const std::string& new_name, + const MTPDeviceTaskHelper::RenameObjectSuccessCallback& success_callback, + const MTPDeviceTaskHelper::ErrorCallback& error_callback) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + MTPDeviceTaskHelper* task_helper = + GetDeviceTaskHelperForStorage(storage_name, read_only); + if (!task_helper) + return; + task_helper->RenameObject(object_id, new_name, success_callback, + error_callback); +} + // Copies the file |source_file_descriptor| to |file_name| in |parent_id|. // // |storage_name| specifies the name of the storage device. @@ -822,8 +847,24 @@ void MTPDeviceDelegateImplLinux::MoveFileLocalInternal( if (source_file_path.DirName() == device_file_path.DirName()) { // If a file is moved in a same directory, rename the file. - // TODO(yawano) Implement rename operation. - error_callback.Run(base::File::FILE_ERROR_SECURITY); + uint32 file_id; + if (CachedPathToId(source_file_path, &file_id)) { + const MTPDeviceTaskHelper::RenameObjectSuccessCallback + success_callback_wrapper = base::Bind( + &MTPDeviceDelegateImplLinux::OnDidMoveFileLocalWithRename, + weak_ptr_factory_.GetWeakPtr(), success_callback, file_id); + const MTPDeviceTaskHelper::ErrorCallback error_callback_wrapper = + base::Bind(&MTPDeviceDelegateImplLinux::HandleDeviceFileError, + weak_ptr_factory_.GetWeakPtr(), error_callback, file_id); + const base::Closure closure = + base::Bind(&RenameObjectOnUIThread, storage_name_, read_only_, + file_id, device_file_path.BaseName().value(), + success_callback_wrapper, error_callback_wrapper); + EnsureInitAndRunTask(PendingTaskInfo( + base::FilePath(), content::BrowserThread::UI, FROM_HERE, closure)); + } else { + error_callback.Run(base::File::FILE_ERROR_NOT_FOUND); + } } else { // If a file is moved to a different directory, create a copy to the // destination path, and remove source file. @@ -1314,6 +1355,16 @@ void MTPDeviceDelegateImplLinux::OnDidCopyFileFromLocalOfCopyFileLocal( success_callback.Run(); } +void MTPDeviceDelegateImplLinux::OnDidMoveFileLocalWithRename( + const MoveFileLocalSuccessCallback& success_callback, + const uint32 file_id) { + DCHECK_CURRENTLY_ON(content::BrowserThread::IO); + + EvictCachedPathToId(file_id); + success_callback.Run(); + PendingRequestDone(); +} + void MTPDeviceDelegateImplLinux::OnDidCopyFileFromLocal( const CopyFileFromLocalSuccessCallback& success_callback, const int source_file_descriptor) { diff --git a/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.h b/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.h index e0a4d38..016993a 100644 --- a/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.h +++ b/chrome/browser/media_galleries/linux/mtp_device_delegate_impl_linux.h @@ -310,6 +310,11 @@ class MTPDeviceDelegateImplLinux : public MTPDeviceAsyncDelegate { const CopyFileFromLocalSuccessCallback success_callback, const base::FilePath& temporary_file_path); + // Called when MoveFileLocal() succeeds with rename operation. + void OnDidMoveFileLocalWithRename( + const MoveFileLocalSuccessCallback& success_callback, + const uint32 file_id); + // Called when CopyFileFromLocal() succeeds. void OnDidCopyFileFromLocal( const CopyFileFromLocalSuccessCallback& success_callback, diff --git a/chrome/browser/media_galleries/linux/mtp_device_task_helper.cc b/chrome/browser/media_galleries/linux/mtp_device_task_helper.cc index c1f7a2b..848e5e0 100644 --- a/chrome/browser/media_galleries/linux/mtp_device_task_helper.cc +++ b/chrome/browser/media_galleries/linux/mtp_device_task_helper.cc @@ -138,6 +138,20 @@ void MTPDeviceTaskHelper::ReadBytes( weak_ptr_factory_.GetWeakPtr(), request)); } +void MTPDeviceTaskHelper::RenameObject( + const uint32 object_id, + const std::string& new_name, + const RenameObjectSuccessCallback& success_callback, + const ErrorCallback& error_callback) { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + + GetMediaTransferProtocolManager()->RenameObject( + device_handle_, object_id, new_name, + base::Bind(&MTPDeviceTaskHelper::OnRenameObject, + weak_ptr_factory_.GetWeakPtr(), success_callback, + error_callback)); +} + // TODO(yawano) storage_name is not used, delete it. void MTPDeviceTaskHelper::CopyFileFromLocal( const std::string& storage_name, @@ -298,6 +312,22 @@ void MTPDeviceTaskHelper::OnDidReadBytes( file_info, data.length())); } +void MTPDeviceTaskHelper::OnRenameObject( + const RenameObjectSuccessCallback& success_callback, + const ErrorCallback& error_callback, + const bool error) const { + DCHECK_CURRENTLY_ON(content::BrowserThread::UI); + if (error) { + content::BrowserThread::PostTask( + content::BrowserThread::IO, FROM_HERE, + base::Bind(error_callback, base::File::FILE_ERROR_FAILED)); + return; + } + + content::BrowserThread::PostTask(content::BrowserThread::IO, FROM_HERE, + success_callback); +} + void MTPDeviceTaskHelper::OnCopyFileFromLocal( const CopyFileFromLocalSuccessCallback& success_callback, const ErrorCallback& error_callback, @@ -311,7 +341,7 @@ void MTPDeviceTaskHelper::OnCopyFileFromLocal( } content::BrowserThread::PostTask(content::BrowserThread::IO, FROM_HERE, - base::Bind(success_callback)); + success_callback); } void MTPDeviceTaskHelper::OnDeleteObject( diff --git a/chrome/browser/media_galleries/linux/mtp_device_task_helper.h b/chrome/browser/media_galleries/linux/mtp_device_task_helper.h index ab99e3f..bbd486f 100644 --- a/chrome/browser/media_galleries/linux/mtp_device_task_helper.h +++ b/chrome/browser/media_galleries/linux/mtp_device_task_helper.h @@ -36,6 +36,8 @@ class MTPDeviceTaskHelper { typedef base::Callback<void(const storage::AsyncFileUtil::EntryList& entries, bool has_more)> ReadDirectorySuccessCallback; + typedef base::Closure RenameObjectSuccessCallback; + typedef base::Closure CopyFileFromLocalSuccessCallback; typedef base::Closure DeleteObjectSuccessCallback; @@ -101,6 +103,12 @@ class MTPDeviceTaskHelper { // called on the IO thread to notify the caller about success or failure. void ReadBytes(const MTPDeviceAsyncDelegate::ReadBytesRequest& request); + // Forwards RenameObject request to the MediaTransferProtocolManager. + void RenameObject(const uint32 object_id, + const std::string& new_name, + const RenameObjectSuccessCallback& success_callback, + const ErrorCallback& error_callback); + // Forwards CopyFileFromLocal request to the MediaTransferProtocolManager. void CopyFileFromLocal( const std::string& storage_name, @@ -179,6 +187,11 @@ class MTPDeviceTaskHelper { const std::string& data, bool error) const; + // Called when RenameObject completes. + void OnRenameObject(const RenameObjectSuccessCallback& success_callback, + const ErrorCallback& error_callback, + const bool error) const; + // Called when CopyFileFromLocal completes. void OnCopyFileFromLocal( const CopyFileFromLocalSuccessCallback& success_callback, diff --git a/components/storage_monitor/test_media_transfer_protocol_manager_linux.cc b/components/storage_monitor/test_media_transfer_protocol_manager_linux.cc index b52f4c4..ab49496 100644 --- a/components/storage_monitor/test_media_transfer_protocol_manager_linux.cc +++ b/components/storage_monitor/test_media_transfer_protocol_manager_linux.cc @@ -67,6 +67,14 @@ void TestMediaTransferProtocolManagerLinux::GetFileInfo( callback.Run(MtpFileEntry(), true); } +void TestMediaTransferProtocolManagerLinux::RenameObject( + const std::string& storage_handle, + const uint32 object_id, + const std::string& new_name, + const RenameObjectCallback& callback) { + callback.Run(true /* error */); +} + void TestMediaTransferProtocolManagerLinux::CopyFileFromLocal( const std::string& storage_handle, const int source_file_descriptor, diff --git a/components/storage_monitor/test_media_transfer_protocol_manager_linux.h b/components/storage_monitor/test_media_transfer_protocol_manager_linux.h index df20bb6..add96df 100644 --- a/components/storage_monitor/test_media_transfer_protocol_manager_linux.h +++ b/components/storage_monitor/test_media_transfer_protocol_manager_linux.h @@ -40,6 +40,10 @@ class TestMediaTransferProtocolManagerLinux void GetFileInfo(const std::string& storage_handle, uint32 file_id, const GetFileInfoCallback& callback) override; + void RenameObject(const std::string& storage_handle, + const uint32 object_id, + const std::string& new_name, + const RenameObjectCallback& callback) override; void CopyFileFromLocal(const std::string& storage_handle, const int source_file_descriptor, const uint32 parent_id, diff --git a/device/media_transfer_protocol/media_transfer_protocol_daemon_client.cc b/device/media_transfer_protocol/media_transfer_protocol_daemon_client.cc index 832d598..8c2b2d9 100644 --- a/device/media_transfer_protocol/media_transfer_protocol_daemon_client.cc +++ b/device/media_transfer_protocol/media_transfer_protocol_daemon_client.cc @@ -171,6 +171,22 @@ class MediaTransferProtocolDaemonClientImpl error_callback)); } + void RenameObject(const std::string& handle, + const uint32 object_id, + const std::string& new_name, + const RenameObjectCallback& callback, + const ErrorCallback& error_callback) override { + dbus::MethodCall method_call(mtpd::kMtpdInterface, mtpd::kRenameObject); + dbus::MessageWriter writer(&method_call); + writer.AppendString(handle); + writer.AppendUint32(object_id); + writer.AppendString(new_name); + proxy_->CallMethod( + &method_call, dbus::ObjectProxy::TIMEOUT_USE_DEFAULT, + base::Bind(&MediaTransferProtocolDaemonClientImpl::OnRenameObject, + weak_ptr_factory_.GetWeakPtr(), callback, error_callback)); + } + void CopyFileFromLocal(const std::string& handle, const int source_file_descriptor, const uint32 parent_id, @@ -385,6 +401,17 @@ class MediaTransferProtocolDaemonClientImpl callback.Run(data); } + void OnRenameObject(const RenameObjectCallback& callback, + const ErrorCallback& error_callback, + dbus::Response* response) { + if (!response) { + error_callback.Run(); + return; + } + + callback.Run(); + } + void OnCopyFileFromLocal(const CopyFileFromLocalCallback& callback, const ErrorCallback& error_callback, dbus::Response* response) { diff --git a/device/media_transfer_protocol/media_transfer_protocol_daemon_client.h b/device/media_transfer_protocol/media_transfer_protocol_daemon_client.h index ae5e8c0..12436d3 100644 --- a/device/media_transfer_protocol/media_transfer_protocol_daemon_client.h +++ b/device/media_transfer_protocol/media_transfer_protocol_daemon_client.h @@ -68,6 +68,9 @@ class MediaTransferProtocolDaemonClient { // The argument is a string containing the file data. typedef base::Callback<void(const std::string& data)> ReadFileCallback; + // A callback to handle the result of RenameObject. + typedef base::Closure RenameObjectCallback; + // A callback to handle the result of CopyFileFromLocal. typedef base::Closure CopyFileFromLocalCallback; @@ -143,6 +146,16 @@ class MediaTransferProtocolDaemonClient { const ReadFileCallback& callback, const ErrorCallback& error_callback) = 0; + // Calls RenameObject method. |callback| is called after the method call + // succeeds, otherwise, |error_callback| is called. + // |object_is| is an id of object to be renamed. + // |new_name| is new name of the object. + virtual void RenameObject(const std::string& handle, + const uint32 object_id, + const std::string& new_name, + const RenameObjectCallback& callback, + const ErrorCallback& error_callback) = 0; + // Calls CopyFileFromLocal method. |callback| is called after the method call // succeeds, otherwise, |error_callback| is called. // |source_file_descriptor| is a file descriptor of source file. diff --git a/device/media_transfer_protocol/media_transfer_protocol_manager.cc b/device/media_transfer_protocol/media_transfer_protocol_manager.cc index 2a7f478..1c21be4 100644 --- a/device/media_transfer_protocol/media_transfer_protocol_manager.cc +++ b/device/media_transfer_protocol/media_transfer_protocol_manager.cc @@ -223,6 +223,24 @@ class MediaTransferProtocolManagerImpl : public MediaTransferProtocolManager { weak_ptr_factory_.GetWeakPtr())); } + void RenameObject(const std::string& storage_handle, + const uint32 object_id, + const std::string& new_name, + const RenameObjectCallback& callback) override { + DCHECK(thread_checker_.CalledOnValidThread()); + if (!ContainsKey(handles_, storage_handle) || !mtp_client_) { + callback.Run(true /* error */); + return; + } + rename_object_callbacks_.push(callback); + mtp_client_->RenameObject( + storage_handle, object_id, new_name, + base::Bind(&MediaTransferProtocolManagerImpl::OnRenameObject, + weak_ptr_factory_.GetWeakPtr()), + base::Bind(&MediaTransferProtocolManagerImpl::OnRenameObjectError, + weak_ptr_factory_.GetWeakPtr())); + } + void CopyFileFromLocal(const std::string& storage_handle, const int source_file_descriptor, const uint32 parent_id, @@ -271,6 +289,7 @@ class MediaTransferProtocolManagerImpl : public MediaTransferProtocolManager { typedef std::queue<ReadDirectoryCallback> ReadDirectoryCallbackQueue; typedef std::queue<ReadFileCallback> ReadFileCallbackQueue; typedef std::queue<GetFileInfoCallback> GetFileInfoCallbackQueue; + typedef std::queue<RenameObjectCallback> RenameObjectCallbackQueue; typedef std::queue<CopyFileFromLocalCallback> CopyFileFromLocalCallbackQueue; typedef std::queue<DeleteObjectCallback> DeleteObjectCallbackQueue; @@ -487,6 +506,18 @@ class MediaTransferProtocolManagerImpl : public MediaTransferProtocolManager { get_file_info_callbacks_.pop(); } + void OnRenameObject() { + DCHECK(thread_checker_.CalledOnValidThread()); + rename_object_callbacks_.front().Run(false /* no error */); + rename_object_callbacks_.pop(); + } + + void OnRenameObjectError() { + DCHECK(thread_checker_.CalledOnValidThread()); + rename_object_callbacks_.front().Run(true /* error */); + rename_object_callbacks_.pop(); + } + void OnCopyFileFromLocal() { DCHECK(thread_checker_.CalledOnValidThread()); copy_file_from_local_callbacks_.front().Run(false /* no error */); @@ -592,6 +623,7 @@ class MediaTransferProtocolManagerImpl : public MediaTransferProtocolManager { ReadDirectoryCallbackQueue read_directory_callbacks_; ReadFileCallbackQueue read_file_callbacks_; GetFileInfoCallbackQueue get_file_info_callbacks_; + RenameObjectCallbackQueue rename_object_callbacks_; CopyFileFromLocalCallbackQueue copy_file_from_local_callbacks_; DeleteObjectCallbackQueue delete_object_callbacks_; diff --git a/device/media_transfer_protocol/media_transfer_protocol_manager.h b/device/media_transfer_protocol/media_transfer_protocol_manager.h index 1915ce2..724fe86 100644 --- a/device/media_transfer_protocol/media_transfer_protocol_manager.h +++ b/device/media_transfer_protocol/media_transfer_protocol_manager.h @@ -59,6 +59,10 @@ class MediaTransferProtocolManager { typedef base::Callback<void(const MtpFileEntry& file_entry, bool error)> GetFileInfoCallback; + // A callback to handle the result of RenameObject. + // The first argument is true if there was an error. + typedef base::Callback<void(bool error)> RenameObjectCallback; + // A callback to handle the result of CopyFileFromLocal. // The first argument is true if there was an error. typedef base::Callback<void(bool error)> CopyFileFromLocalCallback; @@ -124,6 +128,12 @@ class MediaTransferProtocolManager { uint32 file_id, const GetFileInfoCallback& callback) = 0; + // Renames |object_id| to |new_name|. + virtual void RenameObject(const std::string& storage_handle, + const uint32 object_id, + const std::string& new_name, + const RenameObjectCallback& callback) = 0; + // Copies the file from |source_file_descriptor| to |file_name| on // |parent_id|. virtual void CopyFileFromLocal(const std::string& storage_handle, |