Merge Chromium + Blink git repositories
[chromium-blink-merge.git] / ppapi / tests / test_flash_file.cc
blobb252940485a68fa1ed81f4e4f38521924ca7e9ed
1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "ppapi/tests/test_flash_file.h"
7 #include <algorithm>
8 #include <vector>
10 #include "ppapi/c/pp_file_info.h"
11 #include "ppapi/c/ppb_file_io.h"
12 #include "ppapi/cpp/module.h"
13 #include "ppapi/cpp/private/flash_file.h"
14 #include "ppapi/tests/testing_instance.h"
15 #include "ppapi/tests/test_utils.h"
17 #if defined(PPAPI_OS_WIN)
18 #include <windows.h>
19 #else
20 #include <errno.h>
21 #include <unistd.h>
22 #endif
24 using pp::flash::FileModuleLocal;
26 namespace {
28 void CloseFileHandle(PP_FileHandle file_handle) {
29 #if defined(PPAPI_OS_WIN)
30 CloseHandle(file_handle);
31 #else
32 close(file_handle);
33 #endif
36 bool WriteFile(PP_FileHandle file_handle, const std::string& contents) {
37 #if defined(PPAPI_OS_WIN)
38 DWORD bytes_written = 0;
39 BOOL result = ::WriteFile(file_handle, contents.c_str(),
40 static_cast<DWORD>(contents.size()),
41 &bytes_written, NULL);
42 return result && bytes_written == static_cast<DWORD>(contents.size());
43 #else
44 ssize_t bytes_written = 0;
45 do {
46 bytes_written = write(file_handle, contents.c_str(), contents.size());
47 } while (bytes_written == -1 && errno == EINTR);
48 return bytes_written == static_cast<ssize_t>(contents.size());
49 #endif
52 bool ReadFile(PP_FileHandle file_handle, std::string* contents) {
53 static const size_t kBufferSize = 1024;
54 char* buffer = new char[kBufferSize];
55 bool result = false;
56 contents->clear();
58 #if defined(PPAPI_OS_WIN)
59 SetFilePointer(file_handle, 0, NULL, FILE_BEGIN);
60 DWORD bytes_read = 0;
61 do {
62 result = !!::ReadFile(file_handle, buffer, kBufferSize, &bytes_read, NULL);
63 if (result && bytes_read > 0)
64 contents->append(buffer, bytes_read);
65 } while (result && bytes_read > 0);
66 #else
67 lseek(file_handle, 0, SEEK_SET);
68 ssize_t bytes_read = 0;
69 do {
70 do {
71 bytes_read = read(file_handle, buffer, kBufferSize);
72 } while (bytes_read == -1 && errno == EINTR);
73 result = bytes_read != -1;
74 if (bytes_read > 0)
75 contents->append(buffer, bytes_read);
76 } while (bytes_read > 0);
77 #endif
79 delete[] buffer;
80 return result;
83 bool DirEntryEqual(FileModuleLocal::DirEntry i,
84 FileModuleLocal::DirEntry j) {
85 return i.name == j.name && i.is_dir == j.is_dir;
88 bool DirEntryLessThan(FileModuleLocal::DirEntry i,
89 FileModuleLocal::DirEntry j) {
90 if (i.name == j.name)
91 return i.is_dir < j.is_dir;
92 return i.name < j.name;
95 } // namespace
97 REGISTER_TEST_CASE(FlashFile);
99 TestFlashFile::TestFlashFile(TestingInstance* instance)
100 : TestCase(instance) {
103 TestFlashFile::~TestFlashFile() {
106 bool TestFlashFile::Init() {
107 return FileModuleLocal::IsAvailable();
110 void TestFlashFile::RunTests(const std::string& filter) {
111 RUN_TEST(OpenFile, filter);
112 RUN_TEST(RenameFile, filter);
113 RUN_TEST(DeleteFileOrDir, filter);
114 RUN_TEST(CreateDir, filter);
115 RUN_TEST(QueryFile, filter);
116 RUN_TEST(GetDirContents, filter);
117 RUN_TEST(CreateTemporaryFile, filter);
120 void TestFlashFile::SetUp() {
121 // Clear out existing test data.
122 FileModuleLocal::DeleteFileOrDir(instance_, std::string(), true);
123 // Make sure that the root directory exists.
124 FileModuleLocal::CreateDir(instance_, std::string());
127 std::string TestFlashFile::TestOpenFile() {
128 SetUp();
129 std::string filename = "abc.txt";
130 PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_,
131 filename,
132 PP_FILEOPENFLAG_WRITE |
133 PP_FILEOPENFLAG_CREATE);
134 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
136 std::string contents = "This is file.";
137 std::string read_contents;
138 ASSERT_TRUE(WriteFile(file_handle, contents));
139 ASSERT_FALSE(ReadFile(file_handle, &read_contents));
140 CloseFileHandle(file_handle);
142 file_handle = FileModuleLocal::OpenFile(instance_,
143 filename,
144 PP_FILEOPENFLAG_READ);
145 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
147 ASSERT_FALSE(WriteFile(file_handle, contents));
148 ASSERT_TRUE(ReadFile(file_handle, &read_contents));
149 ASSERT_EQ(contents, read_contents);
150 CloseFileHandle(file_handle);
152 PASS();
155 std::string TestFlashFile::TestRenameFile() {
156 SetUp();
157 std::string filename = "abc.txt";
158 std::string new_filename = "abc_new.txt";
159 std::string contents = "This is file.";
160 std::string read_contents;
162 PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_,
163 filename,
164 PP_FILEOPENFLAG_WRITE |
165 PP_FILEOPENFLAG_CREATE);
166 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
167 ASSERT_TRUE(WriteFile(file_handle, contents));
168 CloseFileHandle(file_handle);
170 ASSERT_TRUE(FileModuleLocal::RenameFile(instance_, filename, new_filename));
172 file_handle = FileModuleLocal::OpenFile(instance_,
173 new_filename,
174 PP_FILEOPENFLAG_READ);
175 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
176 ASSERT_TRUE(ReadFile(file_handle, &read_contents));
177 ASSERT_EQ(contents, read_contents);
178 CloseFileHandle(file_handle);
180 // Check that the old file no longer exists.
181 PP_FileInfo unused;
182 ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, filename, &unused));
184 PASS();
187 std::string TestFlashFile::TestDeleteFileOrDir() {
188 SetUp();
189 std::string filename = "abc.txt";
190 std::string dirname = "def";
191 std::string contents = "This is file.";
193 // Test file deletion.
194 PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_,
195 filename,
196 PP_FILEOPENFLAG_WRITE |
197 PP_FILEOPENFLAG_CREATE);
198 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
199 ASSERT_TRUE(WriteFile(file_handle, contents));
200 CloseFileHandle(file_handle);
201 ASSERT_TRUE(FileModuleLocal::DeleteFileOrDir(instance_, filename, false));
202 PP_FileInfo unused;
203 ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, filename, &unused));
205 // Test directory deletion.
206 ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname));
207 ASSERT_TRUE(FileModuleLocal::DeleteFileOrDir(instance_, dirname, false));
208 ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, dirname, &unused));
210 // Test recursive directory deletion.
211 ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname));
212 file_handle = FileModuleLocal::OpenFile(
213 instance_, dirname + "/" + filename,
214 PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_CREATE);
215 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
216 ASSERT_TRUE(WriteFile(file_handle, contents));
217 CloseFileHandle(file_handle);
218 ASSERT_FALSE(FileModuleLocal::DeleteFileOrDir(instance_, dirname, false));
219 ASSERT_TRUE(FileModuleLocal::DeleteFileOrDir(instance_, dirname, true));
220 ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, filename, &unused));
222 PASS();
225 std::string TestFlashFile::TestCreateDir() {
226 SetUp();
227 std::string dirname = "abc";
228 PP_FileInfo info;
229 ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, dirname, &info));
230 ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname));
231 ASSERT_TRUE(FileModuleLocal::QueryFile(instance_, dirname, &info));
232 ASSERT_EQ(PP_FILETYPE_DIRECTORY, info.type);
234 PASS();
237 std::string TestFlashFile::TestQueryFile() {
238 std::string filename = "abc.txt";
239 std::string dirname = "def";
240 std::string contents = "This is file.";
241 PP_FileInfo info;
243 // Test querying a file.
244 PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_,
245 filename,
246 PP_FILEOPENFLAG_WRITE |
247 PP_FILEOPENFLAG_CREATE);
248 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
249 ASSERT_TRUE(WriteFile(file_handle, contents));
250 CloseFileHandle(file_handle);
251 ASSERT_TRUE(FileModuleLocal::QueryFile(instance_, filename, &info));
252 ASSERT_EQ(static_cast<size_t>(info.size), contents.size());
253 ASSERT_EQ(PP_FILETYPE_REGULAR, info.type);
254 // TODO(raymes): Test the other fields.
256 // Test querying a directory.
257 ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname));
258 ASSERT_TRUE(FileModuleLocal::QueryFile(instance_, dirname, &info));
259 ASSERT_EQ(PP_FILETYPE_DIRECTORY, info.type);
260 // TODO(raymes): Test the other fields.
262 // Test querying a non-existent file.
263 ASSERT_FALSE(FileModuleLocal::QueryFile(instance_, "xx", &info));
265 PASS();
268 std::string TestFlashFile::TestGetDirContents() {
269 SetUp();
270 std::vector<FileModuleLocal::DirEntry> result;
271 ASSERT_TRUE(FileModuleLocal::GetDirContents(instance_, std::string(),
272 &result));
273 ASSERT_EQ(1, result.size());
274 ASSERT_EQ(result[0].name, "..");
275 ASSERT_EQ(result[0].is_dir, true);
277 std::string filename = "abc.txt";
278 std::string dirname = "def";
279 std::string contents = "This is file.";
280 PP_FileHandle file_handle = FileModuleLocal::OpenFile(instance_,
281 filename,
282 PP_FILEOPENFLAG_WRITE |
283 PP_FILEOPENFLAG_CREATE);
284 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
285 ASSERT_TRUE(WriteFile(file_handle, contents));
286 CloseFileHandle(file_handle);
287 ASSERT_TRUE(FileModuleLocal::CreateDir(instance_, dirname));
289 ASSERT_TRUE(
290 FileModuleLocal::GetDirContents(instance_, std::string(), &result));
291 FileModuleLocal::DirEntry expected[] = { { "..", true }, { filename, false },
292 { dirname, true } };
293 size_t expected_size = sizeof(expected) / sizeof(expected[0]);
295 std::sort(expected, expected + expected_size, DirEntryLessThan);
296 std::sort(result.begin(), result.end(), DirEntryLessThan);
298 ASSERT_EQ(expected_size, result.size());
299 ASSERT_TRUE(std::equal(expected, expected + expected_size, result.begin(),
300 DirEntryEqual));
302 PASS();
305 std::string TestFlashFile::TestCreateTemporaryFile() {
306 SetUp();
307 size_t before_create = 0;
308 ASSERT_SUBTEST_SUCCESS(GetItemCountUnderModuleLocalRoot(&before_create));
310 PP_FileHandle file_handle = FileModuleLocal::CreateTemporaryFile(instance_);
311 ASSERT_NE(PP_kInvalidFileHandle, file_handle);
313 std::string contents = "This is a temp file.";
314 ASSERT_TRUE(WriteFile(file_handle, contents));
315 std::string read_contents;
316 ASSERT_TRUE(ReadFile(file_handle, &read_contents));
317 ASSERT_EQ(contents, read_contents);
319 CloseFileHandle(file_handle);
321 size_t after_close = 0;
322 ASSERT_SUBTEST_SUCCESS(GetItemCountUnderModuleLocalRoot(&after_close));
323 ASSERT_EQ(before_create, after_close);
325 PASS();
328 std::string TestFlashFile::GetItemCountUnderModuleLocalRoot(
329 size_t* item_count) {
330 std::vector<FileModuleLocal::DirEntry> contents;
331 ASSERT_TRUE(
332 FileModuleLocal::GetDirContents(instance_, std::string(), &contents));
333 *item_count = contents.size();
334 PASS();