summaryrefslogtreecommitdiffstats
path: root/otherlibs/bigarray/mmap_unix.c
diff options
context:
space:
mode:
authorXavier Leroy <xavier.leroy@inria.fr>2012-04-09 10:23:50 +0000
committerXavier Leroy <xavier.leroy@inria.fr>2012-04-09 10:23:50 +0000
commit2330a3b30fe5b910f4776bf9c41f35ce2b980fb1 (patch)
tree2a4daf18833123751ad9a41292895073b7bbf5f9 /otherlibs/bigarray/mmap_unix.c
parent0d2e9941ebfbfcaaf28eae3e21dd7a8d35fdbb91 (diff)
PR#3571: in Bigarrays, call msync() before unmapping to commit changes
PR#5463: Bigarray.*.map_file fail if empty array is requested Bigarray: added "release" functions that free memory and file mappings just like GC finalization does eventually, but does it immediately. git-svn-id: http://caml.inria.fr/svn/ocaml/trunk@12327 f963ae5c-01c2-4b8c-9fe0-0dff7051ff02
Diffstat (limited to 'otherlibs/bigarray/mmap_unix.c')
-rw-r--r--otherlibs/bigarray/mmap_unix.c21
1 files changed, 15 insertions, 6 deletions
diff --git a/otherlibs/bigarray/mmap_unix.c b/otherlibs/bigarray/mmap_unix.c
index f10835443..30294cc4b 100644
--- a/otherlibs/bigarray/mmap_unix.c
+++ b/otherlibs/bigarray/mmap_unix.c
@@ -152,11 +152,14 @@ CAMLprim value caml_ba_map_file(value vfd, value vkind, value vlayout,
}
/* Determine offset so that the mapping starts at the given file pos */
page = getpagesize();
- delta = (uintnat) (startpos % page);
+ delta = (uintnat) startpos % page;
/* Do the mmap */
shared = Bool_val(vshared) ? MAP_SHARED : MAP_PRIVATE;
- addr = mmap(NULL, array_size + delta, PROT_READ | PROT_WRITE,
- shared, fd, startpos - delta);
+ if (array_size > 0)
+ addr = mmap(NULL, array_size + delta, PROT_READ | PROT_WRITE,
+ shared, fd, startpos - delta);
+ else
+ addr = NULL; /* PR#5463 - mmap fails on empty region */
caml_leave_blocking_section();
if (addr == (void *) MAP_FAILED) caml_sys_error(NO_ARG);
addr = (void *) ((uintnat) addr + delta);
@@ -166,8 +169,8 @@ CAMLprim value caml_ba_map_file(value vfd, value vkind, value vlayout,
#else
-value caml_ba_map_file(value vfd, value vkind, value vlayout,
- value vshared, value vdim, value vpos)
+CAMLprim value caml_ba_map_file(value vfd, value vkind, value vlayout,
+ value vshared, value vdim, value vpos)
{
caml_invalid_argument("Bigarray.map_file: not supported");
return Val_unit;
@@ -186,6 +189,12 @@ void caml_ba_unmap_file(void * addr, uintnat len)
#if defined(HAS_MMAP)
uintnat page = getpagesize();
uintnat delta = (uintnat) addr % page;
- munmap((void *)((uintnat)addr - delta), len + delta);
+ if (len == 0) return; /* PR#5463 */
+ addr = (void *)((uintnat)addr - delta);
+ len = len + delta;
+#if defined(_POSIX_SYNCHRONIZED_IO)
+ msync(addr, len, MS_ASYNC); /* PR#3571 */
+#endif
+ munmap(addr, len);
#endif
}