Skip to content

Commit ddd572b

Browse files
authored
Merge pull request #746 from ldorau/Add_support_for_mapping_with_MAP_SYNC_to_file_provider
Add support for mapping with MAP_SYNC to file provider
2 parents e9eaca0 + dadb2b6 commit ddd572b

File tree

8 files changed

+90
-29
lines changed

8 files changed

+90
-29
lines changed

README.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -200,6 +200,8 @@ so it should be used with a pool manager that will take over
200200
the managing of the provided memory - for example the jemalloc pool
201201
with the `disable_provider_free` parameter set to true.
202202

203+
The memory visibility mode parameter must be set to `UMF_MEM_MAP_SYNC` in case of FSDAX.
204+
203205
##### Requirements
204206

205207
1) Linux OS

include/umf/memory_provider.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,8 @@ extern "C" {
2020
/// @brief Memory visibility mode
2121
typedef enum umf_memory_visibility_t {
2222
UMF_MEM_MAP_PRIVATE = 1, ///< private memory mapping
23-
UMF_MEM_MAP_SHARED, ///< shared memory mapping (supported on Linux only)
23+
UMF_MEM_MAP_SHARED, ///< shared memory mapping (Linux only)
24+
UMF_MEM_MAP_SYNC, ///< direct mapping of persistent memory (supported only for files supporting DAX, Linux only)
2425
} umf_memory_visibility_t;
2526

2627
/// @brief Protection of the memory allocations

src/provider/provider_devdax_memory.c

Lines changed: 14 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -130,8 +130,13 @@ static umf_result_t devdax_initialize(void *params, void **provider) {
130130
goto err_free_devdax_provider;
131131
}
132132

133-
devdax_provider->base = utils_devdax_mmap(NULL, devdax_provider->size,
134-
devdax_provider->protection, fd);
133+
unsigned map_sync_flag = 0;
134+
utils_translate_mem_visibility_flag(UMF_MEM_MAP_SYNC, &map_sync_flag);
135+
136+
// mmap /dev/dax with the MAP_SYNC xor MAP_SHARED flag (if MAP_SYNC fails)
137+
devdax_provider->base = utils_mmap_file(NULL, devdax_provider->size,
138+
devdax_provider->protection,
139+
map_sync_flag, fd, 0 /* offset */);
135140
utils_close_fd(fd);
136141
if (devdax_provider->base == NULL) {
137142
LOG_PDEBUG("devdax memory mapping failed (path=%s, size=%zu)",
@@ -458,8 +463,13 @@ static umf_result_t devdax_open_ipc_handle(void *provider,
458463
return UMF_RESULT_ERROR_INVALID_ARGUMENT;
459464
}
460465

461-
char *base = utils_devdax_mmap(NULL, devdax_provider->size,
462-
devdax_provider->protection, fd);
466+
unsigned map_sync_flag = 0;
467+
utils_translate_mem_visibility_flag(UMF_MEM_MAP_SYNC, &map_sync_flag);
468+
469+
// mmap /dev/dax with the MAP_SYNC xor MAP_SHARED flag (if MAP_SYNC fails)
470+
char *base = utils_mmap_file(NULL, devdax_provider->size,
471+
devdax_provider->protection, map_sync_flag, fd,
472+
0 /* offset */);
463473
if (base == NULL) {
464474
devdax_store_last_native_error(UMF_DEVDAX_RESULT_ERROR_ALLOC_FAILED,
465475
errno);

src/provider/provider_file_memory.c

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -261,7 +261,7 @@ static umf_result_t file_mmap_aligned(file_memory_provider_t *file_provider,
261261
ASSERT_IS_ALIGNED(extended_size, page_size);
262262
ASSERT_IS_ALIGNED(offset_fd, page_size);
263263

264-
void *ptr = utils_mmap(NULL, extended_size, prot, flag, fd, offset_fd);
264+
void *ptr = utils_mmap_file(NULL, extended_size, prot, flag, fd, offset_fd);
265265
if (ptr == NULL) {
266266
LOG_PERR("memory mapping failed");
267267
return UMF_RESULT_ERROR_MEMORY_PROVIDER_SPECIFIC;
@@ -612,8 +612,9 @@ static umf_result_t file_open_ipc_handle(void *provider, void *providerIpcData,
612612
return UMF_RESULT_ERROR_INVALID_ARGUMENT;
613613
}
614614

615-
*ptr = utils_mmap(NULL, file_ipc_data->size, file_provider->protection,
616-
file_provider->visibility, fd, file_ipc_data->offset_fd);
615+
*ptr = utils_mmap_file(NULL, file_ipc_data->size, file_provider->protection,
616+
file_provider->visibility, fd,
617+
file_ipc_data->offset_fd);
617618
(void)utils_close_fd(fd);
618619
if (*ptr == NULL) {
619620
file_store_last_native_error(UMF_FILE_RESULT_ERROR_ALLOC_FAILED, errno);

src/utils/utils_common.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -124,7 +124,8 @@ int utils_set_file_size(int fd, size_t size);
124124
void *utils_mmap(void *hint_addr, size_t length, int prot, int flag, int fd,
125125
size_t fd_offset);
126126

127-
void *utils_devdax_mmap(void *hint_addr, size_t length, int prot, int fd);
127+
void *utils_mmap_file(void *hint_addr, size_t length, int prot, int flags,
128+
int fd, size_t fd_offset);
128129

129130
int utils_munmap(void *addr, size_t length);
130131

src/utils/utils_linux_common.c

Lines changed: 53 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -31,29 +31,65 @@ utils_translate_mem_visibility_flag(umf_memory_visibility_t in_flag,
3131
case UMF_MEM_MAP_SHARED:
3232
*out_flag = MAP_SHARED;
3333
return UMF_RESULT_SUCCESS;
34+
case UMF_MEM_MAP_SYNC:
35+
*out_flag = MAP_SYNC;
36+
return UMF_RESULT_SUCCESS;
3437
}
3538
return UMF_RESULT_ERROR_INVALID_ARGUMENT;
3639
}
3740

3841
/*
39-
* MMap a /dev/dax device.
40-
* First try to mmap with (MAP_SHARED_VALIDATE | MAP_SYNC) flags
41-
* which allows flushing from the user-space. If MAP_SYNC fails
42-
* try to mmap with MAP_SHARED flag (without MAP_SYNC).
42+
* Map given file into memory.
43+
* If (flags & MAP_PRIVATE) it uses just mmap. Otherwise, if (flags & MAP_SYNC)
44+
* it tries to mmap with (flags | MAP_SHARED_VALIDATE | MAP_SYNC)
45+
* which allows flushing from the user-space. If MAP_SYNC fails and the user
46+
* did not specify it by himself it tries to mmap with (flags | MAP_SHARED).
4347
*/
44-
void *utils_devdax_mmap(void *hint_addr, size_t length, int prot, int fd) {
45-
void *ptr = utils_mmap(hint_addr, length, prot,
46-
MAP_SHARED_VALIDATE | MAP_SYNC, fd, 0);
47-
if (ptr) {
48-
LOG_DEBUG(
49-
"devdax mapped with the (MAP_SHARED_VALIDATE | MAP_SYNC) flags");
50-
return ptr;
51-
}
52-
53-
ptr = utils_mmap(hint_addr, length, prot, MAP_SHARED, fd, 0);
54-
if (ptr) {
55-
LOG_DEBUG("devdax mapped with the MAP_SHARED flag");
56-
return ptr;
48+
void *utils_mmap_file(void *hint_addr, size_t length, int prot, int flags,
49+
int fd, size_t fd_offset) {
50+
void *addr;
51+
52+
/*
53+
* MAP_PRIVATE and MAP_SHARED are mutually exclusive,
54+
* therefore mmap with MAP_PRIVATE is executed separately.
55+
*/
56+
if (flags & MAP_PRIVATE) {
57+
addr = utils_mmap(hint_addr, length, prot, flags, fd, fd_offset);
58+
if (addr == MAP_FAILED) {
59+
LOG_PERR("mapping file with the MAP_PRIVATE flag failed");
60+
return NULL;
61+
}
62+
63+
LOG_DEBUG("file mapped with the MAP_PRIVATE flag");
64+
return addr;
65+
}
66+
67+
errno = 0;
68+
69+
if (flags & MAP_SYNC) {
70+
/* try to mmap with MAP_SYNC flag */
71+
const int sync_flags = MAP_SHARED_VALIDATE | MAP_SYNC;
72+
addr = utils_mmap(hint_addr, length, prot, flags | sync_flags, fd,
73+
fd_offset);
74+
if (addr) {
75+
LOG_DEBUG("file mapped with the MAP_SYNC flag");
76+
return addr;
77+
}
78+
79+
LOG_PERR("mapping file with the MAP_SYNC flag failed");
80+
}
81+
82+
if ((!(flags & MAP_SYNC)) || errno == EINVAL || errno == ENOTSUP ||
83+
errno == EOPNOTSUPP) {
84+
/* try to mmap with MAP_SHARED flag (without MAP_SYNC) */
85+
const int shared_flags = (flags & (~MAP_SYNC)) | MAP_SHARED;
86+
addr = utils_mmap(hint_addr, length, prot, shared_flags, fd, fd_offset);
87+
if (addr) {
88+
LOG_DEBUG("file mapped with the MAP_SHARED flag");
89+
return addr;
90+
}
91+
92+
LOG_PERR("mapping file with the MAP_SHARED flag failed");
5793
}
5894

5995
return NULL;

src/utils/utils_macosx_common.c

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -23,15 +23,20 @@ utils_translate_mem_visibility_flag(umf_memory_visibility_t in_flag,
2323
return UMF_RESULT_SUCCESS;
2424
case UMF_MEM_MAP_SHARED:
2525
return UMF_RESULT_ERROR_NOT_SUPPORTED; // not supported on MacOSX
26+
case UMF_MEM_MAP_SYNC:
27+
return UMF_RESULT_ERROR_NOT_SUPPORTED; // not supported on MacOSX
2628
}
2729
return UMF_RESULT_ERROR_INVALID_ARGUMENT;
2830
}
2931

30-
void *utils_devdax_mmap(void *hint_addr, size_t length, int prot, int fd) {
32+
void *utils_mmap_file(void *hint_addr, size_t length, int prot, int flags,
33+
int fd, size_t fd_offset) {
3134
(void)hint_addr; // unused
3235
(void)length; // unused
3336
(void)prot; // unused
37+
(void)flags; // unused
3438
(void)fd; // unused
39+
(void)fd_offset; // unused
3540
return NULL; // not supported
3641
}
3742

src/utils/utils_windows_common.c

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -96,6 +96,8 @@ utils_translate_mem_visibility_flag(umf_memory_visibility_t in_flag,
9696
return UMF_RESULT_SUCCESS;
9797
case UMF_MEM_MAP_SHARED:
9898
return UMF_RESULT_ERROR_NOT_SUPPORTED; // not supported on Windows yet
99+
case UMF_MEM_MAP_SYNC:
100+
return UMF_RESULT_ERROR_NOT_SUPPORTED; // not supported on Windows yet
99101
}
100102
return UMF_RESULT_ERROR_INVALID_ARGUMENT;
101103
}
@@ -145,12 +147,15 @@ void *utils_mmap(void *hint_addr, size_t length, int prot, int flag, int fd,
145147
return VirtualAlloc(hint_addr, length, MEM_RESERVE | MEM_COMMIT, prot);
146148
}
147149

148-
void *utils_devdax_mmap(void *hint_addr, size_t length, int prot, int fd) {
150+
void *utils_mmap_file(void *hint_addr, size_t length, int prot, int flags,
151+
int fd, size_t fd_offset) {
149152
(void)hint_addr; // unused
150153
(void)length; // unused
151154
(void)prot; // unused
155+
(void)flags; // unused
152156
(void)fd; // unused
153-
return NULL; // not supported on Windows
157+
(void)fd_offset; // unused
158+
return NULL; // not supported
154159
}
155160

156161
int utils_munmap(void *addr, size_t length) {

0 commit comments

Comments
 (0)