QNX IPC: RscTable - Use MAP_NOINIT Flag to Allocate Mem
authorAngela Stegmaier <angelabaker@ti.com>
Fri, 23 Aug 2013 16:45:21 +0000 (11:45 -0500)
committerChris Ring <cring@ti.com>
Thu, 3 Oct 2013 03:18:47 +0000 (20:18 -0700)
The QNX IPC dynamically allocates memory for the remote
core sections based on the resource table.  These sections
are allocated using an mmap call and can be quite large.
There is a performance improvement if the allocated
memory is not zero-initialized during allocation with
mmap. It may be desireable to trade off zero-initialization
of the memory for the performance improvement, so to
enable the memory to not be zero-initialized, the MAP_NOINIT
flag is added to the flags in the mmap call.

It is important to note that the MAP_NOINIT flag will only
relax the zero-init requirement if the memory being mapped
was previously freed using UNMAP_INIT_OPTIONAL. This is
considered set for any memory that hasn't been allocated before,
so can help with boot-up time. Also, The default behavior of munmap
is to not have this flag set. However, if the "-m~i" option is
used on the procnto command line, the default behavior of
munmap is changed to act like UNMAP_INIT_OPTIONAL is set.

So, this change will only gurantee the zero-init to be relaxed if the
additional change is made to use the "-m~i" option.

To be safe, this patch also explicitly zero-initializes the
vring memory after allocation, so that even if the zero-init
requirement is relaxed, the vring memory will be zero-ed.

Also, a flag named "ZEROINIT_CHUNKS" is added in the file, and
set to 0 by default. If it is desired to restore the behavior of
zero-initialization of the chunks, this can be set to 1, and
the QNX IPC rebuilt.

Signed-off-by: Angela Stegmaier <angelabaker@ti.com>
qnx/src/ipc3x_dev/ti/syslink/resources/RscTable.c

index af4255c322617b240a33419b66f41037b301a823..90cbf6dfaff7fae02c964eb8c1bd8bd52889de65 100644 (file)
@@ -67,6 +67,13 @@ extern "C" {
  *  Macros and types
  * =============================================================================
  */
+/*
+ * ZEROINIT_CHUNKS - Set to 1 to zero-init chunk allocations for
+ *                   dynamically allocated remote core memory carveout
+ *                   sections. Default is 0 to achieve better startup
+ *                   performance.
+ */
+#define ZEROINIT_CHUNKS 0
 
 #define RSC_TABLE_STRING ".resource_table"
 #define DDR_MEM 0x80000000
@@ -416,7 +423,11 @@ Int Chunk_allocate (RscTable_Object *obj, UInt32 size, UInt32 * pa)
         // first try to allocate contiguous mem
         da = mmap64(NULL, size,
                     PROT_NOCACHE | PROT_READ | PROT_WRITE,
+#if ZEROINIT_CHUNKS
                     MAP_ANON | MAP_PHYS | MAP_SHARED,
+#else
+                    MAP_ANON | MAP_PHYS | MAP_SHARED | MAP_NOINIT,
+#endif
                     NOFD,
                     0);
         if (da == MAP_FAILED) {
@@ -628,6 +639,9 @@ RscTable_process (UInt16 procId, Bool mmuEnabled, UInt32 numCarveouts,
     RscTable_Header * table = NULL;
     UInt i = 0, j = 0;
     UInt dmem_num = 0;
+#if !ZEROINIT_CHUNKS
+    UInt32 vringVA = 0, vringSize = 0;
+#endif
 
     // Find the table for this coreId, if not found, return an error
     if (procId >= MultiProc_MAXPROCESSORS || !RscTable_state.handles[procId]) {
@@ -839,6 +853,22 @@ RscTable_process (UInt16 procId, Bool mmuEnabled, UInt32 numCarveouts,
                 }
 
                 if (!ret) {
+#if !ZEROINIT_CHUNKS
+                    /* Map the phys mem to local */
+                    vringSize = vr_size + vr_bufs_size;
+                    vringVA = (UInt32)mmap_device_io(vringSize, pa);
+                    if (vringVA != MAP_DEVICE_FAILED) {
+                        /* Zero-init the vring */
+                        Memory_set((Ptr)vringVA, 0, vringSize);
+                        munmap_device_io(vringVA, vringSize);
+                    }
+                    else {
+                        GT_0trace(curTrace, GT_4CLASS,
+                                  "RscTable_alloc: "
+                                  "Warning - Unable to zero-init vring mem");
+                    }
+#endif
+
                     obj->vringPa = pa;
                     obj->vringBufsPa = pa + vr_size;
                 }