Eneboo - Documentación para desarrolladores
|
00001 // -*- C++ -*- 00002 00003 /* 00004 00005 Heap Layers: An Extensible Memory Allocation Infrastructure 00006 00007 Copyright (C) 2000-2005 by Emery Berger 00008 http://www.cs.umass.edu/~emery 00009 emery@cs.umass.edu 00010 00011 This program is free software; you can redistribute it and/or modify 00012 it under the terms of the GNU General Public License as published by 00013 the Free Software Foundation; either version 2 of the License, or 00014 (at your option) any later version. 00015 00016 This program is distributed in the hope that it will be useful, 00017 but WITHOUT ANY WARRANTY; without even the implied warranty of 00018 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00019 GNU General Public License for more details. 00020 00021 You should have received a copy of the GNU General Public License 00022 along with this program; if not, write to the Free Software 00023 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 00024 00025 */ 00026 00027 #ifndef _MMAPWRAPPER_H_ 00028 #define _MMAPWRAPPER_H_ 00029 00030 #if defined(_WIN32) 00031 #include <windows.h> 00032 #else 00033 // UNIX 00034 #include <sys/types.h> 00035 #include <sys/stat.h> 00036 #include <fcntl.h> 00037 #include <unistd.h> 00038 #include <sys/mman.h> 00039 #include <map> 00040 #endif 00041 00042 #if HL_EXECUTABLE_HEAP 00043 #define HL_MMAP_PROTECTION_MASK (PROT_READ | PROT_WRITE | PROT_EXEC) 00044 #else 00045 #define HL_MMAP_PROTECTION_MASK (PROT_READ | PROT_WRITE) 00046 #endif 00047 00048 #if !defined(MAP_ANONYMOUS) && defined(MAP_ANON) 00049 #define MAP_ANONYMOUS MAP_ANON 00050 #endif 00051 00052 namespace HL { 00053 00054 class MmapWrapper { 00055 public: 00056 00057 #if defined(_WIN32) 00058 00059 // Microsoft Windows has 4K pages aligned to a 64K boundary. 00060 enum { Size = 4 * 1024 }; 00061 enum { Alignment = 64 * 1024 }; 00062 00063 static void * map (size_t sz) { 00064 void * ptr; 00065 #if HL_EXECUTABLE_HEAP 00066 const int permflags = PAGE_EXECUTE_READWRITE; 00067 #else 00068 const int permflags = PAGE_READWRITE; 00069 #endif 00070 ptr = VirtualAlloc (NULL, sz, MEM_RESERVE | MEM_COMMIT | MEM_TOP_DOWN, permflags); 00071 return ptr; 00072 } 00073 00074 static void unmap (void * ptr, size_t) { 00075 VirtualFree (ptr, 0, MEM_RELEASE); 00076 } 00077 00078 #else 00079 00080 #if defined(__SVR4) 00081 // Solaris aligns 8K pages to a 64K boundary. 00082 enum { Size = 8 * 1024 }; 00083 enum { Alignment = 64 * 1024 }; 00084 #else 00085 // Linux and most other operating systems align memory to a 4K boundary. 00086 enum { Size = 4 * 1024 }; 00087 enum { Alignment = 4 * 1024 }; 00088 #endif 00089 00090 static void * map (size_t sz) { 00091 00092 if (sz == 0) { 00093 return NULL; 00094 } 00095 00096 void * ptr; 00097 00098 #if defined(MAP_ALIGN) && defined(MAP_ANON) 00099 // Request memory aligned to the Alignment value above. 00100 ptr = mmap ((char *) Alignment, sz, HL_MMAP_PROTECTION_MASK, MAP_PRIVATE | MAP_ALIGN | MAP_ANON, -1, 0); 00101 #elif !defined(MAP_ANONYMOUS) 00102 static int fd = ::open ("/dev/zero", O_RDWR); 00103 ptr = mmap (NULL, sz, HL_MMAP_PROTECTION_MASK, MAP_PRIVATE, fd, 0); 00104 #else 00105 ptr = mmap (0, sz, HL_MMAP_PROTECTION_MASK, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); 00106 #endif 00107 00108 if (ptr == MAP_FAILED) { 00109 fprintf (stderr, "Virtual memory exhausted.\n"); 00110 return NULL; 00111 } else { 00112 return ptr; 00113 } 00114 } 00115 00116 static void unmap (void * ptr, size_t sz) { 00117 munmap (reinterpret_cast<char *>(ptr), sz); 00118 } 00119 00120 #endif 00121 00122 }; 00123 00124 } 00125 00126 #endif