mm/shm: Move the vma allocators to separate functions
This will allow changing the underlying backend, i.e. granule allocator, to something more efficient, if this is needed later. Also, it gives easier access to the common SHM book keeping.
This commit is contained in:
parent
458ff380e5
commit
48b9a8d6f4
@ -63,6 +63,12 @@
|
||||
# define shminfo minfo
|
||||
#endif
|
||||
|
||||
/****************************************************************************
|
||||
* Public Type Definitions
|
||||
****************************************************************************/
|
||||
|
||||
struct task_group_s; /* Forward declaration */
|
||||
|
||||
/****************************************************************************
|
||||
* Public Types
|
||||
****************************************************************************/
|
||||
@ -110,7 +116,6 @@ struct group_shm_s
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
struct task_group_s; /* Forward reference */
|
||||
int shm_group_initialize(FAR struct task_group_s *group);
|
||||
|
||||
/****************************************************************************
|
||||
@ -128,8 +133,43 @@ int shm_group_initialize(FAR struct task_group_s *group);
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
struct task_group_s; /* Forward reference */
|
||||
void shm_group_release(FAR struct task_group_s *group);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: shm_alloc
|
||||
*
|
||||
* Description:
|
||||
* Allocate virtual memory region from the shared memory pool.
|
||||
*
|
||||
* Input Parameters:
|
||||
* group - A reference to the group structure to be un-initialized.
|
||||
* vaddr - Virtual start address where the allocation starts, if NULL, will
|
||||
* seek and return an address that satisfies the 'size' parameter
|
||||
* size - Size of the area to allocate
|
||||
*
|
||||
* Returned Value:
|
||||
* Pointer to reserved vaddr, or NULL if out-of-memory
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR void *shm_alloc(FAR struct task_group_s *group, FAR void *vaddr,
|
||||
size_t size);
|
||||
|
||||
/****************************************************************************
|
||||
* Name: shm_free
|
||||
*
|
||||
* Description:
|
||||
* Free a previously allocated virtual memory region back to the shared
|
||||
* memory pool.
|
||||
*
|
||||
* Input Parameters:
|
||||
* group - A reference to the group structure to be un-initialized.
|
||||
* vaddr - Virtual start address where the allocation starts.
|
||||
* size - Size of the allocated area.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void shm_free(FAR struct task_group_s *group, FAR void *vaddr, size_t size);
|
||||
|
||||
#endif /* CONFIG_MM_SHM */
|
||||
#endif /* __INCLUDE_NUTTX_MM_SHM_H */
|
||||
|
@ -21,7 +21,7 @@
|
||||
# Shared memory allocator
|
||||
|
||||
ifeq ($(CONFIG_MM_SHM),y)
|
||||
CSRCS += shm_initialize.c
|
||||
CSRCS += shm_initialize.c shm_alloc.c
|
||||
CSRCS += shmat.c shmctl.c shmdt.c shmget.c
|
||||
|
||||
# Add the shared memory directory to the build
|
||||
|
109
mm/shm/shm_alloc.c
Normal file
109
mm/shm/shm_alloc.c
Normal file
@ -0,0 +1,109 @@
|
||||
/****************************************************************************
|
||||
* mm/shm/shm_alloc.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 <nuttx/config.h>
|
||||
|
||||
#include <assert.h>
|
||||
#include <debug.h>
|
||||
#include <errno.h>
|
||||
|
||||
#include <nuttx/addrenv.h>
|
||||
#include <nuttx/sched.h>
|
||||
#include <nuttx/mm/gran.h>
|
||||
#include <nuttx/pgalloc.h>
|
||||
#include <nuttx/mm/shm.h>
|
||||
|
||||
#include "shm/shm.h"
|
||||
|
||||
#ifdef CONFIG_MM_SHM
|
||||
|
||||
/****************************************************************************
|
||||
* Public Functions
|
||||
****************************************************************************/
|
||||
|
||||
/****************************************************************************
|
||||
* Name: shm_alloc
|
||||
*
|
||||
* Description:
|
||||
* Allocate virtual memory region from the shared memory pool.
|
||||
*
|
||||
* Input Parameters:
|
||||
* group - A reference to the group structure to be un-initialized.
|
||||
* vaddr - Virtual start address where the allocation starts, if NULL, will
|
||||
* seek and return an address that satisfies the 'size' parameter
|
||||
* size - Size of the area to allocate
|
||||
*
|
||||
* Returned Value:
|
||||
* Pointer to reserved vaddr, or NULL if out-of-memory
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
FAR void *shm_alloc(FAR struct task_group_s *group, FAR void *vaddr,
|
||||
size_t size)
|
||||
{
|
||||
FAR void *ret = NULL;
|
||||
|
||||
DEBUGASSERT(group != NULL);
|
||||
|
||||
if (group->tg_shm.gs_handle != NULL)
|
||||
{
|
||||
if (vaddr == NULL)
|
||||
{
|
||||
ret = gran_alloc(group->tg_shm.gs_handle, size);
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = gran_reserve(group->tg_shm.gs_handle, (uintptr_t)vaddr,
|
||||
size);
|
||||
}
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
/****************************************************************************
|
||||
* Name: shm_free
|
||||
*
|
||||
* Description:
|
||||
* Free a previously allocated virtual memory region back to the shared
|
||||
* memory pool.
|
||||
*
|
||||
* Input Parameters:
|
||||
* group - A reference to the group structure to be un-initialized.
|
||||
* vaddr - Virtual start address where the allocation starts.
|
||||
* size - Size of the allocated area.
|
||||
*
|
||||
****************************************************************************/
|
||||
|
||||
void shm_free(FAR struct task_group_s *group, FAR void *vaddr, size_t size)
|
||||
{
|
||||
DEBUGASSERT(group != NULL);
|
||||
|
||||
if (group->tg_shm.gs_handle != NULL)
|
||||
{
|
||||
gran_free(group->tg_shm.gs_handle, vaddr, size);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* CONFIG_MM_SHM */
|
@ -100,7 +100,7 @@ FAR void *shmat(int shmid, FAR const void *shmaddr, int shmflg)
|
||||
FAR struct shm_region_s *region;
|
||||
FAR struct task_group_s *group;
|
||||
FAR struct tcb_s *tcb;
|
||||
uintptr_t vaddr;
|
||||
FAR void *vaddr;
|
||||
unsigned int npages;
|
||||
int ret;
|
||||
|
||||
@ -129,11 +129,10 @@ FAR void *shmat(int shmid, FAR const void *shmaddr, int shmflg)
|
||||
|
||||
/* Set aside a virtual address space to span this physical region */
|
||||
|
||||
vaddr = (uintptr_t)gran_alloc(group->tg_shm.gs_handle,
|
||||
region->sr_ds.shm_segsz);
|
||||
if (vaddr == 0)
|
||||
vaddr = shm_alloc(group, NULL, region->sr_ds.shm_segsz);
|
||||
if (vaddr == NULL)
|
||||
{
|
||||
shmerr("ERROR: gran_alloc() failed\n");
|
||||
shmerr("ERROR: shm_alloc() failed\n");
|
||||
ret = -ENOMEM;
|
||||
goto errout_with_lock;
|
||||
}
|
||||
@ -144,7 +143,7 @@ FAR void *shmat(int shmid, FAR const void *shmaddr, int shmflg)
|
||||
|
||||
/* Attach, i.e, map, on shared memory region to the user virtual address. */
|
||||
|
||||
ret = up_shmat(region->sr_pages, npages, vaddr);
|
||||
ret = up_shmat(region->sr_pages, npages, (uintptr_t)vaddr);
|
||||
if (ret < 0)
|
||||
{
|
||||
shmerr("ERROR: up_shmat() failed\n");
|
||||
@ -156,7 +155,7 @@ FAR void *shmat(int shmid, FAR const void *shmaddr, int shmflg)
|
||||
* detach, we need to get the region table index.
|
||||
*/
|
||||
|
||||
group->tg_shm.gs_vaddr[shmid] = vaddr;
|
||||
group->tg_shm.gs_vaddr[shmid] = (uintptr_t)vaddr;
|
||||
|
||||
/* Increment the count of processes attached to this region */
|
||||
|
||||
@ -173,11 +172,10 @@ FAR void *shmat(int shmid, FAR const void *shmaddr, int shmflg)
|
||||
/* Release our lock on the entry */
|
||||
|
||||
nxmutex_unlock(®ion->sr_lock);
|
||||
return (FAR void *)vaddr;
|
||||
return vaddr;
|
||||
|
||||
errout_with_vaddr:
|
||||
gran_free(group->tg_shm.gs_handle, (FAR void *)vaddr,
|
||||
region->sr_ds.shm_segsz);
|
||||
shm_free(group, vaddr, region->sr_ds.shm_segsz);
|
||||
|
||||
errout_with_lock:
|
||||
nxmutex_unlock(®ion->sr_lock);
|
||||
|
@ -81,7 +81,6 @@ int shmdt(FAR const void *shmaddr)
|
||||
tcb = nxsched_self();
|
||||
DEBUGASSERT(tcb && tcb->group);
|
||||
group = tcb->group;
|
||||
DEBUGASSERT(group->tg_shm.gs_handle != NULL);
|
||||
|
||||
/* Perform the reverse lookup to get the shmid corresponding to this
|
||||
* shmaddr.
|
||||
@ -116,8 +115,7 @@ int shmdt(FAR const void *shmaddr)
|
||||
|
||||
/* Free the virtual address space */
|
||||
|
||||
gran_free(group->tg_shm.gs_handle, (FAR void *)shmaddr,
|
||||
region->sr_ds.shm_segsz);
|
||||
shm_free(group, (FAR void *)shmaddr, region->sr_ds.shm_segsz);
|
||||
|
||||
/* Convert the region size to pages */
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user