diff options
author | Max Kellermann <max@duempel.org> | 2015-02-26 18:11:02 +0100 |
---|---|---|
committer | Max Kellermann <max@duempel.org> | 2015-02-26 18:11:02 +0100 |
commit | 4f0f81a047a3a5b78f28b583ee4a6518c12af578 (patch) | |
tree | 9339fa70d743bb303917a0eaa007e8c3a23a6df9 /src/fs/DirectoryReader.hxx | |
parent | e3908c8de6645b2a7577b47cb5c5e76c7c0b24be (diff) |
fs/DirectoryReader: use FindFirstFile(), FindNextFile() on WIN32
Diffstat (limited to 'src/fs/DirectoryReader.hxx')
-rw-r--r-- | src/fs/DirectoryReader.hxx | 85 |
1 files changed, 85 insertions, 0 deletions
diff --git a/src/fs/DirectoryReader.hxx b/src/fs/DirectoryReader.hxx index cd15952a1..ce27d2b9b 100644 --- a/src/fs/DirectoryReader.hxx +++ b/src/fs/DirectoryReader.hxx @@ -23,6 +23,89 @@ #include "check.h" #include "Path.hxx" +#ifdef WIN32 + +#include <windows.h> +#include <tchar.h> + +/** + * Reader for directory entries. + */ +class DirectoryReader { + const HANDLE handle; + WIN32_FIND_DATA data; + bool first; + + class MakeWildcardPath { + PathTraitsFS::pointer path; + + public: + MakeWildcardPath(PathTraitsFS::const_pointer _path) { + auto l = _tcslen(_path); + path = new PathTraitsFS::value_type[l + 3]; + _tcscpy(path, _path); + path[l] = _T('\\'); + path[l + 1] = _T('*'); + path[l + 2] = 0; + } + + ~MakeWildcardPath() { + delete[] path; + } + + operator PathTraitsFS::const_pointer() const { + return path; + } + }; + +public: + /** + * Creates new directory reader for the specified #dir. + */ + explicit DirectoryReader(Path dir) + :handle(FindFirstFile(MakeWildcardPath(dir.c_str()), &data)), + first(true) {} + + DirectoryReader(const DirectoryReader &other) = delete; + DirectoryReader &operator=(const DirectoryReader &other) = delete; + + /** + * Destroys this instance. + */ + ~DirectoryReader() { + if (!HasFailed()) + FindClose(handle); + } + + /** + * Checks if directory failed to open. + */ + bool HasFailed() const { + return handle == INVALID_HANDLE_VALUE; + } + + /** + * Reads next directory entry. + */ + bool ReadEntry() { + if (first) { + first = false; + return true; + } + + return FindNextFile(handle, &data) != 0; + } + + /** + * Extracts directory entry that was previously read by #ReadEntry. + */ + Path GetEntry() const { + return Path::FromFS(data.cFileName); + } +}; + +#else + #include <dirent.h> /** @@ -85,3 +168,5 @@ public: }; #endif + +#endif |