diff --git a/mooncake-store/include/client_metric.h b/mooncake-store/include/client_metric.h index f1c75680e8..d8c97ffb16 100644 --- a/mooncake-store/include/client_metric.h +++ b/mooncake-store/include/client_metric.h @@ -16,7 +16,7 @@ #include #include "environ.h" #include "hybrid_metric.h" -#include "utils.h" +#include "common/byte_size.h" namespace mooncake { diff --git a/mooncake-store/include/utils/base64.h b/mooncake-store/include/common/base64.h similarity index 100% rename from mooncake-store/include/utils/base64.h rename to mooncake-store/include/common/base64.h diff --git a/mooncake-store/include/common/byte_size.h b/mooncake-store/include/common/byte_size.h new file mode 100644 index 0000000000..e11814d362 --- /dev/null +++ b/mooncake-store/include/common/byte_size.h @@ -0,0 +1,101 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace mooncake { + +[[nodiscard]] inline std::string byte_size_to_string(uint64_t bytes) { + constexpr double kKiB = 1024.0; + constexpr double kMiB = kKiB * 1024.0; + constexpr double kGiB = kMiB * 1024.0; + constexpr double kTiB = kGiB * 1024.0; + + std::ostringstream oss; + oss << std::fixed << std::setprecision(2); + if (static_cast(bytes) == std::numeric_limits::max()) { + oss << "infinite"; + } else if (bytes >= static_cast(kTiB)) { + oss << bytes / kTiB << " TB"; + } else if (bytes >= static_cast(kGiB)) { + oss << bytes / kGiB << " GB"; + } else if (bytes >= static_cast(kMiB)) { + oss << bytes / kMiB << " MB"; + } else if (bytes >= static_cast(kKiB)) { + oss << bytes / kKiB << " KB"; + } else { + oss.unsetf(std::ios::fixed); + oss << bytes << " B"; + } + return oss.str(); +} + +[[nodiscard]] inline std::optional try_string_to_byte_size( + const std::string& str) { + if (str.empty()) { + return std::nullopt; + } + + std::string value_string = str; + value_string.erase(0, value_string.find_first_not_of(" \t\r\n")); + value_string.erase(value_string.find_last_not_of(" \t\r\n") + 1); + if (value_string.empty()) { + return std::nullopt; + } + if (value_string == "infinite") { + return std::numeric_limits::max(); + } + + size_t unit_offset = 0; + double value = 0; + try { + value = std::stod(value_string, &unit_offset); + } catch (const std::exception&) { + return std::nullopt; + } + if (value < 0) { + return std::nullopt; + } + if (unit_offset >= value_string.length()) { + return static_cast(value); + } + + std::string unit = value_string.substr(unit_offset); + unit.erase(0, unit.find_first_not_of(" \t\r\n")); + std::transform(unit.begin(), unit.end(), unit.begin(), + [](unsigned char c) -> char { return std::toupper(c); }); + + constexpr double kKiB = 1024.0; + constexpr double kMiB = kKiB * 1024.0; + constexpr double kGiB = kMiB * 1024.0; + constexpr double kTiB = kGiB * 1024.0; + if (unit == "KB" || unit == "K") { + return static_cast(value * kKiB); + } + if (unit == "MB" || unit == "M") { + return static_cast(value * kMiB); + } + if (unit == "GB" || unit == "G") { + return static_cast(value * kGiB); + } + if (unit == "TB" || unit == "T") { + return static_cast(value * kTiB); + } + if (unit == "B" || unit.empty()) { + return static_cast(value); + } + return std::nullopt; +} + +[[nodiscard]] inline uint64_t string_to_byte_size(const std::string& str) { + return try_string_to_byte_size(str).value_or(0); +} + +} // namespace mooncake diff --git a/mooncake-store/include/common/client_buffer_allocation.h b/mooncake-store/include/common/client_buffer_allocation.h new file mode 100644 index 0000000000..71bbf50a90 --- /dev/null +++ b/mooncake-store/include/common/client_buffer_allocation.h @@ -0,0 +1,103 @@ +#pragma once + +#include +#include +#include +#include +#include +#include + +#include +#include + +#include "common/byte_size.h" + +namespace mooncake { + +constexpr size_t SZ_2MB = 2 * 1024 * 1024; +constexpr size_t SZ_512MB = 512 * 1024 * 1024; + +// 512MiB hugepages on arm64 kernels with 64K base pages may not be +// defined by older glibc/kernel headers. +#ifndef MAP_HUGE_512MB +#define MAP_HUGE_512MB (29 << 26) // MAP_HUGE_SHIFT = 26 +#endif +#ifndef MFD_HUGE_512MB +#define MFD_HUGE_512MB (29 << 26) // MFD_HUGE_SHIFT = 26 +#endif +constexpr size_t SZ_1GB = 1024 * 1024 * 1024; +constexpr double BYTES_PER_GIB = static_cast(SZ_1GB); + +void* allocate_buffer_allocator_memory( + size_t total_size, const std::string& protocol = "", + size_t alignment = facebook::cachelib::Slab::kSize, + bool use_spdk_dma = false); + +void free_memory(const std::string& protocol, void* ptr, + bool use_spdk_dma = false); + +inline size_t align_up(size_t size, size_t alignment) { + if (alignment == 0) { + return size; + } + return ((size + alignment - 1) / alignment) * alignment; +} + +[[nodiscard]] inline size_t get_hugepage_size_from_env( + unsigned int* out_flags = nullptr, bool use_memfd = false) { + if (std::getenv("MC_STORE_USE_HUGEPAGE") == nullptr) { + return 0; + } + + size_t size = SZ_2MB; + if (const char* size_env = std::getenv("MC_STORE_HUGEPAGE_SIZE")) { + const size_t parsed_size = string_to_byte_size(size_env); + if (parsed_size == SZ_2MB || parsed_size == SZ_512MB || + parsed_size == SZ_1GB) { + size = parsed_size; + } else { + LOG(WARNING) << "Invalid MC_STORE_HUGEPAGE_SIZE='" << size_env + << "'. Supported: 2MB, 512MB, 1GB. Fallback to 2MB."; + } + } + + if (out_flags == nullptr) { + return size; + } + if (use_memfd) { + *out_flags |= MFD_HUGETLB; + *out_flags |= size == SZ_2MB ? MFD_HUGE_2MB + : size == SZ_512MB ? MFD_HUGE_512MB + : MFD_HUGE_1GB; + } else { + *out_flags |= MAP_HUGETLB; + *out_flags |= size == SZ_2MB ? MAP_HUGE_2MB + : size == SZ_512MB ? MAP_HUGE_512MB + : MAP_HUGE_1GB; + } + LOG(INFO) << "Using hugepage size: " + << (size == SZ_2MB ? "2MB" + : size == SZ_512MB ? "512MB" + : "1GB"); + return size; +} + +void populate_hugetlb_mapping(void* ptr, size_t total_size); + +void populate_hugetlb_numa_mapping(void* ptr, size_t total_size, + const std::vector& numa_nodes); + +void* allocate_buffer_mmap_memory(size_t total_size, size_t alignment); + +void* allocate_buffer_mmap_memory(size_t total_size, size_t alignment, + bool defer_hugetlb_population); + +[[nodiscard]] bool is_mmap_arena_allocation(const void* ptr); + +void free_buffer_mmap_memory(void* ptr, size_t total_size); + +void* allocate_buffer_numa_segments(size_t total_size, + const std::vector& numa_nodes, + size_t page_size = 0); + +} // namespace mooncake diff --git a/mooncake-store/include/utils/file_util.h b/mooncake-store/include/common/file_util.h similarity index 85% rename from mooncake-store/include/utils/file_util.h rename to mooncake-store/include/common/file_util.h index a79e42b912..67388d640a 100644 --- a/mooncake-store/include/utils/file_util.h +++ b/mooncake-store/include/common/file_util.h @@ -12,6 +12,10 @@ namespace fs = std::filesystem; class FileUtil { public: + static std::string ResolvePathFromKey(const std::string& key, + const std::string& root_dir, + const std::string& fsdir); + /** * @brief Save string content to file * @param content Content to save diff --git a/mooncake-store/include/common/network.h b/mooncake-store/include/common/network.h new file mode 100644 index 0000000000..54b6239c7a --- /dev/null +++ b/mooncake-store/include/common/network.h @@ -0,0 +1,40 @@ +#pragma once + +#include +#include + +#include + +namespace mooncake { + +bool isPortAvailable(int port); + +class AutoPortBinder { + public: + AutoPortBinder(int min_port = 12300, int max_port = 14300); + ~AutoPortBinder(); + + AutoPortBinder(const AutoPortBinder&) = delete; + AutoPortBinder& operator=(const AutoPortBinder&) = delete; + AutoPortBinder(AutoPortBinder&&) = delete; + AutoPortBinder& operator=(AutoPortBinder&&) = delete; + + int getPort() const { return port_; } + + private: + int socket_fd_; + int port_; +}; + +tl::expected httpGet(const std::string& url); + +tl::expected GetInterfaceIPv4Address( + const std::string& interface_name); + +int getFreeTcpPort(); + +std::vector getFreeTcpPorts(int count); + +std::string ResolveMooncakeHostId(const std::string& local_hostname); + +} // namespace mooncake diff --git a/mooncake-store/include/common/result.h b/mooncake-store/include/common/result.h new file mode 100644 index 0000000000..e1e3e23b1e --- /dev/null +++ b/mooncake-store/include/common/result.h @@ -0,0 +1,131 @@ +#pragma once + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#include "rpc_types.h" +#include "types.h" + +namespace mooncake { + +template +constexpr bool is_supported_return_type_v = + std::is_void_v || std::is_integral_v; + +template + requires is_supported_return_type_v +int64_t to_py_ret(const tl::expected& exp) noexcept { + if (!exp) { + return static_cast(toInt(exp.error())); + } + if constexpr (std::is_void_v) { + return 0; + } else { + return static_cast(exp.value()); + } +} + +template +void to_stream(std::ostream& os, const T& value); + +template +void to_stream(std::ostream& os, const std::vector& vec); + +template +void to_stream(std::ostream& os, const std::pair& p); + +template +void to_stream(std::ostream& os, const T& value) { + if constexpr (std::is_same_v) { + os << (value ? "true" : "false"); + } else if constexpr (std::is_arithmetic_v) { + os << value; + } else if constexpr (std::is_convertible_v) { + os << "\"" << value << "\""; + } else if constexpr (ylt::reflection::is_ylt_refl_v) { + std::string str; + struct_json::to_json(value, str); + os << str; + } else { + os << value; + } +} + +template +void to_stream(std::ostream& os, const std::vector& vec) { + os << "["; + for (size_t i = 0; i < vec.size(); ++i) { + to_stream(os, vec[i]); + if (i + 1 < vec.size()) { + os << ","; + } + } + os << "]"; +} + +template +void to_stream(std::ostream& os, const std::unordered_map& map) { + os << "{"; + auto it = map.begin(); + while (it != map.end()) { + to_stream(os, it->first); + os << ": "; + to_stream(os, it->second); + if (++it != map.end()) { + os << ", "; + } + } + os << "}"; +} + +template +void to_stream(std::ostream& os, const std::unordered_map& map) { + to_stream>(os, map); +} + +template +void to_stream(std::ostream& os, const std::pair& p) { + os << "{\"first\":"; + to_stream(os, p.first); + os << ",\"second\":"; + to_stream(os, p.second); + os << "}"; +} + +template +void to_stream(std::ostream& os, const std::optional& opt) { + if (opt.has_value()) { + to_stream(os, opt.value()); + } else { + os << "nullopt"; + } +} + +template +std::string expected_to_str(const tl::expected& expected) { + std::ostringstream oss; + if (expected.has_value()) { + oss << "status=success, value="; + if constexpr (std::is_same_v) { + oss << "void"; + } else { + to_stream(oss, expected.value()); + } + } else { + oss << "status=failed, error=" << toString(expected.error()); + } + return oss.str(); +} + +} // namespace mooncake diff --git a/mooncake-store/include/utils/s3_helper.h b/mooncake-store/include/common/s3_helper.h similarity index 100% rename from mooncake-store/include/utils/s3_helper.h rename to mooncake-store/include/common/s3_helper.h diff --git a/mooncake-store/include/utils/scoped_vlog_timer.h b/mooncake-store/include/common/scoped_vlog_timer.h similarity index 98% rename from mooncake-store/include/utils/scoped_vlog_timer.h rename to mooncake-store/include/common/scoped_vlog_timer.h index 6565acbf1a..2580b8ef09 100644 --- a/mooncake-store/include/utils/scoped_vlog_timer.h +++ b/mooncake-store/include/common/scoped_vlog_timer.h @@ -10,7 +10,7 @@ #include #include "types.h" -#include "utils.h" +#include "common/result.h" #include "ylt/struct_json/json_reader.h" #include "ylt/struct_json/json_writer.h" #include "ylt/util/tl/expected.hpp" @@ -131,4 +131,4 @@ class ScopedVLogTimer { bool logged_response_ = false; }; -} // namespace mooncake \ No newline at end of file +} // namespace mooncake diff --git a/mooncake-store/include/common/timestamp.h b/mooncake-store/include/common/timestamp.h new file mode 100644 index 0000000000..a5668c4925 --- /dev/null +++ b/mooncake-store/include/common/timestamp.h @@ -0,0 +1,14 @@ +#pragma once + +#include +#include + +namespace mooncake { + +inline int64_t time_gen() { + return std::chrono::duration_cast( + std::chrono::system_clock::now().time_since_epoch()) + .count(); +} + +} // namespace mooncake diff --git a/mooncake-store/include/utils/transparent_string_hash.h b/mooncake-store/include/common/transparent_string_hash.h similarity index 100% rename from mooncake-store/include/utils/transparent_string_hash.h rename to mooncake-store/include/common/transparent_string_hash.h diff --git a/mooncake-store/include/utils/zstd_util.h b/mooncake-store/include/common/zstd_util.h similarity index 100% rename from mooncake-store/include/utils/zstd_util.h rename to mooncake-store/include/common/zstd_util.h diff --git a/mooncake-store/include/dummy_client.h b/mooncake-store/include/dummy_client.h index 23eb79e262..d66d7755d3 100644 --- a/mooncake-store/include/dummy_client.h +++ b/mooncake-store/include/dummy_client.h @@ -1,5 +1,7 @@ #pragma once +#include "common/result.h" + #include #include #include diff --git a/mooncake-store/include/placement/index.h b/mooncake-store/include/placement/index.h index 665b9f954a..0ee5800494 100644 --- a/mooncake-store/include/placement/index.h +++ b/mooncake-store/include/placement/index.h @@ -15,7 +15,7 @@ #include "placement/target.h" #include "types.h" -#include "utils/transparent_string_hash.h" +#include "common/transparent_string_hash.h" namespace mooncake { diff --git a/mooncake-store/include/pyclient.h b/mooncake-store/include/pyclient.h index 7d650beb69..5d3d567f41 100644 --- a/mooncake-store/include/pyclient.h +++ b/mooncake-store/include/pyclient.h @@ -14,7 +14,7 @@ #include "client_service.h" #include "client_buffer.h" #include "mutex.h" -#include "utils.h" +#include "common/result.h" #include "file_storage.h" namespace mooncake { diff --git a/mooncake-store/include/real_client.h b/mooncake-store/include/real_client.h index f3f51b0a1d..7e22484092 100644 --- a/mooncake-store/include/real_client.h +++ b/mooncake-store/include/real_client.h @@ -15,12 +15,13 @@ #include #include -#include "pyclient.h" -#include "client_service.h" +#include "common/client_buffer_allocation.h" #include "client_buffer.h" +#include "client_service.h" #include "device/cuda_ipc_buffer_handle.h" #include "mutex.h" -#include "utils.h" +#include "common/network.h" +#include "pyclient.h" #include "rpc_types.h" #if defined(USE_SUNRISE) #include "sunrise_allocator.h" diff --git a/mooncake-store/include/rpc_helper.h b/mooncake-store/include/rpc_helper.h index 27f43f55b9..91534b9dec 100644 --- a/mooncake-store/include/rpc_helper.h +++ b/mooncake-store/include/rpc_helper.h @@ -8,7 +8,7 @@ #include #include "types.h" -#include "utils/scoped_vlog_timer.h" +#include "common/scoped_vlog_timer.h" namespace mooncake { diff --git a/mooncake-store/include/utils.h b/mooncake-store/include/utils.h deleted file mode 100644 index d357d0e339..0000000000 --- a/mooncake-store/include/utils.h +++ /dev/null @@ -1,503 +0,0 @@ -#pragma once - -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include -#include - -#include "rpc_types.h" -#include "types.h" - -namespace mooncake { - -// Convert ErrorCode to integer for Python bindings -template -constexpr bool is_supported_return_type_v = - std::is_void_v || std::is_integral_v; - -template - requires is_supported_return_type_v -int64_t to_py_ret(const tl::expected& exp) noexcept { - if (!exp) { - return static_cast(toInt(exp.error())); - } - - if constexpr (std::is_void_v) { - return 0; - } else if constexpr (std::is_integral_v) { - return static_cast(exp.value()); - } else { - static_assert(!sizeof(T), "Unsupported payload type in to_py_ret()"); - } -} - -// Forward declarations -template -void to_stream(std::ostream& os, const T& value); - -template -void to_stream(std::ostream& os, const std::vector& vec); - -template -void to_stream(std::ostream& os, const std::pair& p); - -// Implementation of the base template -template -void to_stream(std::ostream& os, const T& value) { - if constexpr (std::is_same_v) { - os << (value ? "true" : "false"); - } else if constexpr (std::is_arithmetic_v) { - os << value; - } else if constexpr (std::is_convertible_v) { - os << "\"" << value << "\""; - } else if constexpr (ylt::reflection::is_ylt_refl_v) { - std::string str; - struct_json::to_json(value, str); - os << str; - } else { - os << value; - } -} - -// Specialization for std::vector -template -void to_stream(std::ostream& os, const std::vector& vec) { - os << "["; - for (size_t i = 0; i < vec.size(); ++i) { - to_stream(os, vec[i]); - if (i < vec.size() - 1) { - os << ","; - } - } - os << "]"; -} - -template -void to_stream(std::ostream& os, const std::unordered_map& map) { - to_stream>(os, map); -} - -template -void to_stream(std::ostream& os, const std::unordered_map& map) { - os << "{"; - auto it = map.begin(); - while (it != map.end()) { - to_stream(os, it->first); - os << ": "; - to_stream(os, it->second); - ++it; - if (it != map.end()) { - os << ", "; - } - } - os << "}"; -} - -// Specialization for std::pair -template -void to_stream(std::ostream& os, const std::pair& p) { - os << "{\"first\":"; - to_stream(os, p.first); - os << ",\"second\":"; - to_stream(os, p.second); - os << "}"; -} - -// Specialization for std::optional -template -void to_stream(std::ostream& os, const std::optional& opt) { - if (opt.has_value()) { - to_stream(os, opt.value()); - } else { - os << "nullopt"; - } -} - -template -std::string expected_to_str(const tl::expected& expected) { - std::ostringstream oss; - if (expected.has_value()) { - oss << "status=success, value="; - if constexpr (std::is_same_v) { - oss << "void"; - } else { - to_stream(oss, expected.value()); - } - } else { - oss << "status=failed, error=" << toString(expected.error()); - } - return oss.str(); -} - -// String utility functions - -/** - * @brief Convert a byte size to a human-readable string - * @param bytes Number of bytes - * @return std::string Human-readable string representation of size - */ -[[nodiscard]] inline std::string byte_size_to_string(uint64_t bytes) { - const double KB = 1024.0; - const double MB = KB * 1024.0; - const double GB = MB * 1024.0; - const double TB = GB * 1024.0; - - std::ostringstream oss; - oss << std::fixed << std::setprecision(2); - if (static_cast(bytes) == std::numeric_limits::max()) { - oss << "infinite"; - } else if (bytes >= static_cast(TB)) { - oss << bytes / TB << " TB"; - } else if (bytes >= static_cast(GB)) { - oss << bytes / GB << " GB"; - } else if (bytes >= static_cast(MB)) { - oss << bytes / MB << " MB"; - } else if (bytes >= static_cast(KB)) { - oss << bytes / KB << " KB"; - } else { - // Less than 1 KB, don't use fixed point - oss.unsetf(std::ios::fixed); - oss << bytes << " B"; - return oss.str(); - } - - return oss.str(); -} - -/** - * @brief Parse a string representation of size to bytes - * @param str String representation of size (e.g., "1.5 GB", "1024 MB", - * "1048576") - * @return Parsed byte size, or std::nullopt if parsing fails - */ -[[nodiscard]] inline std::optional try_string_to_byte_size( - const std::string& str) { - if (str.empty()) { - return std::nullopt; - } - - // Create a copy for manipulation - std::string s = str; - - // Remove leading/trailing whitespace - s.erase(0, s.find_first_not_of(" \t\r\n")); - s.erase(s.find_last_not_of(" \t\r\n") + 1); - - if (s.empty()) { - return std::nullopt; - } - - // Handle special case for "infinite" - if (s == "infinite") { - return std::numeric_limits::max(); - } - - // Parse the numeric part - size_t pos = 0; - double value = 0; - - try { - value = std::stod(s, &pos); - } catch (const std::exception&) { - return std::nullopt; // Failed to parse number - } - if (value < 0) { - return std::nullopt; - } - - if (pos >= s.length()) { - // No unit specified, assume bytes - return static_cast(value); - } - - // Extract unit (remaining part of the string) - std::string unit = s.substr(pos); - // Remove leading whitespace from unit - unit.erase(0, unit.find_first_not_of(" \t\r\n")); - - // Convert to uppercase for comparison - std::transform(unit.begin(), unit.end(), unit.begin(), - [](unsigned char c) -> char { return std::toupper(c); }); - - // Apply unit multiplier - const double KB = 1024.0; - const double MB = KB * 1024.0; - const double GB = MB * 1024.0; - const double TB = GB * 1024.0; - - if (unit == "KB" || unit == "K") { - return static_cast(value * KB); - } else if (unit == "MB" || unit == "M") { - return static_cast(value * MB); - } else if (unit == "GB" || unit == "G") { - return static_cast(value * GB); - } else if (unit == "TB" || unit == "T") { - return static_cast(value * TB); - } else if (unit == "B" || unit.empty()) { - return static_cast(value); - } else { - // Unknown unit - return std::nullopt; - } -} - -/** - * @brief Convert a string representation of size to bytes - * @param str String representation of size (e.g., "1.5 GB", "1024 MB", - * "1048576") - * @return uint64_t Number of bytes, or 0 if parsing fails - */ -[[nodiscard]] inline uint64_t string_to_byte_size(const std::string& str) { - auto parsed = try_string_to_byte_size(str); - return parsed.value_or(0); -} - -// Buffer allocator functions - -constexpr size_t SZ_2MB = 2 * 1024 * 1024; -constexpr size_t SZ_512MB = 512 * 1024 * 1024; -constexpr size_t SZ_1GB = 1024 * 1024 * 1024; -constexpr double BYTES_PER_GIB = static_cast(SZ_1GB); - -// 512MiB hugepages (PMD size on arm64 kernels with 64K base pages) are not -// defined by older glibc/kernel headers; provide fallbacks. -#ifndef MAP_HUGE_512MB -#define MAP_HUGE_512MB (29 << 26) // MAP_HUGE_SHIFT = 26 -#endif -#ifndef MFD_HUGE_512MB -#define MFD_HUGE_512MB (29 << 26) // MFD_HUGE_SHIFT = 26 -#endif - -/** - * @brief Allocates memory for the `BufferAllocator` class. - * @param total_size The total size of the memory to allocate. - * @return A pointer to the allocated memory. - */ -void* allocate_buffer_allocator_memory( - size_t total_size, const std::string& protocol = "", - size_t alignment = facebook::cachelib::Slab::kSize, - bool use_spdk_dma = false); - -inline size_t align_up(size_t size, size_t alignment) { - if (alignment == 0) { - return size; - } - return ((size + alignment - 1) / alignment) * alignment; -} - -/** - * @brief Get hugepage size from env and optionally set the corresponding memfd - * flags. - * * @param out_flags Optional pointer to an int. If provided, - * MAP_HUGETLB and MAP_HUGE_2MB/512MB/1GB will be OR-ed into it. - * @return size_t Hugepage size in bytes, or 0 if disabled. - */ -[[nodiscard]] inline size_t get_hugepage_size_from_env( - unsigned int* out_flags = nullptr, bool use_memfd = false) { - const char* use_hp_env = std::getenv("MC_STORE_USE_HUGEPAGE"); - if (use_hp_env == nullptr) { - return 0; - } - - size_t size = SZ_2MB; // Default to 2MB - - const char* size_env = std::getenv("MC_STORE_HUGEPAGE_SIZE"); - if (size_env != nullptr) { - size_t parsed_size = string_to_byte_size(size_env); - - if (parsed_size == SZ_2MB || parsed_size == SZ_512MB || - parsed_size == SZ_1GB) { - size = parsed_size; - } else { - LOG(WARNING) << "Invalid MC_STORE_HUGEPAGE_SIZE='" << size_env - << "'. Supported: 2MB, 512MB, 1GB. Fallback to 2MB."; - size = SZ_2MB; - } - } - - if (out_flags != nullptr) { - if (use_memfd) { - *out_flags |= MFD_HUGETLB; - } else { - *out_flags |= MAP_HUGETLB; - } - - // Add size specific flag - if (size == SZ_2MB) { - if (use_memfd) { - *out_flags |= MFD_HUGE_2MB; - } else { - *out_flags |= MAP_HUGE_2MB; - } - } else if (size == SZ_512MB) { - if (use_memfd) { - *out_flags |= MFD_HUGE_512MB; - } else { - *out_flags |= MAP_HUGE_512MB; - } - } else if (size == SZ_1GB) { - if (use_memfd) { - *out_flags |= MFD_HUGE_1GB; - } else { - *out_flags |= MAP_HUGE_1GB; - } - } - LOG(INFO) << "Using hugepage size: " - << (size == SZ_2MB ? "2MB" - : size == SZ_512MB ? "512MB" - : "1GB"); - } - - return size; -} - -/** - * @brief Fault in a fresh HugeTLB mapping with parallel CPU writes. - * - * Touches one byte per configured hugepage. Call this only for a newly - * allocated mapping whose contents may be zeroed. - */ -void populate_hugetlb_mapping(void* ptr, size_t total_size); - -/** - * @brief Fault in an mbind-partitioned HugeTLB mapping with NUMA-local workers. - * - * The mapping is divided into equal regions in the same order as numa_nodes. - * Workers are scheduled on the corresponding node before touching that - * region. - */ -void populate_hugetlb_numa_mapping(void* ptr, size_t total_size, - const std::vector& numa_nodes); - -/** - * Allocate mmap-backed buffer memory for host KV / transfer buffers. - * - * When the global mmap arena is enabled, this function serves allocations - * from the arena and still honors the caller's requested alignment. - * Arena-owned allocations remain owned by the arena until process shutdown. - * - * When the arena is disabled or unavailable, this falls back to a direct - * mmap() allocation and returns a pointer aligned to at least the system page - * size (or the configured hugepage size when available). - * - * @param total_size Total buffer size in bytes. - * @param alignment Minimum alignment requested by the caller. - * @return Pointer to the allocation, or nullptr on failure. - */ -void* allocate_buffer_mmap_memory(size_t total_size, size_t alignment); - -/** - * Allocate mmap-backed memory, optionally deferring direct HugeTLB population. - * - * When defer_hugetlb_population is true, a direct HugeTLB mmap omits - * MAP_POPULATE so the caller can populate the mapping later. Arena allocations - * retain their existing eager-population behavior. - */ -void* allocate_buffer_mmap_memory(size_t total_size, size_t alignment, - bool defer_hugetlb_population); - -/** - * @brief Return whether ptr is backed by the global mmap arena. - * - * Intended for callers that need to distinguish an eagerly populated arena - * allocation from a direct mmap fallback. - */ -[[nodiscard]] bool is_mmap_arena_allocation(const void* ptr); - -/** - * Release memory previously returned by allocate_buffer_mmap_memory(). - * - * Direct-mmap allocations are unmapped immediately. Arena-owned pointers are - * intentionally not unmapped individually; in that case this function is a - * no-op and the arena releases the backing pool during process teardown. - * - * @param ptr Pointer previously returned by allocate_buffer_mmap_memory(). - * @param total_size Original allocation size in bytes. - */ -void free_buffer_mmap_memory(void* ptr, size_t total_size); - -/** - * @brief Allocate a contiguous buffer with per-NUMA-region binding. - * - * Reserves a single VMA via mmap, divides it into N equal regions, - * binds each region to the corresponding NUMA node via mbind(MPOL_BIND). - * The mapping remains lazy after allocation. The caller may populate it with - * NUMA-local workers or let ibv_reg_mr() fault and pin pages while respecting - * the mbind policy. - * - * @param total_size Total buffer size in bytes - * @param numa_nodes NUMA node IDs to bind regions to (e.g., {1,3,5,7}) - * @param page_size Page size for alignment (0 = auto-detect via - * getpagesize()) - * @return Pointer to the allocated buffer, or nullptr on failure - */ -void* allocate_buffer_numa_segments(size_t total_size, - const std::vector& numa_nodes, - size_t page_size = 0); - -void free_memory(const std::string& protocol, void* ptr, - bool use_spdk_dma = false); - -// Network utility functions - -/** - * @brief Check if a TCP port is available for binding - * @param port The port number to check - * @return true if port is available, false otherwise - */ -bool isPortAvailable(int port); - -// Simple RAII class for automatically binding to an available port -// The socket is bound during construction and released during destruction -class AutoPortBinder { - public: - // Constructs binder and attempts to bind to an available port in range - // [min_port, max_port] After successful construction, the port is bound and - // reserved until destruction - AutoPortBinder(int min_port = 12300, int max_port = 14300); - ~AutoPortBinder(); - - // Non-copyable, non-movable - AutoPortBinder(const AutoPortBinder&) = delete; - AutoPortBinder& operator=(const AutoPortBinder&) = delete; - AutoPortBinder(AutoPortBinder&&) = delete; - AutoPortBinder& operator=(AutoPortBinder&&) = delete; - - int getPort() const { return port_; } - - private: - int socket_fd_; - int port_; -}; - -// HTTP utility: simple GET, returns body on 200, otherwise error code -tl::expected httpGet(const std::string& url); - -// Network utility: resolve an active interface name to its IPv4 address -tl::expected GetInterfaceIPv4Address( - const std::string& interface_name); - -// Network utility: obtain an available TCP port on loopback by binding to 0 -int getFreeTcpPort(); - -// Obtain multiple unique available TCP ports atomically. -// All ports are bound simultaneously before any are released, preventing -// duplicate port assignments that can occur with repeated getFreeTcpPort() -// calls. -std::vector getFreeTcpPorts(int count); - -int64_t time_gen(); - -std::string ResolveMooncakeHostId(const std::string& local_hostname); - -std::string ResolvePathFromKey(const std::string& key, - const std::string& root_dir, - const std::string& fsdir); -} // namespace mooncake diff --git a/mooncake-store/src/CMakeLists.txt b/mooncake-store/src/CMakeLists.txt index 435206082d..8d6f06a38f 100644 --- a/mooncake-store/src/CMakeLists.txt +++ b/mooncake-store/src/CMakeLists.txt @@ -3,15 +3,14 @@ add_subdirectory(local_ssd) set(MOONCAKE_STORE_SHARED_SOURCES types.cpp - utils.cpp - mmap_arena.cpp + common/network.cpp thread_pool.cpp etcd_helper.cpp uds_transport.cpp config/distributed_storage_config.cpp storage/distributed/distributed_storage_backend.cpp storage/distributed/posix_fs_adapter.cpp - utils/file_util.cpp) + common/file_util.cpp) set(MOONCAKE_STORE_MASTER_SOURCES allocation_strategy.cpp @@ -72,7 +71,9 @@ set(MOONCAKE_STORE_MASTER_SOURCES ha_metric_manager.cpp) set(MOONCAKE_STORE_CLIENT_SOURCES - client_buffer_allocation.cpp + common/client_buffer_allocation.cpp + mmap_arena.cpp + common/mmap_buffer.cpp client_service.cpp client_metric.cpp master_client.cpp @@ -168,7 +169,7 @@ if(AWSSDK_FOUND) message(STATUS "AWS SDK found: ${AWSSDK_VERSION}") set(HAVE_AWS_SDK TRUE) # Add S3 related source files - list(APPEND MOONCAKE_STORE_MASTER_SOURCES utils/s3_helper.cpp) + list(APPEND MOONCAKE_STORE_MASTER_SOURCES common/s3_helper.cpp) else() message(STATUS "AWS SDK not found, S3 functionality will be disabled") set(HAVE_AWS_SDK FALSE) diff --git a/mooncake-store/src/aligned_client_buffer.cpp b/mooncake-store/src/aligned_client_buffer.cpp index 7569868e42..82f9eca21b 100644 --- a/mooncake-store/src/aligned_client_buffer.cpp +++ b/mooncake-store/src/aligned_client_buffer.cpp @@ -6,7 +6,7 @@ #include #include -#include "utils.h" +#include "common/client_buffer_allocation.h" #if defined(USE_SUNRISE) #include "sunrise_allocator.h" diff --git a/mooncake-store/src/client_buffer.cpp b/mooncake-store/src/client_buffer.cpp index 9206a93c46..dd84ab1533 100644 --- a/mooncake-store/src/client_buffer.cpp +++ b/mooncake-store/src/client_buffer.cpp @@ -8,7 +8,7 @@ #include // For O_CREAT, O_RDWR #include // For ftruncate, close, shm_unlink -#include "utils.h" +#include "common/client_buffer_allocation.h" #if defined(USE_SUNRISE) #include "sunrise_allocator.h" diff --git a/mooncake-store/src/client_metric.cpp b/mooncake-store/src/client_metric.cpp index 41f9fca5e4..080a488eb1 100644 --- a/mooncake-store/src/client_metric.cpp +++ b/mooncake-store/src/client_metric.cpp @@ -4,6 +4,7 @@ #include #include +#include "common/byte_size.h" #include "version.h" namespace mooncake { diff --git a/mooncake-store/src/client_service.cpp b/mooncake-store/src/client_service.cpp index bd92a50797..d189166929 100644 --- a/mooncake-store/src/client_service.cpp +++ b/mooncake-store/src/client_service.cpp @@ -38,7 +38,7 @@ #include "ha/leadership/leader_coordinator_factory.h" #include "types.h" #include "client_buffer.h" -#include "utils.h" +#include "common/network.h" #include "rpc_types.h" #include "local_hot_cache.h" #include "device/accelerator_registry.h" diff --git a/mooncake-store/src/client_buffer_allocation.cpp b/mooncake-store/src/common/client_buffer_allocation.cpp similarity index 98% rename from mooncake-store/src/client_buffer_allocation.cpp rename to mooncake-store/src/common/client_buffer_allocation.cpp index bd92bed680..925d9d5828 100644 --- a/mooncake-store/src/client_buffer_allocation.cpp +++ b/mooncake-store/src/common/client_buffer_allocation.cpp @@ -1,4 +1,4 @@ -#include "utils.h" +#include "common/client_buffer_allocation.h" #include "config.h" #include "ub_allocator.h" @@ -23,6 +23,7 @@ #endif namespace mooncake { +namespace { #ifdef USE_VRAM_SEGMENT tl::expected allocate_vram_memory( @@ -54,6 +55,8 @@ tl::expected allocate_vram_memory( } #endif +} // namespace + void *allocate_buffer_allocator_memory(size_t total_size, const std::string &protocol, size_t alignment, bool use_spdk_dma) { diff --git a/mooncake-store/src/utils/file_util.cpp b/mooncake-store/src/common/file_util.cpp similarity index 79% rename from mooncake-store/src/utils/file_util.cpp rename to mooncake-store/src/common/file_util.cpp index 019a2c5618..be10319982 100644 --- a/mooncake-store/src/utils/file_util.cpp +++ b/mooncake-store/src/common/file_util.cpp @@ -1,12 +1,26 @@ -#include "utils/file_util.h" +#include "common/file_util.h" #include #include #include +#include #include +#include namespace mooncake { namespace { +std::string SanitizeKey(const std::string &key) { + constexpr std::string_view kInvalidChars = "/\\:*?\"<>|"; + std::string sanitized_key; + sanitized_key.reserve(key.size()); + for (char c : key) { + const bool invalid = + c == '\0' || kInvalidChars.find(c) != std::string_view::npos; + sanitized_key.push_back(invalid ? '_' : c); + } + return sanitized_key; +} + constexpr std::size_t kDefaultChunkSize = 64ull * 1024 * 1024; // 64 MB tl::expected PrepareOutputFile(const std::string &file_path, @@ -51,6 +65,20 @@ tl::expected WriteChunks(std::ofstream &file, } // namespace +std::string FileUtil::ResolvePathFromKey(const std::string &key, + const std::string &root_dir, + const std::string &fsdir) { + const size_t hash = std::hash{}(key); + const char dir1 = static_cast('a' + (hash & 0x0F)); + const char dir2 = static_cast('a' + ((hash >> 4) & 0x0F)); + const std::filesystem::path dir_path = + std::filesystem::path(std::string(1, dir1)) / std::string(1, dir2); + return (std::filesystem::path(root_dir) / fsdir / dir_path / + SanitizeKey(key)) + .lexically_normal() + .string(); +} + tl::expected FileUtil::SaveStringToFile( const std::string &content, const std::string &file_path) { try { diff --git a/mooncake-store/src/utils.cpp b/mooncake-store/src/common/mmap_buffer.cpp similarity index 66% rename from mooncake-store/src/utils.cpp rename to mooncake-store/src/common/mmap_buffer.cpp index 12e00b56ea..821e440427 100644 --- a/mooncake-store/src/utils.cpp +++ b/mooncake-store/src/common/mmap_buffer.cpp @@ -1,25 +1,12 @@ -#include "utils.h" -#include "random.h" -#include "mmap_arena.h" -#include "common.h" +#include "common/client_buffer_allocation.h" -#include "ascii_string.h" #include "bool_parser.h" #include "environ.h" +#include "mmap_arena.h" -#include -#include -#include -#include -#include -#include -#include -#include #include #include #include -#include -#include #include #include #include @@ -27,69 +14,19 @@ #include #include #include +#include #include -// Feature flag to enable/disable arena allocator. Disabled by default so the -// library does not pre-map a large pool unless the operator opts in via gflag -// or an explicit MC_MMAP_ARENA_POOL_SIZE environment override. + +#include +#include + DEFINE_bool(use_mmap_arena_allocator, false, "Enable the lock-free mmap arena allocator for mmap buffers"); - -// Arena pool size (default 8GiB when explicitly enabled without an env -// override). DEFINE_uint64(mmap_arena_pool_size, 8ULL * 1024 * 1024 * 1024, "Arena allocator pool size in bytes"); -#include namespace mooncake { -bool isPortAvailable(int port) { - int sock = socket(AF_INET, SOCK_STREAM, 0); - if (sock < 0) return false; - - int opt = 1; - setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt)); - - struct sockaddr_in addr; - memset(&addr, 0, sizeof(addr)); - addr.sin_family = AF_INET; - addr.sin_addr.s_addr = INADDR_ANY; - addr.sin_port = htons(port); - - bool available = (bind(sock, (struct sockaddr *)&addr, sizeof(addr)) == 0); - close(sock); - return available; -} - -// AutoPortBinder implementation -AutoPortBinder::AutoPortBinder(int min_port, int max_port) - : socket_fd_(-1), port_(-1) { - for (int attempt = 0; attempt < 20; ++attempt) { - int port = randomUniform(min_port, max_port); - - socket_fd_ = socket(AF_INET, SOCK_STREAM, 0); - if (socket_fd_ < 0) continue; - - sockaddr_in addr = {}; - addr.sin_family = AF_INET; - addr.sin_addr.s_addr = INADDR_ANY; - addr.sin_port = htons(port); - - if (bind(socket_fd_, (sockaddr *)&addr, sizeof(addr)) == 0) { - port_ = port; - break; - } else { - close(socket_fd_); - socket_fd_ = -1; - } - } -} - -AutoPortBinder::~AutoPortBinder() { - if (socket_fd_ >= 0) { - close(socket_fd_); - } -} - // Global arena instance (lazy initialization) static std::unique_ptr g_mmap_arena; static std::once_flag g_arena_init_flag; @@ -475,192 +412,4 @@ void *allocate_buffer_numa_segments(size_t total_size, return ptr; } -tl::expected httpGet(const std::string &url) { - coro_http::coro_http_client client; - auto res = client.get(url); - if (res.status == 200) { - return std::string(res.resp_body); - } - return tl::unexpected(res.status); -} - -tl::expected GetInterfaceIPv4Address( - const std::string &interface_name) { - if (interface_name.empty()) { - return tl::unexpected(std::string("network interface name is empty")); - } - - struct ifaddrs *interfaces = nullptr; - if (getifaddrs(&interfaces) != 0) { - return tl::unexpected("getifaddrs failed: " + - std::string(strerror(errno))); - } - std::unique_ptr interface_guard( - interfaces, freeifaddrs); - - bool found_interface = false; - bool interface_is_up = false; - for (auto *current = interfaces; current != nullptr; - current = current->ifa_next) { - if (current->ifa_name == nullptr || - interface_name != current->ifa_name) { - continue; - } - - found_interface = true; - if ((current->ifa_flags & IFF_UP) == 0) { - continue; - } - interface_is_up = true; - - if (current->ifa_addr == nullptr || - current->ifa_addr->sa_family != AF_INET) { - continue; - } - - char host[NI_MAXHOST] = {}; - auto *ipv4_addr = reinterpret_cast(current->ifa_addr); - if (getnameinfo(reinterpret_cast(ipv4_addr), - sizeof(*ipv4_addr), host, sizeof(host), nullptr, 0, - NI_NUMERICHOST) == 0) { - return std::string(host); - } - } - - if (!found_interface) { - return tl::unexpected("network interface '" + interface_name + - "' was not found"); - } - if (!interface_is_up) { - return tl::unexpected("network interface '" + interface_name + - "' is down"); - } - return tl::unexpected("network interface '" + interface_name + - "' has no IPv4 address"); -} - -int getFreeTcpPort() { - int sock = ::socket(AF_INET, SOCK_STREAM, 0); - if (sock < 0) return -1; - sockaddr_in addr{}; - addr.sin_family = AF_INET; - addr.sin_addr.s_addr = htonl(INADDR_LOOPBACK); - addr.sin_port = htons(0); - if (::bind(sock, reinterpret_cast(&addr), sizeof(addr)) != 0) { - ::close(sock); - return -1; - } - socklen_t len = sizeof(addr); - if (::getsockname(sock, reinterpret_cast(&addr), &len) != 0) { - ::close(sock); - return -1; - } - int port = ntohs(addr.sin_port); - ::close(sock); - return port; -} - -std::vector getFreeTcpPorts(int count) { - std::vector ports; - std::vector sockets; - ports.reserve(count); - sockets.reserve(count); - - for (int i = 0; i < count; ++i) { - int sock = ::socket(AF_INET, SOCK_STREAM, 0); - if (sock < 0) break; - sockaddr_in addr{}; - addr.sin_family = AF_INET; - addr.sin_addr.s_addr = htonl(INADDR_LOOPBACK); - addr.sin_port = htons(0); - if (::bind(sock, reinterpret_cast(&addr), sizeof(addr)) != - 0) { - ::close(sock); - break; - } - socklen_t len = sizeof(addr); - if (::getsockname(sock, reinterpret_cast(&addr), &len) != - 0) { - ::close(sock); - break; - } - ports.push_back(ntohs(addr.sin_port)); - sockets.push_back(sock); - } - - for (int sock : sockets) { - ::close(sock); - } - return ports; -} - -int64_t time_gen() { - return std::chrono::duration_cast( - std::chrono::system_clock::now().time_since_epoch()) - .count(); -} - -static bool IsUsableMooncakeHostId(std::string_view host_id) { - return !host_id.empty() && - !AsciiCaseInsensitiveEquals(host_id, "localhost") && - host_id != "127.0.0.1" && host_id != "0.0.0.0" && host_id != "::1" && - host_id != "[::1]" && host_id != "::" && host_id != "[::]"; -} - -static std::string NormalizeMooncakeHostId(std::string_view value) { - const std::string hostname(TrimAsciiWhitespace(value)); - const std::string host_id = (hostname == "::1" || hostname == "::") - ? hostname - : std::string(TrimAsciiWhitespace( - getHostNameWithoutPort(hostname))); - return IsUsableMooncakeHostId(host_id) ? host_id : ""; -} - -std::string ResolveMooncakeHostId(const std::string &local_hostname) { - const std::string configured_host_id( - TrimAsciiWhitespace(Environ::GetString("MOONCAKE_HOST_ID", ""))); - if (!configured_host_id.empty()) { - return NormalizeMooncakeHostId(configured_host_id); - } - - return NormalizeMooncakeHostId(local_hostname); -} - -static std::string SanitizeKey(const std::string &key) { - // Set of invalid filesystem characters to be replaced - constexpr std::string_view kInvalidChars = "/\\:*?\"<>|"; - std::string sanitized_key; - sanitized_key.reserve(key.size()); - - for (char c : key) { - // Replace invalid characters with underscore - const bool invalid = - c == '\0' || kInvalidChars.find(c) != std::string_view::npos; - sanitized_key.push_back(invalid ? '_' : c); - } - return sanitized_key; -} - -std::string ResolvePathFromKey(const std::string &key, - const std::string &root_dir, - const std::string &fsdir) { - // Compute hash of the key - size_t hash = std::hash{}(key); - - // Use low 8 bits to create 2-level directory structure (e.g. "a1/b2") - char dir1 = - static_cast('a' + (hash & 0x0F)); // Lower 4 bits -> 16 dirs - char dir2 = static_cast( - 'a' + ((hash >> 4) & 0x0F)); // Next 4 bits -> 16 subdirs - - // Safely construct path using std::filesystem - namespace fs = std::filesystem; - fs::path dir_path = fs::path(std::string(1, dir1)) / std::string(1, dir2); - - // Combine directory path with sanitized filename - fs::path full_path = - fs::path(root_dir) / fsdir / dir_path / SanitizeKey(key); - - return full_path.lexically_normal().string(); -} } // namespace mooncake diff --git a/mooncake-store/src/common/network.cpp b/mooncake-store/src/common/network.cpp new file mode 100644 index 0000000000..e8a6d21e8f --- /dev/null +++ b/mooncake-store/src/common/network.cpp @@ -0,0 +1,216 @@ +#include "common/network.h" +#include "environ.h" + +#include "common.h" +#include "ascii_string.h" +#include "random.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +namespace mooncake { + +bool isPortAvailable(int port) { + int sock = socket(AF_INET, SOCK_STREAM, 0); + if (sock < 0) return false; + + int opt = 1; + setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, &opt, sizeof(opt)); + + struct sockaddr_in addr; + memset(&addr, 0, sizeof(addr)); + addr.sin_family = AF_INET; + addr.sin_addr.s_addr = INADDR_ANY; + addr.sin_port = htons(port); + + bool available = (bind(sock, (struct sockaddr *)&addr, sizeof(addr)) == 0); + close(sock); + return available; +} + +// AutoPortBinder implementation +AutoPortBinder::AutoPortBinder(int min_port, int max_port) + : socket_fd_(-1), port_(-1) { + for (int attempt = 0; attempt < 20; ++attempt) { + int port = randomUniform(min_port, max_port); + + socket_fd_ = socket(AF_INET, SOCK_STREAM, 0); + if (socket_fd_ < 0) continue; + + sockaddr_in addr = {}; + addr.sin_family = AF_INET; + addr.sin_addr.s_addr = INADDR_ANY; + addr.sin_port = htons(port); + + if (bind(socket_fd_, (sockaddr *)&addr, sizeof(addr)) == 0) { + port_ = port; + break; + } else { + close(socket_fd_); + socket_fd_ = -1; + } + } +} + +AutoPortBinder::~AutoPortBinder() { + if (socket_fd_ >= 0) { + close(socket_fd_); + } +} + +tl::expected httpGet(const std::string &url) { + coro_http::coro_http_client client; + auto res = client.get(url); + if (res.status == 200) { + return std::string(res.resp_body); + } + return tl::unexpected(res.status); +} + +tl::expected GetInterfaceIPv4Address( + const std::string &interface_name) { + if (interface_name.empty()) { + return tl::unexpected(std::string("network interface name is empty")); + } + + struct ifaddrs *interfaces = nullptr; + if (getifaddrs(&interfaces) != 0) { + return tl::unexpected("getifaddrs failed: " + + std::string(strerror(errno))); + } + std::unique_ptr interface_guard( + interfaces, freeifaddrs); + + bool found_interface = false; + bool interface_is_up = false; + for (auto *current = interfaces; current != nullptr; + current = current->ifa_next) { + if (current->ifa_name == nullptr || + interface_name != current->ifa_name) { + continue; + } + + found_interface = true; + if ((current->ifa_flags & IFF_UP) == 0) { + continue; + } + interface_is_up = true; + + if (current->ifa_addr == nullptr || + current->ifa_addr->sa_family != AF_INET) { + continue; + } + + char host[NI_MAXHOST] = {}; + auto *ipv4_addr = reinterpret_cast(current->ifa_addr); + if (getnameinfo(reinterpret_cast(ipv4_addr), + sizeof(*ipv4_addr), host, sizeof(host), nullptr, 0, + NI_NUMERICHOST) == 0) { + return std::string(host); + } + } + + if (!found_interface) { + return tl::unexpected("network interface '" + interface_name + + "' was not found"); + } + if (!interface_is_up) { + return tl::unexpected("network interface '" + interface_name + + "' is down"); + } + return tl::unexpected("network interface '" + interface_name + + "' has no IPv4 address"); +} + +int getFreeTcpPort() { + int sock = ::socket(AF_INET, SOCK_STREAM, 0); + if (sock < 0) return -1; + sockaddr_in addr{}; + addr.sin_family = AF_INET; + addr.sin_addr.s_addr = htonl(INADDR_LOOPBACK); + addr.sin_port = htons(0); + if (::bind(sock, reinterpret_cast(&addr), sizeof(addr)) != 0) { + ::close(sock); + return -1; + } + socklen_t len = sizeof(addr); + if (::getsockname(sock, reinterpret_cast(&addr), &len) != 0) { + ::close(sock); + return -1; + } + int port = ntohs(addr.sin_port); + ::close(sock); + return port; +} + +std::vector getFreeTcpPorts(int count) { + std::vector ports; + std::vector sockets; + ports.reserve(count); + sockets.reserve(count); + + for (int i = 0; i < count; ++i) { + int sock = ::socket(AF_INET, SOCK_STREAM, 0); + if (sock < 0) break; + sockaddr_in addr{}; + addr.sin_family = AF_INET; + addr.sin_addr.s_addr = htonl(INADDR_LOOPBACK); + addr.sin_port = htons(0); + if (::bind(sock, reinterpret_cast(&addr), sizeof(addr)) != + 0) { + ::close(sock); + break; + } + socklen_t len = sizeof(addr); + if (::getsockname(sock, reinterpret_cast(&addr), &len) != + 0) { + ::close(sock); + break; + } + ports.push_back(ntohs(addr.sin_port)); + sockets.push_back(sock); + } + + for (int sock : sockets) { + ::close(sock); + } + return ports; +} + +static bool IsUsableMooncakeHostId(std::string_view host_id) { + return !host_id.empty() && + !AsciiCaseInsensitiveEquals(host_id, "localhost") && + host_id != "127.0.0.1" && host_id != "0.0.0.0" && host_id != "::1" && + host_id != "[::1]" && host_id != "::" && host_id != "[::]"; +} + +static std::string NormalizeMooncakeHostId(std::string_view value) { + const std::string hostname(TrimAsciiWhitespace(value)); + const std::string host_id = (hostname == "::1" || hostname == "::") + ? hostname + : std::string(TrimAsciiWhitespace( + getHostNameWithoutPort(hostname))); + return IsUsableMooncakeHostId(host_id) ? host_id : ""; +} + +std::string ResolveMooncakeHostId(const std::string &local_hostname) { + const std::string configured_host_id( + TrimAsciiWhitespace(Environ::GetString("MOONCAKE_HOST_ID", ""))); + if (!configured_host_id.empty()) { + return NormalizeMooncakeHostId(configured_host_id); + } + + return NormalizeMooncakeHostId(local_hostname); +} + +} // namespace mooncake diff --git a/mooncake-store/src/utils/s3_helper.cpp b/mooncake-store/src/common/s3_helper.cpp similarity index 99% rename from mooncake-store/src/utils/s3_helper.cpp rename to mooncake-store/src/common/s3_helper.cpp index 9faf252f64..e4edc2dbe1 100644 --- a/mooncake-store/src/utils/s3_helper.cpp +++ b/mooncake-store/src/common/s3_helper.cpp @@ -1,4 +1,4 @@ -#include "utils/s3_helper.h" +#include "common/s3_helper.h" #include #include @@ -33,7 +33,7 @@ #include "crc32c.h" #include "environ.h" #include "fmt/format.h" -#include "utils/base64.h" +#include "common/base64.h" namespace mooncake { diff --git a/mooncake-store/src/dummy_client.cpp b/mooncake-store/src/dummy_client.cpp index 9386bcb317..db48f15e6a 100644 --- a/mooncake-store/src/dummy_client.cpp +++ b/mooncake-store/src/dummy_client.cpp @@ -14,9 +14,10 @@ #include "real_client.h" #include "dummy_client.h" +#include "common/client_buffer_allocation.h" #include "uds_transport.h" -#include "utils.h" -#include "utils/scoped_vlog_timer.h" +#include "common/result.h" +#include "common/scoped_vlog_timer.h" #include "rpc_types.h" #include "types.h" #include "default_config.h" diff --git a/mooncake-store/src/file_storage.cpp b/mooncake-store/src/file_storage.cpp index bc7aaee7a6..96f58a743d 100644 --- a/mooncake-store/src/file_storage.cpp +++ b/mooncake-store/src/file_storage.cpp @@ -10,7 +10,7 @@ #include "storage_backend.h" #include "storage/distributed/distributed_storage_backend.h" #include "client_metric.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" #include "device/accelerator_registry.h" #ifdef USE_URING #include "file_interface.h" diff --git a/mooncake-store/src/ha/oplog/oplog_batch_codec.cpp b/mooncake-store/src/ha/oplog/oplog_batch_codec.cpp index 87e544b125..2fbb8174e5 100644 --- a/mooncake-store/src/ha/oplog/oplog_batch_codec.cpp +++ b/mooncake-store/src/ha/oplog/oplog_batch_codec.cpp @@ -11,7 +11,7 @@ #include #endif -#include "utils/base64.h" +#include "common/base64.h" namespace mooncake { diff --git a/mooncake-store/src/ha/snapshot/catalog_backed_snapshot_provider.cpp b/mooncake-store/src/ha/snapshot/catalog_backed_snapshot_provider.cpp index b9547fb34e..ee128e9690 100644 --- a/mooncake-store/src/ha/snapshot/catalog_backed_snapshot_provider.cpp +++ b/mooncake-store/src/ha/snapshot/catalog_backed_snapshot_provider.cpp @@ -17,7 +17,7 @@ #include "ha/snapshot/object/snapshot_object_store.h" #include "segment.h" #include "serialize/serializer.h" -#include "utils/zstd_util.h" +#include "common/zstd_util.h" namespace mooncake { diff --git a/mooncake-store/src/ha/snapshot/object/backends/s3/s3_snapshot_object_store.cpp b/mooncake-store/src/ha/snapshot/object/backends/s3/s3_snapshot_object_store.cpp index 754d385ce7..b8a39bcac4 100644 --- a/mooncake-store/src/ha/snapshot/object/backends/s3/s3_snapshot_object_store.cpp +++ b/mooncake-store/src/ha/snapshot/object/backends/s3/s3_snapshot_object_store.cpp @@ -8,7 +8,7 @@ #include -#include "utils/s3_helper.h" +#include "common/s3_helper.h" namespace mooncake { diff --git a/mooncake-store/src/master.cpp b/mooncake-store/src/master.cpp index f8cc590d06..b0d0e9a2a6 100644 --- a/mooncake-store/src/master.cpp +++ b/mooncake-store/src/master.cpp @@ -21,7 +21,7 @@ #include "master_admin_service.h" #include "rpc_service.h" #include "types.h" -#include "utils.h" +#include "common/network.h" #include "master_config.h" #include "version.h" diff --git a/mooncake-store/src/master_client.cpp b/mooncake-store/src/master_client.cpp index 4dcb58e4f1..92721836bb 100644 --- a/mooncake-store/src/master_client.cpp +++ b/mooncake-store/src/master_client.cpp @@ -13,7 +13,7 @@ #include "mutex.h" #include "rpc_service.h" #include "types.h" -#include "utils/scoped_vlog_timer.h" +#include "common/scoped_vlog_timer.h" #include "master_metric_manager.h" #include "version.h" diff --git a/mooncake-store/src/master_metric_manager.cpp b/mooncake-store/src/master_metric_manager.cpp index 4339a74fe6..19f41ed304 100644 --- a/mooncake-store/src/master_metric_manager.cpp +++ b/mooncake-store/src/master_metric_manager.cpp @@ -7,8 +7,8 @@ #include // Required by histogram serialization #include +#include "common/byte_size.h" #include "segment.h" -#include "utils.h" #include "version.h" namespace mooncake { diff --git a/mooncake-store/src/master_service.cpp b/mooncake-store/src/master_service.cpp index 0fc622f62b..27eb305ffa 100644 --- a/mooncake-store/src/master_service.cpp +++ b/mooncake-store/src/master_service.cpp @@ -53,12 +53,11 @@ #include "types.h" #include "serialize/serializer.h" #include "ha/snapshot/snapshot_logger.h" -#include "utils/zstd_util.h" -#include "utils/file_util.h" +#include "common/zstd_util.h" +#include "common/file_util.h" #include "storage/distributed/dfs_global_allocator.h" #include "storage/distributed/distributed_storage_backend.h" #include "random.h" -#include "utils.h" #include "kv_event/kv_event_config.h" #include "master_snapshot_manager.h" #include "master_snapshot_repository.h" @@ -4514,7 +4513,7 @@ auto MasterService::AllocateAndInsertMetadata( if (use_disk_replica_) { std::string file_path = - ResolvePathFromKey(key, root_fs_dir_, cluster_id_); + FileUtil::ResolvePathFromKey(key, root_fs_dir_, cluster_id_); replicas.emplace_back(file_path, value_length, ReplicaStatus::PROCESSING); } diff --git a/mooncake-store/src/master_snapshot_manager.cpp b/mooncake-store/src/master_snapshot_manager.cpp index 5a7b831faa..9aea0a3a87 100644 --- a/mooncake-store/src/master_snapshot_manager.cpp +++ b/mooncake-store/src/master_snapshot_manager.cpp @@ -21,8 +21,8 @@ #include "serialize/serializer.h" #include "segment.h" #include "task_manager.h" -#include "utils/file_util.h" -#include "utils/zstd_util.h" +#include "common/file_util.h" +#include "common/zstd_util.h" namespace mooncake { diff --git a/mooncake-store/src/master_snapshot_repository.cpp b/mooncake-store/src/master_snapshot_repository.cpp index b441196bdb..148448f9f8 100644 --- a/mooncake-store/src/master_snapshot_repository.cpp +++ b/mooncake-store/src/master_snapshot_repository.cpp @@ -9,7 +9,7 @@ #include "ha/snapshot/object/snapshot_object_store.h" #include "ha/snapshot/snapshot_constants.h" #include "ha/snapshot/snapshot_logger.h" -#include "utils/file_util.h" +#include "common/file_util.h" namespace mooncake { diff --git a/mooncake-store/src/mmap_arena.cpp b/mooncake-store/src/mmap_arena.cpp index 8ee216f9d5..b92f972fdd 100644 --- a/mooncake-store/src/mmap_arena.cpp +++ b/mooncake-store/src/mmap_arena.cpp @@ -2,7 +2,7 @@ // Simple arena allocator implementation #include "mmap_arena.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" #include #include #include diff --git a/mooncake-store/src/offset_allocator.cpp b/mooncake-store/src/offset_allocator.cpp index 17f2369e2e..be69d8757e 100644 --- a/mooncake-store/src/offset_allocator.cpp +++ b/mooncake-store/src/offset_allocator.cpp @@ -7,8 +7,8 @@ #include #include +#include "common/byte_size.h" #include "mutex.h" -#include "utils.h" #ifdef DEBUG #include diff --git a/mooncake-store/src/real_client.cpp b/mooncake-store/src/real_client.cpp index d82ac4b09a..086a8a7ffc 100644 --- a/mooncake-store/src/real_client.cpp +++ b/mooncake-store/src/real_client.cpp @@ -17,6 +17,7 @@ #include #include "real_client.h" +#include "common/client_buffer_allocation.h" #include "registered_pinned_memory.h" #include "client_buffer.h" #include "replica_selection.h" @@ -28,7 +29,8 @@ #include "integer_parser.h" #include "mutex.h" #include "types.h" -#include "utils.h" +#include "common/network.h" +#include "common/result.h" #include "rpc_types.h" #include "file_storage.h" #include "device/accelerator_registry.h" diff --git a/mooncake-store/src/real_client_main.cpp b/mooncake-store/src/real_client_main.cpp index a0b627fb5e..b56e49adf8 100644 --- a/mooncake-store/src/real_client_main.cpp +++ b/mooncake-store/src/real_client_main.cpp @@ -5,6 +5,7 @@ #include "client_service.h" #include "common.h" #include "config.h" +#include "common/byte_size.h" #include "real_client.h" #include "version.h" diff --git a/mooncake-store/src/rpc_service.cpp b/mooncake-store/src/rpc_service.cpp index af4c2c7fd1..e65bff71c1 100644 --- a/mooncake-store/src/rpc_service.cpp +++ b/mooncake-store/src/rpc_service.cpp @@ -12,7 +12,7 @@ #include "master_service.h" #include "rpc_helper.h" #include "types.h" -#include "utils/scoped_vlog_timer.h" +#include "common/scoped_vlog_timer.h" #include "version.h" namespace mooncake { diff --git a/mooncake-store/src/segment.cpp b/mooncake-store/src/segment.cpp index 0ecfefdd5a..7942aacd83 100644 --- a/mooncake-store/src/segment.cpp +++ b/mooncake-store/src/segment.cpp @@ -2,7 +2,7 @@ #include "ha/snapshot/local_ssd_codec.h" #include "master_metric_manager.h" -#include "utils/zstd_util.h" +#include "common/zstd_util.h" #include #include diff --git a/mooncake-store/src/serialize/serializer.cpp b/mooncake-store/src/serialize/serializer.cpp index 7a3519e642..55e416fa7c 100644 --- a/mooncake-store/src/serialize/serializer.cpp +++ b/mooncake-store/src/serialize/serializer.cpp @@ -5,7 +5,7 @@ #include "offset_allocator/offset_allocator.h" #include "types.h" #include "master_service.h" -#include "utils/zstd_util.h" +#include "common/zstd_util.h" namespace mooncake { diff --git a/mooncake-store/src/shm_helper.cpp b/mooncake-store/src/shm_helper.cpp index 40e40d7f1b..0f44235d87 100644 --- a/mooncake-store/src/shm_helper.cpp +++ b/mooncake-store/src/shm_helper.cpp @@ -9,7 +9,7 @@ #include #include -#include "utils.h" +#include "common/client_buffer_allocation.h" #include "config.h" #if defined(USE_ASCEND_DIRECT) #include "ascend_allocator.h" diff --git a/mooncake-store/src/storage/distributed/dfs_global_allocator.cpp b/mooncake-store/src/storage/distributed/dfs_global_allocator.cpp index 99ae56427f..c09171dc90 100644 --- a/mooncake-store/src/storage/distributed/dfs_global_allocator.cpp +++ b/mooncake-store/src/storage/distributed/dfs_global_allocator.cpp @@ -10,7 +10,6 @@ #include "config/distributed_storage_config.h" #include "storage/distributed/fs_adapter.h" #include "storage/distributed/posix_fs_adapter.h" -#include "utils.h" #ifdef USE_3FS #include "storage/distributed/hf3fs_adapter.h" #endif diff --git a/mooncake-store/src/storage/distributed/distributed_storage_backend.cpp b/mooncake-store/src/storage/distributed/distributed_storage_backend.cpp index 46b93d55ed..3539efdc61 100644 --- a/mooncake-store/src/storage/distributed/distributed_storage_backend.cpp +++ b/mooncake-store/src/storage/distributed/distributed_storage_backend.cpp @@ -6,7 +6,6 @@ #include "storage/distributed/dfs_global_allocator.h" #include "types.h" -#include "utils.h" namespace mooncake { diff --git a/mooncake-store/src/storage_backend.cpp b/mooncake-store/src/storage_backend.cpp index c4a627364c..b375208d36 100644 --- a/mooncake-store/src/storage_backend.cpp +++ b/mooncake-store/src/storage_backend.cpp @@ -25,7 +25,8 @@ #include "mutex.h" #include "nvme_kv_backend.h" -#include "utils.h" +#include "common/timestamp.h" +#include "common/file_util.h" #include "crc32c.h" #include "environ.h" @@ -1300,9 +1301,9 @@ tl::expected StorageBackendAdaptor::BatchOffload( continue; // Simulate StoreObject failure } - auto path = - ResolvePathFromKey(kv.key, file_storage_config_.storage_filepath, - file_per_key_config_.fsdir); + auto path = FileUtil::ResolvePathFromKey( + kv.key, file_storage_config_.storage_filepath, + file_per_key_config_.fsdir); kv.value = ConcatSlicesToString(value); std::string kv_buf; @@ -1359,8 +1360,8 @@ StorageBackendAdaptor::EvictAboveDiskWatermark( tl::expected StorageBackendAdaptor::IsExist( const std::string& key) { - auto path = ResolvePathFromKey(key, file_storage_config_.storage_filepath, - file_per_key_config_.fsdir); + auto path = FileUtil::ResolvePathFromKey( + key, file_storage_config_.storage_filepath, file_per_key_config_.fsdir); namespace fs = std::filesystem; return fs::exists(path); } @@ -1370,9 +1371,9 @@ tl::expected StorageBackendAdaptor::BatchLoad( for (const auto& [key, slice] : batched_slices) { KVEntry kv; kv.key = key; - auto path = - ResolvePathFromKey(kv.key, file_storage_config_.storage_filepath, - file_per_key_config_.fsdir); + auto path = FileUtil::ResolvePathFromKey( + kv.key, file_storage_config_.storage_filepath, + file_per_key_config_.fsdir); kv.value.resize(slice.size); diff --git a/mooncake-store/src/task_manager.cpp b/mooncake-store/src/task_manager.cpp index 14672fdea3..d2aacb06fa 100644 --- a/mooncake-store/src/task_manager.cpp +++ b/mooncake-store/src/task_manager.cpp @@ -1,7 +1,7 @@ #include "task_manager.h" #include #include -#include "utils/zstd_util.h" +#include "common/zstd_util.h" namespace mooncake { diff --git a/mooncake-store/tests/CMakeLists.txt b/mooncake-store/tests/CMakeLists.txt index b269084e79..1383d59cad 100644 --- a/mooncake-store/tests/CMakeLists.txt +++ b/mooncake-store/tests/CMakeLists.txt @@ -179,7 +179,10 @@ target_link_libraries(local_ssd_test PRIVATE mooncake_local_ssd gtest add_test(NAME local_ssd_test COMMAND local_ssd_test) add_store_test(local_ssd_codec_test ha/snapshot/local_ssd_codec_test.cpp) add_store_test(offset_allocator_test offset_allocator_test.cpp) -add_store_test(utils_test utils_test.cpp) +add_store_test(byte_size_test byte_size_test.cpp) +add_store_test(network_test network_test.cpp) +add_store_test(hugepage_size_env_test hugepage_size_env_test.cpp) +add_store_test(random_test random_test.cpp) add_store_test(client_buffer_test client_buffer_test.cpp) add_store_test(client_auto_port_config_test client_auto_port_config_test.cpp) add_store_test(local_hot_cache_config_test local_hot_cache_config_test.cpp) diff --git a/mooncake-store/tests/batch_remove_test.cpp b/mooncake-store/tests/batch_remove_test.cpp index 519b38dd70..a3bacef53e 100644 --- a/mooncake-store/tests/batch_remove_test.cpp +++ b/mooncake-store/tests/batch_remove_test.cpp @@ -9,6 +9,7 @@ #include #include "allocator.h" +#include "common/client_buffer_allocation.h" #include "client_service.h" #include "test_server_helpers.h" #include "default_config.h" diff --git a/mooncake-store/tests/byte_size_test.cpp b/mooncake-store/tests/byte_size_test.cpp new file mode 100644 index 0000000000..45c6a95180 --- /dev/null +++ b/mooncake-store/tests/byte_size_test.cpp @@ -0,0 +1,34 @@ +#include "common/byte_size.h" + +#include + +using namespace mooncake; + +TEST(UtilsTest, ByteSizeToString) { + EXPECT_EQ(byte_size_to_string(999), "999 B"); + EXPECT_EQ(byte_size_to_string(2048), "2.00 KB"); + EXPECT_EQ(byte_size_to_string(5ULL * 1024 * 1024 + 1234), "5.00 MB"); + EXPECT_EQ(byte_size_to_string(15ULL * 1024 * 1024 * 1024), "15.00 GB"); + EXPECT_EQ(byte_size_to_string(0), "0 B"); + EXPECT_EQ(byte_size_to_string(1), "1 B"); + EXPECT_EQ(byte_size_to_string(1024), "1.00 KB"); + EXPECT_EQ(byte_size_to_string(1024 * 1024), "1.00 MB"); + EXPECT_EQ(byte_size_to_string(1024ULL * 1024 * 1024), "1.00 GB"); + EXPECT_EQ(byte_size_to_string(1024ULL * 1024 * 1024 * 1024), "1.00 TB"); + EXPECT_EQ(byte_size_to_string(15 * 1024 + 134), "15.13 KB"); + EXPECT_EQ(byte_size_to_string(15 * 1024 * 1024 + 44048), "15.04 MB"); +} + +TEST(UtilsTest, StringToByteSize) { + auto parsed = try_string_to_byte_size("16 MB"); + ASSERT_TRUE(parsed.has_value()); + EXPECT_EQ(parsed.value(), 16ULL * 1024 * 1024); + + parsed = try_string_to_byte_size("0"); + ASSERT_TRUE(parsed.has_value()); + EXPECT_EQ(parsed.value(), 0); + + EXPECT_FALSE(try_string_to_byte_size("-5").has_value()); + EXPECT_FALSE(try_string_to_byte_size("16XB").has_value()); + EXPECT_EQ(string_to_byte_size("-5"), 0); +} diff --git a/mooncake-store/tests/client_integration_test.cpp b/mooncake-store/tests/client_integration_test.cpp index 22012eb308..b913004840 100644 --- a/mooncake-store/tests/client_integration_test.cpp +++ b/mooncake-store/tests/client_integration_test.cpp @@ -21,7 +21,7 @@ #include "allocator.h" #include "client_service.h" #include "types.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" #include "test_server_helpers.h" #include "default_config.h" #include "crc_checksum.h" diff --git a/mooncake-store/tests/client_local_hot_cache_test.cpp b/mooncake-store/tests/client_local_hot_cache_test.cpp index 70fbf7c162..1b87cd7616 100644 --- a/mooncake-store/tests/client_local_hot_cache_test.cpp +++ b/mooncake-store/tests/client_local_hot_cache_test.cpp @@ -1,11 +1,11 @@ // client_local_hot_cache_test.cpp #include "client_service.h" #include "client_buffer.h" +#include "common/client_buffer_allocation.h" #include "count_min_sketch.h" #include "local_hot_cache.h" #include "replica.h" #include "test_server_helpers.h" -#include "utils.h" #include #include diff --git a/mooncake-store/tests/client_metrics_test.cpp b/mooncake-store/tests/client_metrics_test.cpp index 5053067404..11b114a1dc 100644 --- a/mooncake-store/tests/client_metrics_test.cpp +++ b/mooncake-store/tests/client_metrics_test.cpp @@ -11,10 +11,10 @@ #include #include "client_metric.h" +#include "common/network.h" #include "environment_variables.h" #include "real_client.h" #include "test_server_helpers.h" -#include "utils.h" #include "version.h" namespace mooncake::test { diff --git a/mooncake-store/tests/client_tcp_local_memcpy_test.cpp b/mooncake-store/tests/client_tcp_local_memcpy_test.cpp index 289ba85a76..24377ebf3d 100644 --- a/mooncake-store/tests/client_tcp_local_memcpy_test.cpp +++ b/mooncake-store/tests/client_tcp_local_memcpy_test.cpp @@ -14,7 +14,8 @@ #include "client_service.h" #include "test_server_helpers.h" #include "types.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" +#include "common/network.h" namespace mooncake { namespace testing { @@ -505,4 +506,4 @@ INSTANTIATE_TEST_SUITE_P( }); } // namespace testing -} // namespace mooncake \ No newline at end of file +} // namespace mooncake diff --git a/mooncake-store/tests/cxl_client_integration_test.cpp b/mooncake-store/tests/cxl_client_integration_test.cpp index 35a4649acc..f3428ab1a3 100644 --- a/mooncake-store/tests/cxl_client_integration_test.cpp +++ b/mooncake-store/tests/cxl_client_integration_test.cpp @@ -19,7 +19,6 @@ #include "allocator.h" #include "client_service.h" #include "types.h" -#include "utils.h" #include "test_server_helpers.h" #include "default_config.h" @@ -476,4 +475,4 @@ int main(int argc, char** argv) { mooncake::init_ylt_log_level(); // Run all tests return RUN_ALL_TESTS(); -} \ No newline at end of file +} diff --git a/mooncake-store/tests/dfs_sync_client_test.cpp b/mooncake-store/tests/dfs_sync_client_test.cpp index 873cad93f2..381f230a75 100644 --- a/mooncake-store/tests/dfs_sync_client_test.cpp +++ b/mooncake-store/tests/dfs_sync_client_test.cpp @@ -18,7 +18,7 @@ #include "storage/distributed/distributed_storage_backend.h" #include "storage/distributed/posix_fs_adapter.h" #include "test_server_helpers.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" namespace mooncake::test { diff --git a/mooncake-store/tests/dummy_client_get_buffer_test.cpp b/mooncake-store/tests/dummy_client_get_buffer_test.cpp index d27521a4fb..5fa1a574c4 100644 --- a/mooncake-store/tests/dummy_client_get_buffer_test.cpp +++ b/mooncake-store/tests/dummy_client_get_buffer_test.cpp @@ -18,10 +18,11 @@ #include #include +#include "common/network.h" +#include "default_config.h" #include "dummy_client.h" #include "environ.h" #include "real_client.h" -#include "default_config.h" #include "test_server_helpers.h" DEFINE_string(protocol, "tcp", "Transfer protocol: rdma|tcp"); diff --git a/mooncake-store/tests/e2e/chaos_rand_test.cpp b/mooncake-store/tests/e2e/chaos_rand_test.cpp index cd714da293..f4e6c4910f 100644 --- a/mooncake-store/tests/e2e/chaos_rand_test.cpp +++ b/mooncake-store/tests/e2e/chaos_rand_test.cpp @@ -11,7 +11,6 @@ #include "ha/leadership/leader_coordinator_factory.h" #include "process_handler.h" #include "types.h" -#include "utils.h" // Define flags USE_engine_flags; diff --git a/mooncake-store/tests/e2e/chaos_test.cpp b/mooncake-store/tests/e2e/chaos_test.cpp index 619a89c555..f5d9116f89 100644 --- a/mooncake-store/tests/e2e/chaos_test.cpp +++ b/mooncake-store/tests/e2e/chaos_test.cpp @@ -11,7 +11,6 @@ #include "ha/leadership/leader_coordinator_factory.h" #include "process_handler.h" #include "types.h" -#include "utils.h" USE_engine_flags; FLAG_etcd_endpoints; diff --git a/mooncake-store/tests/e2e/client_runner.cpp b/mooncake-store/tests/e2e/client_runner.cpp index f6be1006f3..f71e63ebff 100644 --- a/mooncake-store/tests/e2e/client_runner.cpp +++ b/mooncake-store/tests/e2e/client_runner.cpp @@ -8,7 +8,6 @@ #include "e2e_utils.h" #include "process_handler.h" #include "types.h" -#include "utils.h" // Command line flags USE_engine_flags; @@ -220,4 +219,4 @@ int main(int argc, char** argv) { client_runner.Run(); return 0; -} \ No newline at end of file +} diff --git a/mooncake-store/tests/e2e/client_wrapper.cpp b/mooncake-store/tests/e2e/client_wrapper.cpp index 0f76a5a43e..bbdb6d89e1 100644 --- a/mooncake-store/tests/e2e/client_wrapper.cpp +++ b/mooncake-store/tests/e2e/client_wrapper.cpp @@ -3,7 +3,7 @@ #include #include -#include "utils.h" +#include "common/client_buffer_allocation.h" namespace mooncake { namespace testing { diff --git a/mooncake-store/tests/e2e/clientctl.cpp b/mooncake-store/tests/e2e/clientctl.cpp index 29555a3f81..6dd2bf24c0 100644 --- a/mooncake-store/tests/e2e/clientctl.cpp +++ b/mooncake-store/tests/e2e/clientctl.cpp @@ -8,7 +8,6 @@ #include "client_wrapper.h" #include "types.h" -#include "utils.h" #include "e2e_utils.h" // Command line flags diff --git a/mooncake-store/tests/e2e/e2e_rand_test.cpp b/mooncake-store/tests/e2e/e2e_rand_test.cpp index 415e2b810e..668b6e07de 100644 --- a/mooncake-store/tests/e2e/e2e_rand_test.cpp +++ b/mooncake-store/tests/e2e/e2e_rand_test.cpp @@ -10,7 +10,6 @@ #include "e2e_utils.h" #include "process_handler.h" #include "types.h" -#include "utils.h" USE_engine_flags; FLAG_etcd_endpoints; diff --git a/mooncake-store/tests/e2e/oplog_ha_client.cpp b/mooncake-store/tests/e2e/oplog_ha_client.cpp index d4cdce2318..2b3bec478c 100644 --- a/mooncake-store/tests/e2e/oplog_ha_client.cpp +++ b/mooncake-store/tests/e2e/oplog_ha_client.cpp @@ -15,7 +15,6 @@ #include "client_wrapper.h" #include "e2e_utils.h" #include "types.h" -#include "utils.h" USE_engine_flags; DEFINE_string(master_server_entry, "etcd://0.0.0.0:2379", diff --git a/mooncake-store/tests/e2e/storage_backend_e2e_test.cpp b/mooncake-store/tests/e2e/storage_backend_e2e_test.cpp index 1a4d9b5d70..68e88d0256 100644 --- a/mooncake-store/tests/e2e/storage_backend_e2e_test.cpp +++ b/mooncake-store/tests/e2e/storage_backend_e2e_test.cpp @@ -28,7 +28,6 @@ #include "client_wrapper.h" #include "test_server_helpers.h" #include "types.h" -#include "utils.h" DEFINE_string(protocol, "tcp", "Transfer protocol: rdma|tcp"); DEFINE_string(device_name, "ibp6s0", diff --git a/mooncake-store/tests/file_storage_test.cpp b/mooncake-store/tests/file_storage_test.cpp index fee227b244..84d1f5058a 100644 --- a/mooncake-store/tests/file_storage_test.cpp +++ b/mooncake-store/tests/file_storage_test.cpp @@ -10,11 +10,12 @@ #include "allocator.h" #include "client_metric.h" +#include "common/network.h" #include "file_storage.h" #include "storage_backend.h" #include "tenant_id.h" #include "test_server_helpers.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" #include "utils/common.h" namespace mooncake { diff --git a/mooncake-store/tests/file_util_test.cpp b/mooncake-store/tests/file_util_test.cpp index 2d76b2166e..e53eaf5ca5 100644 --- a/mooncake-store/tests/file_util_test.cpp +++ b/mooncake-store/tests/file_util_test.cpp @@ -7,7 +7,7 @@ #include #include -#include "utils/file_util.h" +#include "common/file_util.h" namespace mooncake::test { diff --git a/mooncake-store/tests/ha/leadership/high_availability_test.cpp b/mooncake-store/tests/ha/leadership/high_availability_test.cpp index c648b25494..396e632023 100644 --- a/mooncake-store/tests/ha/leadership/high_availability_test.cpp +++ b/mooncake-store/tests/ha/leadership/high_availability_test.cpp @@ -17,12 +17,12 @@ #ifdef STORE_USE_ETCD #include "etcd_helper.h" #endif +#include "common/network.h" #include "ha/leadership/leader_coordinator_factory.h" #include "ha/leadership/high_availability_test_fixture.h" #include "ha/leadership/master_service_supervisor.h" #include "master_service.h" #include "types.h" -#include "utils.h" namespace mooncake { namespace testing { diff --git a/mooncake-store/tests/ha/snapshot/master_snapshot_codec_test.cpp b/mooncake-store/tests/ha/snapshot/master_snapshot_codec_test.cpp index f2f2263301..a690846a9c 100644 --- a/mooncake-store/tests/ha/snapshot/master_snapshot_codec_test.cpp +++ b/mooncake-store/tests/ha/snapshot/master_snapshot_codec_test.cpp @@ -12,7 +12,7 @@ #include "segment.h" #include "task_manager.h" #include "tenant_id.h" -#include "utils/zstd_util.h" +#include "common/zstd_util.h" namespace mooncake::ha { diff --git a/mooncake-store/tests/ha/snapshot/snapshot_child_process_test.cpp b/mooncake-store/tests/ha/snapshot/snapshot_child_process_test.cpp index 6a773672a4..28657f30b3 100644 --- a/mooncake-store/tests/ha/snapshot/snapshot_child_process_test.cpp +++ b/mooncake-store/tests/ha/snapshot/snapshot_child_process_test.cpp @@ -28,7 +28,7 @@ #include #include -#include "utils/file_util.h" +#include "common/file_util.h" namespace mooncake::test { diff --git a/mooncake-store/tests/ha/snapshot/snapshot_test_utils.h b/mooncake-store/tests/ha/snapshot/snapshot_test_utils.h index d576e77e3f..f9decf6bbd 100644 --- a/mooncake-store/tests/ha/snapshot/snapshot_test_utils.h +++ b/mooncake-store/tests/ha/snapshot/snapshot_test_utils.h @@ -22,7 +22,7 @@ #include "segment.h" #include "serialize/serializer.h" #include "types.h" -#include "utils/zstd_util.h" +#include "common/zstd_util.h" namespace mooncake::test { diff --git a/mooncake-store/tests/health_check_test.cpp b/mooncake-store/tests/health_check_test.cpp index c755cc2f5d..018674585f 100644 --- a/mooncake-store/tests/health_check_test.cpp +++ b/mooncake-store/tests/health_check_test.cpp @@ -11,9 +11,10 @@ #include #include "client_service.h" +#include "common/network.h" +#include "default_config.h" #include "real_client.h" #include "test_server_helpers.h" -#include "default_config.h" #include "version.h" DEFINE_string(protocol, "tcp", "Transfer protocol: rdma|tcp"); diff --git a/mooncake-store/tests/host_port_fix_test.cpp b/mooncake-store/tests/host_port_fix_test.cpp index 6609ef9e7d..75ff3291ce 100644 --- a/mooncake-store/tests/host_port_fix_test.cpp +++ b/mooncake-store/tests/host_port_fix_test.cpp @@ -3,7 +3,7 @@ #include #include "common.h" -#include "utils.h" +#include "common/network.h" namespace mooncake { namespace { diff --git a/mooncake-store/tests/http_metadata_server_test.cpp b/mooncake-store/tests/http_metadata_server_test.cpp index 26b3726b9f..41de266b55 100644 --- a/mooncake-store/tests/http_metadata_server_test.cpp +++ b/mooncake-store/tests/http_metadata_server_test.cpp @@ -8,7 +8,7 @@ #include #include "http_metadata_server.h" -#include "utils.h" +#include "common/network.h" namespace mooncake::testing { diff --git a/mooncake-store/tests/hugepage_size_env_test.cpp b/mooncake-store/tests/hugepage_size_env_test.cpp new file mode 100644 index 0000000000..845a378c27 --- /dev/null +++ b/mooncake-store/tests/hugepage_size_env_test.cpp @@ -0,0 +1,36 @@ +#include "common/client_buffer_allocation.h" + +#include +#include + +using namespace mooncake; + +TEST(HugepageSizeEnvTest, Accepts512Mb) { + setenv("MC_STORE_USE_HUGEPAGE", "1", 1); + setenv("MC_STORE_HUGEPAGE_SIZE", "512MB", 1); + + unsigned int flags = 0; + EXPECT_EQ(get_hugepage_size_from_env(&flags), SZ_512MB); + EXPECT_TRUE(flags & MAP_HUGETLB); + EXPECT_TRUE(flags & MAP_HUGE_512MB); + + flags = 0; + EXPECT_EQ(get_hugepage_size_from_env(&flags, /*use_memfd=*/true), SZ_512MB); + EXPECT_TRUE(flags & MFD_HUGETLB); + EXPECT_TRUE(flags & MFD_HUGE_512MB); + + unsetenv("MC_STORE_HUGEPAGE_SIZE"); + unsetenv("MC_STORE_USE_HUGEPAGE"); +} + +TEST(HugepageSizeEnvTest, FallsBackTo2MbOnInvalidSize) { + setenv("MC_STORE_USE_HUGEPAGE", "1", 1); + setenv("MC_STORE_HUGEPAGE_SIZE", "256MB", 1); + + unsigned int flags = 0; + EXPECT_EQ(get_hugepage_size_from_env(&flags), SZ_2MB); + EXPECT_TRUE(flags & MAP_HUGE_2MB); + + unsetenv("MC_STORE_HUGEPAGE_SIZE"); + unsetenv("MC_STORE_USE_HUGEPAGE"); +} diff --git a/mooncake-store/tests/master_admin_server_test.cpp b/mooncake-store/tests/master_admin_server_test.cpp index 898cf4440a..e1d21c52f0 100644 --- a/mooncake-store/tests/master_admin_server_test.cpp +++ b/mooncake-store/tests/master_admin_server_test.cpp @@ -14,13 +14,13 @@ #include #include +#include "common/network.h" #include "ha/ha_types.h" #include "master_admin_service.h" #include "master_config.h" #include "rpc_service.h" #include "tenant_quota_policy_store.h" #include "types.h" -#include "utils.h" #include "version.h" #include diff --git a/mooncake-store/tests/master_metrics_test.cpp b/mooncake-store/tests/master_metrics_test.cpp index da557a88ff..2a9664e26a 100644 --- a/mooncake-store/tests/master_metrics_test.cpp +++ b/mooncake-store/tests/master_metrics_test.cpp @@ -10,7 +10,7 @@ #include -#include "utils.h" +#include "common/network.h" #include "master_admin_service.h" #include "master_service.h" #include "segment.h" diff --git a/mooncake-store/tests/master_service_test.cpp b/mooncake-store/tests/master_service_test.cpp index fecd14b3b8..d46eead2fa 100644 --- a/mooncake-store/tests/master_service_test.cpp +++ b/mooncake-store/tests/master_service_test.cpp @@ -27,7 +27,7 @@ #include "tenant_quota_policy_store.h" #include "types.h" -#include "utils.h" +#include "common/network.h" #include "master_service_test_fixture.h" namespace mooncake::test { diff --git a/mooncake-store/tests/mmap_arena_fallback_test.cpp b/mooncake-store/tests/mmap_arena_fallback_test.cpp index da92436a98..417953c176 100644 --- a/mooncake-store/tests/mmap_arena_fallback_test.cpp +++ b/mooncake-store/tests/mmap_arena_fallback_test.cpp @@ -13,7 +13,7 @@ #include #include -#include "utils.h" +#include "common/client_buffer_allocation.h" #if defined(__has_feature) #define MC_HAS_FEATURE(x) __has_feature(x) diff --git a/mooncake-store/tests/mmap_arena_test.cpp b/mooncake-store/tests/mmap_arena_test.cpp index 438aea2b14..53ce5ef075 100644 --- a/mooncake-store/tests/mmap_arena_test.cpp +++ b/mooncake-store/tests/mmap_arena_test.cpp @@ -5,7 +5,6 @@ #include #include #include "mmap_arena.h" -#include "utils.h" #include #include #include diff --git a/mooncake-store/tests/utils_test.cpp b/mooncake-store/tests/network_test.cpp similarity index 52% rename from mooncake-store/tests/utils_test.cpp rename to mooncake-store/tests/network_test.cpp index 7bf4c1cc1f..ee9f7c80f2 100644 --- a/mooncake-store/tests/utils_test.cpp +++ b/mooncake-store/tests/network_test.cpp @@ -1,113 +1,14 @@ -#include "utils.h" -#include "random.h" +#include "common/network.h" -#include -#include -#include -#include +#include +#include #include -#include #include -#include #include -#include - -using namespace mooncake; - -TEST(RandomTest, ReusesEngineWithinThread) { - EXPECT_EQ(&threadLocalRandomEngine(), &threadLocalRandomEngine()); -} - -TEST(RandomTest, UsesDifferentEngineAcrossThreads) { - auto* main_engine = &threadLocalRandomEngine(); - std::promise worker_address; - std::promise release_worker; - auto release_future = release_worker.get_future(); - - std::thread worker([&] { - worker_address.set_value(&threadLocalRandomEngine()); - release_future.wait(); - }); - - EXPECT_NE(main_engine, worker_address.get_future().get()); - release_worker.set_value(); - worker.join(); -} - -TEST(RandomTest, RandomIndexStaysWithinBounds) { - std::mt19937_64 engine(42); - for (size_t i = 0; i < 10000; ++i) { - EXPECT_LT(randomIndex(17, engine), 17); - } -} - -TEST(RandomTest, ExplicitEngineIsDeterministic) { - std::mt19937_64 first(42); - std::mt19937_64 second(42); - for (size_t i = 0; i < 100; ++i) { - EXPECT_EQ(randomIndex(1000, first), randomIndex(1000, second)); - } -} -TEST(RandomTest, RandomUniformIncludesRequestedBounds) { - std::mt19937_64 engine(42); - for (size_t i = 0; i < 10000; ++i) { - int value = randomUniform(-5, 9, engine); - EXPECT_GE(value, -5); - EXPECT_LE(value, 9); - } - EXPECT_EQ(randomUniform(7, 7, engine), 7); -} - -TEST(RandomTest, RandomUniformSupportsNarrowIntegers) { - std::mt19937_64 engine(42); - for (size_t i = 0; i < 1000; ++i) { - auto signed_value = randomUniform(-5, 9, engine); - EXPECT_GE(signed_value, -5); - EXPECT_LE(signed_value, 9); - - auto unsigned_value = randomUniform(2, 7, engine); - EXPECT_GE(unsigned_value, 2); - EXPECT_LE(unsigned_value, 7); - } - EXPECT_FALSE(randomUniform(false, false, engine)); - EXPECT_TRUE(randomUniform(true, true, engine)); -} - -TEST(RandomTest, RejectsInvalidBounds) { - std::mt19937_64 engine(42); - EXPECT_THROW(randomIndex(0, engine), std::invalid_argument); - EXPECT_THROW(randomUniform(2, 1, engine), std::invalid_argument); -} - -TEST(UtilsTest, ByteSizeToString) { - EXPECT_EQ(byte_size_to_string(999), "999 B"); - EXPECT_EQ(byte_size_to_string(2048), "2.00 KB"); - EXPECT_EQ(byte_size_to_string(5ULL * 1024 * 1024 + 1234), "5.00 MB"); - EXPECT_EQ(byte_size_to_string(15ULL * 1024 * 1024 * 1024), "15.00 GB"); - EXPECT_EQ(byte_size_to_string(0), "0 B"); - EXPECT_EQ(byte_size_to_string(1), "1 B"); - EXPECT_EQ(byte_size_to_string(1024), "1.00 KB"); - EXPECT_EQ(byte_size_to_string(1024 * 1024), "1.00 MB"); - EXPECT_EQ(byte_size_to_string(1024ULL * 1024 * 1024), "1.00 GB"); - EXPECT_EQ(byte_size_to_string(1024ULL * 1024 * 1024 * 1024), "1.00 TB"); - EXPECT_EQ(byte_size_to_string(15 * 1024 + 134), "15.13 KB"); - EXPECT_EQ(byte_size_to_string(15 * 1024 * 1024 + 44048), "15.04 MB"); -} - -TEST(UtilsTest, StringToByteSize) { - auto parsed = try_string_to_byte_size("16 MB"); - ASSERT_TRUE(parsed.has_value()); - EXPECT_EQ(parsed.value(), 16ULL * 1024 * 1024); - - parsed = try_string_to_byte_size("0"); - ASSERT_TRUE(parsed.has_value()); - EXPECT_EQ(parsed.value(), 0); +#include - EXPECT_FALSE(try_string_to_byte_size("-5").has_value()); - EXPECT_FALSE(try_string_to_byte_size("16XB").has_value()); - EXPECT_EQ(string_to_byte_size("-5"), 0); -} +using namespace mooncake; TEST(UtilsTest, IsPortAvailable) { // Find an available port @@ -269,33 +170,3 @@ TEST(UtilsTest, AutoPortBinderCustomRange) { EXPECT_GE(port, 50000); EXPECT_LE(port, 50100); } - -TEST(HugepageSizeEnvTest, Accepts512Mb) { - setenv("MC_STORE_USE_HUGEPAGE", "1", 1); - setenv("MC_STORE_HUGEPAGE_SIZE", "512MB", 1); - - unsigned int flags = 0; - EXPECT_EQ(get_hugepage_size_from_env(&flags), SZ_512MB); - EXPECT_TRUE(flags & MAP_HUGETLB); - EXPECT_TRUE(flags & MAP_HUGE_512MB); - - flags = 0; - EXPECT_EQ(get_hugepage_size_from_env(&flags, /*use_memfd=*/true), SZ_512MB); - EXPECT_TRUE(flags & MFD_HUGETLB); - EXPECT_TRUE(flags & MFD_HUGE_512MB); - - unsetenv("MC_STORE_HUGEPAGE_SIZE"); - unsetenv("MC_STORE_USE_HUGEPAGE"); -} - -TEST(HugepageSizeEnvTest, FallsBackTo2MbOnInvalidSize) { - setenv("MC_STORE_USE_HUGEPAGE", "1", 1); - setenv("MC_STORE_HUGEPAGE_SIZE", "256MB", 1); - - unsigned int flags = 0; - EXPECT_EQ(get_hugepage_size_from_env(&flags), SZ_2MB); - EXPECT_TRUE(flags & MAP_HUGE_2MB); - - unsetenv("MC_STORE_HUGEPAGE_SIZE"); - unsetenv("MC_STORE_USE_HUGEPAGE"); -} diff --git a/mooncake-store/tests/non_ha_reconnect_test.cpp b/mooncake-store/tests/non_ha_reconnect_test.cpp index 4c3de3a4cb..a7ab5305fc 100644 --- a/mooncake-store/tests/non_ha_reconnect_test.cpp +++ b/mooncake-store/tests/non_ha_reconnect_test.cpp @@ -15,7 +15,7 @@ #include "client_service.h" #include "master_metric_manager.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" #include "test_server_helpers.h" #include "default_config.h" diff --git a/mooncake-store/tests/random_test.cpp b/mooncake-store/tests/random_test.cpp new file mode 100644 index 0000000000..2a09b9b6c7 --- /dev/null +++ b/mooncake-store/tests/random_test.cpp @@ -0,0 +1,76 @@ +#include "random.h" + +#include +#include +#include +#include + +#include + +using namespace mooncake; + +TEST(RandomTest, ReusesEngineWithinThread) { + EXPECT_EQ(&threadLocalRandomEngine(), &threadLocalRandomEngine()); +} + +TEST(RandomTest, UsesDifferentEngineAcrossThreads) { + auto* main_engine = &threadLocalRandomEngine(); + std::promise worker_address; + std::promise release_worker; + auto release_future = release_worker.get_future(); + + std::thread worker([&] { + worker_address.set_value(&threadLocalRandomEngine()); + release_future.wait(); + }); + + EXPECT_NE(main_engine, worker_address.get_future().get()); + release_worker.set_value(); + worker.join(); +} + +TEST(RandomTest, RandomIndexStaysWithinBounds) { + std::mt19937_64 engine(42); + for (size_t i = 0; i < 10000; ++i) { + EXPECT_LT(randomIndex(17, engine), 17); + } +} + +TEST(RandomTest, ExplicitEngineIsDeterministic) { + std::mt19937_64 first(42); + std::mt19937_64 second(42); + for (size_t i = 0; i < 100; ++i) { + EXPECT_EQ(randomIndex(1000, first), randomIndex(1000, second)); + } +} + +TEST(RandomTest, RandomUniformIncludesRequestedBounds) { + std::mt19937_64 engine(42); + for (size_t i = 0; i < 10000; ++i) { + int value = randomUniform(-5, 9, engine); + EXPECT_GE(value, -5); + EXPECT_LE(value, 9); + } + EXPECT_EQ(randomUniform(7, 7, engine), 7); +} + +TEST(RandomTest, RandomUniformSupportsNarrowIntegers) { + std::mt19937_64 engine(42); + for (size_t i = 0; i < 1000; ++i) { + auto signed_value = randomUniform(-5, 9, engine); + EXPECT_GE(signed_value, -5); + EXPECT_LE(signed_value, 9); + + auto unsigned_value = randomUniform(2, 7, engine); + EXPECT_GE(unsigned_value, 2); + EXPECT_LE(unsigned_value, 7); + } + EXPECT_FALSE(randomUniform(false, false, engine)); + EXPECT_TRUE(randomUniform(true, true, engine)); +} + +TEST(RandomTest, RejectsInvalidBounds) { + std::mt19937_64 engine(42); + EXPECT_THROW(randomIndex(0, engine), std::invalid_argument); + EXPECT_THROW(randomUniform(2, 1, engine), std::invalid_argument); +} diff --git a/mooncake-store/tests/storage_backend_test.cpp b/mooncake-store/tests/storage_backend_test.cpp index e33f0ba017..28214b8ef2 100644 --- a/mooncake-store/tests/storage_backend_test.cpp +++ b/mooncake-store/tests/storage_backend_test.cpp @@ -27,7 +27,8 @@ #include #include "allocator.h" -#include "utils.h" +#include "common/timestamp.h" +#include "common/file_util.h" #include "utils/common.h" namespace fs = std::filesystem; diff --git a/mooncake-store/tests/stress_workload_test.cpp b/mooncake-store/tests/stress_workload_test.cpp index fe46b35070..e0d7d4d469 100644 --- a/mooncake-store/tests/stress_workload_test.cpp +++ b/mooncake-store/tests/stress_workload_test.cpp @@ -14,7 +14,7 @@ #include "allocator.h" #include "client_service.h" #include "types.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" // Configuration flags DEFINE_string(protocol, "rdma", "Transfer protocol: rdma|tcp"); diff --git a/mooncake-store/tests/task_integration_test.cpp b/mooncake-store/tests/task_integration_test.cpp index 499d97d537..f5c5e618ac 100644 --- a/mooncake-store/tests/task_integration_test.cpp +++ b/mooncake-store/tests/task_integration_test.cpp @@ -19,7 +19,8 @@ #include "master_client.h" #include "task_manager.h" #include "types.h" -#include "utils.h" +#include "common/client_buffer_allocation.h" +#include "common/network.h" #include "test_server_helpers.h" #include "default_config.h" #include "allocator.h" diff --git a/mooncake-store/tests/test_server_helpers.h b/mooncake-store/tests/test_server_helpers.h index 83052ed1ff..91d40866b6 100644 --- a/mooncake-store/tests/test_server_helpers.h +++ b/mooncake-store/tests/test_server_helpers.h @@ -17,7 +17,7 @@ #include "rpc_service.h" #include "types.h" #include -#include "utils.h" +#include "common/network.h" namespace mooncake { namespace testing { diff --git a/mooncake-store/tests/zstd_util_test.cpp b/mooncake-store/tests/zstd_util_test.cpp index 2edb5a0d41..9aba810082 100644 --- a/mooncake-store/tests/zstd_util_test.cpp +++ b/mooncake-store/tests/zstd_util_test.cpp @@ -5,7 +5,7 @@ #include #include -#include "utils/zstd_util.h" +#include "common/zstd_util.h" namespace mooncake::test {