Apache Arrow (C++)
A columnar in-memory analytics layer designed to accelerate big data.
mman.h
Go to the documentation of this file.
1 // Copyright https://code.google.com/p/mman-win32/
2 //
3 // Licensed under the MIT License;
4 // You may obtain a copy of the License at
5 //
6 // https://opensource.org/licenses/MIT
7 
8 #ifndef _MMAN_WIN32_H
9 #define _MMAN_WIN32_H
10 
11 // Allow use of features specific to Windows XP or later.
12 #ifndef _WIN32_WINNT
13 // Change this to the appropriate value to target other versions of Windows.
14 #define _WIN32_WINNT 0x0501
15 
16 #endif
17 
19 
20 #include <errno.h>
21 #include <io.h>
22 #include <sys/types.h>
23 
24 #define PROT_NONE 0
25 #define PROT_READ 1
26 #define PROT_WRITE 2
27 #define PROT_EXEC 4
28 
29 #define MAP_FILE 0
30 #define MAP_SHARED 1
31 #define MAP_PRIVATE 2
32 #define MAP_TYPE 0xf
33 #define MAP_FIXED 0x10
34 #define MAP_ANONYMOUS 0x20
35 #define MAP_ANON MAP_ANONYMOUS
36 
37 #define MAP_FAILED ((void*)-1)
38 
39 /* Flags for msync. */
40 #define MS_ASYNC 1
41 #define MS_SYNC 2
42 #define MS_INVALIDATE 4
43 
44 #ifndef FILE_MAP_EXECUTE
45 #define FILE_MAP_EXECUTE 0x0020
46 #endif
47 
48 static int __map_mman_error(const DWORD err, const int deferr) {
49  if (err == 0) return 0;
50  // TODO: implement
51  return err;
52 }
53 
54 static DWORD __map_mmap_prot_page(const int prot) {
55  DWORD protect = 0;
56 
57  if (prot == PROT_NONE) return protect;
58 
59  if ((prot & PROT_EXEC) != 0) {
60  protect = ((prot & PROT_WRITE) != 0) ? PAGE_EXECUTE_READWRITE : PAGE_EXECUTE_READ;
61  } else {
62  protect = ((prot & PROT_WRITE) != 0) ? PAGE_READWRITE : PAGE_READONLY;
63  }
64 
65  return protect;
66 }
67 
68 static DWORD __map_mmap_prot_file(const int prot) {
69  DWORD desiredAccess = 0;
70 
71  if (prot == PROT_NONE) return desiredAccess;
72 
73  if ((prot & PROT_READ) != 0) desiredAccess |= FILE_MAP_READ;
74  if ((prot & PROT_WRITE) != 0) desiredAccess |= FILE_MAP_WRITE;
75  if ((prot & PROT_EXEC) != 0) desiredAccess |= FILE_MAP_EXECUTE;
76 
77  return desiredAccess;
78 }
79 
80 static void* mmap(void* addr, size_t len, int prot, int flags, int fildes, off_t off) {
81  HANDLE fm, h;
82 
83  void* map = MAP_FAILED;
84 
85 #ifdef _MSC_VER
86 #pragma warning(push)
87 #pragma warning(disable : 4293)
88 #endif
89 
90  const DWORD dwFileOffsetLow =
91  (sizeof(off_t) <= sizeof(DWORD)) ? (DWORD)off : (DWORD)(off & 0xFFFFFFFFL);
92  const DWORD dwFileOffsetHigh =
93  (sizeof(off_t) <= sizeof(DWORD)) ? (DWORD)0 : (DWORD)((off >> 32) & 0xFFFFFFFFL);
94  const DWORD protect = __map_mmap_prot_page(prot);
95  const DWORD desiredAccess = __map_mmap_prot_file(prot);
96 
97  const size_t maxSize = off + len;
98 
99  const DWORD dwMaxSizeLow = static_cast<DWORD>(maxSize & 0xFFFFFFFFL);
100  const DWORD dwMaxSizeHigh = static_cast<DWORD>((maxSize >> 32) & 0xFFFFFFFFL);
101 
102 #ifdef _MSC_VER
103 #pragma warning(pop)
104 #endif
105 
106  errno = 0;
107 
108  if (len == 0
109  /* Unsupported flag combinations */
110  || (flags & MAP_FIXED) != 0
111  /* Usupported protection combinations */
112  || prot == PROT_EXEC) {
113  errno = EINVAL;
114  return MAP_FAILED;
115  }
116 
117  h = ((flags & MAP_ANONYMOUS) == 0) ? (HANDLE)_get_osfhandle(fildes)
118  : INVALID_HANDLE_VALUE;
119 
120  if ((flags & MAP_ANONYMOUS) == 0 && h == INVALID_HANDLE_VALUE) {
121  errno = EBADF;
122  return MAP_FAILED;
123  }
124 
125  fm = CreateFileMapping(h, NULL, protect, dwMaxSizeHigh, dwMaxSizeLow, NULL);
126 
127  if (fm == NULL) {
128  errno = __map_mman_error(GetLastError(), EPERM);
129  return MAP_FAILED;
130  }
131 
132  map = MapViewOfFile(fm, desiredAccess, dwFileOffsetHigh, dwFileOffsetLow, len);
133 
134  CloseHandle(fm);
135 
136  if (map == NULL) {
137  errno = __map_mman_error(GetLastError(), EPERM);
138  return MAP_FAILED;
139  }
140 
141  return map;
142 }
143 
144 static int munmap(void* addr, size_t len) {
145  if (UnmapViewOfFile(addr)) return 0;
146 
147  errno = __map_mman_error(GetLastError(), EPERM);
148 
149  return -1;
150 }
151 
152 static int mprotect(void* addr, size_t len, int prot) {
153  DWORD newProtect = __map_mmap_prot_page(prot);
154  DWORD oldProtect = 0;
155 
156  if (VirtualProtect(addr, len, newProtect, &oldProtect)) return 0;
157 
158  errno = __map_mman_error(GetLastError(), EPERM);
159 
160  return -1;
161 }
162 
163 static int msync(void* addr, size_t len, int flags) {
164  if (FlushViewOfFile(addr, len)) return 0;
165 
166  errno = __map_mman_error(GetLastError(), EPERM);
167 
168  return -1;
169 }
170 
171 static int mlock(const void* addr, size_t len) {
172  if (VirtualLock((LPVOID)addr, len)) return 0;
173 
174  errno = __map_mman_error(GetLastError(), EPERM);
175 
176  return -1;
177 }
178 
179 static int munlock(const void* addr, size_t len) {
180  if (VirtualUnlock((LPVOID)addr, len)) return 0;
181 
182  errno = __map_mman_error(GetLastError(), EPERM);
183 
184  return -1;
185 }
186 
187 #endif
#define FILE_MAP_EXECUTE
Definition: mman.h:45
#define MAP_FAILED
Definition: mman.h:37
#define PROT_WRITE
Definition: mman.h:26
#define PROT_READ
Definition: mman.h:25
#define MAP_FIXED
Definition: mman.h:33
#define PROT_NONE
Definition: mman.h:24
#define MAP_ANONYMOUS
Definition: mman.h:34
#define PROT_EXEC
Definition: mman.h:27