You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@nuttx.apache.org by xi...@apache.org on 2020/03/27 05:04:54 UTC

[incubator-nuttx] 07/07: sim: Use executable memory for the heap

This is an automated email from the ASF dual-hosted git repository.

xiaoxiang pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/incubator-nuttx.git

commit a493c92826fd0918231cbfe470e1cf9b48e96de3
Author: YAMAMOTO Takashi <ya...@midokura.com>
AuthorDate: Thu Mar 26 13:58:26 2020 +0900

    sim: Use executable memory for the heap
    
    On modern environments, bss is not executable.
    
    Alternatively we can use the ARCH_HAVE_MODULE_TEXT mechanism.
    But it's considered overkill for the sim, which is mainly
    for development.
---
 arch/sim/src/Makefile              |  6 +++++
 arch/sim/src/sim/up_allocateheap.c | 20 ++++++++++++--
 arch/sim/src/sim/up_hostmemory.c   | 55 ++++++++++++++++++++++++++++++++++++++
 arch/sim/src/sim/up_internal.h     |  4 +++
 4 files changed, 83 insertions(+), 2 deletions(-)

diff --git a/arch/sim/src/Makefile b/arch/sim/src/Makefile
index a454caf..8d4376d 100644
--- a/arch/sim/src/Makefile
+++ b/arch/sim/src/Makefile
@@ -76,6 +76,12 @@ DEPPATH = $(patsubst %,--dep-path %,$(subst :, ,$(VPATH)))
 
 HOSTSRCS = up_hosttime.c
 
+ifeq ($(CONFIG_LIBC_MODLIB),y)
+  HOSTSRCS += up_hostmemory.c
+else ifeq ($(CONFIG_BINFMT_LOADABLE),y)
+  HOSTSRCS += up_hostmemory.c
+endif
+
 ifeq ($(CONFIG_STACK_COLORATION),y)
   CSRCS += up_checkstack.c
 endif
diff --git a/arch/sim/src/sim/up_allocateheap.c b/arch/sim/src/sim/up_allocateheap.c
index 980cda9..e9329a6 100644
--- a/arch/sim/src/sim/up_allocateheap.c
+++ b/arch/sim/src/sim/up_allocateheap.c
@@ -52,8 +52,6 @@
  * Private Data
  ****************************************************************************/
 
-static uint8_t sim_heap[SIM_HEAP_SIZE];
-
 /****************************************************************************
  * Public Functions
  ****************************************************************************/
@@ -71,6 +69,24 @@ static uint8_t sim_heap[SIM_HEAP_SIZE];
 
 void up_allocate_heap(void **heap_start, size_t *heap_size)
 {
+  /* Note: Some subsystems like modlib and binfmt need to allocate
+   * executable memory.
+   */
+
+#if defined(CONFIG_LIBC_MODLIB) || defined(CONFIG_BINFMT_LOADABLE)
+  /* We make the entire heap executable here to keep
+   * the sim simpler. If it turns out to be a problem, the
+   * ARCH_HAVE_MODULE_TEXT mechanism can be an alternative.
+   */
+
+  uint8_t *sim_heap = host_alloc_heap(SIM_HEAP_SIZE);
+#else
+  /* This sim_heap would be placed in BSS, which is often not
+   * executable on modern environments.
+   */
+
+  static uint8_t sim_heap[SIM_HEAP_SIZE];
+#endif
   *heap_start = sim_heap;
   *heap_size  = SIM_HEAP_SIZE;
 }
diff --git a/arch/sim/src/sim/up_hostmemory.c b/arch/sim/src/sim/up_hostmemory.c
new file mode 100644
index 0000000..6c4345b
--- /dev/null
+++ b/arch/sim/src/sim/up_hostmemory.c
@@ -0,0 +1,55 @@
+/****************************************************************************
+ * arch/sim/src/sim/up_hostmemory.c
+ *
+ * Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements.  See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.  The
+ * ASF licenses this file to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance with the
+ * License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.  See the
+ * License for the specific language governing permissions and limitations
+ * under the License.
+ *
+ ****************************************************************************/
+
+/****************************************************************************
+ * Included Files
+ ****************************************************************************/
+
+#include <sys/mman.h>
+
+#include <stdio.h>
+#include <stdlib.h>
+
+/****************************************************************************
+ * Public Functions
+ ****************************************************************************/
+
+/****************************************************************************
+ * Name: host_alloc_heap
+ *
+ * Description:
+ *   Allocate executable memory for heap.
+ *
+ ****************************************************************************/
+
+void *host_alloc_heap(size_t sz)
+{
+  void *p;
+
+  p = mmap(NULL, sz, PROT_READ | PROT_WRITE | PROT_EXEC,
+           MAP_ANON | MAP_PRIVATE, -1, 0);
+  if (p == MAP_FAILED)
+    {
+      perror("Failed to allocate heap with mmap");
+      exit(EXIT_FAILURE);
+    }
+
+  return p;
+}
diff --git a/arch/sim/src/sim/up_internal.h b/arch/sim/src/sim/up_internal.h
index d12a313..65b8d1f 100644
--- a/arch/sim/src/sim/up_internal.h
+++ b/arch/sim/src/sim/up_internal.h
@@ -224,6 +224,10 @@ volatile spinlock_t g_cpu_paused[CONFIG_SMP_NCPUS] SP_SECTION;
 int  up_setjmp(xcpt_reg_t *jb);
 void up_longjmp(xcpt_reg_t *jb, int val) noreturn_function;
 
+/* up_hostmemory.c **********************************************************/
+
+void *host_alloc_heap(size_t sz);
+
 /* up_hosttime.c ************************************************************/
 
 uint64_t host_gettime(bool rtc);