source: rtems/cpukit/libcsupport/src/malloc_deferred.c @ 67de508

5
Last change on this file since 67de508 was 9d1f3943, checked in by Sebastian Huber <sebastian.huber@…>, on 02/25/16 at 08:02:43

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.

  • Property mode set to 100644
File size: 3.1 KB
Line 
1/**
2 *  @file
3 *
4 *  @brief Malloc Deferred Support
5 *  @ingroup libcsupport
6 */
7
8/*
9 *  Process free requests deferred because they were from ISR
10 *  or other critical section.
11 *
12 *  COPYRIGHT (c) 1989-2007.
13 *  On-Line Applications Research Corporation (OAR).
14 *
15 *  The license and distribution terms for this file may be
16 *  found in the file LICENSE in this distribution or at
17 *  http://www.rtems.org/license/LICENSE.
18 */
19
20#if HAVE_CONFIG_H
21#include "config.h"
22#endif
23
24#ifdef RTEMS_NEWLIB
25#include <stdlib.h>
26
27#include "malloc_p.h"
28
29#include <rtems/chain.h>
30#include <rtems/score/sysstate.h>
31#include <rtems/score/threaddispatch.h>
32
33static RTEMS_CHAIN_DEFINE_EMPTY( _Malloc_GC_list );
34
35RTEMS_INTERRUPT_LOCK_DEFINE( static, _Malloc_GC_lock, "Malloc GC" )
36
37Malloc_System_state _Malloc_System_state( void )
38{
39  System_state_Codes state = _System_state_Get();
40
41  if ( _System_state_Is_up( state ) ) {
42    if ( _Thread_Dispatch_is_enabled() ) {
43      return MALLOC_SYSTEM_STATE_NORMAL;
44    } else {
45      return MALLOC_SYSTEM_STATE_NO_ALLOCATION;
46    }
47  } else if ( _System_state_Is_before_multitasking( state ) ) {
48    return MALLOC_SYSTEM_STATE_NORMAL;
49  } else {
50    return MALLOC_SYSTEM_STATE_NO_PROTECTION;
51  }
52}
53
54static void *_Malloc_Get_deferred_free( void )
55{
56  rtems_interrupt_lock_context lock_context;
57  void *p;
58
59  rtems_interrupt_lock_acquire( &_Malloc_GC_lock, &lock_context );
60  p = rtems_chain_get_unprotected( &_Malloc_GC_list );
61  rtems_interrupt_lock_release( &_Malloc_GC_lock, &lock_context );
62
63  return p;
64}
65
66static void _Malloc_Process_deferred_frees( void )
67{
68  rtems_chain_node *to_be_freed;
69
70  /*
71   *  If some free's have been deferred, then do them now.
72   */
73  while ( ( to_be_freed = _Malloc_Get_deferred_free() ) != NULL ) {
74    free( to_be_freed );
75  }
76}
77
78void *rtems_heap_allocate_aligned_with_boundary(
79  uintptr_t size,
80  uintptr_t alignment,
81  uintptr_t boundary
82)
83{
84  Heap_Control *heap = RTEMS_Malloc_Heap;
85  void *p;
86
87  switch ( _Malloc_System_state() ) {
88    case MALLOC_SYSTEM_STATE_NORMAL:
89      _Malloc_Process_deferred_frees();
90      p = _Protected_heap_Allocate_aligned_with_boundary(
91        heap,
92        size,
93        alignment,
94        boundary
95      );
96      break;
97    case MALLOC_SYSTEM_STATE_NO_PROTECTION:
98      p = _Heap_Allocate_aligned_with_boundary(
99        heap,
100        size,
101        alignment,
102        boundary
103      );
104      break;
105    default:
106      /*
107       *  Do not attempt to allocate memory if not in correct system state.
108       */
109      return NULL;
110  }
111
112  if ( p == NULL && alignment == 0 && boundary == 0 ) {
113    p = (*rtems_malloc_extend_handler)( heap, size );
114  }
115
116  /*
117   *  If the user wants us to dirty the allocated memory, then do it.
118   */
119  if ( p != NULL && rtems_malloc_dirty_helper != NULL )
120    (*rtems_malloc_dirty_helper)( p, size );
121
122  return p;
123}
124
125void _Malloc_Deferred_free( void *p )
126{
127  rtems_interrupt_lock_context lock_context;
128
129  rtems_interrupt_lock_acquire( &_Malloc_GC_lock, &lock_context );
130  rtems_chain_append_unprotected( &_Malloc_GC_list, (rtems_chain_node *) p );
131  rtems_interrupt_lock_release( &_Malloc_GC_lock, &lock_context );
132}
133#endif
Note: See TracBrowser for help on using the repository browser.