static inline memkind_t hbw_get_kind(int pagesize) { memkind_t result = NULL; int policy = hbw_get_policy(); if (policy == HBW_POLICY_BIND || policy == HBW_POLICY_INTERLEAVE) { switch (pagesize) { case HBW_PAGESIZE_2MB: result = MEMKIND_HBW_HUGETLB; break; case HBW_PAGESIZE_1GB: case HBW_PAGESIZE_1GB_STRICT: result = MEMKIND_HBW_GBTLB; break; default: if (policy == HBW_POLICY_BIND) { result = MEMKIND_HBW; } else { result = MEMKIND_HBW_INTERLEAVE; } break; } } else if (memkind_check_available(MEMKIND_HBW) == 0) { switch (pagesize) { case HBW_PAGESIZE_2MB: result = MEMKIND_HBW_PREFERRED_HUGETLB; break; case HBW_PAGESIZE_1GB: case HBW_PAGESIZE_1GB_STRICT: result = MEMKIND_HBW_PREFERRED_GBTLB; break; default: result = MEMKIND_HBW_PREFERRED; break; } } else { switch (pagesize) { case HBW_PAGESIZE_2MB: result = MEMKIND_HUGETLB; break; case HBW_PAGESIZE_1GB: case HBW_PAGESIZE_1GB_STRICT: result = MEMKIND_GBTLB; break; default: result = MEMKIND_DEFAULT; break; } } return result; }
MEMKIND_EXPORT int hbw_posix_memalign_psize(void **memptr, size_t alignment, size_t size, hbw_pagesize_t pagesize) { if (pagesize == HBW_PAGESIZE_1GB_STRICT && size % (1 << 30)) { return EINVAL; } if((pagesize == HBW_PAGESIZE_2MB || pagesize == HBW_PAGESIZE_1GB_STRICT || pagesize == HBW_PAGESIZE_1GB) && hbw_get_policy() == HBW_POLICY_INTERLEAVE) { log_err("HBW_POLICY_INTERLEAVE is unsupported with used page size!"); return EINVAL; } return memkind_posix_memalign(hbw_get_kind(pagesize), memptr, alignment, size); }
// This function is intended to be called once per pagesize // Getting kind should be done using hbw_get_kind() defined below static memkind_t hbw_choose_kind(hbw_pagesize_t pagesize) { memkind_t result = NULL; hbw_set_policy(hbw_policy_g); int policy = hbw_get_policy(); // PREFERRED policy have separate handling cause it can fallback // to non-HBW kinds in case of HBW absence if (policy != HBW_POLICY_PREFERRED ) { switch (pagesize) { case HBW_PAGESIZE_2MB: if(policy == HBW_POLICY_BIND_ALL) { result = MEMKIND_HBW_ALL_HUGETLB; } else { result = MEMKIND_HBW_HUGETLB; } break; case HBW_PAGESIZE_1GB: case HBW_PAGESIZE_1GB_STRICT: result = MEMKIND_HBW_GBTLB; break; default: if (policy == HBW_POLICY_BIND) { result = MEMKIND_HBW; } else if (policy == HBW_POLICY_BIND_ALL) { result = MEMKIND_HBW_ALL; } else { result = MEMKIND_HBW_INTERLEAVE; } break; } } else if (memkind_check_available(MEMKIND_HBW) == 0) { switch (pagesize) { case HBW_PAGESIZE_2MB: result = MEMKIND_HBW_PREFERRED_HUGETLB; break; case HBW_PAGESIZE_1GB: case HBW_PAGESIZE_1GB_STRICT: result = MEMKIND_HBW_PREFERRED_GBTLB; break; default: result = MEMKIND_HBW_PREFERRED; break; } } else { switch (pagesize) { case HBW_PAGESIZE_2MB: result = MEMKIND_HUGETLB; break; case HBW_PAGESIZE_1GB: case HBW_PAGESIZE_1GB_STRICT: result = MEMKIND_GBTLB; break; default: result = MEMKIND_DEFAULT; break; } } return result; }
TEST_F(BABindTest, test_TC_MEMKIND_HBW_Bind_Policy) { hbw_set_policy(HBW_POLICY_BIND); EXPECT_EQ(HBW_POLICY_BIND, hbw_get_policy()); }
TEST_F(BATest, test_TC_MEMKIND_HBW_Pref_Policy) { hbw_set_policy(HBW_POLICY_PREFERRED); EXPECT_EQ(HBW_POLICY_PREFERRED, hbw_get_policy()); }