-
Notifications
You must be signed in to change notification settings - Fork 13
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
(WIP) [skip ci] decoupling segment storage
- Loading branch information
Showing
12 changed files
with
560 additions
and
445 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,145 @@ | ||
// Copyright 2023 Lawrence Livermore National Security, LLC and other Metall | ||
// Project Developers. See the top-level COPYRIGHT file for details. | ||
// | ||
// SPDX-License-Identifier: (Apache-2.0 OR MIT) | ||
|
||
#ifndef METALL_INCLUDE_METALL_KERNEL_DATA_STORAGE_HPP | ||
#define METALL_INCLUDE_METALL_KERNEL_DATA_STORAGE_HPP | ||
|
||
namespace metall::kernel { | ||
|
||
/// \brief A class for manage all datastore data (files) on file system. | ||
template <typename data_storage_impl> | ||
class data_storage { | ||
private: | ||
using imp_type = data_storage_impl; | ||
|
||
public: | ||
// TODO: Change design | ||
using size_type = typename imp_type::size_type; | ||
using different_type = typename imp_type::different_type; | ||
|
||
using path_type = typename imp_type::path_type; | ||
|
||
data_storage() = default; | ||
|
||
~data_storage() = default; | ||
|
||
data_storage(const data_storage &) = delete; | ||
data_storage &operator=(const data_storage &) = delete; | ||
|
||
data_storage(data_storage &&other) noexcept = default; | ||
data_storage &operator=(data_storage &&other) noexcept = default; | ||
|
||
/// \brief Returns the directory path where segment manager can store files. | ||
inline static path_type get_path(const path_type &base_path) { | ||
return imp_type::get_path(base_path); | ||
} | ||
|
||
/// \brief Gets the size of an existing segment. | ||
/// This is a static version of size() method. | ||
/// \param base_path A path to a segment. | ||
inline static size_type get_size(const path_type &base_path) { | ||
return imp_type::get_size(base_path); | ||
} | ||
|
||
/// \brief Checks if a segment is openable. | ||
/// \param base_path A path to a segment. | ||
/// \return Return true if success; otherwise, false. | ||
inline static bool openable(const path_type &base_path) { | ||
return imp_type::openable(base_path); | ||
} | ||
|
||
/// \brief Copies segment to another location. | ||
/// \param source_path A path to a source segment. | ||
/// \param destination_path A destination path. | ||
/// \param clone If true, uses clone (reflink) for copying files. | ||
/// \param max_num_threads The maximum number of threads to use. | ||
/// If <= 0 is given, the value is automatically determined. | ||
/// \return Return true if success; otherwise, false. | ||
inline static bool copy(const path_type &source_path, | ||
const path_type &destination_path, const bool clone, | ||
const int max_num_threads) { | ||
return imp_type::copy(source_path, destination_path, clone, | ||
max_num_threads); | ||
} | ||
|
||
/// \brief Creates a new segment. | ||
/// Calling this function fails if this class already manages an opened | ||
/// segment. \base_path A base directory path to create a segment. \param | ||
/// vm_region_size The size of a reserved VM region. \param vm_region The | ||
/// address of a reserved VM region. \block_size The block size. \return | ||
/// Return true if success; otherwise, false. | ||
inline bool create(const path_type &base_path, const size_type vm_region_size, | ||
void *const vm_region, const size_type block_size) { | ||
return m_impl.create(base_path, vm_region_size, vm_region, block_size); | ||
} | ||
|
||
/// \brief Opens an existing segment. | ||
/// Calling this function fails if this class already manages an opened | ||
/// segment. \base_path A base directory path to create a segment. \param | ||
/// vm_region_size The size of a VM region. \param vm_region The address of a | ||
/// VM region. \param read_only If true, this segment is read only. \return | ||
/// Return true if success; otherwise, false. | ||
inline bool open(const path_type &base_path, const size_type vm_region_size, | ||
void *const vm_region, const bool read_only) { | ||
return m_impl.open(base_path, vm_region_size, vm_region, read_only); | ||
} | ||
|
||
/// \brief Extends the currently opened segment if necessary. | ||
/// \param request_size A segment size to extend to. | ||
/// \return Returns true if the segment is extended to or already larger than | ||
/// the requested size. Returns false on failure. | ||
inline bool extend(const size_type request_size) { | ||
return m_impl.extend(request_size); | ||
} | ||
|
||
/// \brief Destroys the segment --- the data will be lost. | ||
/// To save data to files, sync() must be called beforehand. | ||
inline bool destroy() { return m_impl.destroy(); } | ||
|
||
/// \brief Syncs the segment with backing files. | ||
/// \param sync If false is specified, this function returns before finishing | ||
/// the sync operation. | ||
inline bool sync(const bool sync) { return m_impl.sync(sync); } | ||
|
||
/// \brief Tries to free the specified region in DRAM and file(s). | ||
/// The actual behavior depends on the running system. | ||
/// \param offset An offset to the region from the beginning of the segment. | ||
/// \param nbytes The size of the region. | ||
inline bool free_region(const different_type offset, const size_type nbytes) { | ||
return m_impl.free_region(offset, nbytes); | ||
} | ||
|
||
/// \brief Returns the address of the segment. | ||
/// \return The address of the segment. | ||
inline void *get_segment() const { return m_impl.get_segment(); } | ||
|
||
/// \brief Returns the current size. | ||
/// \return The current segment size. | ||
inline size_type size() const { return m_impl.size(); } | ||
|
||
/// \brief Returns the page size. | ||
/// \return The page size of the system. | ||
inline size_type page_size() const { return m_impl.page_size(); } | ||
|
||
/// \brief Checks if the segment is read only. | ||
/// \return Returns true if the segment is read only; otherwise, returns | ||
/// false. | ||
inline bool read_only() const { return m_impl.read_only(); } | ||
|
||
/// \brief Checks if there is a segment already open. | ||
/// \return Returns true if there is a segment already open. | ||
inline bool is_open() const { return m_impl.is_open(); } | ||
|
||
/// \brief Checks the sanity. | ||
/// \return Returns true if there is no issue; otherwise, returns false. | ||
/// If false is returned, the instance of this class cannot be used anymore. | ||
inline bool check_sanity() const { return m_impl.check_sanity(); } | ||
|
||
private: | ||
imp_type m_impl; | ||
}; | ||
} // namespace metall::kernel | ||
|
||
#endif // METALL_INCLUDE_METALL_KERNEL_DATA_STORAGE_HPP |
Oops, something went wrong.