15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved. 25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be 35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file. 45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/tests/test_file_io.h" 65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include <errno.h> 8c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include <fcntl.h> 97d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles)#include <stdio.h> 105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <string.h> 11c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include <sys/stat.h> 12c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include <sys/types.h> 135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include <vector> 155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/c/dev/ppb_testing_dev.h" 175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/c/pp_errors.h" 185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/c/ppb_file_io.h" 19c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include "ppapi/c/private/pp_file_handle.h" 205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/c/trusted/ppb_file_io_trusted.h" 215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/cpp/file_io.h" 225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/cpp/file_ref.h" 235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/cpp/file_system.h" 245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/cpp/instance.h" 255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/cpp/module.h" 26c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include "ppapi/cpp/private/file_io_private.h" 27c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#include "ppapi/cpp/private/pass_file_handle.h" 285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/tests/test_utils.h" 295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#include "ppapi/tests/testing_instance.h" 305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 31c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#if defined(PPAPI_OS_WIN) 32c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# include <io.h> 33c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# include <windows.h> 34c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)// TODO(hamaji): Use standard windows APIs instead of compatibility layer? 35c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# define lseek _lseek 36c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# define read _read 37c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# define write _write 38c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# define ssize_t int 39c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#else 40c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# include <sys/mman.h> 41c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)# include <unistd.h> 42c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#endif 43c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)REGISTER_TEST_CASE(FileIO); 455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace { 475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string ReportMismatch(const std::string& method_name, 495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const std::string& returned_result, 505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const std::string& expected_result) { 515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return method_name + " returned '" + returned_result + "'; '" + 525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) expected_result + "' expected."; 535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string ReportOpenError(int32_t open_flags) { 565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) static const char* kFlagNames[] = { 575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "PP_FILEOPENFLAG_READ", 585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "PP_FILEOPENFLAG_WRITE", 595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "PP_FILEOPENFLAG_CREATE", 605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "PP_FILEOPENFLAG_TRUNCATE", 615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "PP_FILEOPENFLAG_EXCLUSIVE" 625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) }; 635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string result = "FileIO:Open had unexpected behavior with flags: "; 655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool first_flag = true; 665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (int32_t mask = 1, index = 0; mask <= PP_FILEOPENFLAG_EXCLUSIVE; 675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) mask <<= 1, ++index) { 685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (mask & open_flags) { 695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (first_flag) { 705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) first_flag = false; 715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result += " | "; 735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result += kFlagNames[index]; 755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (first_flag) 785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result += "[None]"; 795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int32_t ReadEntireFile(PP_Instance instance, 845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO* file_io, 855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t offset, 86c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) std::string* data, 87c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CallbackType callback_type) { 88c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance, callback_type); 895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) char buf[256]; 905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t read_offset = offset; 915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (;;) { 93c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult( 94c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) file_io->Read(read_offset, buf, sizeof(buf), callback.GetCallback())); 95c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback.result() < 0) 96c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return callback.result(); 97c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback.result() == 0) 985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) break; 99c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) read_offset += callback.result(); 100c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) data->append(buf, callback.result()); 1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return PP_OK; 1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)int32_t ReadToArrayEntireFile(PP_Instance instance, 1072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pp::FileIO* file_io, 1082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int32_t offset, 1092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) std::string* data, 110c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CallbackType callback_type) { 1112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) TestCompletionCallbackWithOutput< std::vector<char> > callback( 112c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) instance, callback_type); 1132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) for (;;) { 115c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io->Read(offset, 256, callback.GetCallback())); 1162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) int32_t rv = callback.result(); 1172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (rv < 0) 1182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) return rv; 1192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) if (rv == 0) 1202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) break; 121c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) const std::vector<char>& output = callback.output(); 122c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) assert(rv == static_cast<int32_t>(output.size())); 1232a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) offset += rv; 124c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) data->append(output.begin(), output.end()); 1252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) } 1262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 1272a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) return PP_OK; 1282a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 1292a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 130a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles)bool ReadEntireFileFromFileHandle(int fd, std::string* data) { 131a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (lseek(fd, 0, SEEK_SET) < 0) 132a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return false; 133a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) data->clear(); 134a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 135a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) int ret; 136a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) do { 137a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) char buf[8192]; 138a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ret = read(fd, buf, sizeof(buf)); 139a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (ret > 0) 140a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) data->append(buf, ret); 141a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) } while (ret > 0); 142a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ret == 0; 143a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles)} 144a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)int32_t WriteEntireBuffer(PP_Instance instance, 1465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO* file_io, 1475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t offset, 148c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) const std::string& data, 149c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CallbackType callback_type) { 150c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance, callback_type); 1515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t write_offset = offset; 1525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const char* buf = data.c_str(); 1535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t size = data.size(); 1545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) while (write_offset < offset + size) { 156c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io->Write(write_offset, 157c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &buf[write_offset - offset], 158c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) size - write_offset + offset, 159c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 160c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback.result() < 0) 161c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return callback.result(); 162c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback.result() == 0) 1635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return PP_ERROR_FAILED; 164c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) write_offset += callback.result(); 1655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 1665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return PP_OK; 1685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} // namespace 1715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)bool TestFileIO::Init() { 1735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return CheckTestingInterface() && EnsureRunningOverHTTP(); 1745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)void TestFileIO::RunTests(const std::string& filter) { 177c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, Open, filter); 178c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, OpenDirectory, filter); 179c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, ReadWriteSetLength, filter); 180c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, ReadToArrayWriteSetLength, filter); 181c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, TouchQuery, filter); 182c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, AbortCalls, filter); 183c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, ParallelReads, filter); 184c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, ParallelWrites, filter); 185c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, NotAllowMixedReadWrite, filter); 186c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, WillWriteWillSetLength, filter); 187c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, RequestOSFileHandle, filter); 188868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, RequestOSFileHandleWithOpenExclusive, filter); 189a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) RUN_CALLBACK_TEST(TestFileIO, Mmap, filter); 1905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // TODO(viettrungluu): add tests: 1925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // - that PP_ERROR_PENDING is correctly returned 1935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // - that operations respect the file open modes (flags) 1945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 1955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestOpen() { 197c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 1985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 2005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_open"); 201c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 202c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 203c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 204c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 2055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string result; 2075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_READ, 2105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DONT_CREATE_IF_DOESNT_EXIST | OPEN_IF_EXISTS | DONT_TRUNCATE_IF_EXISTS); 2115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Test the behavior of the power set of 2155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // { PP_FILEOPENFLAG_CREATE, 2165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // PP_FILEOPENFLAG_TRUNCATE, 2175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // PP_FILEOPENFLAG_EXCLUSIVE }. 2185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // First of all, none of them are specified. 2205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE, 2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DONT_CREATE_IF_DOESNT_EXIST | OPEN_IF_EXISTS | DONT_TRUNCATE_IF_EXISTS); 2245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_CREATE, 2305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CREATE_IF_DOESNT_EXIST | OPEN_IF_EXISTS | DONT_TRUNCATE_IF_EXISTS); 2315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_EXCLUSIVE, 2375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DONT_CREATE_IF_DOESNT_EXIST | OPEN_IF_EXISTS | DONT_TRUNCATE_IF_EXISTS); 2385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_TRUNCATE, 2445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DONT_CREATE_IF_DOESNT_EXIST | OPEN_IF_EXISTS | TRUNCATE_IF_EXISTS); 2455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_CREATE | 2515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_EXCLUSIVE, 2525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CREATE_IF_DOESNT_EXIST | DONT_OPEN_IF_EXISTS | DONT_TRUNCATE_IF_EXISTS); 2535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_CREATE | PP_FILEOPENFLAG_TRUNCATE, 2595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CREATE_IF_DOESNT_EXIST | OPEN_IF_EXISTS | TRUNCATE_IF_EXISTS); 2605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_EXCLUSIVE | 2665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE, 2675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) DONT_CREATE_IF_DOESNT_EXIST | OPEN_IF_EXISTS | TRUNCATE_IF_EXISTS); 2685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | PP_FILEOPENFLAG_CREATE | 2745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_EXCLUSIVE | PP_FILEOPENFLAG_TRUNCATE, 2755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) CREATE_IF_DOESNT_EXIST | DONT_OPEN_IF_EXISTS | DONT_TRUNCATE_IF_EXISTS); 2765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Invalid combination: PP_FILEOPENFLAG_TRUNCATE without 2805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // PP_FILEOPENFLAG_WRITE. 2815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) result = MatchOpenExpectations( 2825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) &file_system, 2835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FILEOPENFLAG_READ | PP_FILEOPENFLAG_TRUNCATE, 2845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) INVALID_FLAG_COMBINATION); 2855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!result.empty()) 2865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return result; 2875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 2895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 2905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 2912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)std::string TestFileIO::TestOpenDirectory() { 292c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 2932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 2942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 295c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 296c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 297c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 2982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 2992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Make a directory. 3002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pp::FileRef dir_ref(file_system, "/test_dir_open_directory"); 301c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(dir_ref.MakeDirectory(callback.GetCallback())); 302c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 303c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 3042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 3052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Open the directory. This is expected to fail since directories cannot be 3062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // opened. 3072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pp::FileIO file_io(instance_); 308c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(dir_ref, PP_FILEOPENFLAG_READ, 309c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 310c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 311c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_ERROR_NOTAFILE, callback.result()); 3122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 3132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) PASS(); 3142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 3152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 3165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestReadWriteSetLength() { 317c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 3185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 3205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_read_write_setlength"); 321c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 322c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 323c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 3245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 326c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 327c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 328c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 329c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_READ | 330c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 331c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 332c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 333c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 3345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Write something to the file. 336c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int32_t rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 0, 337c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) "test_test", callback_type()); 338c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 3395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 340c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Attempt to read a negative number of bytes; it should fail. 3415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) char buf[256]; 342c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Read(0, 343c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) buf, 344c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) -1, 345c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 346c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 347c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_ERROR_FAILED, callback.result()); 3485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Read the entire file. 3505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string read_buffer; 351c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, &read_buffer, 352c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 353c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 354c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test_test"), read_buffer); 3555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Truncate the file. 357c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.SetLength(4, callback.GetCallback())); 358c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 359c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 3605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Check the file contents. 3625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) read_buffer.clear(); 363c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, &read_buffer, 364c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 365c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 366c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test"), read_buffer); 3675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Try to read past the end of the file. 3695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) read_buffer.clear(); 370c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 100, &read_buffer, 371c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 372c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 373c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(read_buffer.empty()); 3745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Write past the end of the file. The file should be zero-padded. 376c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 8, "test", 377c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 378c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 3795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Check the contents of the file. 3815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) read_buffer.clear(); 382c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, &read_buffer, 383c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 384c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 385c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test\0\0\0\0test", 12), read_buffer); 3865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Extend the file. 388c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.SetLength(16, callback.GetCallback())); 389c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 390c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 3915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Check the contents of the file. 3935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) read_buffer.clear(); 394c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, &read_buffer, 395c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 396c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 397c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test\0\0\0\0test\0\0\0\0", 16), read_buffer); 3985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 3995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Write in the middle of the file. 400c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 4, "test", 401c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 402c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 4035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Check the contents of the file. 4055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) read_buffer.clear(); 406c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, &read_buffer, 407c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 408c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 409c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("testtesttest\0\0\0\0", 16), read_buffer); 4105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Read from the middle of the file. 4125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) read_buffer.clear(); 413c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 4, &read_buffer, 414c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 415c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 416c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("testtest\0\0\0\0", 12), read_buffer); 4175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4187d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) // Append to the end of the file. 4197d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) pp::FileIO file_io2(instance_); 4207d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) callback.WaitForResult(file_io2.Open(file_ref, 4217d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) PP_FILEOPENFLAG_CREATE | 4227d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) PP_FILEOPENFLAG_READ | 4237d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) PP_FILEOPENFLAG_APPEND, 4247d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) callback.GetCallback())); 4257d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) rv = WriteEntireBuffer(instance_->pp_instance(), &file_io2, 0, "appended", 4267d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) callback_type()); 4277d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) ASSERT_EQ(PP_OK, rv); 4287d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) read_buffer.clear(); 4297d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io2, 0, &read_buffer, 4307d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) callback_type()); 4317d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) ASSERT_EQ(PP_OK, rv); 4327d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) ASSERT_EQ(std::string("testtesttest\0\0\0\0appended", 24), read_buffer); 4337d4cd473f85ac64c3747c96c277f9e506a0d2246Torne (Richard Coles) 4345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 4355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 4365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 4372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// This is basically a copy of TestReadWriteSetLength, but with the new Read 4382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// API. With this test case, we can make sure the two Read's have the same 4392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// behavior. 4402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)std::string TestFileIO::TestReadToArrayWriteSetLength() { 441c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback_type() == PP_BLOCKING) { 442c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // This test does not make sense for blocking callbacks. 443c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PASS(); 444c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) } 445c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 4462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 4482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pp::FileRef file_ref(file_system, "/file_read_write_setlength"); 449c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 450c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 451c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 4522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) pp::FileIO file_io(instance_); 454c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 455c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 456c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 457c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_READ | 458c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 459c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 460c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 461c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 4622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Write something to the file. 464c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int32_t rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 0, 465c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) "test_test", callback_type()); 466c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 4672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) TestCompletionCallbackWithOutput< std::vector<char> > callback2( 469c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) instance_->pp_instance(), callback_type()); 470c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Attempt to read a negative number of bytes; it should fail. 471c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback2.WaitForResult(file_io.Read(0, -1, callback2.GetCallback())); 4722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback2); 473c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_ERROR_FAILED, callback2.result()); 4742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Read the entire file. 4762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) std::string read_buffer; 4772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) read_buffer.reserve(10); 4782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = ReadToArrayEntireFile(instance_->pp_instance(), &file_io, 0, 479c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 480c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 481c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test_test"), read_buffer); 4822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Truncate the file. 484c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.SetLength(4, callback.GetCallback())); 485c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 486c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 4872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Check the file contents. 4892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) read_buffer.clear(); 4902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = ReadToArrayEntireFile(instance_->pp_instance(), &file_io, 0, 491c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 492c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 493c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test"), read_buffer); 4942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 4952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Try to read past the end of the file. 4962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) read_buffer.clear(); 4972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = ReadToArrayEntireFile(instance_->pp_instance(), &file_io, 100, 498c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 499c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 500c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(read_buffer.empty()); 5012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Write past the end of the file. The file should be zero-padded. 503c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 8, "test", 504c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 505c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 5062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Check the contents of the file. 5082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) read_buffer.clear(); 5092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = ReadToArrayEntireFile(instance_->pp_instance(), &file_io, 0, 510c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 511c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 512c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test\0\0\0\0test", 12), read_buffer); 5132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Extend the file. 515c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.SetLength(16, callback.GetCallback())); 516c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 517c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 5182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Check the contents of the file. 5202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) read_buffer.clear(); 5212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = ReadToArrayEntireFile(instance_->pp_instance(), &file_io, 0, 522c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 523c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 524c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test\0\0\0\0test\0\0\0\0", 16), read_buffer); 5252a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5262a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Write in the middle of the file. 527c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 4, "test", 528c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 529c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 5302a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5312a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Check the contents of the file. 5322a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) read_buffer.clear(); 5332a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = ReadToArrayEntireFile(instance_->pp_instance(), &file_io, 0, 534c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 535c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 536c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("testtesttest\0\0\0\0", 16), read_buffer); 5372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) // Read from the middle of the file. 5392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) read_buffer.clear(); 5402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = ReadToArrayEntireFile(instance_->pp_instance(), &file_io, 4, 541c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 542c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 543c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("testtest\0\0\0\0", 12), read_buffer); 5442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) PASS(); 5462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)} 5472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) 5485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestTouchQuery() { 549c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 5505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 552c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 553c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 554c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 5555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_touch"); 5575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 558c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 559c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 560c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 561c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 562c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 563c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 564c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 5655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Write some data to have a non-zero file size. 567c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Write(0, "test", 4, callback.GetCallback())); 568c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 569c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(4, callback.result()); 5705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 571a36e5920737c6adbddd3e43b760e5de8431db6e0Torne (Richard Coles) const PP_Time last_access_time = 123 * 24 * 3600.0; 5724311e82a78ceafbe0585f51d4c8a86df9f21aa0dBen Murdoch // last_modified_time's granularity is 2 seconds 5734311e82a78ceafbe0585f51d4c8a86df9f21aa0dBen Murdoch // NOTE: In NaCl on Windows, NaClDescIO uses _fstat64 to retrieve file info. 5744311e82a78ceafbe0585f51d4c8a86df9f21aa0dBen Murdoch // This function returns strange values for very small time values (near the 5754311e82a78ceafbe0585f51d4c8a86df9f21aa0dBen Murdoch // Unix Epoch). For a value like 246.0, it returns -1. For larger values, it 5764311e82a78ceafbe0585f51d4c8a86df9f21aa0dBen Murdoch // returns values that are exactly an hour less. The value below is handled 5774311e82a78ceafbe0585f51d4c8a86df9f21aa0dBen Murdoch // correctly, and is only 100 days after the start of Unix time. 5784311e82a78ceafbe0585f51d4c8a86df9f21aa0dBen Murdoch const PP_Time last_modified_time = 100 * 24 * 3600.0; 579c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Touch(last_access_time, last_modified_time, 580c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 581c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 582c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 5835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FileInfo info; 585c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Query(&info, callback.GetCallback())); 586c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 587c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 5885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if ((info.size != 4) || 5905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (info.type != PP_FILETYPE_REGULAR) || 5915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (info.system_type != PP_FILESYSTEMTYPE_LOCALTEMPORARY) || 5925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (info.last_access_time != last_access_time) || 5935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) (info.last_modified_time != last_modified_time)) 5945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return "FileIO::Query() has returned bad data."; 5955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 5965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Call |Query()| again, to make sure it works a second time. 597c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Query(&info, callback.GetCallback())); 598c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 599c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 6005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 6025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 6035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestAbortCalls() { 605c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 6065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 6085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_abort_calls"); 609c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 610c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 611c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 612c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 613c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int32_t rv = PP_ERROR_FAILED; 614c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // First, create a file on which to do ops. 6155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 6165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 617c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult( 618c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) file_io.Open(file_ref, 619c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | PP_FILEOPENFLAG_WRITE, 620c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 621c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 622c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 6235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // N.B.: Should write at least 3 bytes. 625c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 0, 626c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) "foobarbazquux", callback_type()); 627c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 6285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Abort |Open()|. 6315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 632c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = pp::FileIO(instance_) 633c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) .Open(file_ref, PP_FILEOPENFLAG_READ, callback.GetCallback()); 6345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 635c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForAbortResult(rv); 636c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 6375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Abort |Query()|. 6395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 6405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FileInfo info = { 0 }; 641c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Save a copy and make sure |info| doesn't get written to if it is aborted. 642c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FileInfo info_copy; 643c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) memcpy(&info_copy, &info, sizeof(info)); 6445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 6455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 646c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, PP_FILEOPENFLAG_READ, 647c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 648c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 649c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 650c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 6512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = file_io.Query(&info, callback.GetCallback()); 6525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } // Destroy |file_io|. 653c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(rv); 654c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 655c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback_type() == PP_BLOCKING) { 656c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(callback.result(), PP_OK); 657c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // The operation completed synchronously, so |info| should have changed. 658c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_NE(0, memcmp(&info_copy, &info, sizeof(info))); 659c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) } else { 660c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(callback.result(), PP_ERROR_ABORTED); 661c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(0, memcmp(&info_copy, &info, sizeof(info))); 6625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Abort |Touch()|. 6665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 6675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 6685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 669c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, PP_FILEOPENFLAG_WRITE, 670c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 671c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 672c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 673c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 6742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = file_io.Touch(0, 0, callback.GetCallback()); 6755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } // Destroy |file_io|. 676c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForAbortResult(rv); 677c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 6785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 6795821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 6805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Abort |Read()|. 6815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 6825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) char buf[3] = { 0 }; 6835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 6845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 685c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, PP_FILEOPENFLAG_READ, 686c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 687c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 688c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 689c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 6902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = file_io.Read(0, buf, sizeof(buf), callback.GetCallback()); 6915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } // Destroy |file_io|. 692c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Save a copy to make sure buf isn't written to in the async case. 693c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) char buf_copy[3]; 694c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) memcpy(&buf_copy, &buf, sizeof(buf)); 695c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(rv); 696c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 697c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback_type() == PP_BLOCKING) { 698c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(callback.result(), sizeof(buf)); 699c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) } else { 700c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(callback.result(), PP_ERROR_ABORTED); 701c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(0, memcmp(&buf_copy, &buf, sizeof(buf))); 7025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Abort |Write()|. 7065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 7075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) char buf[3] = { 0 }; 7085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 7095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 710c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, PP_FILEOPENFLAG_WRITE, 711c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 712c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 713c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 714c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 7152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = file_io.Write(0, buf, sizeof(buf), callback.GetCallback()); 7165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } // Destroy |file_io|. 717c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(rv); 718c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 719c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback_type() == PP_BLOCKING) 720c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(callback.result(), sizeof(buf)); 721c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) else 722c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(callback.result(), PP_ERROR_ABORTED); 7235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Abort |SetLength()|. 7265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 7275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 7285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 729c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, PP_FILEOPENFLAG_READ, 730c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 731c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 732c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 733c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 7342a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = file_io.SetLength(3, callback.GetCallback()); 7355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } // Destroy |file_io|. 736c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForAbortResult(rv); 737c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 7385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 740c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Abort |Flush|. 7415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 7425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 7435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 744c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, PP_FILEOPENFLAG_WRITE, 745c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 746c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 747c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 748c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 7492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv = file_io.Flush(callback.GetCallback()); 7505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } // Destroy |file_io|. 751c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForAbortResult(rv); 752c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 7535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 7545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 7565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 7575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestParallelReads() { 759c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 7605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 7615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_parallel_reads"); 762c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 763c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 764c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 7655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 767c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 768c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 769c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 770c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_READ | 771c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 772c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 773c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 774c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 7755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Set up testing contents. 777c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int32_t rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 0, 778c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) "abcdefghijkl", callback_type()); 779c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 7805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 7815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Parallel read operations. 7825821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const char* border = "__border__"; 7835821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const int32_t border_size = strlen(border); 7845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 785c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback_1(instance_->pp_instance(), callback_type()); 7865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t read_offset_1 = 0; 7875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t size_1 = 3; 7885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::vector<char> extended_buf_1(border_size * 2 + size_1); 7895821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) char* buf_1 = &extended_buf_1[border_size]; 7905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) memcpy(&extended_buf_1[0], border, border_size); 7915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) memcpy(buf_1 + size_1, border, border_size); 7925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 793c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback_2(instance_->pp_instance(), callback_type()); 7945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t read_offset_2 = size_1; 7955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t size_2 = 9; 7965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::vector<char> extended_buf_2(border_size * 2 + size_2); 7975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) char* buf_2 = &extended_buf_2[border_size]; 7985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) memcpy(&extended_buf_2[0], border, border_size); 7995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) memcpy(buf_2 + size_2, border, border_size); 8005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t rv_1 = PP_OK; 8025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t rv_2 = PP_OK; 8035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) while (size_1 >= 0 && size_2 >= 0 && size_1 + size_2 > 0) { 8045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_1 > 0) { 8052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv_1 = file_io.Read(read_offset_1, buf_1, size_1, 8062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_1.GetCallback()); 8075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_2 > 0) { 8092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv_2 = file_io.Read(read_offset_2, buf_2, size_2, 8102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_2.GetCallback()); 8115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_1 > 0) { 813c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_1.WaitForResult(rv_1); 814c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_1); 815c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(callback_1.result() > 0); 816c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) read_offset_1 += callback_1.result(); 817c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) buf_1 += callback_1.result(); 818c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) size_1 -= callback_1.result(); 8195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_2 > 0) { 822c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.WaitForResult(rv_2); 823c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_2); 824c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(callback_2.result() > 0); 825c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) read_offset_2 += callback_2.result(); 826c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) buf_2 += callback_2.result(); 827c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) size_2 -= callback_2.result(); 8285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 831c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // If |size_1| or |size_2| is not 0, we have invoked wrong callback(s). 832c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(0, size_1); 833c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(0, size_2); 8345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Make sure every read operation writes into the correct buffer. 8365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const char expected_result_1[] = "__border__abc__border__"; 8375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const char expected_result_2[] = "__border__defghijkl__border__"; 838c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(strncmp(&extended_buf_1[0], expected_result_1, 839c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) strlen(expected_result_1)) == 0); 840c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(strncmp(&extended_buf_2[0], expected_result_2, 841c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) strlen(expected_result_2)) == 0); 8425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 8435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 8445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestParallelWrites() { 846c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 8475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 8485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_parallel_writes"); 849c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 850c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 851c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 8525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 854c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 855c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 856c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 857c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_READ | 858c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 859c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 860c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 861c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 8625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Parallel write operations. 864c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback_1(instance_->pp_instance(), callback_type()); 8655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t write_offset_1 = 0; 8665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const char* buf_1 = "abc"; 8675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t size_1 = strlen(buf_1); 8685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 869c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback_2(instance_->pp_instance(), callback_type()); 8705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t write_offset_2 = size_1; 8715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const char* buf_2 = "defghijkl"; 8725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t size_2 = strlen(buf_2); 8735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t rv_1 = PP_OK; 8755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t rv_2 = PP_OK; 8765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) while (size_1 >= 0 && size_2 >= 0 && size_1 + size_2 > 0) { 8775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_1 > 0) { 8782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv_1 = file_io.Write(write_offset_1, buf_1, size_1, 8792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_1.GetCallback()); 8805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_2 > 0) { 8822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv_2 = file_io.Write(write_offset_2, buf_2, size_2, 8832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_2.GetCallback()); 8845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8855821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_1 > 0) { 887c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_1.WaitForResult(rv_1); 888c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_1); 889c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(callback_1.result() > 0); 890c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) write_offset_1 += callback_1.result(); 891c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) buf_1 += callback_1.result(); 892c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) size_1 -= callback_1.result(); 8935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 8945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 8955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (size_2 > 0) { 896c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.WaitForResult(rv_2); 897c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_2); 898c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(callback_2.result() > 0); 899c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) write_offset_2 += callback_2.result(); 900c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) buf_2 += callback_2.result(); 901c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) size_2 -= callback_2.result(); 9025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 9035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 9045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 905c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // If |size_1| or |size_2| is not 0, we have invoked wrong callback(s). 906c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(0, size_1); 907c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(0, size_2); 9085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Check the file contents. 9105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string read_buffer; 911c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int32_t rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, 912c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) &read_buffer, callback_type()); 913c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 914c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("abcdefghijkl"), read_buffer); 9155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 9175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 9185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestNotAllowMixedReadWrite() { 920c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (callback_type() == PP_BLOCKING) { 921c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // This test does not make sense for blocking callbacks. 922c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PASS(); 923c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) } 924c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 9255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 9275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_not_allow_mixed_read_write"); 928c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 929c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 930c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 9315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 933c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 934c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 935c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 936c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_READ | 937c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 938c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 939c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 940c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 941c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 942c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback_1(instance_->pp_instance(), PP_REQUIRED); 9435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t write_offset_1 = 0; 9445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const char* buf_1 = "mnopqrstuvw"; 9455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t rv_1 = file_io.Write(write_offset_1, buf_1, strlen(buf_1), 9462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_1.GetCallback()); 947c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK_COMPLETIONPENDING, rv_1); 9485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 949c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback_2(instance_->pp_instance(), callback_type()); 9505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t read_offset_2 = 4; 9515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) char buf_2[3]; 952c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.WaitForResult(file_io.Read(read_offset_2, buf_2, sizeof(buf_2), 953c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.GetCallback())); 954c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_2); 955c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_ERROR_INPROGRESS, callback_2.result()); 956c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_1.WaitForResult(rv_1); 957c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_1); 9585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Cannot query while a write is pending. 9602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv_1 = file_io.Write(write_offset_1, buf_1, strlen(buf_1), 9612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_1.GetCallback()); 9625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ(PP_OK_COMPLETIONPENDING, rv_1); 9635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FileInfo info; 964c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.WaitForResult(file_io.Query(&info, callback_2.GetCallback())); 965c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_2); 966c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_ERROR_INPROGRESS, callback_2.result()); 967c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_1.WaitForResult(rv_1); 968c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_1); 9695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Cannot touch while a write is pending. 9712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv_1 = file_io.Write(write_offset_1, buf_1, strlen(buf_1), 9722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_1.GetCallback()); 9735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ(PP_OK_COMPLETIONPENDING, rv_1); 974c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.WaitForResult(file_io.Touch(1234.0, 5678.0, 975c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.GetCallback())); 976c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_2); 977c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_ERROR_INPROGRESS, callback_2.result()); 978c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_1.WaitForResult(rv_1); 979c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_1); 9805821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9815821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Cannot set length while a write is pending. 9822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) rv_1 = file_io.Write(write_offset_1, buf_1, strlen(buf_1), 9832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) callback_1.GetCallback()); 9845821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) ASSERT_EQ(PP_OK_COMPLETIONPENDING, rv_1); 985c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_2.WaitForResult(file_io.SetLength(123, callback_2.GetCallback())); 986c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_2); 987c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_ERROR_INPROGRESS, callback_2.result()); 988c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_1.WaitForResult(rv_1); 989c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback_1); 9905821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9915821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 9925821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 9935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::TestWillWriteWillSetLength() { 995c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 9965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 9975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 9985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_will_write"); 999c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 1000c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1001c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 10025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO file_io(instance_); 1004c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 1005c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 1006c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 1007c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_READ | 1008c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 1009c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 1010c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1011c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 10125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const PPB_FileIOTrusted* trusted = static_cast<const PPB_FileIOTrusted*>( 10145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::Module::Get()->GetBrowserInterface(PPB_FILEIOTRUSTED_INTERFACE)); 1015c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(trusted); 10165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Get file descriptor. This is only supported in-process for now, so don't 10185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // test out of process. 10195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) const PPB_Testing_Dev* testing_interface = GetTestingInterface(); 10205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (testing_interface && !testing_interface->IsOutOfProcess()) { 10215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) int32_t fd = trusted->GetOSFileDescriptor(file_io.pp_resource()); 1022c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(fd >= 0); 10235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 10245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Calling WillWrite. 1026c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(trusted->WillWrite( 10275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) file_io.pp_resource(), 0, 9, 1028c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback().pp_completion_callback())); 1029c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1030c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(9, callback.result()); 10315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Writing the actual data. 1033c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int32_t rv = WriteEntireBuffer(instance_->pp_instance(), &file_io, 0, 1034c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) "test_test", callback_type()); 1035c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 10365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string read_buffer; 1038c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, &read_buffer, 1039c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 1040c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 1041c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test_test"), read_buffer); 10425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Calling WillSetLength. 1044c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(trusted->WillSetLength( 10455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) file_io.pp_resource(), 4, 1046c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback().pp_completion_callback())); 1047c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1048c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 10495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Calling actual SetLength. 1051c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.SetLength(4, callback.GetCallback())); 1052c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1053c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 10545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 10555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) read_buffer.clear(); 1056c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) rv = ReadEntireFile(instance_->pp_instance(), &file_io, 0, &read_buffer, 1057c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback_type()); 1058c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 1059c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(std::string("test"), read_buffer); 1060c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1061c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PASS(); 1062c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)} 1063c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1064c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)std::string TestFileIO::TestRequestOSFileHandle() { 1065c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 1066c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1067c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 1068c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) pp::FileRef file_ref(file_system, "/file_os_fd"); 1069c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1070c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 1071c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1072c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1073c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) pp::FileIO_Private file_io(instance_); 1074c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 1075c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 1076c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 1077c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_READ | 1078c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 1079c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 1080c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1081c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1082c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallbackWithOutput<pp::PassFileHandle> output_callback( 1083c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) instance_->pp_instance(), callback_type()); 1084c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) output_callback.WaitForResult( 1085c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) file_io.RequestOSFileHandle(output_callback.GetCallback())); 1086c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FileHandle handle = output_callback.output().Release(); 1087c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, output_callback.result()); 1088c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1089c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (handle == PP_kInvalidFileHandle) 1090c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return "FileIO::RequestOSFileHandle() returned a bad file handle."; 1091c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#if defined(PPAPI_OS_WIN) 1092c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int fd = _open_osfhandle(reinterpret_cast<intptr_t>(handle), 1093c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) _O_RDWR | _O_BINARY); 1094c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#else 1095c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int fd = handle; 1096c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#endif 1097c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (fd < 0) 1098c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return "FileIO::RequestOSFileHandle() returned a bad file descriptor."; 1099c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1100c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Check write(2) for the native FD. 1101c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) const std::string msg = "foobar"; 1102c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ssize_t cnt = write(fd, msg.data(), msg.size()); 1103c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (cnt < 0) 1104c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("write for native FD returned error", errno); 1105c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (cnt != static_cast<ssize_t>(msg.size())) 1106c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("write for native FD count mismatch", cnt); 1107c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1108c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Check lseek(2) for the native FD. 1109c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) off_t off = lseek(fd, 0, SEEK_CUR); 1110c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (off == static_cast<off_t>(-1)) 1111c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("lseek for native FD returned error", errno); 1112c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (off != static_cast<off_t>(msg.size())) 1113c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("lseek for native FD offset mismatch", off); 1114c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1115c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) off = lseek(fd, 0, SEEK_SET); 1116c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (off == static_cast<off_t>(-1)) 1117c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("lseek for native FD returned error", errno); 1118c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (off != 0) 1119c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("lseek for native FD offset mismatch", off); 1120c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1121c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Check read(2) for the native FD. 1122c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) std::string buf(msg.size(), '\0'); 1123c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) cnt = read(fd, &buf[0], msg.size()); 1124c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (cnt < 0) 1125c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("read for native FD returned error", errno); 1126c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (cnt != static_cast<ssize_t>(msg.size())) 1127c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("read for native FD count mismatch", cnt); 1128c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if (msg != buf) 1129c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportMismatch("read for native FD", buf, msg); 1130a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) PASS(); 1131a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles)} 1132c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1133868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)// Calling RequestOSFileHandle with the FileIO that is opened with 1134868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)// PP_FILEOPENFLAG_EXCLUSIVE used to cause NaCl module to crash while loading. 1135868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)// This is a regression test for crbug.com/243241. 1136868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)std::string TestFileIO::TestRequestOSFileHandleWithOpenExclusive() { 1137868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 1138868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 1139868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 1140868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) pp::FileRef file_ref(file_system, "/file_os_fd2"); 1141868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 1142868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 1143868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1144868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 11452385ea399aae016c0806a4f9ef3c9cfe3d2a39dfBen Murdoch // Open with PP_FILEOPENFLAG_CREATE and PP_FILEOPENFLAG_EXCLUSIVE will fail 11462385ea399aae016c0806a4f9ef3c9cfe3d2a39dfBen Murdoch // if the file already exists. Delete it here to make sure it does not. 11472385ea399aae016c0806a4f9ef3c9cfe3d2a39dfBen Murdoch callback.WaitForResult(file_ref.Delete(callback.GetCallback())); 11482385ea399aae016c0806a4f9ef3c9cfe3d2a39dfBen Murdoch 1149868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) pp::FileIO_Private file_io(instance_); 1150868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 1151868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) PP_FILEOPENFLAG_CREATE | 1152868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) PP_FILEOPENFLAG_READ | 1153868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) PP_FILEOPENFLAG_WRITE | 1154868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) PP_FILEOPENFLAG_EXCLUSIVE, 1155868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) callback.GetCallback())); 1156868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1157868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 1158868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) TestCompletionCallbackWithOutput<pp::PassFileHandle> output_callback( 1159868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) instance_->pp_instance(), callback_type()); 1160868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) output_callback.WaitForResult( 1161868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) file_io.RequestOSFileHandle(output_callback.GetCallback())); 1162868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) PP_FileHandle handle = output_callback.output().Release(); 1163868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) if (handle == PP_kInvalidFileHandle) 1164868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) return "FileIO::RequestOSFileHandle() returned a bad file handle."; 1165868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) ASSERT_EQ(PP_OK, output_callback.result()); 1166868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 1167868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) PASS(); 1168868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles)} 1169868fa2fe829687343ffae624259930155e16dbd8Torne (Richard Coles) 1170a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles)std::string TestFileIO::TestMmap() { 1171c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles)#if !defined(PPAPI_OS_WIN) 1172a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 1173a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1174a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) pp::FileSystem file_system(instance_, PP_FILESYSTEMTYPE_LOCALTEMPORARY); 1175a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) pp::FileRef file_ref(file_system, "/file_os_fd"); 1176a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1177a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) callback.WaitForResult(file_system.Open(1024, callback.GetCallback())); 1178a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1179a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1180a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) pp::FileIO_Private file_io(instance_); 1181a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 1182a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | 1183a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) PP_FILEOPENFLAG_TRUNCATE | 1184a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) PP_FILEOPENFLAG_READ | 1185a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) PP_FILEOPENFLAG_WRITE, 1186a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) callback.GetCallback())); 1187a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1188a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1189a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) TestCompletionCallbackWithOutput<pp::PassFileHandle> output_callback( 1190a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) instance_->pp_instance(), callback_type()); 1191a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) output_callback.WaitForResult( 1192a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) file_io.RequestOSFileHandle(output_callback.GetCallback())); 1193a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) PP_FileHandle handle = output_callback.output().Release(); 1194a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_EQ(PP_OK, output_callback.result()); 1195a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1196a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (handle == PP_kInvalidFileHandle) 1197a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return "FileIO::RequestOSFileHandle() returned a bad file handle."; 1198a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) int fd = handle; 1199a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (fd < 0) 1200a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return "FileIO::RequestOSFileHandle() returned a bad file descriptor."; 1201a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1202a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Check write(2) for the native FD. 1203a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) const std::string msg = "foobar"; 1204a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ssize_t cnt = write(fd, msg.data(), msg.size()); 1205a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (cnt < 0) 1206a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("write for native FD returned error", errno); 1207a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (cnt != static_cast<ssize_t>(msg.size())) 1208a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("write for native FD count mismatch", cnt); 1209a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1210a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // BEGIN mmap(2) test with a file handle opened in READ-WRITE mode. 1211c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) // Check mmap(2) for read. 1212a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) { 1213a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) char* mapped = reinterpret_cast<char*>( 1214a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) mmap(NULL, msg.size(), PROT_READ, MAP_PRIVATE, fd, 0)); 1215a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (mapped == MAP_FAILED) 1216a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("mmap(r) for native FD returned errno", errno); 1217a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Make sure the buffer is cleared. 1218a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) std::string buf = std::string(msg.size(), '\0'); 1219a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) memcpy(&buf[0], mapped, msg.size()); 1220a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (msg != buf) 1221a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportMismatch("mmap(r) for native FD", buf, msg); 1222a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) int r = munmap(mapped, msg.size()); 1223a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (r < 0) 1224a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("munmap for native FD returned error", errno); 1225a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) } 1226c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1227a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Check mmap(2) for write with MAP_PRIVATE 1228a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) { 1229a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) char* mapped = reinterpret_cast<char*>( 1230a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) mmap(NULL, msg.size(), PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0)); 1231a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (mapped == MAP_FAILED) 1232a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("mmap(r) for native FD returned errno", errno); 1233a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Make sure the file is not polluted by writing to privage mmap. 1234a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) strncpy(mapped, "baz", 3); 1235a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) std::string read_buffer; 1236a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_TRUE(ReadEntireFileFromFileHandle(fd, &read_buffer)); 1237a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (msg != read_buffer) 1238a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportMismatch("file content != msg", read_buffer, msg); 1239a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) int r = munmap(mapped, msg.size()); 1240a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (r < 0) 1241a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("munmap for native FD returned error", errno); 1242a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) } 1243a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1244a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Check mmap(2) for write with MAP_SHARED. 1245a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) { 1246a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) char* mapped = reinterpret_cast<char*>( 1247a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) mmap(NULL, msg.size(), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0)); 1248a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (mapped == MAP_FAILED) 1249a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("mmap(w) for native FD returned errno", errno); 1250a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // s/foo/baz/ 1251a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) strncpy(mapped, "baz", 3); 1252a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) std::string read_buffer; 1253a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_TRUE(ReadEntireFileFromFileHandle(fd, &read_buffer)); 1254a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (read_buffer != "bazbar") 1255a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportMismatch("file content != msg", read_buffer, "bazbar"); 1256a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) int r = munmap(mapped, msg.size()); 1257a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (r < 0) 1258a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("munmap for native FD returned error", errno); 1259a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) } 1260a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // END mmap(2) test with a file handle opened in READ-WRITE mode. 1261a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1262a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (close(fd) < 0) 1263c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) return ReportError("close for native FD returned error", errno); 1264c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 1265a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // BEGIN mmap(2) test with a file handle opened in READONLY mode. 1266a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) file_io = pp::FileIO_Private(instance_); 1267a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) callback.WaitForResult(file_io.Open(file_ref, 1268a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) PP_FILEOPENFLAG_READ, 1269a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) callback.GetCallback())); 1270a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1271a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1272a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) output_callback = TestCompletionCallbackWithOutput<pp::PassFileHandle>( 1273a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) instance_->pp_instance(), callback_type()); 1274a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) output_callback.WaitForResult( 1275a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) file_io.RequestOSFileHandle(output_callback.GetCallback())); 1276a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) handle = output_callback.output().Release(); 1277a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_EQ(PP_OK, output_callback.result()); 1278a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1279a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (handle == PP_kInvalidFileHandle) 1280a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return "FileIO::RequestOSFileHandle() returned a bad file handle."; 1281a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) fd = handle; 1282a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (fd < 0) 1283a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return "FileIO::RequestOSFileHandle() returned a bad file descriptor."; 1284a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1285a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) const std::string msg2 = "bazbar"; 1286a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1287a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Check mmap(2) for read. 1288a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) { 1289a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) char* mapped = reinterpret_cast<char*>( 1290a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) mmap(NULL, msg2.size(), PROT_READ, MAP_PRIVATE, fd, 0)); 1291a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (mapped == MAP_FAILED) 1292a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("mmap(r) for native FD returned errno", errno); 1293a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Make sure the buffer is cleared. 1294a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) std::string buf = std::string(msg2.size(), '\0'); 1295a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) memcpy(&buf[0], mapped, msg2.size()); 1296a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (msg2 != buf) 1297a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportMismatch("mmap(r) for native FD", buf, msg2); 1298a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) int r = munmap(mapped, msg2.size()); 1299a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (r < 0) 1300a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("munmap for native FD returned error", errno); 1301a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) } 1302a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1303a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Check mmap(2) for write with MAP_PRIVATE 1304a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) { 1305a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) char* mapped = reinterpret_cast<char*>( 1306a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) mmap(NULL, msg2.size(), PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0)); 1307a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (mapped == MAP_FAILED) 1308a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("mmap(r) for native FD returned errno", errno); 1309a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Make sure the file is not polluted by writing to privage mmap. 1310a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) strncpy(mapped, "baz", 3); 1311a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) std::string read_buffer; 1312a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) ASSERT_TRUE(ReadEntireFileFromFileHandle(fd, &read_buffer)); 1313a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (msg2 != read_buffer) 1314a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportMismatch("file content != msg2", read_buffer, msg2); 1315a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) int r = munmap(mapped, msg2.size()); 1316a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (r < 0) 1317a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("munmap for native FD returned error", errno); 1318a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) } 1319a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1320a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // Check mmap(2) for write with MAP_SHARED. 1321a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) { 1322a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) char* mapped = reinterpret_cast<char*>( 1323a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) mmap(NULL, msg2.size(), PROT_READ | PROT_WRITE, MAP_SHARED, fd, 0)); 1324a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (mapped != MAP_FAILED) 1325a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("mmap(w) for native FD must fail when opened readonly", 1326a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) -1); 1327a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) } 1328a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) // END mmap(2) test with a file handle opened in READONLY mode. 1329a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) 1330a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) if (close(fd) < 0) 1331a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles) return ReportError("close for native FD returned error", errno); 1332a93a17c8d99d686bd4a1511e5504e5e6cc9fcadfTorne (Richard Coles)#endif // !defined(PPAPI_OS_WIN) 13335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 13345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PASS(); 13355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 13365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 13375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)std::string TestFileIO::MatchOpenExpectations(pp::FileSystem* file_system, 13385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) size_t open_flags, 13395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) size_t expectations) { 13405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) std::string bad_argument = 13415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) "TestFileIO::MatchOpenExpectations has invalid input arguments."; 13425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool invalid_combination = !!(expectations & INVALID_FLAG_COMBINATION); 13435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (invalid_combination) { 13445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (expectations != INVALID_FLAG_COMBINATION) 13455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return bad_argument; 13465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } else { 13475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Validate that one and only one of <some_expectation> and 13485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // DONT_<some_expectation> is specified. 13495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) for (size_t remains = expectations, end = END_OF_OPEN_EXPECATION_PAIRS; 13505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) end != 0; remains >>= 2, end >>= 2) { 13515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!!(remains & 1) == !!(remains & 2)) 13525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return bad_argument; 13535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 13545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 13555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool create_if_doesnt_exist = !!(expectations & CREATE_IF_DOESNT_EXIST); 13565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool open_if_exists = !!(expectations & OPEN_IF_EXISTS); 13575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) bool truncate_if_exists = !!(expectations & TRUNCATE_IF_EXISTS); 13585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 1359c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) TestCompletionCallback callback(instance_->pp_instance(), callback_type()); 13605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef existent_file_ref( 13615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *file_system, "/match_open_expectation_existent_non_empty_file"); 13625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileRef nonexistent_file_ref( 13635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) *file_system, "/match_open_expectation_nonexistent_file"); 13645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 13655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) // Setup files for test. 13665821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) { 1367c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(existent_file_ref.Delete(callback.GetCallback())); 1368c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1369c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(callback.result() == PP_OK || 1370c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.result() == PP_ERROR_FILENOTFOUND); 1371c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(nonexistent_file_ref.Delete(callback.GetCallback())); 1372c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1373c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_TRUE(callback.result() == PP_OK || 1374c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.result() == PP_ERROR_FILENOTFOUND); 13755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 13765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO existent_file_io(instance_); 1377c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(existent_file_io.Open( 1378c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) existent_file_ref, 1379c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) PP_FILEOPENFLAG_CREATE | PP_FILEOPENFLAG_WRITE, 1380c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 1381c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1382c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 1383c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) int32_t rv = WriteEntireBuffer(instance_->pp_instance(), &existent_file_io, 1384c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) 0, "foobar", callback_type()); 1385c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, rv); 13865821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 13875821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 13885821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO existent_file_io(instance_); 1389c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(existent_file_io.Open(existent_file_ref, open_flags, 1390c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 1391c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1392c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if ((invalid_combination && callback.result() == PP_OK) || 1393c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) (!invalid_combination && 1394c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ((callback.result() == PP_OK) != open_if_exists))) { 13955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return ReportOpenError(open_flags); 13965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 13975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 13985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (!invalid_combination && open_if_exists) { 13995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) PP_FileInfo info; 1400c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(existent_file_io.Query(&info, 1401c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 1402c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1403c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ASSERT_EQ(PP_OK, callback.result()); 14045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) if (truncate_if_exists != (info.size == 0)) 14055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return ReportOpenError(open_flags); 14065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 14075821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 14085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) pp::FileIO nonexistent_file_io(instance_); 1409c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.WaitForResult(nonexistent_file_io.Open(nonexistent_file_ref, 1410c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) open_flags, 1411c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) callback.GetCallback())); 1412c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) CHECK_CALLBACK_BEHAVIOR(callback); 1413c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) if ((invalid_combination && callback.result() == PP_OK) || 1414c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) (!invalid_combination && 1415c2e0dbddbe15c98d52c4786dac06cb8952a8ae6dTorne (Richard Coles) ((callback.result() == PP_OK) != create_if_doesnt_exist))) { 14165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return ReportOpenError(open_flags); 14175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) } 14185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 14195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) return std::string(); 14205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)} 14215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) 14225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// TODO(viettrungluu): Test Close(). crbug.com/69457 1423