| // Copyright (c) 2013 The Chromium OS Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #ifndef CRYPTOHOME_MOCK_PLATFORM_H_ |
| #define CRYPTOHOME_MOCK_PLATFORM_H_ |
| |
| #include <map> |
| #include <memory> |
| #include <string> |
| #include <utility> |
| #include <vector> |
| |
| #include <base/files/file.h> |
| #include <base/files/file_path.h> |
| #include <base/files/file_util.h> |
| #include <base/time/time.h> |
| #include <gmock/gmock.h> |
| |
| #include "cryptohome/platform.h" |
| |
| namespace cryptohome { |
| |
| using ::testing::_; |
| using ::testing::NiceMock; |
| using ::testing::Invoke; |
| using ::testing::Return; |
| |
| class MockFileEnumerator : public FileEnumerator { |
| public: |
| MockFileEnumerator() { |
| ON_CALL(*this, Next()) |
| .WillByDefault(Invoke(this, &MockFileEnumerator::MockNext)); |
| ON_CALL(*this, GetInfo()) |
| .WillByDefault(Invoke(this, &MockFileEnumerator::MockGetInfo)); |
| } |
| virtual ~MockFileEnumerator() {} |
| |
| MOCK_METHOD0(Next, base::FilePath(void)); |
| MOCK_METHOD0(GetInfo, FileInfo(void)); |
| |
| std::vector<FileInfo> entries_; |
| |
| protected: |
| virtual base::FilePath MockNext() { |
| if (entries_.empty()) |
| return base::FilePath(); |
| current_ = entries_.at(0); |
| entries_.erase(entries_.begin(), entries_.begin()+1); |
| return current_.GetName(); |
| } |
| virtual const FileInfo& MockGetInfo() { |
| return current_; |
| } |
| FileInfo current_; |
| }; |
| |
| // TODO(wad) Migrate to an in-memory-only mock filesystem. |
| ACTION(CallDeleteFile) { return base::DeleteFile(base::FilePath(arg0), arg1); } |
| ACTION(CallEnumerateDirectoryEntries) { |
| // Pass a call to EnumerateDirectoryEntries through to a real Platform if it's |
| // not mocked. |
| Platform p; |
| return p.EnumerateDirectoryEntries(arg0, arg1, arg2); |
| } |
| ACTION(CallDirectoryExists) { |
| return base::DirectoryExists(base::FilePath(arg0)); |
| } |
| ACTION(CallPathExists) { |
| return base::PathExists(base::FilePath(arg0)); |
| } |
| ACTION(CallCreateDirectory) { |
| return base::CreateDirectory(base::FilePath(arg0)); |
| } |
| ACTION(CallReadFile) { return Platform().ReadFile(arg0, arg1); } |
| ACTION(CallReadFileToString) { return Platform().ReadFileToString(arg0, arg1); } |
| ACTION(CallCopy) { return Platform().Copy(arg0, arg1); } |
| ACTION(CallRename) { return Platform().Rename(arg0, arg1); } |
| ACTION(CallComputeDirectorySize) { |
| return Platform().ComputeDirectorySize(arg0); |
| } |
| ACTION(CallStatVFS) { return Platform().StatVFS(arg0, arg1); } |
| ACTION(CallReportFilesystemDetails) { |
| return Platform().ReportFilesystemDetails(arg0, arg1); |
| } |
| ACTION(CallFindFilesystemDevice) { |
| return Platform().FindFilesystemDevice(arg0, arg1); |
| } |
| |
| class MockPlatform : public Platform { |
| public: |
| MockPlatform(); |
| virtual ~MockPlatform(); |
| MOCK_METHOD4(Mount, bool(const base::FilePath&, const base::FilePath&, |
| const std::string&, const std::string&)); |
| MOCK_METHOD2(Bind, bool(const base::FilePath&, const base::FilePath&)); |
| MOCK_METHOD3(Unmount, bool(const base::FilePath&, bool, bool*)); |
| MOCK_METHOD1(LazyUnmount, void(const base::FilePath&)); |
| MOCK_METHOD1(GetLoopDeviceMounts, bool( |
| std::multimap<const base::FilePath, const base::FilePath>*)); |
| MOCK_METHOD2(GetMountsBySourcePrefix, bool(const base::FilePath&, |
| std::multimap<const base::FilePath, const base::FilePath>*)); |
| MOCK_METHOD1(IsDirectoryMounted, bool(const base::FilePath&)); |
| MOCK_METHOD2(GetProcessesWithOpenFiles, void(const base::FilePath&, |
| std::vector<ProcessInformation>*)); |
| MOCK_CONST_METHOD4(GetOwnership, |
| bool(const base::FilePath&, uid_t*, gid_t*, bool)); |
| MOCK_CONST_METHOD4(SetOwnership, |
| bool(const base::FilePath&, uid_t, gid_t, bool)); |
| MOCK_CONST_METHOD2(GetPermissions, bool(const base::FilePath&, mode_t*)); |
| MOCK_CONST_METHOD2(SetPermissions, bool(const base::FilePath&, mode_t)); |
| MOCK_CONST_METHOD3(SetGroupAccessible, bool(const base::FilePath&, |
| gid_t group_id, |
| mode_t group_mode)); |
| MOCK_CONST_METHOD1(SetMask, int(int)); |
| MOCK_CONST_METHOD3(GetUserId, bool(const std::string&, uid_t*, gid_t*)); |
| MOCK_CONST_METHOD2(GetGroupId, bool(const std::string&, gid_t*)); |
| MOCK_CONST_METHOD1(AmountOfFreeDiskSpace, int64_t(const base::FilePath&)); |
| MOCK_METHOD2(Symlink, bool(const base::FilePath&, const base::FilePath&)); |
| MOCK_METHOD1(FileExists, bool(const base::FilePath&)); |
| MOCK_METHOD2(GetFileSize, bool(const base::FilePath&, int64_t*)); |
| MOCK_METHOD1(ComputeDirectorySize, int64_t(const base::FilePath&)); |
| MOCK_METHOD2(OpenFile, FILE*(const base::FilePath&, const char*)); |
| MOCK_METHOD3(InitializeFile, |
| void(base::File*, const base::FilePath&, uint32_t)); |
| MOCK_METHOD1(LockFile, bool(int)); |
| MOCK_METHOD1(CloseFile, bool(FILE*)); // NOLINT(readability/function) |
| MOCK_METHOD1(CreateAndOpenTemporaryFile, FILE*(base::FilePath*)); |
| MOCK_METHOD2(Stat, bool(const base::FilePath&, struct stat*)); |
| MOCK_METHOD2(HasExtendedFileAttribute, |
| bool(const base::FilePath&, const std::string&)); |
| MOCK_METHOD2(ListExtendedFileAttributes, |
| bool(const base::FilePath&, std::vector<std::string>*)); |
| MOCK_METHOD3(GetExtendedFileAttributeAsString, |
| bool(const base::FilePath&, const std::string&, std::string*)); |
| MOCK_METHOD4( |
| GetExtendedFileAttribute, |
| bool(const base::FilePath&, const std::string&, char*, ssize_t size)); |
| MOCK_METHOD4( |
| SetExtendedFileAttribute, |
| bool(const base::FilePath&, const std::string&, const char*, size_t)); |
| MOCK_METHOD2(RemoveExtendedFileAttribute, |
| bool(const base::FilePath&, const std::string&)); |
| MOCK_METHOD2(GetExtFileAttributes, bool(const base::FilePath&, int*)); |
| MOCK_METHOD2(SetExtFileAttributes, bool(const base::FilePath&, int)); |
| MOCK_METHOD1(HasNoDumpFileAttribute, bool(const base::FilePath&)); |
| MOCK_METHOD2(ReadFile, bool(const base::FilePath&, brillo::Blob*)); |
| MOCK_METHOD2(ReadFileToString, bool(const base::FilePath&, std::string*)); |
| MOCK_METHOD2(Rename, bool(const base::FilePath&, const base::FilePath&)); |
| MOCK_METHOD2(WriteOpenFile, bool(FILE*, const brillo::Blob&)); |
| MOCK_METHOD2(WriteFile, bool(const base::FilePath&, const brillo::Blob&)); |
| MOCK_METHOD3(WriteFileAtomic, bool(const base::FilePath&, |
| const brillo::Blob&, |
| mode_t mode)); |
| MOCK_METHOD3(WriteFileAtomicDurable, bool(const base::FilePath&, |
| const brillo::Blob&, |
| mode_t mode)); |
| MOCK_METHOD2(WriteStringToFile, bool(const base::FilePath&, |
| const std::string&)); |
| MOCK_METHOD3(WriteStringToFileAtomicDurable, bool(const base::FilePath&, |
| const std::string&, |
| mode_t mode)); |
| MOCK_METHOD3(WriteArrayToFile, bool(const base::FilePath& path, |
| const char* data, |
| size_t size)); |
| MOCK_METHOD1(TouchFileDurable, bool(const base::FilePath& path)); |
| MOCK_CONST_METHOD0(GetCurrentTime, base::Time()); |
| MOCK_METHOD2(Copy, bool(const base::FilePath&, const base::FilePath&)); |
| MOCK_METHOD2(Move, bool(const base::FilePath&, const base::FilePath&)); |
| MOCK_METHOD2(StatVFS, bool(const base::FilePath&, struct statvfs*)); |
| MOCK_METHOD2(ReportFilesystemDetails, bool(const base::FilePath&, |
| const base::FilePath&)); |
| MOCK_METHOD2(FindFilesystemDevice, bool(const base::FilePath&, |
| std::string*)); |
| MOCK_METHOD3(EnumerateDirectoryEntries, bool(const base::FilePath&, bool, |
| std::vector<base::FilePath>*)); |
| MOCK_METHOD2(DeleteFile, bool(const base::FilePath&, bool)); |
| MOCK_METHOD2(DeleteFileDurable, bool(const base::FilePath&, bool)); |
| MOCK_METHOD1(DirectoryExists, bool(const base::FilePath&)); |
| MOCK_METHOD1(CreateDirectory, bool(const base::FilePath&)); |
| MOCK_METHOD0(SetupProcessKeyring, bool()); |
| MOCK_METHOD1(GetDirCryptoKeyState, |
| dircrypto::KeyState(const base::FilePath&)); |
| MOCK_METHOD2(SetDirCryptoKey, bool(const base::FilePath&, |
| const brillo::SecureBlob&)); |
| MOCK_METHOD3(AddDirCryptoKeyToKeyring, bool(const brillo::SecureBlob&, |
| const brillo::SecureBlob&, |
| key_serial_t*)); |
| MOCK_METHOD2(InvalidateDirCryptoKey, bool(key_serial_t, |
| const base::FilePath&)); |
| MOCK_METHOD0(ClearUserKeyring, bool(void)); |
| MOCK_METHOD3(AddEcryptfsAuthToken, |
| bool(const brillo::SecureBlob&, |
| const std::string&, |
| const brillo::SecureBlob&)); |
| MOCK_METHOD3(GetFileEnumerator, FileEnumerator*(const base::FilePath&, |
| bool, |
| int)); |
| MOCK_METHOD0(FirmwareWriteProtected, bool(void)); |
| MOCK_METHOD1(DataSyncFile, bool(const base::FilePath&)); |
| MOCK_METHOD1(SyncFile, bool(const base::FilePath&)); |
| MOCK_METHOD1(SyncDirectory, bool(const base::FilePath&)); |
| MOCK_METHOD0(Sync, void()); |
| MOCK_METHOD0(GetHardwareID, std::string(void)); |
| MOCK_METHOD2(CreateSymbolicLink, |
| bool(const base::FilePath&, const base::FilePath&)); |
| MOCK_METHOD2(ReadLink, bool(const base::FilePath&, base::FilePath*)); |
| MOCK_METHOD4(SetFileTimes, |
| bool(const base::FilePath&, |
| const struct timespec&, |
| const struct timespec&, |
| bool)); |
| MOCK_METHOD4(SendFile, bool(int, int, off_t, size_t)); |
| MOCK_METHOD2(CreateSparseFile, bool(const base::FilePath&, size_t)); |
| MOCK_METHOD1(AttachLoop, base::FilePath(const base::FilePath&)); |
| MOCK_METHOD1(DetachLoop, bool(const base::FilePath&)); |
| MOCK_METHOD0(GetAttachedLoopDevices, std::vector<LoopDevice>()); |
| MOCK_METHOD1(FormatExt4, bool(const base::FilePath&)); |
| |
| MockFileEnumerator* mock_enumerator() { return mock_enumerator_.get(); } |
| |
| private: |
| bool MockGetOwnership(const base::FilePath& path, |
| uid_t* user_id, |
| gid_t* group_id, |
| bool dereference_links) const { |
| *user_id = getuid(); |
| *group_id = getgid(); |
| return true; |
| } |
| |
| bool MockGetPermissions(const base::FilePath& path, mode_t* mode) const { |
| *mode = S_IRWXU | S_IRGRP | S_IXGRP; |
| return true; |
| } |
| |
| bool MockGetUserId(const std::string& user, uid_t* user_id, gid_t* group_id) { |
| *user_id = getuid(); |
| *group_id = getgid(); |
| return true; |
| } |
| |
| bool MockGetGroupId(const std::string& group, gid_t* group_id) { |
| *group_id = getgid(); |
| return true; |
| } |
| |
| FileEnumerator* MockGetFileEnumerator(const base::FilePath& root_path, |
| bool recursive, |
| int file_type) { |
| MockFileEnumerator* e = mock_enumerator_.release(); |
| mock_enumerator_.reset(new NiceMock<MockFileEnumerator>()); |
| mock_enumerator_->entries_.assign(e->entries_.begin(), e->entries_.end()); |
| return e; |
| } |
| std::unique_ptr<MockFileEnumerator> mock_enumerator_; |
| }; |
| |
| } // namespace cryptohome |
| |
| #endif // CRYPTOHOME_MOCK_PLATFORM_H_ |