summaryrefslogtreecommitdiffstats
path: root/src/rocksdb/port/win/env_win.h
diff options
context:
space:
mode:
Diffstat (limited to '')
-rw-r--r--src/rocksdb/port/win/env_win.h304
1 files changed, 304 insertions, 0 deletions
diff --git a/src/rocksdb/port/win/env_win.h b/src/rocksdb/port/win/env_win.h
new file mode 100644
index 000000000..8fbfb8246
--- /dev/null
+++ b/src/rocksdb/port/win/env_win.h
@@ -0,0 +1,304 @@
+// Copyright (c) 2011-present, Facebook, Inc. All rights reserved.
+// This source code is licensed under both the GPLv2 (found in the
+// COPYING file in the root directory) and Apache 2.0 License
+// (found in the LICENSE.Apache file in the root directory).
+// Copyright (c) 2011 The LevelDB Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file. See the AUTHORS file for names of contributors.
+//
+// An Env is an interface used by the rocksdb implementation to access
+// operating system functionality like the filesystem etc. Callers
+// may wish to provide a custom Env object when opening a database to
+// get fine gain control; e.g., to rate limit file system operations.
+//
+// All Env implementations are safe for concurrent access from
+// multiple threads without any external synchronization.
+
+#pragma once
+#include <stdint.h>
+#include <windows.h>
+
+#include <mutex>
+#include <string>
+#include <vector>
+
+#include "env/composite_env_wrapper.h"
+#include "port/port.h"
+#include "rocksdb/env.h"
+#include "rocksdb/file_system.h"
+#include "rocksdb/system_clock.h"
+#include "util/threadpool_imp.h"
+
+#undef GetCurrentTime
+#undef DeleteFile
+#undef LoadLibrary
+
+namespace ROCKSDB_NAMESPACE {
+namespace port {
+
+// Currently not designed for inheritance but rather a replacement
+class WinEnvThreads {
+ public:
+ explicit WinEnvThreads(Env* hosted_env);
+
+ ~WinEnvThreads();
+
+ WinEnvThreads(const WinEnvThreads&) = delete;
+ WinEnvThreads& operator=(const WinEnvThreads&) = delete;
+
+ void Schedule(void (*function)(void*), void* arg, Env::Priority pri,
+ void* tag, void (*unschedFunction)(void* arg));
+
+ int UnSchedule(void* arg, Env::Priority pri);
+
+ void StartThread(void (*function)(void* arg), void* arg);
+
+ void WaitForJoin();
+
+ unsigned int GetThreadPoolQueueLen(Env::Priority pri) const;
+
+ int ReserveThreads(int threads_to_be_reserved, Env::Priority pri);
+
+ int ReleaseThreads(int threads_to_be_released, Env::Priority pri);
+
+ static uint64_t gettid();
+
+ uint64_t GetThreadID() const;
+
+ // Allow increasing the number of worker threads.
+ void SetBackgroundThreads(int num, Env::Priority pri);
+ int GetBackgroundThreads(Env::Priority pri);
+
+ void IncBackgroundThreadsIfNeeded(int num, Env::Priority pri);
+
+ private:
+ Env* hosted_env_;
+ mutable std::mutex mu_;
+ std::vector<ThreadPoolImpl> thread_pools_;
+ std::vector<Thread> threads_to_join_;
+};
+
+class WinClock : public SystemClock {
+ public:
+ WinClock();
+ virtual ~WinClock() {}
+
+ static const char* kClassName() { return "WindowsClock"; }
+ const char* Name() const override { return kDefaultName(); }
+ const char* NickName() const override { return kClassName(); }
+
+ uint64_t NowMicros() override;
+
+ uint64_t NowNanos() override;
+
+ // 0 indicates not supported
+ uint64_t CPUMicros() override { return 0; }
+ void SleepForMicroseconds(int micros) override;
+
+ Status GetCurrentTime(int64_t* unix_time) override;
+ // Converts seconds-since-Jan-01-1970 to a printable string
+ virtual std::string TimeToString(uint64_t time);
+
+ uint64_t GetPerfCounterFrequency() const { return perf_counter_frequency_; }
+
+ private:
+ using FnGetSystemTimePreciseAsFileTime = VOID(WINAPI*)(LPFILETIME);
+
+ uint64_t perf_counter_frequency_;
+ uint64_t nano_seconds_per_period_;
+ FnGetSystemTimePreciseAsFileTime GetSystemTimePreciseAsFileTime_;
+};
+
+class WinFileSystem : public FileSystem {
+ public:
+ static const std::shared_ptr<WinFileSystem>& Default();
+ WinFileSystem(const std::shared_ptr<SystemClock>& clock);
+ ~WinFileSystem() {}
+ static const char* kClassName() { return "WinFS"; }
+ const char* Name() const override { return kClassName(); }
+ const char* NickName() const { return kDefaultName(); }
+
+ static size_t GetSectorSize(const std::string& fname);
+ size_t GetPageSize() const { return page_size_; }
+ size_t GetAllocationGranularity() const { return allocation_granularity_; }
+
+ IOStatus DeleteFile(const std::string& fname, const IOOptions& options,
+ IODebugContext* dbg) override;
+
+ // Truncate the named file to the specified size.
+ IOStatus Truncate(const std::string& /*fname*/, size_t /*size*/,
+ const IOOptions& /*options*/,
+ IODebugContext* /*dbg*/) override;
+ IOStatus NewSequentialFile(const std::string& fname,
+ const FileOptions& file_opts,
+ std::unique_ptr<FSSequentialFile>* result,
+ IODebugContext* dbg) override;
+
+ IOStatus NewRandomAccessFile(const std::string& fname,
+ const FileOptions& options,
+ std::unique_ptr<FSRandomAccessFile>* result,
+ IODebugContext* /*dbg*/) override;
+ IOStatus NewWritableFile(const std::string& f, const FileOptions& file_opts,
+ std::unique_ptr<FSWritableFile>* r,
+ IODebugContext* dbg) override;
+ IOStatus ReopenWritableFile(const std::string& fname,
+ const FileOptions& options,
+ std::unique_ptr<FSWritableFile>* result,
+ IODebugContext* dbg) override;
+
+ IOStatus NewRandomRWFile(const std::string& fname,
+ const FileOptions& file_opts,
+ std::unique_ptr<FSRandomRWFile>* result,
+ IODebugContext* dbg) override;
+ IOStatus NewMemoryMappedFileBuffer(
+ const std::string& fname,
+ std::unique_ptr<MemoryMappedFileBuffer>* result) override;
+
+ IOStatus NewDirectory(const std::string& name, const IOOptions& io_opts,
+ std::unique_ptr<FSDirectory>* result,
+ IODebugContext* dbg) override;
+ IOStatus FileExists(const std::string& f, const IOOptions& io_opts,
+ IODebugContext* dbg) override;
+ IOStatus GetChildren(const std::string& dir, const IOOptions& io_opts,
+ std::vector<std::string>* r,
+ IODebugContext* dbg) override;
+ IOStatus CreateDir(const std::string& dirname, const IOOptions& options,
+ IODebugContext* dbg) override;
+
+ // Creates directory if missing. Return Ok if it exists, or successful in
+ // Creating.
+ IOStatus CreateDirIfMissing(const std::string& dirname,
+ const IOOptions& options,
+ IODebugContext* dbg) override;
+
+ // Delete the specified directory.
+ IOStatus DeleteDir(const std::string& dirname, const IOOptions& options,
+ IODebugContext* dbg) override;
+ // Store the size of fname in *file_size.
+ IOStatus GetFileSize(const std::string& fname, const IOOptions& options,
+ uint64_t* file_size, IODebugContext* dbg) override;
+ // Store the last modification time of fname in *file_mtime.
+ IOStatus GetFileModificationTime(const std::string& fname,
+ const IOOptions& options,
+ uint64_t* file_mtime,
+ IODebugContext* dbg) override;
+ // Rename file src to target.
+ IOStatus RenameFile(const std::string& src, const std::string& target,
+ const IOOptions& options, IODebugContext* dbg) override;
+
+ // Hard Link file src to target.
+ IOStatus LinkFile(const std::string& /*src*/, const std::string& /*target*/,
+ const IOOptions& /*options*/,
+ IODebugContext* /*dbg*/) override;
+ IOStatus NumFileLinks(const std::string& /*fname*/,
+ const IOOptions& /*options*/, uint64_t* /*count*/,
+ IODebugContext* /*dbg*/) override;
+ IOStatus AreFilesSame(const std::string& /*first*/,
+ const std::string& /*second*/,
+ const IOOptions& /*options*/, bool* /*res*/,
+ IODebugContext* /*dbg*/) override;
+ IOStatus LockFile(const std::string& fname, const IOOptions& options,
+ FileLock** lock, IODebugContext* dbg) override;
+ IOStatus UnlockFile(FileLock* lock, const IOOptions& options,
+ IODebugContext* dbg) override;
+ IOStatus GetTestDirectory(const IOOptions& options, std::string* path,
+ IODebugContext* dbg) override;
+
+ // Create and returns a default logger (an instance of EnvLogger) for storing
+ // informational messages. Derived classes can override to provide custom
+ // logger.
+ IOStatus NewLogger(const std::string& fname, const IOOptions& io_opts,
+ std::shared_ptr<Logger>* result,
+ IODebugContext* dbg) override;
+ // Get full directory name for this db.
+ IOStatus GetAbsolutePath(const std::string& db_path, const IOOptions& options,
+ std::string* output_path,
+ IODebugContext* dbg) override;
+ IOStatus IsDirectory(const std::string& /*path*/, const IOOptions& options,
+ bool* is_dir, IODebugContext* /*dgb*/) override;
+ // This seems to clash with a macro on Windows, so #undef it here
+#undef GetFreeSpace
+ IOStatus GetFreeSpace(const std::string& /*path*/,
+ const IOOptions& /*options*/, uint64_t* /*diskfree*/,
+ IODebugContext* /*dbg*/) override;
+ FileOptions OptimizeForLogWrite(const FileOptions& file_options,
+ const DBOptions& db_options) const override;
+ FileOptions OptimizeForManifestRead(
+ const FileOptions& file_options) const override;
+ FileOptions OptimizeForManifestWrite(
+ const FileOptions& file_options) const override;
+
+ protected:
+ static uint64_t FileTimeToUnixTime(const FILETIME& ftTime);
+ // Returns true iff the named directory exists and is a directory.
+
+ virtual bool DirExists(const std::string& dname);
+ // Helper for NewWritable and ReopenWritableFile
+ virtual IOStatus OpenWritableFile(const std::string& fname,
+ const FileOptions& options,
+ std::unique_ptr<FSWritableFile>* result,
+ bool reopen);
+
+ private:
+ std::shared_ptr<SystemClock> clock_;
+ size_t page_size_;
+ size_t allocation_granularity_;
+};
+
+// Designed for inheritance so can be re-used
+// but certain parts replaced
+class WinEnvIO {
+ public:
+ explicit WinEnvIO(Env* hosted_env);
+
+ virtual ~WinEnvIO();
+
+ virtual Status GetHostName(char* name, uint64_t len);
+
+ private:
+ Env* hosted_env_;
+};
+
+class WinEnv : public CompositeEnv {
+ public:
+ WinEnv();
+
+ ~WinEnv();
+ static const char* kClassName() { return "WinEnv"; }
+ const char* Name() const override { return kClassName(); }
+ const char* NickName() const override { return kDefaultName(); }
+
+ Status GetHostName(char* name, uint64_t len) override;
+
+ Status GetThreadList(std::vector<ThreadStatus>* thread_list) override;
+
+ void Schedule(void (*function)(void*), void* arg, Env::Priority pri,
+ void* tag, void (*unschedFunction)(void* arg)) override;
+
+ int UnSchedule(void* arg, Env::Priority pri) override;
+
+ void StartThread(void (*function)(void* arg), void* arg) override;
+
+ void WaitForJoin() override;
+
+ unsigned int GetThreadPoolQueueLen(Env::Priority pri) const override;
+
+ int ReserveThreads(int threads_to_be_reserved, Env::Priority pri) override;
+
+ int ReleaseThreads(int threads_to_be_released, Env::Priority pri) override;
+
+ uint64_t GetThreadID() const override;
+
+ // Allow increasing the number of worker threads.
+ void SetBackgroundThreads(int num, Env::Priority pri) override;
+ int GetBackgroundThreads(Env::Priority pri) override;
+
+ void IncBackgroundThreadsIfNeeded(int num, Env::Priority pri) override;
+
+ private:
+ WinEnvIO winenv_io_;
+ WinEnvThreads winenv_threads_;
+};
+
+} // namespace port
+} // namespace ROCKSDB_NAMESPACE