diff options
author | Sebastian Huber <sebastian.huber@embedded-brains.de> | 2016-02-25 09:02:43 +0100 |
---|---|---|
committer | Sebastian Huber <sebastian.huber@embedded-brains.de> | 2016-02-25 11:35:54 +0100 |
commit | 9d1f39434585e8d3f8897d95a2bfe1ddccb79aec (patch) | |
tree | 2d3a0868f410cff137871f5ce493df4f27a22b1a /cpukit/libcsupport/src/malloc_deferred.c | |
parent | malloc: Use dedicated lock for deferred frees (diff) | |
download | rtems-9d1f39434585e8d3f8897d95a2bfe1ddccb79aec.tar.bz2 |
malloc: Add _Malloc_System_state()
Replace malloc_is_system_state_OK() with _Malloc_System_state() to allow
early allocations, e.g. in bsp_start(). Here the _Thread_Executing is
NULL, thus an _API_Mutex_Lock() would lead to a NULL pointer access.
Move malloc() support code to general case
rtems_heap_allocate_aligned_with_boundary(). Use
rtems_heap_allocate_aligned_with_boundary() to avoid duplicated code.
Diffstat (limited to 'cpukit/libcsupport/src/malloc_deferred.c')
-rw-r--r-- | cpukit/libcsupport/src/malloc_deferred.c | 68 |
1 files changed, 63 insertions, 5 deletions
diff --git a/cpukit/libcsupport/src/malloc_deferred.c b/cpukit/libcsupport/src/malloc_deferred.c index 395ed64d34..e781a05bd5 100644 --- a/cpukit/libcsupport/src/malloc_deferred.c +++ b/cpukit/libcsupport/src/malloc_deferred.c @@ -34,10 +34,21 @@ static RTEMS_CHAIN_DEFINE_EMPTY( _Malloc_GC_list ); RTEMS_INTERRUPT_LOCK_DEFINE( static, _Malloc_GC_lock, "Malloc GC" ) -bool malloc_is_system_state_OK(void) +Malloc_System_state _Malloc_System_state( void ) { - return !_System_state_Is_up( _System_state_Get() ) - || _Thread_Dispatch_is_enabled(); + System_state_Codes state = _System_state_Get(); + + if ( _System_state_Is_up( state ) ) { + if ( _Thread_Dispatch_is_enabled() ) { + return MALLOC_SYSTEM_STATE_NORMAL; + } else { + return MALLOC_SYSTEM_STATE_NO_ALLOCATION; + } + } else if ( _System_state_Is_before_multitasking( state ) ) { + return MALLOC_SYSTEM_STATE_NORMAL; + } else { + return MALLOC_SYSTEM_STATE_NO_PROTECTION; + } } static void *_Malloc_Get_deferred_free( void ) @@ -52,7 +63,7 @@ static void *_Malloc_Get_deferred_free( void ) return p; } -void malloc_deferred_frees_process( void ) +static void _Malloc_Process_deferred_frees( void ) { rtems_chain_node *to_be_freed; @@ -64,7 +75,54 @@ void malloc_deferred_frees_process( void ) } } -void malloc_deferred_free( void *p ) +void *rtems_heap_allocate_aligned_with_boundary( + uintptr_t size, + uintptr_t alignment, + uintptr_t boundary +) +{ + Heap_Control *heap = RTEMS_Malloc_Heap; + void *p; + + switch ( _Malloc_System_state() ) { + case MALLOC_SYSTEM_STATE_NORMAL: + _Malloc_Process_deferred_frees(); + p = _Protected_heap_Allocate_aligned_with_boundary( + heap, + size, + alignment, + boundary + ); + break; + case MALLOC_SYSTEM_STATE_NO_PROTECTION: + p = _Heap_Allocate_aligned_with_boundary( + heap, + size, + alignment, + boundary + ); + break; + default: + /* + * Do not attempt to allocate memory if not in correct system state. + */ + return NULL; + } + + if ( p == NULL && alignment == 0 && boundary == 0 ) { + p = (*rtems_malloc_extend_handler)( heap, size ); + } + + /* + * If the user wants us to dirty the allocated memory, then do it. + */ + if ( p != NULL && rtems_malloc_dirty_helper != NULL ) + (*rtems_malloc_dirty_helper)( p, size ); + + return p; +} + +void _Malloc_Deferred_free( void *p ) { rtems_interrupt_lock_context lock_context; |