diff options
author | Håvard Pettersen <havardpe@yahooinc.com> | 2023-02-28 12:44:11 +0000 |
---|---|---|
committer | Håvard Pettersen <havardpe@yahooinc.com> | 2023-02-28 12:44:11 +0000 |
commit | 9ce9ed480a5248ffb14439473f6498c6769d74ee (patch) | |
tree | 4e9309b1d3feced5f3ed3a60b22880d289e886b4 /fastos/src | |
parent | c111113d5b5342b56fd29b1f3cf54c5cf2d0097d (diff) |
move fastos file code to vespalib
Diffstat (limited to 'fastos/src')
-rw-r--r-- | fastos/src/tests/.gitignore | 17 | ||||
-rw-r--r-- | fastos/src/tests/CMakeLists.txt | 15 | ||||
-rw-r--r-- | fastos/src/tests/coretest2.cpp | 41 | ||||
-rw-r--r-- | fastos/src/tests/filetest.cpp | 555 | ||||
-rw-r--r-- | fastos/src/tests/hello.txt | 1 | ||||
-rw-r--r-- | fastos/src/tests/mazeserver.cpp | 4 | ||||
-rw-r--r-- | fastos/src/tests/performancetest.cpp | 54 | ||||
-rw-r--r-- | fastos/src/tests/tests.h | 149 | ||||
-rw-r--r-- | fastos/src/tests/typetest.cpp | 44 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/CMakeLists.txt | 4 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/file.cpp | 357 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/file.h | 745 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/file_rw_ops.cpp | 13 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/file_rw_ops.h | 33 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/linux_file.cpp | 436 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/linux_file.h | 57 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/types.h | 9 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/unix_file.cpp | 590 | ||||
-rw-r--r-- | fastos/src/vespa/fastos/unix_file.h | 130 |
19 files changed, 0 insertions, 3254 deletions
diff --git a/fastos/src/tests/.gitignore b/fastos/src/tests/.gitignore deleted file mode 100644 index ccb5f0210ab..00000000000 --- a/fastos/src/tests/.gitignore +++ /dev/null @@ -1,17 +0,0 @@ -/Makefile -/backtracetest -/backtracetest.log -/filetest -/filetest.log -/processtest -/processtest.log -/sockettest -/sockettest.log -/threadtest -/threadtest.log -/timetest -/timetest.log -/typetest -/typetest.log -/usecputest -*test_app diff --git a/fastos/src/tests/CMakeLists.txt b/fastos/src/tests/CMakeLists.txt deleted file mode 100644 index 7d4b014b6b3..00000000000 --- a/fastos/src/tests/CMakeLists.txt +++ /dev/null @@ -1,15 +0,0 @@ -# Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -vespa_add_executable(fastos_filetest_app TEST - SOURCES - filetest.cpp - DEPENDS - fastos -) -vespa_add_test(NAME fastos_filetest_app NO_VALGRIND COMMAND fastos_filetest_app) -vespa_add_executable(fastos_typetest_app TEST - SOURCES - typetest.cpp - DEPENDS - fastos -) -vespa_add_test(NAME fastos_typetest_app NO_VALGRIND COMMAND fastos_typetest_app) diff --git a/fastos/src/tests/coretest2.cpp b/fastos/src/tests/coretest2.cpp deleted file mode 100644 index bd93623922b..00000000000 --- a/fastos/src/tests/coretest2.cpp +++ /dev/null @@ -1,41 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - - - - -static void -bomb(void) -{ - char *p; - - p = nullptr; - *p = 4; -} - -void *BomberRun(void *arg) -{ - (void) arg; - bomb(); - return nullptr; -}; - -static int -bombMain(void) -{ - pthread_t thread; - void *ret; - - (void) pthread_create(&thread, nullptr, BomberRun, nullptr); - ret = nullptr; - (void) pthread_join(thread, &ret); - return (0); -} - - -int -main(int argc, char **argv) -{ - (void) argc; - (void) argv; - return bombMain(); -} diff --git a/fastos/src/tests/filetest.cpp b/fastos/src/tests/filetest.cpp deleted file mode 100644 index d0f8bbfd98b..00000000000 --- a/fastos/src/tests/filetest.cpp +++ /dev/null @@ -1,555 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#include "tests.h" -#include <vespa/fastos/file.h> -#include <memory> -#include <cassert> -#include <sys/mman.h> -#include <filesystem> - -class FileTest : public BaseTest -{ -public: - const std::string srcDir = getenv("SOURCE_DIRECTORY") ? getenv("SOURCE_DIRECTORY") : "."; - const std::string roFilename = srcDir + "/hello.txt"; - const std::string woFilename = "generated/writeonlytest.txt"; - const std::string rwFilename = "generated/readwritetest.txt"; - - void GetCurrentDirTest () - { - TestHeader ("Get Current Directory Test"); - - std::string currentDir = FastOS_File::getCurrentDirectory(); - - Progress(!currentDir.empty(), - "Current dir: %s", !currentDir.empty() ? - currentDir.c_str() : "<failed>"); - - bool dirrc = FastOS_File::SetCurrentDirectory(".."); - - std::string parentDir; - - if (dirrc) { - parentDir = FastOS_File::getCurrentDirectory(); - } - - Progress(dirrc && strcmp(currentDir.c_str(), parentDir.c_str()) != 0, - "Parent dir: %s", !parentDir.empty() ? - parentDir.c_str() : "<failed>"); - - dirrc = FastOS_File::SetCurrentDirectory(currentDir.c_str()); - - Progress(dirrc, "Changed back to working directory."); - - PrintSeparator(); - } - - void MemoryMapTest (int mmap_flags) - { - TestHeader ("Memory Map Test"); - - int i; - const int bufSize = 1000; - - std::filesystem::create_directory(std::filesystem::path("generated")); - FastOS_File file("generated/memorymaptest"); - - bool rc = file.OpenReadWrite(); - Progress(rc, "Opening file 'generated/memorymaptest'"); - - if (rc) { - char *buffer = new char [bufSize]; - for (i = 0; i < bufSize; i++) { - buffer[i] = i % 256; - } - ssize_t wroteB = file.Write2(buffer, bufSize); - Progress(wroteB == bufSize, "Writing %d bytes to file", bufSize); - - bool close_ok = file.Close(); - assert(close_ok); - file.enableMemoryMap(mmap_flags); - - rc = file.OpenReadOnly(); - - Progress(rc, "Opening file 'generated/memorymaptest' read-only"); - if (rc) { - bool mmapEnabled; - char *mmapBuffer = nullptr; - - mmapEnabled = file.IsMemoryMapped(); - mmapBuffer = static_cast<char *>(file.MemoryMapPtr(0)); - - Progress(rc, "Memory mapping %s", - mmapEnabled ? "enabled" : "disabled"); - Progress(rc, "Map address: 0x%p", mmapBuffer); - - if (mmapEnabled) { - rc = 0; - for (i = 0; i < bufSize; i++) { - rc |= (mmapBuffer[i] == i % 256); - } - Progress(rc, "Reading %d bytes from memory map", bufSize); - } - } - delete [] buffer; - } - std::filesystem::remove_all(std::filesystem::path("generated")); - PrintSeparator(); - } - - void DirectIOTest () - { - TestHeader ("Direct Disk IO Test"); - - int i; - const int bufSize = 40000; - - std::filesystem::create_directory(std::filesystem::path("generated")); - FastOS_File file("generated/diotest"); - - bool rc = file.OpenWriteOnly(); - Progress(rc, "Opening file 'generated/diotest' write-only"); - - if (rc) { - char *buffer = new char [bufSize]; - - for (i=0; i<bufSize; i++) { - buffer[i] = 'A' + (i % 17); - } - ssize_t wroteB = file.Write2(buffer, bufSize); - Progress(wroteB == bufSize, "Writing %d bytes to file", bufSize); - - bool close_ok = file.Close(); - assert(close_ok); - - if (rc) { - file.EnableDirectIO(); - - rc = file.OpenReadOnly(); - Progress(rc, "Opening file 'generated/diotest' read-only"); - if (rc) { - bool dioEnabled; - size_t memoryAlignment=0; - size_t transferGranularity=0; - size_t transferMaximum=0; - - dioEnabled = file.GetDirectIORestrictions(memoryAlignment, - transferGranularity, - transferMaximum); - - Progress(rc, "DirectIO %s", dioEnabled ? "enabled" : "disabled"); - Progress(rc, "Memory alignment: %u bytes", memoryAlignment); - Progress(rc, "Transfer granularity: %u bytes", transferGranularity); - Progress(rc, "Transfer maximum: %u bytes", transferMaximum); - - if (dioEnabled) { - int eachRead = (8192 + transferGranularity - 1) / transferGranularity; - - char *buffer2 = new char [(eachRead * transferGranularity + - memoryAlignment - 1)]; - char *alignPtr = buffer2; - unsigned int align = - static_cast<unsigned int> - (reinterpret_cast<unsigned long>(alignPtr) & - (memoryAlignment - 1)); - if (align != 0) { - alignPtr = &alignPtr[memoryAlignment - align]; - } - int residue = bufSize; - int pos=0; - while (residue > 0) { - int readThisTime = eachRead * transferGranularity; - if (readThisTime > residue) { - readThisTime = residue; - } - file.ReadBuf(alignPtr, readThisTime, pos); - - for (i=0; i<readThisTime; i++) { - rc = (alignPtr[i] == 'A' + ((i+pos) % 17)); - if (!rc) { - Progress(false, "Read error at offset %d", i); - break; - } - } - residue -= readThisTime; - pos += readThisTime; - - if (!rc) break; - } - if (rc) { - Progress(true, "Read success"); - - rc = file.SetPosition(1); - Progress(rc, "SetPosition(1)"); - if (rc) { - try { - const int attemptReadBytes = 173; - ssize_t readB = file.Read(buffer, attemptReadBytes); - Progress(false, "Expected to get an exception for unaligned read"); - ProgressI64(readB == attemptReadBytes, "Got %ld bytes from attempted 173", readB); - } catch(const DirectIOException &e) { - Progress(true, "Got exception as expected"); - } - } - if (rc) { - rc = file.SetPosition(1); - Progress(rc, "SetPosition(1)"); - if (rc) { - try { - const int attemptReadBytes = 4096; - ssize_t readB = file.Read(buffer, attemptReadBytes); - Progress(false, "Expected to get an exception for unaligned read"); - ProgressI64(readB == attemptReadBytes, "Got %ld bytes from attempted 4096", readB); - } catch(const DirectIOException &e) { - Progress(true, "Got exception as expected"); - } - } - } - } - delete [] buffer2; - } else { - memset(buffer, 0, bufSize); - - ssize_t readBytes = file.Read(buffer, bufSize); - Progress(readBytes == bufSize, - "Reading %d bytes from file", bufSize); - - for (i=0; i<bufSize; i++) { - rc = (buffer[i] == 'A' + (i % 17)); - if (!rc) { - Progress(false, "Read error at offset %d", i); - break; - } - } - if (rc) Progress(true, "Read success"); - } - } - } - delete [] buffer; - } - - std::filesystem::remove_all(std::filesystem::path("generated")); - PrintSeparator(); - } - - void ReadOnlyTest () - { - TestHeader("Read-Only Test"); - - FastOS_File *myFile = new FastOS_File(roFilename.c_str()); - - if (myFile->OpenReadOnly()) { - int64_t filesize; - filesize = myFile->GetSize(); - ProgressI64((filesize == 27), "File size: %ld", filesize); - - char dummyData[6] = "Dummy"; - bool writeResult = myFile->CheckedWrite(dummyData, 6); - - if (writeResult) { - Progress(false, "Should not be able to write a file opened for read-only access."); - } else { - char dummyData2[28]; - Progress(true, "Write failed with read-only access."); - - bool rc = myFile->SetPosition(1); - Progress(rc, "Setting position to 1"); - - if (rc) { - ssize_t readBytes; - int64_t filePosition; - readBytes = myFile->Read(dummyData2, 28); - - Progress(readBytes == 26, "Attempting to read 28 bytes, should get 26. Got: %d", readBytes); - - filePosition = myFile->GetPosition(); - Progress(filePosition == 27, "File position should now be 27. Was: %d", int(filePosition)); - - readBytes = myFile->Read(dummyData2, 6); - Progress(readBytes == 0, "We should now get 0 bytes. Read: %d bytes", readBytes); - - filePosition = myFile->GetPosition(); - Progress(filePosition == 27, "File position should now be 27. Was: %d", int(filePosition)); - } - } - } else { - Progress(false, "Unable to open file '%s'.", roFilename.c_str()); - } - delete(myFile); - PrintSeparator(); - } - - void WriteOnlyTest () - { - TestHeader("Write-Only Test"); - std::filesystem::create_directory(std::filesystem::path("generated")); - - FastOS_File *myFile = new FastOS_File(woFilename.c_str()); - - if (myFile->OpenWriteOnly()) { - int64_t filesize; - filesize = myFile->GetSize(); - - ProgressI64((filesize == 0), "File size: %ld", filesize); - - char dummyData[6] = "Dummy"; - bool writeResult = myFile->CheckedWrite(dummyData, 6); - - if (!writeResult) { - Progress(false, "Should be able to write to file opened for write-only access."); - } else { - Progress(true, "Write 6 bytes ok."); - - int64_t filePosition = myFile->GetPosition(); - if (filePosition == 6) { - Progress(true, "Fileposition is now 6."); - - if (myFile->SetPosition(0)) { - Progress(true, "SetPosition(0) success."); - filePosition = myFile->GetPosition(); - - if (filePosition == 0) { - Progress(true, "Fileposition is now 0."); - - int readBytes = myFile->Read(dummyData, 6); - - if (readBytes != 6) { - Progress(true, "Trying to read a write-only file should fail and it did."); - Progress(true, "Return code was: %d.", readBytes); - } else { - Progress(false, "Read on a file with write-only access should fail, but it didn't."); - } - } else { - ProgressI64(false, "Fileposition should be 6, but was %ld.", filePosition); - } - } else { - Progress(false, "SetPosition(0) failed"); - } - } else { - ProgressI64(false, "Fileposition should be 6, but was %ld.", filePosition); - } - } - bool closeResult = myFile->Close(); - Progress(closeResult, "Close file."); - } else { - Progress(false, "Unable to open file '%s'.", woFilename.c_str()); - } - - - bool deleteResult = myFile->Delete(); - Progress(deleteResult, "Delete file '%s'.", woFilename.c_str()); - - delete(myFile); - std::filesystem::remove_all(std::filesystem::path("generated")); - PrintSeparator(); - } - - void ReadWriteTest () - { - TestHeader("Read/Write Test"); - std::filesystem::create_directory(std::filesystem::path("generated")); - - FastOS_File *myFile = new FastOS_File(rwFilename.c_str()); - - if (myFile->OpenExisting()) { - Progress(false, "OpenExisting() should not work when '%s' does not exist.", rwFilename.c_str()); - bool close_ok = myFile->Close(); - assert(close_ok); - } else { - Progress(true, "OpenExisting() should fail when '%s' does not exist, and it did.", rwFilename.c_str()); - } - - if (myFile->OpenReadWrite()) { - int64_t filesize; - - filesize = myFile->GetSize(); - - ProgressI64((filesize == 0), "File size: %ld", filesize); - - char dummyData[6] = "Dummy"; - - bool writeResult = myFile->CheckedWrite(dummyData, 6); - - if (!writeResult) { - Progress(false, "Should be able to write to file opened for read/write access."); - } else { - Progress(true, "Write 6 bytes ok."); - - int64_t filePosition = myFile->GetPosition(); - - if (filePosition == 6) { - Progress(true, "Fileposition is now 6."); - - if (myFile->SetPosition(0)) { - Progress(true, "SetPosition(0) success."); - filePosition = myFile->GetPosition(); - - if (filePosition == 0) { - Progress(true, "Fileposition is now 0."); - - char dummyData2[7]; - int readBytes = myFile->Read(dummyData2, 6); - - if (readBytes == 6) { - Progress(true, "Reading 6 bytes worked."); - - int cmpResult = memcmp(dummyData, dummyData2, 6); - Progress((cmpResult == 0), "Comparing the written and read result.\n"); - - bool rc = myFile->SetPosition(1); - Progress(rc, "Setting position to 1"); - - if (rc) { - readBytes = myFile->Read(dummyData2, 7); - - Progress(readBytes == 5, "Attempting to read 7 bytes, should get 5. Got: %d", readBytes); - - filePosition = myFile->GetPosition(); - Progress(filePosition == 6, "File position should now be 6. Was: %d", int(filePosition)); - - readBytes = myFile->Read(dummyData2, 6); - Progress(readBytes == 0, "We should not be able to read any more. Read: %d bytes", readBytes); - - filePosition = myFile->GetPosition(); - Progress(filePosition == 6, "File position should now be 6. Was: %d", int(filePosition)); - } - } else { - Progress(false, "Reading 6 bytes failed."); - } - } else { - ProgressI64(false, "Fileposition should be 6, but was %ld.", filePosition); - } - } else { - Progress(false, "SetPosition(0) failed"); - } - } else { - ProgressI64(false, "Fileposition should be 6, but was %ld.", filePosition); - } - } - - bool closeResult = myFile->Close(); - Progress(closeResult, "Close file."); - } else { - Progress(false, "Unable to open file '%s'.", rwFilename.c_str()); - } - bool deleteResult = myFile->Delete(); - Progress(deleteResult, "Delete file '%s'.", rwFilename.c_str()); - - delete(myFile); - std::filesystem::remove_all(std::filesystem::path("generated")); - PrintSeparator(); - } - - void ScanDirectoryTest() - { - TestHeader("DirectoryScan Test"); - - FastOS_DirectoryScan *scanDir = new FastOS_DirectoryScan("."); - - while (scanDir->ReadNext()) { - const char *name = scanDir->GetName(); - bool isDirectory = scanDir->IsDirectory(); - bool isRegular = scanDir->IsRegular(); - - printf("%-30s %s\n", name, - isDirectory ? "DIR" : (isRegular ? "FILE" : "UNKN")); - } - - delete(scanDir); - PrintSeparator(); - } - - void ReadBufTest () - { - TestHeader("ReadBuf Test"); - - FastOS_File file(roFilename.c_str()); - - char buffer[20]; - - if (file.OpenReadOnly()) { - int64_t position = file.GetPosition(); - Progress(position == 0, "File pointer should be 0 after opening file"); - - ssize_t has_read = file.Read(buffer, 4); - Progress(has_read == 4, "Must read 4 bytes"); - buffer[4] = '\0'; - position = file.GetPosition(); - Progress(position == 4, "File pointer should be 4 after reading 4 bytes"); - Progress(strcmp(buffer, "This") == 0, "[This]=[%s]", buffer); - - file.ReadBuf(buffer, 6, 8); - buffer[6] = '\0'; - position = file.GetPosition(); - Progress(position == 4, "File pointer should still be 4 after ReadBuf"); - Progress(strcmp(buffer, "a test") == 0, "[a test]=[%s]", buffer); - } - - PrintSeparator(); - } - - void DiskFreeSpaceTest () - { - TestHeader("DiskFreeSpace Test"); - - int64_t freeSpace = FastOS_File::GetFreeDiskSpace(roFilename.c_str()); - ProgressI64(freeSpace != -1, "DiskFreeSpace using file ('hello.txt'): %ld MB.", freeSpace == -1 ? -1 : freeSpace/(1024*1024)); - freeSpace = FastOS_File::GetFreeDiskSpace("."); - ProgressI64(freeSpace != -1, "DiskFreeSpace using dir (.): %ld MB.", freeSpace == -1 ? -1 : freeSpace/(1024*1024)); - PrintSeparator(); - } - - void MaxLengthTest () - { - TestHeader ("Max Lengths Test"); - - int maxval = FastOS_File::GetMaximumFilenameLength("."); - Progress(maxval > 5 && maxval < (512*1024), - "Maximum filename length = %d", maxval); - - maxval = FastOS_File::GetMaximumPathLength("."); - Progress(maxval > 5 && maxval < (512*1024), - "Maximum path length = %d", maxval); - - PrintSeparator(); - } - - int Main () override - { - printf("This test should be run in the 'tests' directory.\n\n"); - printf("grep for the string '%s' to detect failures.\n\n", failString); - - GetCurrentDirTest(); - DirectIOTest(); - MaxLengthTest(); - DiskFreeSpaceTest(); - ReadOnlyTest(); - WriteOnlyTest(); - ReadWriteTest(); - ScanDirectoryTest(); - ReadBufTest(); - MemoryMapTest(0); -#ifdef __linux__ - MemoryMapTest(MAP_HUGETLB); -#endif - - PrintSeparator(); - printf("END OF TEST (%s)\n", _argv[0]); - - return allWasOk() ? 0 : 1; - } - FileTest(); - ~FileTest(); -}; - -FileTest::FileTest() { } -FileTest::~FileTest() { } - - -int main (int argc, char **argv) -{ - FileTest app; - - setvbuf(stdout, nullptr, _IOLBF, 8192); - return app.Entry(argc, argv); -} diff --git a/fastos/src/tests/hello.txt b/fastos/src/tests/hello.txt deleted file mode 100644 index 62a405393a6..00000000000 --- a/fastos/src/tests/hello.txt +++ /dev/null @@ -1 +0,0 @@ -This is a test input file. diff --git a/fastos/src/tests/mazeserver.cpp b/fastos/src/tests/mazeserver.cpp deleted file mode 100644 index b62e98645f2..00000000000 --- a/fastos/src/tests/mazeserver.cpp +++ /dev/null @@ -1,4 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -#define DO_MAZE_SERVER 1 - -#include "sockettest.cpp" diff --git a/fastos/src/tests/performancetest.cpp b/fastos/src/tests/performancetest.cpp deleted file mode 100644 index f566979957a..00000000000 --- a/fastos/src/tests/performancetest.cpp +++ /dev/null @@ -1,54 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -#include <stdlib.h> - -#include "tests.h" - -void PerformanceTest (char *buffer); - -int main (int argc, char **argv) -{ - (void)argc; - (void)argv; - - void (*test)(char *buffer) = PerformanceTest; - - test(nullptr); - return 0; -} - -void PerformanceTest (char *buffer) -{ - // Cause exception - *static_cast<char *>(nullptr) = 'e'; - -#if 1 - FastOS_File file("test.txt"); - - if(file.OpenReadOnly()) - { - file.Read(buffer, 20); - file.Write2(buffer, 20); - file.Read(buffer, 20); - file.Write2(buffer, 20); - file.Read(buffer, 20); - file.Write2(buffer, 20); - } -#else - - int filedes = open("test.txt", O_RDONLY, 0664); - - if(filedes != -1) - { - write(filedes, buffer, 20); - read(filedes, buffer, 20); - write(filedes, buffer, 20); - read(filedes, buffer, 20); - write(filedes, buffer, 20); - read(filedes, buffer, 20); - write(filedes, buffer, 20); - - close(filedes); - } -#endif -} - diff --git a/fastos/src/tests/tests.h b/fastos/src/tests/tests.h deleted file mode 100644 index 9cd7a10ab48..00000000000 --- a/fastos/src/tests/tests.h +++ /dev/null @@ -1,149 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#include <cstring> -#include <csignal> -#include <cstdio> -#include <cstdint> - -class BaseTest -{ -private: - BaseTest(const BaseTest&); - BaseTest &operator=(const BaseTest&); - - int totallen; - bool _allOkFlag; -public: - int _argc; - char **_argv; - - const char *okString; - const char *failString; - - BaseTest () - : totallen(70), - _allOkFlag(true), - _argc(0), - _argv(nullptr), - okString("SUCCESS"), - failString("FAILURE") - { - } - - virtual int Main() = 0; - - int Entry(int argc, char **argv) { - _argc = argc; - _argv = argv; - return Main(); - } - - virtual ~BaseTest() {}; - - bool allWasOk() const { return _allOkFlag; } - - void PrintSeparator () - { - for(int i=0; i<totallen; i++) printf("-"); - printf("\n"); - } - - virtual void PrintProgress (char *string) - { - printf("%s", string); - } -#define MAX_STR_LEN 3000 - bool Progress (bool result, const char *str) - { - char string[MAX_STR_LEN]; - snprintf(string, sizeof(string), "%s: %s\n", - result ? okString : failString, str); - PrintProgress(string); - if (! result) { _allOkFlag = false; } - return result; - } - - bool Progress (bool result, const char *str, int d1) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, d1); - return Progress(result, string); - } - - bool Progress (bool result, const char *str, int d1, int d2) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, d1, d2); - return Progress(result, string); - } - - bool Progress (bool result, const char *str, const char *s1) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, s1); - return Progress(result, string); - } - - bool Progress (bool result, const char *str, const char *s1, const char *s2) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, s1, s2); - return Progress(result, string); - } - - bool Progress (bool result, const char *str, const char *s1, int d1) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, s1, d1); - return Progress(result, string); - } - - bool Progress (bool result, const char *str, int d1, const char *s1) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, d1, s1); - return Progress(result, string); - } - - bool ProgressI64 (bool result, const char *str, int64_t val) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, val); - return Progress(result, string); - } - - bool ProgressFloat (bool result, const char *str, float val) - { - char string[MAX_STR_LEN-100]; - snprintf(string, sizeof(string), str, val); - return Progress(result, string); - } - - void Ok (const char *string) - { - Progress(true, string); - } - - void Fail (const char *string) - { - Progress(false, string); - } - - void TestHeader (const char *string) - { - int len = strlen(string); - int leftspace = (totallen - len)/2 - 2; - int rightspace = totallen - 4 - len - leftspace; - int i; - - printf("\n\n"); - for(i=0; i<totallen; i++) printf("*"); - printf("\n**"); - for(i=0; i<leftspace; i++) printf(" "); //forgot printf-specifier.. - printf("%s", string); - for(i=0; i<rightspace; i++) printf(" "); - printf("**\n"); - for(i=0; i<totallen; i++) printf("*"); - printf("\n"); - } -}; diff --git a/fastos/src/tests/typetest.cpp b/fastos/src/tests/typetest.cpp deleted file mode 100644 index 7871275e17c..00000000000 --- a/fastos/src/tests/typetest.cpp +++ /dev/null @@ -1,44 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#include "tests.h" -#include <vespa/fastos/file.h> - -class TypeTest : public BaseTest -{ -private: - - void ObjectSizeTest () - { - TestHeader("Object Sizes (bytes)"); - - Progress(true, "FastOS_DirectoryScan %d", sizeof(FastOS_DirectoryScan)); - Progress(true, "FastOS_File: %d", sizeof(FastOS_File)); - Progress(true, "FastOS_StatInfo %d", sizeof(FastOS_StatInfo)); - - PrintSeparator(); - } - -public: - virtual ~TypeTest() {}; - - int Main () override - { - printf("grep for the string '%s' to detect failures.\n\n", failString); - - ObjectSizeTest(); - - PrintSeparator(); - printf("END OF TEST (%s)\n", _argv[0]); - - return allWasOk() ? 0 : 1; - } -}; - - -int main (int argc, char **argv) -{ - setvbuf(stdout, nullptr, _IOLBF, 8192); - TypeTest app; - return app.Entry(argc, argv); -} - diff --git a/fastos/src/vespa/fastos/CMakeLists.txt b/fastos/src/vespa/fastos/CMakeLists.txt index c37eb43b884..29810a4f296 100644 --- a/fastos/src/vespa/fastos/CMakeLists.txt +++ b/fastos/src/vespa/fastos/CMakeLists.txt @@ -1,10 +1,6 @@ # Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. vespa_add_library(fastos_objects OBJECT SOURCES - file.cpp - file_rw_ops.cpp - linux_file.cpp - unix_file.cpp ) vespa_add_library(fastos diff --git a/fastos/src/vespa/fastos/file.cpp b/fastos/src/vespa/fastos/file.cpp deleted file mode 100644 index fdbacb570b4..00000000000 --- a/fastos/src/vespa/fastos/file.cpp +++ /dev/null @@ -1,357 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -//************************************************************************ -/** - * Implementation of FastOS_FileInterface methods. - * - * @author Div, Oivind H. Danielsen - */ - -#include "file.h" -#include <sstream> -#include <cstring> -#include <fcntl.h> -#include <cstdlib> -#include <cassert> - -DirectIOException::DirectIOException(const char * fileName, const void * buffer, size_t length, int64_t offset) : - std::exception(), - _what(), - _fileName(fileName), - _buffer(buffer), - _length(length), - _offset(offset) -{ - std::ostringstream os; - os << "DirectIO failed for file '" << fileName << "' buffer=0x" << std::hex << reinterpret_cast<size_t>(buffer); - os << " length=0x" << length << " offset=0x" << offset; - _what = os.str(); -} - -DirectIOException::~DirectIOException() {} - -#ifdef __linux__ -int FastOS_FileInterface::_defaultFAdviseOptions = POSIX_FADV_NORMAL; -#else -int FastOS_FileInterface::_defaultFAdviseOptions = 0; -#endif - -static const size_t MAX_CHUNK_SIZE = 0x4000000; // 64 MB - -FastOS_FileInterface::FastOS_FileInterface(const char *filename) - : _fAdviseOptions(_defaultFAdviseOptions), - _chunkSize(MAX_CHUNK_SIZE), - _filename(), - _openFlags(0), - _directIOEnabled(false), - _syncWritesEnabled(false) -{ - if (filename != nullptr) - SetFileName(filename); -} - - -FastOS_FileInterface::~FastOS_FileInterface() = default; - -void -FastOS_FileInterface::ReadBuf(void *buffer, size_t length) -{ - ssize_t readResult = Read(buffer, length); - - if ((readResult == -1) || (static_cast<size_t>(readResult) != length)) { - std::string errorString = readResult != -1 ? - std::string("short read") : - FastOS_FileInterface::getLastErrorString(); - std::ostringstream os; - os << "Fatal: Reading " << length << " bytes from '" << GetFileName() << "' failed: " << errorString; - throw std::runtime_error(os.str()); - } -} - -void -FastOS_FileInterface::WriteBuf(const void *buffer, size_t length) -{ - WriteBufInternal(buffer, length); -} - -void -FastOS_FileInterface::WriteBufInternal(const void *buffer, size_t length) -{ - ssize_t writeResult = Write2(buffer, length); - if (length - writeResult != 0) { - std::string errorString = writeResult != -1 ? - std::string("short write") : - FastOS_FileInterface::getLastErrorString(); - std::ostringstream os; - os << "Fatal: Writing " << length << " bytes to '" << GetFileName() << "' failed (wrote " << writeResult << "): " << errorString; - throw std::runtime_error(os.str()); - } -} - -bool -FastOS_FileInterface::CheckedWrite(const void *buffer, size_t len) -{ - ssize_t writeResult = Write2(buffer, len); - if (writeResult < 0) { - std::string errorString = FastOS_FileInterface::getLastErrorString(); - fprintf(stderr, "Writing %lu bytes to '%s' failed: %s\n", - static_cast<unsigned long>(len), - GetFileName(), - errorString.c_str()); - return false; - } - if (writeResult != (ssize_t)len) { - fprintf(stderr, "Short write, tried to write %lu bytes to '%s', only wrote %lu bytes\n", - static_cast<unsigned long>(len), - GetFileName(), - static_cast<unsigned long>(writeResult)); - return false; - } - return true; -} - - -void -FastOS_FileInterface::ReadBuf(void *buffer, size_t length, int64_t readOffset) -{ - if (!SetPosition(readOffset)) { - std::string errorString = FastOS_FileInterface::getLastErrorString(); - std::ostringstream os; - os << "Fatal: Setting fileoffset to " << readOffset << " in '" << GetFileName() << "' : " << errorString; - throw std::runtime_error(os.str()); - } - ReadBuf(buffer, length); -} - - -void -FastOS_FileInterface::EnableDirectIO() -{ - // Only subclasses with support for DirectIO do something here. -} - - -void -FastOS_FileInterface::EnableSyncWrites() -{ - if (!IsOpened()) - _syncWritesEnabled = true; -} - - -bool -FastOS_FileInterface:: -GetDirectIORestrictions(size_t &memoryAlignment, - size_t &transferGranularity, - size_t &transferMaximum) -{ - memoryAlignment = 1; - transferGranularity = 1; - transferMaximum = 0x7FFFFFFF; - return false; -} - -bool -FastOS_FileInterface::DirectIOPadding(int64_t offset, - size_t buflen, - size_t &padBefore, - size_t &padAfter) -{ - (void)offset; - (void)buflen; - padBefore = 0; - padAfter = 0; - return false; -} - - -void * -FastOS_FileInterface::allocateGenericDirectIOBuffer(size_t byteSize, void *&realPtr) -{ - realPtr = malloc(byteSize); // Default - use malloc allignment - return realPtr; -} - -size_t -FastOS_FileInterface::getMaxDirectIOMemAlign() -{ - return 1u; -} - -void * -FastOS_FileInterface::AllocateDirectIOBuffer(size_t byteSize, void *&realPtr) -{ - return allocateGenericDirectIOBuffer(byteSize, realPtr); -} - -void -FastOS_FileInterface::enableMemoryMap(int mmapFlags) -{ - // Only subclases with support for memory mapping do something here. - (void) mmapFlags; -} - - -void * -FastOS_FileInterface::MemoryMapPtr(int64_t position) const -{ - // Only subclases with support for memory mapping do something here. - (void) position; - return nullptr; -} - - -bool -FastOS_FileInterface::IsMemoryMapped() const -{ - // Only subclases with support for memory mapping do something here. - return false; -} - -void -FastOS_FileInterface::SetFileName(const char *filename) -{ - _filename = filename; -} - - -const char * -FastOS_FileInterface::GetFileName() const -{ - return _filename.c_str(); -} - - -bool -FastOS_FileInterface::OpenReadWrite(const char *filename) -{ - return Open(FASTOS_FILE_OPEN_READ | - FASTOS_FILE_OPEN_WRITE, filename); -} - - -bool -FastOS_FileInterface::OpenExisting(bool abortIfNotExist, - const char *filename) -{ - bool rc = Open(FASTOS_FILE_OPEN_READ | - FASTOS_FILE_OPEN_WRITE | - FASTOS_FILE_OPEN_EXISTING, - filename); - - if (abortIfNotExist && (!rc)) { - std::string errorString = - FastOS_FileInterface::getLastErrorString(); - fprintf(stderr, - "Cannot open %s: %s\n", - filename, - errorString.c_str()); - abort(); - } - - return rc; -} - - -bool -FastOS_FileInterface::OpenReadOnlyExisting(bool abortIfNotExist, - const char *filename) -{ - bool rc = Open(FASTOS_FILE_OPEN_READ | - FASTOS_FILE_OPEN_EXISTING, - filename); - - if (abortIfNotExist && (!rc)) { - std::string errorString = - FastOS_FileInterface::getLastErrorString(); - fprintf(stderr, - "Cannot open %s: %s\n", - filename, - errorString.c_str()); - abort(); - } - - return rc; -} - - -bool -FastOS_FileInterface::OpenWriteOnlyTruncate(const char *filename) -{ - // printf("********* OpenWriteOnlyTruncate %s\n", filename); - return Open(FASTOS_FILE_OPEN_WRITE | - FASTOS_FILE_OPEN_CREATE | - FASTOS_FILE_OPEN_TRUNCATE, - filename); -} - - -bool -FastOS_FileInterface::OpenWriteOnlyExisting(bool abortIfNotExist, - const char *filename) -{ - bool rc = Open(FASTOS_FILE_OPEN_WRITE | - FASTOS_FILE_OPEN_EXISTING, - filename); - - if (abortIfNotExist && (!rc)) { - std::string errorString = - FastOS_FileInterface::getLastErrorString(); - fprintf(stderr, - "Cannot open %s: %s\n", - filename, - errorString.c_str()); - abort(); - } - - return rc; -} - -bool -FastOS_FileInterface::OpenReadOnly(const char *filename) -{ - return Open(FASTOS_FILE_OPEN_READ | - FASTOS_FILE_OPEN_EXISTING, - filename); -} - - -bool -FastOS_FileInterface::OpenWriteOnly(const char *filename) -{ - return Open(FASTOS_FILE_OPEN_WRITE, filename); -} - -FastOS_File::Error -FastOS_FileInterface::GetLastError() -{ - return FastOS_File::TranslateError(FastOS_File::GetLastOSError()); -} - - -std::string -FastOS_FileInterface::getLastErrorString() -{ - int err = FastOS_File::GetLastOSError(); - return FastOS_File::getErrorString(err); -} - -bool FastOS_FileInterface::Rename (const char *newFileName) -{ - bool rc=false; - if (FastOS_File::Rename(GetFileName(), newFileName)) { - SetFileName(newFileName); - rc = true; - } - return rc; -} - -void FastOS_FileInterface::dropFromCache() const -{ -} - -FastOS_DirectoryScanInterface::FastOS_DirectoryScanInterface(const char *path) - : _searchPath(path) -{ -} - -FastOS_DirectoryScanInterface::~FastOS_DirectoryScanInterface() = default; diff --git a/fastos/src/vespa/fastos/file.h b/fastos/src/vespa/fastos/file.h deleted file mode 100644 index 1cf6fee71dd..00000000000 --- a/fastos/src/vespa/fastos/file.h +++ /dev/null @@ -1,745 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -//************************************************************************ -/** - * @file - * Class definitions for FastOS_File, FastOS_DirectoryScan and - * FastOS_StatInfo. - * - * @author Div, Oivind H. Danielsen - */ - -#pragma once - -#include "types.h" -#include <cstdint> -#include <string> - -constexpr int FASTOS_FILE_OPEN_READ = (1<<0); -constexpr int FASTOS_FILE_OPEN_WRITE = (1<<1); -constexpr int FASTOS_FILE_OPEN_EXISTING = (1<<2); -constexpr int FASTOS_FILE_OPEN_CREATE = (1<<3); -constexpr int FASTOS_FILE_OPEN_TRUNCATE = (1<<4); -constexpr int FASTOS_FILE_OPEN_STDOUT = (2<<5); -constexpr int FASTOS_FILE_OPEN_STDERR = (3<<5); -constexpr int FASTOS_FILE_OPEN_STDFLAGS = (3<<5); -constexpr int FASTOS_FILE_OPEN_DIRECTIO = (1<<7); -constexpr int FASTOS_FILE_OPEN_SYNCWRITES = (1<<9); // synchronous writes - -/** - * This class contains regular file-access functionality. - * - * Example (how to read 10 bytes from the file 'hello.txt'): - * - * @code - * void Foo::Bar () - * { - * FastOS_File file("hello.txt"); - * - * if(file.OpenReadOnly()) - * { - * char buffer[10]; - * - * if(file.Read(buffer, 10) == 10) - * { - * // Read success - * } - * else - * { - * // Read failure - * } - * } - * else - * { - * // Unable to open file 'hello.txt' - * } - * } - * @endcode - */ - -class DirectIOException : public std::exception -{ -public: - DirectIOException(const char * fileName, const void * buffer, size_t length, int64_t offset); - ~DirectIOException(); - const char* what() const noexcept override { return _what.c_str(); } - const void * getBuffer() const { return _buffer; } - size_t getLength() const { return _length; } - int64_t getOffset() const { return _offset; } - const std::string & getFileName() const { return _fileName; } -private: - std::string _what; - std::string _fileName; - const void * _buffer; - size_t _length; - int64_t _offset; -}; - -class FastOS_FileInterface -{ -private: - FastOS_FileInterface (const FastOS_FileInterface&); - FastOS_FileInterface& operator=(const FastOS_FileInterface&); - - // Default options for madvise used on every file opening. Default is FADV_NORMAL - // Set with setDefaultFAdviseOptions() application wide. - // And setFAdviseOptions() per file. - static int _defaultFAdviseOptions; - int _fAdviseOptions; - size_t _chunkSize; - void WriteBufInternal(const void *buffer, size_t length); - -protected: - std::string _filename; - unsigned int _openFlags; - bool _directIOEnabled; - bool _syncWritesEnabled; - -public: - static void setDefaultFAdviseOptions(int options) { _defaultFAdviseOptions = options; } - int getFAdviseOptions() const { return _fAdviseOptions; } - void setFAdviseOptions(int options) { _fAdviseOptions = options; } - - /** - * Return path separator string. This will yield "/" on UNIX systems. - * @return pointer to path separator character string - */ - static const char *GetPathSeparator() { return "/"; } - - /** - * Constructor. A filename could be supplied at this point, or specified - * later using @ref SetFileName() or @ref Open(). - * @param filename a filename (optional) - */ - FastOS_FileInterface(const char *filename=nullptr); - - /** - * Destructor. If the current file is open, the destructor will close - * it for you. - */ - virtual ~FastOS_FileInterface(); - - /** - * Associate a new filename with this object. This filename will be - * used when performing @ref Open() (unless @ref Open() specifies a - * different filename). - * @param filename filename character string (will be copied internally) - */ - virtual void SetFileName(const char *filename); - - /** - * Return the filename associated with the File object. If no filename - * has been set, an empty string is returned instead. - * @return The filename associated with the File object - */ - virtual const char *GetFileName() const; - - /** - * Open a file. - * @param openFlags A combination of the flags: FASTOS_FILE_OPEN_READ, - * (Is read-access desired?), FASTOS_FILE_OPEN_WRITE - * (Is write-access desired?), and - * FASTOS_FILE_OPEN_EXISTING (The file to be opened - * should already exist. If the file does not exist, - * the call will fail.). - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to - * @ref Open(). - * @return Boolean success/failure - */ - virtual bool Open(unsigned int openFlags, const char *filename=nullptr) = 0; - - /** - * Open a file for read/write access. The file will be created if it does - * not already exist. - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to @ref Open(). - * @return Boolean success/failure - */ - bool OpenReadWrite(const char *filename=nullptr); - - /** - * Open a file for read/write access. This method fails if the file does - * not already exist. - * @param abortIfNotExist Abort the program if the file does not exist. - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to - * @ref Open(). - * @return Boolean success/failure - */ - bool OpenExisting(bool abortIfNotExist=false, const char *filename=nullptr); - - /** - * Open a file for read access. This method fails if the file does - * not already exist. - * @param abortIfNotExist Abort the program if the file does not exist. - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to - * @ref Open(). - * @return Boolean success/failure - */ - bool OpenReadOnlyExisting (bool abortIfNotExist=false, const char *filename=nullptr); - - /** - * Open a file for write access. If the file does not exist, it is created. - * If the file exists, it is truncated to 0 bytes. - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to - * @ref Open(). - * @return Boolean success/failure - */ - bool OpenWriteOnlyTruncate(const char *filename=nullptr); - - /** - * Open a file for write access. This method fails if the file does - * not already exist. - * @param abortIfNotExist Abort the program if the file does not exist. - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to - * @ref Open(). - * @return Boolean success/failure - */ - bool OpenWriteOnlyExisting (bool abortIfNotExist=false, const char *filename=nullptr); - - /** - * Open a file for read-access only. This method fails if the file does - * not already exist. - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to @ref Open(). - * @return Boolean success/failure - */ - bool OpenReadOnly(const char *filename=nullptr); - - /** - * Open a file for write-access only. The file will be created if it does - * not already exist. - * @param filename You may optionally specify a filename here. This - * will replace the currently associated filename - * (if any) set using either the constructor, - * @ref SetFileName() or a previous call to @ref Open(). - * @return Boolean success/failure - */ - bool OpenWriteOnly(const char *filename=nullptr); - - /** - * Close the file. The call will successfully do nothing if the file - * already is closed. - * @return Boolean success/failure - */ - [[nodiscard]] virtual bool Close() = 0; - - /** - * Is the file currently opened? - * @return true if the file is opened, else false - */ - virtual bool IsOpened() const = 0; - - /** - * Read [length] bytes into [buffer]. - * @param buffer buffer pointer - * @param length number of bytes to read - * @return The number of bytes which was actually read, - * or -1 on error. - */ - [[nodiscard]] virtual ssize_t Read(void *buffer, size_t length) = 0; - - /** - * Write [len] bytes from [buffer]. This is just a wrapper for - * Write2, which does the same thing but returns the number of - * bytes written instead of just a bool. - * @param buffer buffer pointer - * @param len number of bytes to write - * @return Boolean success/failure - */ - [[nodiscard]] bool CheckedWrite(const void *buffer, size_t len); - - /** - * Write [len] bytes from [buffer]. - * @param buffer buffer pointer - * @param len number of bytes to write - * @return The number of bytes actually written, or -1 on error - */ - [[nodiscard]] virtual ssize_t Write2(const void *buffer, size_t len) = 0; - - /** - * Read [length] bytes into [buffer]. Caution! If the actual number - * of bytes read != [length], an error message is printed to stderr - * and the program aborts. - * - * The method is included for backwards compatibility reasons. - * @param buffer buffer pointer - * @param length number of bytes to read - */ - virtual void ReadBuf(void *buffer, size_t length); - - /** - * Write [length] bytes from [buffer] in chunks. Caution! If the write fails, - * an error message is printed to stderr and the program aborts. - * - * The method is included for backwards compatibility reasons. - * @param buffer buffer pointer - * @param length number of bytes to write - */ - virtual void WriteBuf(const void *buffer, size_t length); - - - /** - * Read [length] bytes at file offset [readOffset] into [buffer]. - * Only thread-safe if an OS-specific implementation exists. - * - * Caution! If the actual number of bytes read != [length], an - * error message is printed to stderr and the program aborts. - * - * @param buffer buffer pointer - * @param length number of bytes to read - * @param readOffset file offset where the read operation starts - */ - virtual void ReadBuf(void *buffer, size_t length, int64_t readOffset); - - /** - * Set the filepointer. The next @ref Read() or @ref Write() will - * continue from this position. - * @param position position of the new file pointer (in bytes) - * @return Boolean success/failure - */ - virtual bool SetPosition(int64_t position) = 0; - - /** - * Get the filepointer. -1 is returned if the operation fails. - * @return current position of file pointer (in bytes) - */ - virtual int64_t GetPosition() = 0; - - /** - * const version of @link GetPosition - */ - int64_t getPosition() const { return const_cast<FastOS_FileInterface *>(this)->GetPosition(); } - - /** - * Return the file size. This method requires that the file is - * currently opened. If you wish to determine the file size - * without opening the file, use @ref Stat(). - * If an error occurs, the returned value is -1. - * @return file size (in bytes) - */ - virtual int64_t GetSize() = 0; - - /** - * const version of @link GetSize - */ - int64_t getSize() const { return const_cast<FastOS_FileInterface *>(this)->GetSize(); } - - /** - * Return the time when file was last modified. - * @return time of last modification - */ - virtual time_t GetModificationTime() = 0; - - /** - * Delete the file. This method requires that the file is - * currently not opened. - * @return Boolean success/failure - */ - virtual bool Delete() = 0; - - /** - * Rename/move a file or directory. This method requires that - * the file is currently not opened. A move operation is - * supported as long as the source and destination reside - * on the same volume/device. - * The method fails if the destination already exists. - * @param newFileName New file name - * @return Boolean success/failure - */ - virtual bool Rename (const char *newFileName); - - /** - * Force completion of pending disk writes (flush cache). - */ - [[nodiscard]] virtual bool Sync() = 0; - - /** - * Are we in some kind of file read mode? - */ - bool IsReadMode() { - return ((_openFlags & FASTOS_FILE_OPEN_READ) != 0); - } - - /** - * Are we in some kind of file write mode? - */ - bool IsWriteMode() { - return ((_openFlags & FASTOS_FILE_OPEN_WRITE) != 0); - } - - /** - * Truncate or extend the file to the new size. - * The file pointer is also set to [newSize]. - * @ref SetSize() requires write access to the file. - * @param newSize New file size - * @return Boolean success/failure. - */ - virtual bool SetSize(int64_t newSize) = 0; - - /** - * Enable direct disk I/O (disable OS buffering & cache). Reads - * and writes will be performed directly to or from the user - * program buffer, provided appropriate size and alignment - * restrictions are met. If the restrictions are not met, a - * normal read or write is performed as a fallback. - * Call this before opening a file, and query - * @ref GetDirectIORestrictions() after a file is opened to get the - * neccessary alignment restrictions. It is possible that direct - * disk I/O could not be enabled. In that case - * @ref GetDirectIORestrictions will return false. - */ - virtual void EnableDirectIO(); - - virtual void EnableSyncWrites(); - - bool useSyncWrites() const { return _syncWritesEnabled; } - - /** - * Set the write chunk size used in WriteBuf. - */ - void setChunkSize(size_t chunkSize) { _chunkSize = chunkSize; } - size_t getChunkSize() const { return _chunkSize; } - - /** - * Get restrictions for direct disk I/O. The file should be opened - * before this method is called. - * Even though direct disk I/O is enabled through @ref EnableDirectIO(), - * this method could still return false, indicating that direct disk I/O - * is not being used for this file. This could be caused by either: no - * OS support for direct disk I/O, direct disk I/O might only be implemented - * for certain access-modes, the file is on a network drive or other - * partition where direct disk I/O is disallowed. - * - * The restriction-arguments are always filled with valid data, independant - * of the return code and direct disk I/O availability. - * - * @param memoryAlignment Buffer alignment restriction - * @param transferGranularity All transfers must be a multiple of - * [transferGranularity] bytes. All - * file offsets for these transfers must - * also be a multiple of [transferGranularity] - * bytes. - * @param transferMaximum All transfers must be <= [transferMaximum] - * bytes. - * @return True if direct disk I/O is being used for this file, else false. - */ - virtual bool - GetDirectIORestrictions(size_t &memoryAlignment, - size_t &transferGranularity, - size_t &transferMaximum); - - /** - * Retrieve the required padding for direct I/O to be used. - * - * @param offset File offset - * @param buflen Buffer length - * @param padBefore Number of pad bytes needed in front of the buffer - * @param padAfter Number of pad bytes needed after the buffer - * - * @return True if the file access can be accomplished with - * direct I/O, else false. - */ - virtual bool DirectIOPadding(int64_t offset, - size_t buflen, - size_t &padBefore, - size_t &padAfter); - - /** - * Allocate a buffer properly alligned with regards to direct io - * access restrictions. - * @param byteSize Number of bytes to be allocated - * @param realPtr Reference where the actual pointer returned - * from malloc will be saved. Use free() with - * this pointer to deallocate the buffer. - * This value is always set. - * @return Alligned pointer value or nullptr if out of memory - */ - static void *allocateGenericDirectIOBuffer(size_t byteSize, void *&realPtr); - - /** - * Get maximum memory alignment for directio buffers. - * @return maximum memory alignment for directio buffers. - */ - static size_t getMaxDirectIOMemAlign(); - - /** - * Allocate a buffer properly alligned with regards to direct io - * access restrictions. - * @param byteSize Number of bytes to be allocated - * @param realPtr Reference where the actual pointer returned - * from malloc will be saved. Use free() with - * this pointer to deallocate the buffer. - * This value is always set. - * @return Alligned pointer value or nullptr if out of memory - */ - virtual void *AllocateDirectIOBuffer(size_t byteSize, void *&realPtr); - - /** - * Enable mapping of complete file contents into the address space of the - * running process. This only works for small files. This operation - * will be ignored on some file types. - */ - virtual void enableMemoryMap(int mmapFlags); - - /** - * Inquiry about where in memory file data is located. - * @return location of file data in memory. If the file is not mapped, - * nullptr is returned. - */ - virtual void *MemoryMapPtr(int64_t position) const; - - /** - * Inquiry if file content is mapped into memory. - * @return true if file is mapped in memory, false otherwise. - */ - virtual bool IsMemoryMapped() const; - - /** - * Will drop whatever is in the FS cache when called. Does not have effect in the future. - **/ - virtual void dropFromCache() const; - - enum Error - { - ERR_ZERO = 1, // No error New style - ERR_NOENT, // No such file or directory - ERR_NOMEM, // Not enough memory - ERR_ACCES, // Permission denied - ERR_EXIST, // File exists - ERR_INVAL, // Invalid argument - ERR_NFILE, // File table overflow - ERR_MFILE, // Too many open files - ERR_NOSPC, // No space left on device - ERR_INTR, // interrupt - ERR_AGAIN, // Resource unavailable, try again - ERR_BUSY, // Device or resource busy - ERR_IO, // I/O error - ERR_PERM, // Not owner - ERR_NODEV, // No such device - ERR_NXIO, // Device not configured - ERR_UNKNOWN, // Unknown - - ERR_EZERO = 1, // No error Old style - ERR_ENOENT, // No such file or directory - ERR_ENOMEM, // Not enough memory - ERR_EACCES, // Permission denied - ERR_EEXIST, // File exists - ERR_EINVAL, // Invalid argument - ERR_ENFILE, // File table overflow - ERR_EMFILE, // Too many open files - ERR_ENOSPC, // No space left on device - ERR_EINTR, // interrupt - ERR_EAGAIN, // Resource unavailable, try again - ERR_EBUSY, // Device or resource busy - ERR_EIO, // I/O error - ERR_EPERM, // Not owner - ERR_ENODEV, // No such device - ERR_ENXIO // Device not configured - }; - - - /** - * If a file operation fails, the error code can be retrieved - * via this method. See @ref Error for possible error codes. - * @return Error code - */ - static Error GetLastError(); - - /** - * Similar to @ref GetLastError(), but this method returns a string - * instead of an error code. - * @return String describing the last error - */ - static std::string getLastErrorString(); -}; - - -/** - * The class serves as a container for information returned by - * @ref FastOS_File::Stat(). - */ -class FastOS_StatInfo -{ -public: - /** - * Possible error codes. - */ - enum StatError - { - Ok, //!< ok - Unknown, //!< unknown error - FileNotFound //!< file not found error - }; - - StatError _error; - - /** - * Is it a regular file? This field is only valid if @ref _error is - * @ref Ok. - */ - bool _isRegular; - - /** - * Is it a directory? This field is only valid if @ref _error is - * @ref Ok. - */ - bool _isDirectory; - - /** - * File size. This field is only valid if @ref _error is - * @ref Ok. - */ - int64_t _size; - - /** - * Time of last modification in seconds. - */ - time_t _modifiedTime; - - /** - * Time of last modification in seconds. - */ - uint64_t _modifiedTimeNS; -}; - - -/** - * This class enumerates the contents of a given directory. - * - * Example: - * @code - * void Foo::Bar() - * { - * // Scan and print the contents of the directory '/usr/src/include' - * - * FastOS_DirectoryScan dirScan("/usr/src/include"); - * int numEntries = 0; - * - * while(dirScan.ReadNext()) - * { - * const char *name = dirScan.GetName(); - * bool isDirectory = dirScan.IsDirectory(); - * bool isRegular = dirScan.IsRegular(); - * - * printf("%-30s %s\n", name, - * isDirectory ? "DIR" : (isRegular ? "FILE" : "UNKN")); - * - * numEntries++; - * } - * - * printf("The directory contained %d entries.\n", numEntries); - * } - * @endcode - */ -class FastOS_DirectoryScanInterface -{ -private: - FastOS_DirectoryScanInterface(const FastOS_DirectoryScanInterface&); - FastOS_DirectoryScanInterface& operator= (const FastOS_DirectoryScanInterface&); - -protected: - std::string _searchPath; - -public: - - /** - * Constructor. - * - * @param path Path of the directory to be scanned. The path string - * is copied internally. - */ - FastOS_DirectoryScanInterface(const char *path); - - /** - * Destructor. - * - * Frees operating system resources related to the directory scan. - */ - virtual ~FastOS_DirectoryScanInterface(); - - /** - * Get search path. - * This is an internal copy of the path specified in the constructor. - * @return Search path string. - */ - const char *GetSearchPath () { return _searchPath.c_str(); } - - /** - * Read the next entry in the directory scan. Failure indicates - * that there are no more entries. If the call is successful, - * attributes for the entry can be read with @ref IsDirectory(), - * @ref IsRegular() and @ref GetName(). - * - * @return Boolean success/failure - */ - virtual bool ReadNext() = 0; - - /** - * After a successful @ref ReadNext() this method is used to - * determine if the entry is a directory entry or not. Calling this - * method after an unsuccessful @ref ReadNext() or before - * @ref ReadNext() is called for the first time, yields undefined - * results. - * - * @return True if the entry is a directory, else false. - */ - virtual bool IsDirectory() = 0; - - - /** - * After a successful @ref ReadNext() this method is used to - * determine if the entry is a regular file entry or not. Calling - * this method after an unsuccessful @ref ReadNext() or before - * @ref ReadNext() is called for the first time, yields undefined - * results. - * - * @return True if the entry is a regular file, else false. - */ - virtual bool IsRegular() = 0; - - /** - * After a successful @ref ReadNext() this method is used to - * determine the name of the recently read directory entry. Calling - * this method after an unsuccessful @ref ReadNext() or before - * @ref ReadNext() is called for the first time, yields undefined - * results. - * - * @return A pointer to the recently read directory entry. - */ - virtual const char *GetName() = 0; - - /** - * Check whether the creation of a directory scan succeeded or - * failed (e.g. due to resource constraints). - * - * return True if the directory scan is valid. - */ - virtual bool IsValidScan() const = 0; -}; - -#ifdef __linux__ -#include <vespa/fastos/linux_file.h> -typedef FastOS_Linux_File FASTOS_PREFIX(File); -#else -#include <vespa/fastos/unix_file.h> -typedef FastOS_UNIX_File FASTOS_PREFIX(File); -#endif -typedef FastOS_UNIX_DirectoryScan FASTOS_PREFIX(DirectoryScan); diff --git a/fastos/src/vespa/fastos/file_rw_ops.cpp b/fastos/src/vespa/fastos/file_rw_ops.cpp deleted file mode 100644 index 79fe95b21f2..00000000000 --- a/fastos/src/vespa/fastos/file_rw_ops.cpp +++ /dev/null @@ -1,13 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#include "file_rw_ops.h" -#include <unistd.h> - -namespace fastos { - -File_RW_Ops::ReadFunc File_RW_Ops::_read = ::read; -File_RW_Ops::WriteFunc File_RW_Ops::_write = ::write; -File_RW_Ops::PreadFunc File_RW_Ops::_pread = ::pread; -File_RW_Ops::PwriteFunc File_RW_Ops::_pwrite = ::pwrite; - -} diff --git a/fastos/src/vespa/fastos/file_rw_ops.h b/fastos/src/vespa/fastos/file_rw_ops.h deleted file mode 100644 index 4f7aa6f082f..00000000000 --- a/fastos/src/vespa/fastos/file_rw_ops.h +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#pragma once - -#include <sys/types.h> - - -namespace fastos { - -/* - * Class handling pointers to functions used by FastOS_File for read - * and writa access. Unit tests might modify pointers to inject errors. - */ -class File_RW_Ops -{ - using ReadFunc = ssize_t (*)(int fd, void* buf, size_t count); - using WriteFunc = ssize_t (*)(int fd, const void* buf, size_t count); - using PreadFunc = ssize_t (*)(int fd, void* buf, size_t count, off_t offset); - using PwriteFunc = ssize_t (*)(int fd, const void* buf, size_t count, off_t offset); - -public: - static ReadFunc _read; - static WriteFunc _write; - static PreadFunc _pread; - static PwriteFunc _pwrite; - - static ssize_t read(int fd, void* buf, size_t count) { return _read(fd, buf, count); } - static ssize_t write(int fd, const void* buf, size_t count) { return _write(fd, buf, count); } - static ssize_t pread(int fd, void* buf, size_t count, off_t offset) { return _pread(fd, buf, count, offset); } - static ssize_t pwrite(int fd, const void* buf, size_t count, off_t offset) { return _pwrite(fd, buf, count, offset); } -}; - -} diff --git a/fastos/src/vespa/fastos/linux_file.cpp b/fastos/src/vespa/fastos/linux_file.cpp deleted file mode 100644 index 6fb29782957..00000000000 --- a/fastos/src/vespa/fastos/linux_file.cpp +++ /dev/null @@ -1,436 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -/** -****************************************************************************** -* @author Oivind H. Danielsen -* @date Creation date: 2000-09-21 -* @file -* Implementation of FastOS_Linux_File methods. -*****************************************************************************/ - -#ifdef __linux__ -#include "file.h" -#include "file_rw_ops.h" -#include <sstream> -#include <unistd.h> -#include <fcntl.h> -#include <cstdio> -#include <cstring> -#include <system_error> -#include <cassert> - -using fastos::File_RW_Ops; - -const size_t FastOS_Linux_File::_directIOFileAlign = 4096; -const size_t FastOS_Linux_File::_directIOMemAlign = 4096; - -FastOS_Linux_File::FastOS_Linux_File(const char *filename) - : FastOS_UNIX_File(filename), - _cachedSize(-1), - _filePointer(-1) -{ -} - -FastOS_Linux_File::~FastOS_Linux_File () { - bool ok = Close(); - assert(ok); -} - -#define DIRECTIOPOSSIBLE(buf, len, off) \ - (((off) & (_directIOFileAlign - 1)) == 0 && \ - ((len) & (_directIOFileAlign - 1)) == 0 && \ - (reinterpret_cast<unsigned long>(buf) & (_directIOMemAlign - 1)) == 0) - -ssize_t -FastOS_Linux_File::readInternal(int fh, void *buffer, size_t length, int64_t readOffset) -{ - char * data = static_cast<char *>(buffer); - ssize_t has_read(0); - while (has_read < ssize_t(length)) { - size_t lenNow = std::min(getChunkSize(), length - has_read); - ssize_t readNow = File_RW_Ops::pread(fh, data + has_read, lenNow, readOffset + has_read); - if (readNow > 0) { - has_read += readNow; - } else { - return (has_read > 0) ? has_read : readNow; - } - } - return has_read; -} - - -ssize_t -FastOS_Linux_File::readInternal(int fh, void *buffer, size_t length) -{ - char * data = static_cast<char *>(buffer); - ssize_t has_read(0); - while (has_read < ssize_t(length)) { - size_t lenNow = std::min(getChunkSize(), length - has_read); - ssize_t readNow = File_RW_Ops::read(fh, data + has_read, lenNow); - if (readNow > 0) { - has_read += readNow; - } else { - return (has_read > 0) ? has_read : readNow; - } - } - return has_read; -} - - -ssize_t -FastOS_Linux_File::writeInternal(int fh, const void *buffer, size_t length, int64_t writeOffset) -{ - return File_RW_Ops::pwrite(fh, buffer, length, writeOffset); -} - -ssize_t -FastOS_Linux_File::writeInternal(int fh, const void *buffer, size_t length) -{ - return File_RW_Ops::write(fh, buffer, length); -} - - -ssize_t FastOS_Linux_File::readUnalignedEnd(void *buffer, size_t length, int64_t readOffset) -{ - if (length == 0) { return 0; } - int fh = open(GetFileName(), O_RDONLY, 0664); - if (fh < 0) { - std::ostringstream os; - os << "Failed opening file " << GetFileName() << " for reading the unaligend end due to : " << getLastErrorString(); - throw std::runtime_error(os.str()); - } - ssize_t readResult = readInternal(fh, buffer, length, readOffset); - close(fh); - return readResult; -} - -ssize_t FastOS_Linux_File::writeUnalignedEnd(const void *buffer, size_t length, int64_t writeOffset) -{ - if (length == 0) { return 0; } - int fh = open(GetFileName(), O_WRONLY | O_SYNC, 0664); - if (fh < 0) { - std::ostringstream os; - os << "Failed opening file " << GetFileName() << " for reading the unaligend end due to : " << getLastErrorString(); - throw std::runtime_error(os.str()); - } - ssize_t writeResult = writeInternal(fh, buffer, length, writeOffset); - close(fh); - return writeResult; -} - -ssize_t -FastOS_Linux_File::ReadBufInternal(void *buffer, size_t length, int64_t readOffset) -{ - if (length == 0) { return 0; } - ssize_t readResult; - - if (_directIOEnabled) { - if (DIRECTIOPOSSIBLE(buffer, length, readOffset)) { - readResult = readInternal(_filedes, buffer, length, readOffset); - } else { - size_t alignedLength(length & ~(_directIOFileAlign - 1)); - if (DIRECTIOPOSSIBLE(buffer, alignedLength, readOffset)) { - size_t remain(length - alignedLength); - if (alignedLength > 0) { - readResult = readInternal(_filedes, buffer, alignedLength, readOffset); - } else { - readResult = 0; - } - if (static_cast<size_t>(readResult) == alignedLength && (remain != 0)) { - ssize_t readResult2 = readUnalignedEnd(static_cast<char *>(buffer) + alignedLength, - remain, readOffset + alignedLength); - if (readResult == 0) { - readResult = readResult2; - } else if (readResult2 > 0) { - readResult += readResult2; - } - } - } else { - throw DirectIOException(GetFileName(), buffer, length, readOffset); - } - } - } else { - readResult = readInternal(_filedes, buffer, length, readOffset); - } - - if (readResult < 0) { - perror("pread error"); - } - - return readResult; -} - -void -FastOS_Linux_File::ReadBuf(void *buffer, size_t length, int64_t readOffset) -{ - ssize_t readResult(ReadBufInternal(buffer, length, readOffset)); - if (static_cast<size_t>(readResult) != length) { - std::string errorString = (readResult != -1) - ? std::string("short read") - : getLastErrorString(); - std::ostringstream os; - os << "Fatal: Reading " << length << " bytes, got " << readResult << " from '" - << GetFileName() << "' failed: " << errorString; - throw std::runtime_error(os.str()); - } -} - - -ssize_t -FastOS_Linux_File::Read(void *buffer, size_t len) -{ - if (_directIOEnabled) { - ssize_t readResult = ReadBufInternal(buffer, len, _filePointer); - if (readResult > 0) { - _filePointer += readResult; - } - return readResult; - } else { - return readInternal(_filedes, buffer, len); - } -} - - -ssize_t -FastOS_Linux_File::Write2(const void *buffer, size_t length) -{ - const char * data = static_cast<const char *>(buffer); - ssize_t written(0); - while (written < ssize_t(length)) { - size_t lenNow = std::min(getChunkSize(), length - written); - ssize_t writtenNow = internalWrite2(data + written, lenNow); - if (writtenNow > 0) { - written += writtenNow; - } else { - return (written > 0) ? written : writtenNow;; - } - } - return written; -} - -ssize_t -FastOS_Linux_File::internalWrite2(const void *buffer, size_t length) -{ - ssize_t writeRes; - if (_directIOEnabled) { - if (DIRECTIOPOSSIBLE(buffer, length, _filePointer)) { - writeRes = writeInternal(_filedes, buffer, length, _filePointer); - } else { - size_t alignedLength(length & ~(_directIOFileAlign - 1)); - if (DIRECTIOPOSSIBLE(buffer, alignedLength, _filePointer)) { - size_t remain(length - alignedLength); - if (alignedLength > 0) { - writeRes = writeInternal(_filedes, buffer, alignedLength, _filePointer); - } else { - writeRes = 0; - } - if (static_cast<size_t>(writeRes) == alignedLength && remain != 0) { - ssize_t writeRes2 = writeUnalignedEnd(static_cast<const char *>(buffer) + alignedLength, - remain, _filePointer + alignedLength); - if (writeRes == 0) { - writeRes = writeRes2; - } else if (writeRes2 > 0) { - writeRes += writeRes2; - } - } - } else { - throw DirectIOException(GetFileName(), buffer, length, _filePointer); - } - } - if (writeRes > 0) { - _filePointer += writeRes; - if (_filePointer > _cachedSize) { - _cachedSize = _filePointer; - } - } - } else { - writeRes = writeInternal(_filedes, buffer, length); - } - - return writeRes; -} - - -bool -FastOS_Linux_File::SetPosition(int64_t desiredPosition) -{ - bool rc = FastOS_UNIX_File::SetPosition(desiredPosition); - - if (rc && _directIOEnabled) { - _filePointer = desiredPosition; - } - - return rc; -} - - -int64_t -FastOS_Linux_File::GetPosition() -{ - return _directIOEnabled ? _filePointer : FastOS_UNIX_File::GetPosition(); -} - - -bool -FastOS_Linux_File::SetSize(int64_t newSize) -{ - bool rc = FastOS_UNIX_File::SetSize(newSize); - - if (rc) { - _cachedSize = newSize; - } - return rc; -} - - -namespace { - void * align(void * p, size_t alignment) { - const size_t alignMask(alignment-1); - return reinterpret_cast<void *>((reinterpret_cast<unsigned long>(p) + alignMask) & ~alignMask); - } -} - -void * -FastOS_Linux_File::AllocateDirectIOBuffer (size_t byteSize, void *&realPtr) -{ - size_t dummy1, dummy2; - size_t memoryAlignment; - - GetDirectIORestrictions(memoryAlignment, dummy1, dummy2); - - realPtr = malloc(byteSize + memoryAlignment - 1); - return align(realPtr, memoryAlignment); -} - -size_t -FastOS_Linux_File::getMaxDirectIOMemAlign() -{ - return _directIOMemAlign; -} - - -bool -FastOS_Linux_File::GetDirectIORestrictions (size_t &memoryAlignment, size_t &transferGranularity, size_t &transferMaximum) -{ - if (_directIOEnabled) { - memoryAlignment = _directIOMemAlign; - transferGranularity = _directIOFileAlign; - transferMaximum = 0x7FFFFFFF; - return true; - } else { - return FastOS_UNIX_File::GetDirectIORestrictions(memoryAlignment, transferGranularity, transferMaximum); - } -} - - -bool -FastOS_Linux_File::DirectIOPadding (int64_t offset, size_t length, size_t &padBefore, size_t &padAfter) -{ - if (_directIOEnabled) { - - padBefore = offset & (_directIOFileAlign - 1); - padAfter = _directIOFileAlign - ((padBefore + length) & (_directIOFileAlign - 1)); - - if (padAfter == _directIOFileAlign) { - padAfter = 0; - } - if (int64_t(offset+length+padAfter) > _cachedSize) { - // _cachedSize is not really trustworthy, so if we suspect it is not correct, we correct it. - // The main reason is that it will not reflect the file being extended by another filedescriptor. - _cachedSize = GetSize(); - } - if ((padAfter != 0) && - (static_cast<int64_t>(offset + length + padAfter) > _cachedSize) && - (static_cast<int64_t>(offset + length) <= _cachedSize)) - { - padAfter = _cachedSize - (offset + length); - } - - if (static_cast<uint64_t>(offset + length + padAfter) <= static_cast<uint64_t>(_cachedSize)) { - return true; - } - } - - padAfter = 0; - padBefore = 0; - - return false; -} - - -void -FastOS_Linux_File::EnableDirectIO() -{ - if (!IsOpened()) { - _directIOEnabled = true; - } -} - - -bool -FastOS_Linux_File::Open(unsigned int openFlags, const char *filename) -{ - bool rc; - _cachedSize = -1; - _filePointer = -1; - if (_directIOEnabled && (_openFlags & FASTOS_FILE_OPEN_STDFLAGS) != 0) { - _directIOEnabled = false; - } - if (_syncWritesEnabled) { - openFlags |= FASTOS_FILE_OPEN_SYNCWRITES; - } - if (_directIOEnabled) { - rc = FastOS_UNIX_File::Open(openFlags | FASTOS_FILE_OPEN_DIRECTIO, filename); - if ( ! rc ) { //Retry without directIO. - rc = FastOS_UNIX_File::Open(openFlags | FASTOS_FILE_OPEN_SYNCWRITES, filename); - } - if (rc) { - int fadviseOptions = getFAdviseOptions(); - if (POSIX_FADV_NORMAL != fadviseOptions) { - rc = (posix_fadvise(_filedes, 0, 0, fadviseOptions) == 0); - if (!rc) { - bool close_ok = Close(); - assert(close_ok); - } - } - } - if (rc) { - bool sync_ok = Sync(); - assert(sync_ok); - _cachedSize = GetSize(); - _filePointer = 0; - } - } else { - rc = FastOS_UNIX_File::Open(openFlags, filename); - if (rc && (POSIX_FADV_NORMAL != getFAdviseOptions())) { - rc = (posix_fadvise(_filedes, 0, 0, getFAdviseOptions()) == 0); - if (!rc) { - bool close_ok = Close(); - assert(close_ok); - } - } - } - return rc; -} - -int -FastOS_Linux_File::count_open_files() -{ - static const char * const fd_dir_name = "/proc/self/fd"; - int count = 0; - DIR *dp = opendir(fd_dir_name); - if (dp != nullptr) { - struct dirent *ptr; - while ((ptr = readdir(dp)) != nullptr) { - if ((strcmp(".", ptr->d_name) != 0) && (strcmp("..", ptr->d_name) != 0)) { - ++count; - } - } - closedir(dp); - } else { - std::error_code ec(errno, std::system_category()); - fprintf(stderr, "could not scan directory %s: %s\n", fd_dir_name, ec.message().c_str()); - } - return count; -} - -#endif diff --git a/fastos/src/vespa/fastos/linux_file.h b/fastos/src/vespa/fastos/linux_file.h deleted file mode 100644 index 2481b163210..00000000000 --- a/fastos/src/vespa/fastos/linux_file.h +++ /dev/null @@ -1,57 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -/** -****************************************************************************** -* @author Oivind H. Danielsen -* @date Creation date: 2000-09-21 -* @file -* Class definition for FastOS_Linux_File. -*****************************************************************************/ - -#pragma once - -#include "unix_file.h" - -/** - * This is the Linux implementation of @ref FastOS_File. Most - * methods are inherited from @ref FastOS_UNIX_File. - */ -class FastOS_Linux_File : public FastOS_UNIX_File -{ -public: - using FastOS_UNIX_File::ReadBuf; -protected: - int64_t _cachedSize; - int64_t _filePointer; // Only maintained/used in directio mode - -public: - FastOS_Linux_File (const char *filename = nullptr); - ~FastOS_Linux_File () override; - bool GetDirectIORestrictions(size_t &memoryAlignment, size_t &transferGranularity, size_t &transferMaximum) override; - bool DirectIOPadding(int64_t offset, size_t length, size_t &padBefore, size_t &padAfter) override; - void EnableDirectIO() override; - bool SetPosition(int64_t desiredPosition) override; - int64_t GetPosition() override; - bool SetSize(int64_t newSize) override; - void ReadBuf(void *buffer, size_t length, int64_t readOffset) override; - void *AllocateDirectIOBuffer(size_t byteSize, void *&realPtr) override; - - - [[nodiscard]] ssize_t Read(void *buffer, size_t len) override; - [[nodiscard]] ssize_t Write2(const void *buffer, size_t len) override; - bool Open(unsigned int openFlags, const char *filename) override; - - static size_t getMaxDirectIOMemAlign(); - static int count_open_files(); -private: - ssize_t internalWrite2(const void *buffer, size_t len); - ssize_t readUnalignedEnd(void *buffer, size_t length, int64_t readOffset); - ssize_t writeUnalignedEnd(const void *buffer, size_t length, int64_t readOffset); - ssize_t ReadBufInternal(void *buffer, size_t length, int64_t readOffset); - ssize_t readInternal(int fh, void *buffer, size_t length, int64_t readOffset); - ssize_t readInternal(int fh, void *buffer, size_t length); - static ssize_t writeInternal(int fh, const void *buffer, size_t length, int64_t writeOffset); - static ssize_t writeInternal(int fh, const void *buffer, size_t length); - - static const size_t _directIOFileAlign; - static const size_t _directIOMemAlign; -}; diff --git a/fastos/src/vespa/fastos/types.h b/fastos/src/vespa/fastos/types.h deleted file mode 100644 index 69dd3e5231c..00000000000 --- a/fastos/src/vespa/fastos/types.h +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#pragma once - -#define FASTOS_PREFIX(a) FastOS_##a - -// New macros to support the new gcc visibility features. -#define VESPA_DLL_EXPORT __attribute__ ((visibility("default"))) -#define VESPA_DLL_LOCAL __attribute__ ((visibility("hidden"))) diff --git a/fastos/src/vespa/fastos/unix_file.cpp b/fastos/src/vespa/fastos/unix_file.cpp deleted file mode 100644 index 7c4cde19125..00000000000 --- a/fastos/src/vespa/fastos/unix_file.cpp +++ /dev/null @@ -1,590 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -/** -****************************************************************************** -* @author Oivind H. Danielsen -* @date Creation date: 2000-01-18 -* @file -* Implementation of FastOS_UNIX_File methods. -*****************************************************************************/ - -#include "file.h" -#include <sstream> -#include <cassert> -#include <cstring> -#include <unistd.h> -#include <fcntl.h> -#include <dirent.h> -#include <sys/stat.h> -#include <sys/mman.h> -#ifdef __linux__ -#include <sys/vfs.h> -#else -#include <sys/mount.h> -#endif -#ifdef __APPLE__ -#include <libproc.h> -#include <sys/proc_info.h> -#endif -#include "file_rw_ops.h" - -using fastos::File_RW_Ops; - -int FastOS_UNIX_File::GetLastOSError() { - return errno; -} - -ssize_t -FastOS_UNIX_File::Read(void *buffer, size_t len) -{ - return File_RW_Ops::read(_filedes, buffer, len); -} - - -ssize_t -FastOS_UNIX_File::Write2(const void *buffer, size_t len) -{ - return File_RW_Ops::write(_filedes, buffer, len); -} - -bool -FastOS_UNIX_File::SetPosition(int64_t desiredPosition) -{ - int64_t position = lseek(_filedes, desiredPosition, SEEK_SET); - - return (position == desiredPosition); -} - - -int64_t -FastOS_UNIX_File::GetPosition() -{ - return lseek(_filedes, 0, SEEK_CUR); -} - -void FastOS_UNIX_File::ReadBuf(void *buffer, size_t length, - int64_t readOffset) -{ - ssize_t readResult; - - readResult = File_RW_Ops::pread(_filedes, buffer, length, readOffset); - if (static_cast<size_t>(readResult) != length) { - std::string errorString = readResult != -1 ? - std::string("short read") : - FastOS_FileInterface::getLastErrorString(); - std::ostringstream os; - os << "Fatal: Reading " << length << " bytes, got " << readResult << " from '" - << GetFileName() << "' failed: " << errorString; - throw std::runtime_error(os.str()); - } -} - -bool -FastOS_UNIX_File::Stat(const char *filename, FastOS_StatInfo *statInfo) -{ - bool rc = false; - - struct stat stbuf{}; - int lstatres; - - do { - lstatres = lstat(filename, &stbuf); - } while (lstatres == -1 && errno == EINTR); - if (lstatres == 0) { - statInfo->_error = FastOS_StatInfo::Ok; - statInfo->_isRegular = S_ISREG(stbuf.st_mode); - statInfo->_isDirectory = S_ISDIR(stbuf.st_mode); - statInfo->_size = static_cast<int64_t>(stbuf.st_size); - statInfo->_modifiedTime = stbuf.st_mtime; -#ifdef __linux__ - statInfo->_modifiedTimeNS = stbuf.st_mtim.tv_sec; - statInfo->_modifiedTimeNS *= 1000000000; - statInfo->_modifiedTimeNS += stbuf.st_mtim.tv_nsec; -#elif defined(__APPLE__) - statInfo->_modifiedTimeNS = stbuf.st_mtimespec.tv_sec; - statInfo->_modifiedTimeNS *= 1000000000; - statInfo->_modifiedTimeNS += stbuf.st_mtimespec.tv_nsec; -#else - statInfo->_modifiedTimeNS = stbuf.st_mtime; - statInfo->_modifiedTimeNS *= 1000000000; -#endif - rc = true; - } else { - if (errno == ENOENT) { - statInfo->_error = FastOS_StatInfo::FileNotFound; - } else { - statInfo->_error = FastOS_StatInfo::Unknown; - } - } - - return rc; -} - -bool FastOS_UNIX_File::SetCurrentDirectory (const char *pathName) { return (chdir(pathName) == 0); } - - -int FastOS_UNIX_File::GetMaximumFilenameLength (const char *pathName) -{ - return pathconf(pathName, _PC_NAME_MAX); -} - -int FastOS_UNIX_File::GetMaximumPathLength(const char *pathName) -{ - return pathconf(pathName, _PC_PATH_MAX); -} - -std::string -FastOS_UNIX_File::getCurrentDirectory() -{ - std::string res; - int maxPathLen = FastOS_File::GetMaximumPathLength("."); - if (maxPathLen == -1) { - maxPathLen = 16384; - } else if (maxPathLen < 512) { - maxPathLen = 512; - } - - char *currentDir = new char [maxPathLen + 1]; - - if (getcwd(currentDir, maxPathLen) != nullptr) { - res = currentDir; - } - delete [] currentDir; - - return res; -} - - -unsigned int -FastOS_UNIX_File::CalcAccessFlags(unsigned int openFlags) -{ - unsigned int accessFlags=0; - - if ((openFlags & (FASTOS_FILE_OPEN_READ | FASTOS_FILE_OPEN_DIRECTIO)) != 0) { - if ((openFlags & FASTOS_FILE_OPEN_WRITE) != 0) { - // Open for reading and writing - accessFlags = O_RDWR; - } else { - // Open for reading only - accessFlags = O_RDONLY; - } - } else { - // Open for writing only - accessFlags = O_WRONLY; - } - - if (((openFlags & FASTOS_FILE_OPEN_EXISTING) == 0) && ((openFlags & FASTOS_FILE_OPEN_WRITE) != 0)) { - // Create file if it does not exist - accessFlags |= O_CREAT; - } - -#if defined(O_SYNC) - if ((openFlags & FASTOS_FILE_OPEN_SYNCWRITES) != 0) - accessFlags |= O_SYNC; -#elif defined(O_FSYNC) - if ((openFlags & FASTOS_FILE_OPEN_SYNCWRITES) != 0) - accessFlags |= O_FSYNC; -#endif - -#ifdef __linux__ - if ((openFlags & FASTOS_FILE_OPEN_DIRECTIO) != 0) { - accessFlags |= O_DIRECT; - } -#endif - - if ((openFlags & FASTOS_FILE_OPEN_TRUNCATE) != 0) { - // Truncate file on open - accessFlags |= O_TRUNC; - } - return accessFlags; -} - -#ifdef __linux__ -constexpr int ALWAYS_SUPPORTED_MMAP_FLAGS = ~MAP_HUGETLB; -#else -constexpr int ALWAYS_SUPPORTED_MMAP_FLAGS = ~0; -#endif - -bool -FastOS_UNIX_File::Open(unsigned int openFlags, const char *filename) -{ - bool rc = false; - assert(_filedes == -1); - - if ((openFlags & FASTOS_FILE_OPEN_STDFLAGS) != 0) { - FILE *file; - - switch(openFlags & FASTOS_FILE_OPEN_STDFLAGS) { - - case FASTOS_FILE_OPEN_STDOUT: - file = stdout; - SetFileName("stdout"); - break; - - case FASTOS_FILE_OPEN_STDERR: - file = stderr; - SetFileName("stderr"); - break; - - default: - fprintf(stderr, "Invalid open-flags %08X\n", openFlags); - abort(); - } - -#ifdef __linux__ - _filedes = file->_fileno; -#else - _filedes = fileno(file); -#endif - _openFlags = openFlags; - rc = true; - } else { - if (filename != nullptr) { - SetFileName(filename); - } - unsigned int accessFlags = CalcAccessFlags(openFlags); - - _filedes = open(_filename.c_str(), accessFlags, 0664); - - rc = (_filedes != -1); - - if (rc) { - _openFlags = openFlags; - if (_mmapEnabled) { - int64_t filesize = GetSize(); - auto mlen = static_cast<size_t>(filesize); - if ((static_cast<int64_t>(mlen) == filesize) && (mlen > 0)) { - void *mbase = mmap(nullptr, mlen, PROT_READ, MAP_SHARED | _mmapFlags, _filedes, 0); - if (mbase == MAP_FAILED) { - mbase = mmap(nullptr, mlen, PROT_READ, MAP_SHARED | (_mmapFlags & ALWAYS_SUPPORTED_MMAP_FLAGS), _filedes, 0); - } - if (mbase != MAP_FAILED) { -#ifdef __linux__ - int fadviseOptions = getFAdviseOptions(); - int eCode(0); - if (POSIX_FADV_RANDOM == fadviseOptions) { - eCode = posix_madvise(mbase, mlen, POSIX_MADV_RANDOM); - } else if (POSIX_FADV_SEQUENTIAL == fadviseOptions) { - eCode = posix_madvise(mbase, mlen, POSIX_MADV_SEQUENTIAL); - } - if (eCode != 0) { - fprintf(stderr, "Failed: posix_madvise(%p, %ld, %d) = %d\n", mbase, mlen, fadviseOptions, eCode); - } -#endif - _mmapbase = mbase; - _mmaplen = mlen; - } else { - close(_filedes); - _filedes = -1; - std::ostringstream os; - os << "mmap of file '" << GetFileName() << "' with flags '" << std::hex << (MAP_SHARED | _mmapFlags) << std::dec - << "' failed with error :'" << getErrorString(GetLastOSError()) << "'"; - throw std::runtime_error(os.str()); - } - } - } - } - - } - - return rc; -} - -void FastOS_UNIX_File::dropFromCache() const -{ -#ifdef __linux__ - posix_fadvise(_filedes, 0, 0, POSIX_FADV_DONTNEED); -#endif -} - - -bool -FastOS_UNIX_File::Close() -{ - bool ok = true; - - if (_filedes >= 0) { - if ((_openFlags & FASTOS_FILE_OPEN_STDFLAGS) != 0) { - ok = true; - } else { - do { - ok = (close(_filedes) == 0); - } while (!ok && errno == EINTR); - } - - if (_mmapbase != nullptr) { - madvise(_mmapbase, _mmaplen, MADV_DONTNEED); - munmap(static_cast<char *>(_mmapbase), _mmaplen); - _mmapbase = nullptr; - _mmaplen = 0; - } - - _filedes = -1; - } - - _openFlags = 0; - - return ok; -} - - -int64_t -FastOS_UNIX_File::GetSize() -{ - int64_t fileSize=-1; - struct stat stbuf{}; - - assert(IsOpened()); - - int res = fstat(_filedes, &stbuf); - - if (res == 0) { - fileSize = stbuf.st_size; - } - - return fileSize; -} - - -time_t -FastOS_UNIX_File::GetModificationTime() -{ - struct stat stbuf{}; - assert(IsOpened()); - - int res = fstat(_filedes, &stbuf); - assert(res == 0); - (void) res; - - return stbuf.st_mtime; -} - - -bool -FastOS_UNIX_File::Delete(const char *name) -{ - return (unlink(name) == 0); -} - - -bool -FastOS_UNIX_File::Delete() -{ - assert( ! IsOpened()); - - return (unlink(_filename.c_str()) == 0); -} - -bool FastOS_UNIX_File::Rename (const char *currentFileName, const char *newFileName) -{ - bool rc = false; - - // Enforce documentation. If the destination file exists, - // fail Rename. - FastOS_StatInfo statInfo{}; - if (!FastOS_File::Stat(newFileName, &statInfo)) { - rc = (rename(currentFileName, newFileName) == 0); - } else { - errno = EEXIST; - } - return rc; -} - -bool -FastOS_UNIX_File::Sync() -{ - assert(IsOpened()); - - return (fsync(_filedes) == 0); -} - - -bool -FastOS_UNIX_File::SetSize(int64_t newSize) -{ - bool rc = false; - - if (ftruncate(_filedes, static_cast<off_t>(newSize)) == 0) { - rc = SetPosition(newSize); - } - - return rc; -} - - -FastOS_File::Error -FastOS_UNIX_File::TranslateError (const int osError) -{ - switch(osError) { - case ENOENT: return ERR_NOENT; // No such file or directory - case ENOMEM: return ERR_NOMEM; // Not enough memory - case EACCES: return ERR_ACCES; // Permission denied - case EEXIST: return ERR_EXIST; // File exists - case EINVAL: return ERR_INVAL; // Invalid argument - case ENOSPC: return ERR_NOSPC; // No space left on device - case EINTR: return ERR_INTR; // interrupt - case EAGAIN: return ERR_AGAIN; // Resource unavailable, try again - case EBUSY: return ERR_BUSY; // Device or resource busy - case EIO: return ERR_IO; // I/O error - case EPERM: return ERR_PERM; // Not owner - case ENODEV: return ERR_NODEV; // No such device - case ENXIO: return ERR_NXIO; // Device not configured - default: break; - } - - if (osError == ENFILE) - return ERR_NFILE; - - if (osError == EMFILE) - return ERR_MFILE; - - return ERR_UNKNOWN; -} - - -std::string -FastOS_UNIX_File::getErrorString(const int osError) -{ - std::error_code ec(osError, std::system_category()); - return ec.message(); -} - - -int64_t FastOS_UNIX_File::GetFreeDiskSpace (const char *path) -{ - struct statfs statBuf{}; - int statVal = statfs(path, &statBuf); - if (statVal == 0) { - return int64_t(statBuf.f_bavail) * int64_t(statBuf.f_bsize); - } - - return -1; -} - -int -FastOS_UNIX_File::count_open_files() -{ -#ifdef __APPLE__ - int buffer_size = proc_pidinfo(getpid(), PROC_PIDLISTFDS, 0, nullptr, 0); - return buffer_size / sizeof(proc_fdinfo); -#else - return 0; -#endif -} - -FastOS_UNIX_DirectoryScan::FastOS_UNIX_DirectoryScan(const char *searchPath) - : FastOS_DirectoryScanInterface(searchPath), - _statRun(false), - _isDirectory(false), - _isRegular(false), - _statName(nullptr), - _statFilenameP(nullptr), - _dir(nullptr), - _dp(nullptr) -{ - _dir = opendir(searchPath); - - const int minimumLength = 512 + 1; - const int defaultLength = 16384; - - int maxNameLength = FastOS_File::GetMaximumFilenameLength(searchPath); - int maxPathLength = FastOS_File::GetMaximumPathLength(searchPath); - int nameLength = maxNameLength + 1 + maxPathLength; - - if ((maxNameLength == -1) || - (maxPathLength == -1) || - (nameLength < minimumLength)) - { - nameLength = defaultLength; - } - - _statName = new char [nameLength + 1]; // Include null - - strcpy(_statName, searchPath); - strcat(_statName, "/"); - - _statFilenameP = &_statName[strlen(_statName)]; -} - - -FastOS_UNIX_DirectoryScan::~FastOS_UNIX_DirectoryScan() -{ - if (_dir != nullptr) { - closedir(_dir); - _dir = nullptr; - } - delete [] _statName; -} - - -bool -FastOS_UNIX_DirectoryScan::ReadNext() -{ - _statRun = false; - - if (_dir != nullptr) { - _dp = readdir(_dir); - return (_dp != nullptr); - } - - return false; -} - - -void -FastOS_UNIX_DirectoryScan::DoStat() -{ - struct stat stbuf{}; - - assert(_dp != nullptr); - - strcpy(_statFilenameP, _dp->d_name); - - if (lstat(_statName, &stbuf) == 0) { - _isRegular = S_ISREG(stbuf.st_mode); - _isDirectory = S_ISDIR(stbuf.st_mode); - } else { - printf("lstat failed for [%s]\n", _dp->d_name); - _isRegular = false; - _isDirectory = false; - } - - _statRun = true; -} - - -bool -FastOS_UNIX_DirectoryScan::IsDirectory() -{ - if (!_statRun) { - DoStat(); - } - - return _isDirectory; -} - - -bool -FastOS_UNIX_DirectoryScan::IsRegular() -{ - if (!_statRun) { - DoStat(); - } - - return _isRegular; -} - - -const char * -FastOS_UNIX_DirectoryScan::GetName() -{ - assert(_dp != nullptr); - - return static_cast<const char *>(_dp->d_name); -} - - -bool -FastOS_UNIX_DirectoryScan::IsValidScan() const -{ - return _dir != nullptr; -} diff --git a/fastos/src/vespa/fastos/unix_file.h b/fastos/src/vespa/fastos/unix_file.h deleted file mode 100644 index 31e45f8d2fa..00000000000 --- a/fastos/src/vespa/fastos/unix_file.h +++ /dev/null @@ -1,130 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. -/** -****************************************************************************** -* @author Oivind H. Danielsen -* @date Creation date: 2000-01-18 -* @file -* Class definitions for FastOS_UNIX_File and FastOS_UNIX_DirectoryScan. -*****************************************************************************/ - -#pragma once - -#include <vespa/fastos/file.h> - -/** - * This is the generic UNIX implementation of @ref FastOS_FileInterface. - */ -class FastOS_UNIX_File : public FastOS_FileInterface -{ -public: - using FastOS_FileInterface::ReadBuf; -private: - FastOS_UNIX_File(const FastOS_UNIX_File&); - FastOS_UNIX_File& operator=(const FastOS_UNIX_File&); - -protected: - void *_mmapbase; - size_t _mmaplen; - int _filedes; - int _mmapFlags; - bool _mmapEnabled; - - static unsigned int CalcAccessFlags(unsigned int openFlags); - -public: - static bool Rename (const char *currentFileName, const char *newFileName); - bool Rename (const char *newFileName) override { - return FastOS_FileInterface::Rename(newFileName); - } - - static bool Stat(const char *filename, FastOS_StatInfo *statInfo); - - static std::string getCurrentDirectory(); - - static bool SetCurrentDirectory (const char *pathName); - static int GetMaximumFilenameLength (const char *pathName); - static int GetMaximumPathLength (const char *pathName); - - FastOS_UNIX_File(const char *filename=nullptr) - : FastOS_FileInterface(filename), - _mmapbase(nullptr), - _mmaplen(0), - _filedes(-1), - _mmapFlags(0), - _mmapEnabled(false) - { } - - void ReadBuf(void *buffer, size_t length, int64_t readOffset) override; - [[nodiscard]] ssize_t Read(void *buffer, size_t len) override; - [[nodiscard]] ssize_t Write2(const void *buffer, size_t len) override; - bool Open(unsigned int openFlags, const char *filename) override; - [[nodiscard]] bool Close() override; - bool IsOpened() const override { return _filedes >= 0; } - - void enableMemoryMap(int flags) override { - _mmapEnabled = true; - _mmapFlags = flags; - } - - void *MemoryMapPtr(int64_t position) const override { - if (_mmapbase != nullptr) { - if (position < int64_t(_mmaplen)) { - return static_cast<void *>(static_cast<char *>(_mmapbase) + position); - } else { // This is an indication that the file size has changed and a remap/reopen must be done. - return nullptr; - } - } else { - return nullptr; - } - } - - bool IsMemoryMapped() const override { return _mmapbase != nullptr; } - bool SetPosition(int64_t desiredPosition) override; - int64_t GetPosition() override; - int64_t GetSize() override; - time_t GetModificationTime() override; - bool Delete() override; - [[nodiscard]] bool Sync() override; - bool SetSize(int64_t newSize) override; - void dropFromCache() const override; - - static bool Delete(const char *filename); - static int GetLastOSError(); - static Error TranslateError(const int osError); - static std::string getErrorString(const int osError); - static int64_t GetFreeDiskSpace (const char *path); - static int count_open_files(); -}; - -#include <dirent.h> -/** - * This is the generic UNIX implementation of @ref FastOS_DirectoryScan. - */ -class FastOS_UNIX_DirectoryScan : public FastOS_DirectoryScanInterface -{ -private: - FastOS_UNIX_DirectoryScan(const FastOS_UNIX_DirectoryScan&); - FastOS_UNIX_DirectoryScan& operator=(const FastOS_UNIX_DirectoryScan&); - - bool _statRun; - bool _isDirectory; - bool _isRegular; - char *_statName; - char *_statFilenameP; - - void DoStat(); - -protected: - DIR *_dir; - struct dirent *_dp; - -public: - FastOS_UNIX_DirectoryScan(const char *searchPath); - ~FastOS_UNIX_DirectoryScan(); - - bool ReadNext() override; - bool IsDirectory() override; - bool IsRegular() override; - const char *GetName() override; - bool IsValidScan() const override; -}; |