// Copyright 2016 The Fuchsia Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #include #include #include "util.h" #define MB (1 << 20) #define PRINT_SIZE (MB * 100) bool test_maxfile(void) { BEGIN_TEST; int fd = emu_open("::bigfile", O_CREAT | O_RDWR, 0644); ASSERT_GT(fd, 0); char data_a[8192]; char data_b[8192]; char data_c[8192]; memset(data_a, 0xaa, sizeof(data_a)); memset(data_b, 0xbb, sizeof(data_b)); memset(data_c, 0xcc, sizeof(data_c)); ssize_t sz = 0; ssize_t r; auto rotate = [&](const char* data) { if (data == data_a) { return data_b; } else if (data == data_b) { return data_c; } else { return data_a; } }; const char* data = data_a; for (;;) { if ((r = emu_write(fd, data, sizeof(data_a))) < 0) { fprintf(stderr, "bigfile received error: %s\n", strerror(errno)); if ((errno == EFBIG) || (errno == ENOSPC)) { // Either the file should be too big (EFBIG) or the file should // consume the whole volume (ENOSPC). fprintf(stderr, "(This was an expected error)\n"); r = 0; } break; } if ((sz + r) % PRINT_SIZE < (sz % PRINT_SIZE)) { fprintf(stderr, "wrote %zu MB\n", static_cast((sz + r) / MB)); } sz += r; if (r < (ssize_t)(sizeof(data_a))) { fprintf(stderr, "bigfile write short write of %ld bytes\n", r); break; } // Rotate which data buffer we use data = rotate(data); } ASSERT_EQ(r, 0, "Saw an unexpected error from write"); struct stat buf; ASSERT_EQ(emu_fstat(fd, &buf), 0, "Couldn't stat max file"); ASSERT_EQ(buf.st_size, sz, "Unexpected max file size"); // Try closing, re-opening, and verifying the file ASSERT_EQ(emu_close(fd), 0); fd = emu_open("::bigfile", O_RDWR, 0644); char readbuf[8192]; ssize_t bytes_read = 0; data = data_a; while (bytes_read < sz) { r = emu_read(fd, readbuf, sizeof(readbuf)); ASSERT_EQ(r, fbl::min(sz - bytes_read, static_cast(sizeof(readbuf)))); ASSERT_EQ(memcmp(readbuf, data, r), 0, "File failed to verify"); data = rotate(data); bytes_read += r; } ASSERT_EQ(bytes_read, sz); ASSERT_EQ(emu_close(fd), 0); ASSERT_EQ(run_fsck(), 0); END_TEST; } RUN_MINFS_TESTS(maxfile_tests, RUN_TEST_LARGE(test_maxfile) )