OSDN Git Service

For PR351:
authorReid Spencer <rspencer@reidspencer.com>
Mon, 27 Dec 2004 06:17:03 +0000 (06:17 +0000)
committerReid Spencer <rspencer@reidspencer.com>
Mon, 27 Dec 2004 06:17:03 +0000 (06:17 +0000)
* Ensure #includes are wrapped with appropriate HAVE_ guards
* Consolidate implementation from operating system specific directory.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@19157 91177308-0d34-0410-b5e6-96231b3b80d8

lib/System/Unix/Memory.cpp
lib/System/Unix/Memory.inc

index cc461f1..370b318 100644 (file)
 //===----------------------------------------------------------------------===//
 
 #include "Unix.h"
+#include "llvm/System/Process.h"
+
+#ifdef HAVE_SYS_MMAN_H
+#include <sys/mman.h>
+#endif
 
 namespace llvm {
 
+/// AllocateRWXMemory - Allocate a slab of memory with read/write/execute
+/// permissions.  This is typically used for JIT applications where we want
+/// to emit code to the memory then jump to it.  Getting this type of memory
+/// is very OS specific.
+///
+MemoryBlock Memory::AllocateRWX(unsigned NumBytes) {
+  if (NumBytes == 0) return MemoryBlock();
+
+  long pageSize = Process::GetPageSize();
+  unsigned NumPages = (NumBytes+pageSize-1)/pageSize;
+
+  int fd = -1;
+#ifdef NEED_DEV_ZERO_FOR_MMAP
+  static int zero_fd = open("/dev/zero", O_RDWR);
+  if (zero_fd == -1) {
+    ThrowErrno("Can't open /dev/zero device");
+  }
+  fd = zero_fd;
+#endif
+
+  int flags = MAP_PRIVATE |
+#ifdef HAVE_MMAP_ANONYMOUS
+  MAP_ANONYMOUS
+#else
+  MAP_ANON
+#endif
+  ;
+  void *pa = ::mmap(0, pageSize*NumPages, PROT_READ|PROT_WRITE|PROT_EXEC,
+                    flags, fd, 0);
+  if (pa == MAP_FAILED) {
+    ThrowErrno("Can't allocate RWX Memory");
+  }
+  MemoryBlock result;
+  result.Address = pa;
+  result.Size = NumPages*pageSize;
+  return result;
+}
+
+void Memory::ReleaseRWX(MemoryBlock& M) {
+  if (M.Address == 0 || M.Size == 0) return;
+  if (0 != ::munmap(M.Address, M.Size)) {
+    ThrowErrno("Can't release RWX Memory");
+  }
+}
+
 }
 
 // vim: sw=2 smartindent smarttab tw=80 autoindent expandtab
index cc461f1..370b318 100644 (file)
 //===----------------------------------------------------------------------===//
 
 #include "Unix.h"
+#include "llvm/System/Process.h"
+
+#ifdef HAVE_SYS_MMAN_H
+#include <sys/mman.h>
+#endif
 
 namespace llvm {
 
+/// AllocateRWXMemory - Allocate a slab of memory with read/write/execute
+/// permissions.  This is typically used for JIT applications where we want
+/// to emit code to the memory then jump to it.  Getting this type of memory
+/// is very OS specific.
+///
+MemoryBlock Memory::AllocateRWX(unsigned NumBytes) {
+  if (NumBytes == 0) return MemoryBlock();
+
+  long pageSize = Process::GetPageSize();
+  unsigned NumPages = (NumBytes+pageSize-1)/pageSize;
+
+  int fd = -1;
+#ifdef NEED_DEV_ZERO_FOR_MMAP
+  static int zero_fd = open("/dev/zero", O_RDWR);
+  if (zero_fd == -1) {
+    ThrowErrno("Can't open /dev/zero device");
+  }
+  fd = zero_fd;
+#endif
+
+  int flags = MAP_PRIVATE |
+#ifdef HAVE_MMAP_ANONYMOUS
+  MAP_ANONYMOUS
+#else
+  MAP_ANON
+#endif
+  ;
+  void *pa = ::mmap(0, pageSize*NumPages, PROT_READ|PROT_WRITE|PROT_EXEC,
+                    flags, fd, 0);
+  if (pa == MAP_FAILED) {
+    ThrowErrno("Can't allocate RWX Memory");
+  }
+  MemoryBlock result;
+  result.Address = pa;
+  result.Size = NumPages*pageSize;
+  return result;
+}
+
+void Memory::ReleaseRWX(MemoryBlock& M) {
+  if (M.Address == 0 || M.Size == 0) return;
+  if (0 != ::munmap(M.Address, M.Size)) {
+    ThrowErrno("Can't release RWX Memory");
+  }
+}
+
 }
 
 // vim: sw=2 smartindent smarttab tw=80 autoindent expandtab