From e6f7f81766efeb713b3e0a6fa67122f3f1cf9895 Mon Sep 17 00:00:00 2001 From: Sebastian Huber Date: Tue, 23 Jul 2013 16:50:51 +0200 Subject: score: Create heap implementation header Move implementation specific parts of heap.h and heap.inl into new header file heapimpl.h. The heap.h contains now only the application visible API. --- cpukit/rtems/include/rtems/rtems/regionimpl.h | 1 + cpukit/rtems/src/workspacegreedy.c | 1 + cpukit/score/Makefile.am | 2 +- cpukit/score/include/rtems/score/heap.h | 375 +------------- cpukit/score/include/rtems/score/heapimpl.h | 608 +++++++++++++++++++++++ cpukit/score/include/rtems/score/protectedheap.h | 2 +- cpukit/score/inline/rtems/score/heap.inl | 238 --------- cpukit/score/preinstall.am | 8 +- cpukit/score/src/heap.c | 9 +- cpukit/score/src/heapallocate.c | 2 +- cpukit/score/src/heapextend.c | 2 +- cpukit/score/src/heapfree.c | 2 +- cpukit/score/src/heapgetfreeinfo.c | 2 +- cpukit/score/src/heapgetinfo.c | 2 +- cpukit/score/src/heapgreedy.c | 2 +- cpukit/score/src/heapiterate.c | 2 +- cpukit/score/src/heapnoextend.c | 2 +- cpukit/score/src/heapresizeblock.c | 2 +- cpukit/score/src/heapsizeofuserarea.c | 2 +- cpukit/score/src/heapwalk.c | 2 +- cpukit/score/src/wkspace.c | 6 +- testsuites/libtests/heapwalk/init.c | 3 +- testsuites/sptests/sp63/init.c | 2 + testsuites/sptests/spheapprot/init.c | 6 +- testsuites/sptests/spstkalloc02/init.c | 2 +- 25 files changed, 643 insertions(+), 642 deletions(-) create mode 100644 cpukit/score/include/rtems/score/heapimpl.h delete mode 100644 cpukit/score/inline/rtems/score/heap.inl diff --git a/cpukit/rtems/include/rtems/rtems/regionimpl.h b/cpukit/rtems/include/rtems/rtems/regionimpl.h index ad2cacb5f2..6b900f22ed 100644 --- a/cpukit/rtems/include/rtems/rtems/regionimpl.h +++ b/cpukit/rtems/include/rtems/rtems/regionimpl.h @@ -18,6 +18,7 @@ #define _RTEMS_RTEMS_REGIONIMPL_H #include +#include #include #ifdef __cplusplus diff --git a/cpukit/rtems/src/workspacegreedy.c b/cpukit/rtems/src/workspacegreedy.c index 4f46e7d919..c0a0256b52 100644 --- a/cpukit/rtems/src/workspacegreedy.c +++ b/cpukit/rtems/src/workspacegreedy.c @@ -25,6 +25,7 @@ #include #include +#include void *rtems_workspace_greedy_allocate( const uintptr_t *block_sizes, diff --git a/cpukit/score/Makefile.am b/cpukit/score/Makefile.am index d174c37056..4b0e15dd99 100644 --- a/cpukit/score/Makefile.am +++ b/cpukit/score/Makefile.am @@ -31,6 +31,7 @@ include_rtems_score_HEADERS += include/rtems/score/coremuteximpl.h include_rtems_score_HEADERS += include/rtems/score/coresem.h include_rtems_score_HEADERS += include/rtems/score/coresemimpl.h include_rtems_score_HEADERS += include/rtems/score/heap.h +include_rtems_score_HEADERS += include/rtems/score/heapimpl.h include_rtems_score_HEADERS += include/rtems/score/protectedheap.h include_rtems_score_HEADERS += include/rtems/score/interr.h include_rtems_score_HEADERS += include/rtems/score/isr.h @@ -92,7 +93,6 @@ include_rtems_score_HEADERS += include/rtems/score/schedulersimplesmp.h endif ## inline -include_rtems_score_HEADERS += inline/rtems/score/heap.inl include_rtems_score_HEADERS += inline/rtems/score/object.inl include_rtems_score_HEADERS += inline/rtems/score/priority.inl include_rtems_score_HEADERS += inline/rtems/score/prioritybitmap.inl diff --git a/cpukit/score/include/rtems/score/heap.h b/cpukit/score/include/rtems/score/heap.h index bea9f3ec25..5a6b3a1a00 100644 --- a/cpukit/score/include/rtems/score/heap.h +++ b/cpukit/score/include/rtems/score/heap.h @@ -18,8 +18,7 @@ #ifndef _RTEMS_SCORE_HEAP_H #define _RTEMS_SCORE_HEAP_H -#include -#include +#include #ifdef __cplusplus extern "C" { @@ -136,6 +135,8 @@ typedef struct Heap_Block Heap_Block; #ifndef HEAP_PROTECTION #define HEAP_PROTECTION_HEADER_SIZE 0 #else + #include + #define HEAP_PROTECTOR_COUNT 2 #define HEAP_BEGIN_PROTECTOR_0 ((uintptr_t) 0xfd75a98f) @@ -177,17 +178,6 @@ typedef struct Heap_Block Heap_Block; (sizeof(Heap_Protection_block_begin) + sizeof(Heap_Protection_block_end)) #endif -/** - * @brief See also @ref Heap_Block.size_and_flag. - */ -#define HEAP_PREV_BLOCK_USED ((uintptr_t) 1) - -/** - * @brief Size of the part at the block begin which may be used for allocation - * in charge of the previous block. - */ -#define HEAP_ALLOC_BONUS sizeof(uintptr_t) - /** * @brief The block header consists of the two size fields * (@ref Heap_Block.prev_size and @ref Heap_Block.size_and_flag). @@ -377,15 +367,6 @@ typedef struct { Heap_Information Used; } Heap_Information_block; -/** - * @brief See _Heap_Resize_block(). - */ -typedef enum { - HEAP_RESIZE_SUCCESSFUL, - HEAP_RESIZE_UNSATISFIED, - HEAP_RESIZE_FATAL_ERROR -} Heap_Resize_status; - /** * @brief Heap area structure for table based heap initialization and * extension. @@ -413,48 +394,6 @@ typedef uintptr_t (*Heap_Initialization_or_extend_handler)( uintptr_t page_size_or_unused ); -/** - * @brief Gets the first and last block for the heap area with begin - * @a heap_area_begin and size @a heap_area_size. - * - * A page size of @a page_size and minimal block size of @a min_block_size will - * be used for calculation. - * - * Nothing will be written to this area. - * - * In case of success the pointers to the first and last block will be returned - * via @a first_block_ptr and @a last_block_ptr. - * - * Returns @c true if the area is big enough, and @c false otherwise. - */ -bool _Heap_Get_first_and_last_block( - uintptr_t heap_area_begin, - uintptr_t heap_area_size, - uintptr_t page_size, - uintptr_t min_block_size, - Heap_Block **first_block_ptr, - Heap_Block **last_block_ptr -); - -/** - * @brief Initializes the heap control block @a heap to manage the area - * starting at @a area_begin of size @a area_size bytes. - * - * Blocks of memory are allocated from the heap in multiples of @a page_size - * byte units. If the @a page_size is equal to zero or is not multiple of - * @c CPU_ALIGNMENT, it is aligned up to the nearest @c CPU_ALIGNMENT boundary. - * - * Returns the maximum memory available, or zero in case of failure. - * - * @see Heap_Initialization_or_extend_handler. - */ -uintptr_t _Heap_Initialize( - Heap_Control *heap, - void *area_begin, - uintptr_t area_size, - uintptr_t page_size -); - /** * @brief Extends the memory available for the heap @a heap using the memory * area starting at @a area_begin of size @a area_size bytes. @@ -495,316 +434,8 @@ uintptr_t _Heap_No_extend( uintptr_t unused_3 ); -/** - * @brief Allocates a memory area of size @a size bytes from the heap @a heap. - * - * If the alignment parameter @a alignment is not equal to zero, the allocated - * memory area will begin at an address aligned by this value. - * - * If the boundary parameter @a boundary is not equal to zero, the allocated - * memory area will fulfill a boundary constraint. The boundary value - * specifies the set of addresses which are aligned by the boundary value. The - * interior of the allocated memory area will not contain an element of this - * set. The begin or end address of the area may be a member of the set. - * - * A size value of zero will return a unique address which may be freed with - * _Heap_Free(). - * - * Returns a pointer to the begin of the allocated memory area, or @c NULL if - * no memory is available or the parameters are inconsistent. - */ -void *_Heap_Allocate_aligned_with_boundary( - Heap_Control *heap, - uintptr_t size, - uintptr_t alignment, - uintptr_t boundary -); - -/** - * @brief See _Heap_Allocate_aligned_with_boundary() with boundary equals zero. - */ -RTEMS_INLINE_ROUTINE void *_Heap_Allocate_aligned( - Heap_Control *heap, - uintptr_t size, - uintptr_t alignment -) -{ - return _Heap_Allocate_aligned_with_boundary( heap, size, alignment, 0 ); -} - -/** - * @brief See _Heap_Allocate_aligned_with_boundary() with alignment and - * boundary equals zero. - */ -RTEMS_INLINE_ROUTINE void *_Heap_Allocate( Heap_Control *heap, uintptr_t size ) -{ - return _Heap_Allocate_aligned_with_boundary( heap, size, 0, 0 ); -} - -/** - * @brief Frees the allocated memory area starting at @a addr in the heap - * @a heap. - * - * Inappropriate values for @a addr may corrupt the heap. - * - * Returns @c true in case of success, and @c false otherwise. - */ -bool _Heap_Free( Heap_Control *heap, void *addr ); - -/** - * @brief Walks the heap @a heap to verify its integrity. - * - * If @a dump is @c true, then diagnostic messages will be printed to standard - * output. In this case @a source is used to mark the output lines. - * - * Returns @c true if no errors occurred, and @c false if the heap is corrupt. - */ -bool _Heap_Walk( - Heap_Control *heap, - int source, - bool dump -); - -/** - * @brief Heap block visitor. - * - * @see _Heap_Iterate(). - * - * @retval true Stop the iteration. - * @retval false Continue the iteration. - */ -typedef bool (*Heap_Block_visitor)( - const Heap_Block *block, - uintptr_t block_size, - bool block_is_used, - void *visitor_arg -); - -/** - * @brief Iterates over all blocks of the heap. - * - * For each block the @a visitor with the argument @a visitor_arg will be - * called. - */ -void _Heap_Iterate( - Heap_Control *heap, - Heap_Block_visitor visitor, - void *visitor_arg -); - -/** - * @brief Greedy allocate that empties the heap. - * - * Afterwards the heap has at most @a block_count allocatable blocks of sizes - * specified by @a block_sizes. The @a block_sizes must point to an array with - * @a block_count members. All other blocks are used. - * - * @see _Heap_Greedy_free(). - */ -Heap_Block *_Heap_Greedy_allocate( - Heap_Control *heap, - const uintptr_t *block_sizes, - size_t block_count -); - -/** - * @brief Greedy allocate all blocks except the largest free block. - * - * Afterwards the heap has at most one allocatable block. This block is the - * largest free block if it exists. The allocatable size of this block is - * stored in @a allocatable_size. All other blocks are used. - * - * @see _Heap_Greedy_free(). - */ -Heap_Block *_Heap_Greedy_allocate_all_except_largest( - Heap_Control *heap, - uintptr_t *allocatable_size -); - -/** - * @brief Frees blocks of a greedy allocation. - * - * The @a blocks must be the return value of _Heap_Greedy_allocate(). - */ -void _Heap_Greedy_free( - Heap_Control *heap, - Heap_Block *blocks -); - -/** - * @brief Returns information about used and free blocks for the heap @a heap - * in @a info. - */ -void _Heap_Get_information( - Heap_Control *heap, - Heap_Information_block *info -); - -/** - * @brief Returns information about free blocks for the heap @a heap in - * @a info. - */ -void _Heap_Get_free_information( - Heap_Control *heap, - Heap_Information *info -); - -/** - * @brief Returns the size of the allocatable memory area starting at @a addr - * in @a size. - * - * The size value may be greater than the initially requested size in - * _Heap_Allocate_aligned_with_boundary(). - * - * Inappropriate values for @a addr will not corrupt the heap, but may yield - * invalid size values. - * - * Returns @a true if successful, and @c false otherwise. - */ -bool _Heap_Size_of_alloc_area( - Heap_Control *heap, - void *addr, - uintptr_t *size -); - -/** - * @brief Resizes the block of the allocated memory area starting at @a addr. - * - * The new memory area will have a size of at least @a size bytes. A resize - * may be impossible and depends on the current heap usage. - * - * The size available for allocation in the current block before the resize - * will be returned in @a old_size. The size available for allocation in - * the resized block will be returned in @a new_size. If the resize was not - * successful, then a value of zero will be returned in @a new_size. - * - * Inappropriate values for @a addr may corrupt the heap. - */ -Heap_Resize_status _Heap_Resize_block( - Heap_Control *heap, - void *addr, - uintptr_t size, - uintptr_t *old_size, - uintptr_t *new_size -); - -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Align_up( - uintptr_t value, - uintptr_t alignment -) -{ - uintptr_t remainder = value % alignment; - - if ( remainder != 0 ) { - return value - remainder + alignment; - } else { - return value; - } -} - -/** - * @brief Returns the worst case overhead to manage a memory area. - */ -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Area_overhead( - uintptr_t page_size -) -{ - if ( page_size != 0 ) { - page_size = _Heap_Align_up( page_size, CPU_ALIGNMENT ); - } else { - page_size = CPU_ALIGNMENT; - } - - return 2 * (page_size - 1) + HEAP_BLOCK_HEADER_SIZE; -} - -#if !defined(__RTEMS_APPLICATION__) - -#include - -/** - * @brief Allocates the memory area starting at @a alloc_begin of size - * @a alloc_size bytes in the block @a block. - * - * The block may be split up into multiple blocks. The previous and next block - * may be used or free. Free block parts which form a vaild new block will be - * inserted into the free list or merged with an adjacent free block. If the - * block is used, they will be inserted after the free list head. If the block - * is free, they will be inserted after the previous block in the free list. - * - * Inappropriate values for @a alloc_begin or @a alloc_size may corrupt the - * heap. - * - * Returns the block containing the allocated memory area. - */ -Heap_Block *_Heap_Block_allocate( - Heap_Control *heap, - Heap_Block *block, - uintptr_t alloc_begin, - uintptr_t alloc_size -); - -#ifndef HEAP_PROTECTION - #define _Heap_Protection_block_initialize( heap, block ) ((void) 0) - #define _Heap_Protection_block_check( heap, block ) ((void) 0) - #define _Heap_Protection_block_error( heap, block ) ((void) 0) - #define _Heap_Protection_free_all_delayed_blocks( heap ) ((void) 0) -#else - static inline void _Heap_Protection_block_initialize( - Heap_Control *heap, - Heap_Block *block - ) - { - (*heap->Protection.block_initialize)( heap, block ); - } - - static inline void _Heap_Protection_block_check( - Heap_Control *heap, - Heap_Block *block - ) - { - (*heap->Protection.block_check)( heap, block ); - } - - static inline void _Heap_Protection_block_error( - Heap_Control *heap, - Heap_Block *block - ) - { - (*heap->Protection.block_error)( heap, block ); - } - - static inline void _Heap_Protection_free_all_delayed_blocks( Heap_Control *heap ) - { - uintptr_t large = 0 - - (uintptr_t) HEAP_BLOCK_HEADER_SIZE - - (uintptr_t) HEAP_ALLOC_BONUS - - (uintptr_t) 1; - void *p = _Heap_Allocate( heap, large ); - _Heap_Free( heap, p ); - } -#endif - /** @} */ -#ifdef RTEMS_DEBUG - #define RTEMS_HEAP_DEBUG -#endif - -#ifdef RTEMS_HEAP_DEBUG - #include - #define _HAssert( cond ) \ - do { \ - if ( !(cond) ) { \ - __assert( __FILE__, __LINE__, #cond ); \ - } \ - } while (0) -#else - #define _HAssert( cond ) ((void) 0) -#endif - -#endif /* !defined(__RTEMS_APPLICATION__) */ - #ifdef __cplusplus } #endif diff --git a/cpukit/score/include/rtems/score/heapimpl.h b/cpukit/score/include/rtems/score/heapimpl.h new file mode 100644 index 0000000000..27c3a2334a --- /dev/null +++ b/cpukit/score/include/rtems/score/heapimpl.h @@ -0,0 +1,608 @@ +/** + * @file + * + * @ingroup ScoreHeap + * + * @brief Heap Handler Implementation + */ + +/* + * COPYRIGHT (c) 1989-2008. + * On-Line Applications Research Corporation (OAR). + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.com/license/LICENSE. + */ + +#ifndef _RTEMS_SCORE_HEAPIMPL_H +#define _RTEMS_SCORE_HEAPIMPL_H + +#include + +#ifdef __cplusplus +extern "C" { +#endif + +/** + * @addtogroup ScoreHeap + */ +/**@{**/ + +/** + * @brief See also @ref Heap_Block.size_and_flag. + */ +#define HEAP_PREV_BLOCK_USED ((uintptr_t) 1) + +/** + * @brief Size of the part at the block begin which may be used for allocation + * in charge of the previous block. + */ +#define HEAP_ALLOC_BONUS sizeof(uintptr_t) + +/** + * @brief See _Heap_Resize_block(). + */ +typedef enum { + HEAP_RESIZE_SUCCESSFUL, + HEAP_RESIZE_UNSATISFIED, + HEAP_RESIZE_FATAL_ERROR +} Heap_Resize_status; + +/** + * @brief Gets the first and last block for the heap area with begin + * @a heap_area_begin and size @a heap_area_size. + * + * A page size of @a page_size and minimal block size of @a min_block_size will + * be used for calculation. + * + * Nothing will be written to this area. + * + * In case of success the pointers to the first and last block will be returned + * via @a first_block_ptr and @a last_block_ptr. + * + * Returns @c true if the area is big enough, and @c false otherwise. + */ +bool _Heap_Get_first_and_last_block( + uintptr_t heap_area_begin, + uintptr_t heap_area_size, + uintptr_t page_size, + uintptr_t min_block_size, + Heap_Block **first_block_ptr, + Heap_Block **last_block_ptr +); + +/** + * @brief Initializes the heap control block @a heap to manage the area + * starting at @a area_begin of size @a area_size bytes. + * + * Blocks of memory are allocated from the heap in multiples of @a page_size + * byte units. If the @a page_size is equal to zero or is not multiple of + * @c CPU_ALIGNMENT, it is aligned up to the nearest @c CPU_ALIGNMENT boundary. + * + * Returns the maximum memory available, or zero in case of failure. + * + * @see Heap_Initialization_or_extend_handler. + */ +uintptr_t _Heap_Initialize( + Heap_Control *heap, + void *area_begin, + uintptr_t area_size, + uintptr_t page_size +); + +/** + * @brief Allocates a memory area of size @a size bytes from the heap @a heap. + * + * If the alignment parameter @a alignment is not equal to zero, the allocated + * memory area will begin at an address aligned by this value. + * + * If the boundary parameter @a boundary is not equal to zero, the allocated + * memory area will fulfill a boundary constraint. The boundary value + * specifies the set of addresses which are aligned by the boundary value. The + * interior of the allocated memory area will not contain an element of this + * set. The begin or end address of the area may be a member of the set. + * + * A size value of zero will return a unique address which may be freed with + * _Heap_Free(). + * + * Returns a pointer to the begin of the allocated memory area, or @c NULL if + * no memory is available or the parameters are inconsistent. + */ +void *_Heap_Allocate_aligned_with_boundary( + Heap_Control *heap, + uintptr_t size, + uintptr_t alignment, + uintptr_t boundary +); + +/** + * @brief See _Heap_Allocate_aligned_with_boundary() with boundary equals zero. + */ +RTEMS_INLINE_ROUTINE void *_Heap_Allocate_aligned( + Heap_Control *heap, + uintptr_t size, + uintptr_t alignment +) +{ + return _Heap_Allocate_aligned_with_boundary( heap, size, alignment, 0 ); +} + +/** + * @brief See _Heap_Allocate_aligned_with_boundary() with alignment and + * boundary equals zero. + */ +RTEMS_INLINE_ROUTINE void *_Heap_Allocate( Heap_Control *heap, uintptr_t size ) +{ + return _Heap_Allocate_aligned_with_boundary( heap, size, 0, 0 ); +} + +/** + * @brief Frees the allocated memory area starting at @a addr in the heap + * @a heap. + * + * Inappropriate values for @a addr may corrupt the heap. + * + * Returns @c true in case of success, and @c false otherwise. + */ +bool _Heap_Free( Heap_Control *heap, void *addr ); + +/** + * @brief Walks the heap @a heap to verify its integrity. + * + * If @a dump is @c true, then diagnostic messages will be printed to standard + * output. In this case @a source is used to mark the output lines. + * + * Returns @c true if no errors occurred, and @c false if the heap is corrupt. + */ +bool _Heap_Walk( + Heap_Control *heap, + int source, + bool dump +); + +/** + * @brief Heap block visitor. + * + * @see _Heap_Iterate(). + * + * @retval true Stop the iteration. + * @retval false Continue the iteration. + */ +typedef bool (*Heap_Block_visitor)( + const Heap_Block *block, + uintptr_t block_size, + bool block_is_used, + void *visitor_arg +); + +/** + * @brief Iterates over all blocks of the heap. + * + * For each block the @a visitor with the argument @a visitor_arg will be + * called. + */ +void _Heap_Iterate( + Heap_Control *heap, + Heap_Block_visitor visitor, + void *visitor_arg +); + +/** + * @brief Greedy allocate that empties the heap. + * + * Afterwards the heap has at most @a block_count allocatable blocks of sizes + * specified by @a block_sizes. The @a block_sizes must point to an array with + * @a block_count members. All other blocks are used. + * + * @see _Heap_Greedy_free(). + */ +Heap_Block *_Heap_Greedy_allocate( + Heap_Control *heap, + const uintptr_t *block_sizes, + size_t block_count +); + +/** + * @brief Greedy allocate all blocks except the largest free block. + * + * Afterwards the heap has at most one allocatable block. This block is the + * largest free block if it exists. The allocatable size of this block is + * stored in @a allocatable_size. All other blocks are used. + * + * @see _Heap_Greedy_free(). + */ +Heap_Block *_Heap_Greedy_allocate_all_except_largest( + Heap_Control *heap, + uintptr_t *allocatable_size +); + +/** + * @brief Frees blocks of a greedy allocation. + * + * The @a blocks must be the return value of _Heap_Greedy_allocate(). + */ +void _Heap_Greedy_free( + Heap_Control *heap, + Heap_Block *blocks +); + +/** + * @brief Returns information about used and free blocks for the heap @a heap + * in @a info. + */ +void _Heap_Get_information( + Heap_Control *heap, + Heap_Information_block *info +); + +/** + * @brief Returns information about free blocks for the heap @a heap in + * @a info. + */ +void _Heap_Get_free_information( + Heap_Control *heap, + Heap_Information *info +); + +/** + * @brief Returns the size of the allocatable memory area starting at @a addr + * in @a size. + * + * The size value may be greater than the initially requested size in + * _Heap_Allocate_aligned_with_boundary(). + * + * Inappropriate values for @a addr will not corrupt the heap, but may yield + * invalid size values. + * + * Returns @a true if successful, and @c false otherwise. + */ +bool _Heap_Size_of_alloc_area( + Heap_Control *heap, + void *addr, + uintptr_t *size +); + +/** + * @brief Resizes the block of the allocated memory area starting at @a addr. + * + * The new memory area will have a size of at least @a size bytes. A resize + * may be impossible and depends on the current heap usage. + * + * The size available for allocation in the current block before the resize + * will be returned in @a old_size. The size available for allocation in + * the resized block will be returned in @a new_size. If the resize was not + * successful, then a value of zero will be returned in @a new_size. + * + * Inappropriate values for @a addr may corrupt the heap. + */ +Heap_Resize_status _Heap_Resize_block( + Heap_Control *heap, + void *addr, + uintptr_t size, + uintptr_t *old_size, + uintptr_t *new_size +); + +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Align_up( + uintptr_t value, + uintptr_t alignment +) +{ + uintptr_t remainder = value % alignment; + + if ( remainder != 0 ) { + return value - remainder + alignment; + } else { + return value; + } +} + +/** + * @brief Returns the worst case overhead to manage a memory area. + */ +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Area_overhead( + uintptr_t page_size +) +{ + if ( page_size != 0 ) { + page_size = _Heap_Align_up( page_size, CPU_ALIGNMENT ); + } else { + page_size = CPU_ALIGNMENT; + } + + return 2 * (page_size - 1) + HEAP_BLOCK_HEADER_SIZE; +} + +/** + * @brief Allocates the memory area starting at @a alloc_begin of size + * @a alloc_size bytes in the block @a block. + * + * The block may be split up into multiple blocks. The previous and next block + * may be used or free. Free block parts which form a vaild new block will be + * inserted into the free list or merged with an adjacent free block. If the + * block is used, they will be inserted after the free list head. If the block + * is free, they will be inserted after the previous block in the free list. + * + * Inappropriate values for @a alloc_begin or @a alloc_size may corrupt the + * heap. + * + * Returns the block containing the allocated memory area. + */ +Heap_Block *_Heap_Block_allocate( + Heap_Control *heap, + Heap_Block *block, + uintptr_t alloc_begin, + uintptr_t alloc_size +); + +#ifndef HEAP_PROTECTION + #define _Heap_Protection_block_initialize( heap, block ) ((void) 0) + #define _Heap_Protection_block_check( heap, block ) ((void) 0) + #define _Heap_Protection_block_error( heap, block ) ((void) 0) + #define _Heap_Protection_free_all_delayed_blocks( heap ) ((void) 0) +#else + static inline void _Heap_Protection_block_initialize( + Heap_Control *heap, + Heap_Block *block + ) + { + (*heap->Protection.block_initialize)( heap, block ); + } + + static inline void _Heap_Protection_block_check( + Heap_Control *heap, + Heap_Block *block + ) + { + (*heap->Protection.block_check)( heap, block ); + } + + static inline void _Heap_Protection_block_error( + Heap_Control *heap, + Heap_Block *block + ) + { + (*heap->Protection.block_error)( heap, block ); + } + + static inline void _Heap_Protection_free_all_delayed_blocks( Heap_Control *heap ) + { + uintptr_t large = 0 + - (uintptr_t) HEAP_BLOCK_HEADER_SIZE + - (uintptr_t) HEAP_ALLOC_BONUS + - (uintptr_t) 1; + void *p = _Heap_Allocate( heap, large ); + _Heap_Free( heap, p ); + } +#endif + +RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_head( Heap_Control *heap ) +{ + return &heap->free_list; +} + +RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_tail( Heap_Control *heap ) +{ + return &heap->free_list; +} + +RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_first( Heap_Control *heap ) +{ + return _Heap_Free_list_head(heap)->next; +} + +RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_last( Heap_Control *heap ) +{ + return _Heap_Free_list_tail(heap)->prev; +} + +RTEMS_INLINE_ROUTINE void _Heap_Free_list_remove( Heap_Block *block ) +{ + Heap_Block *next = block->next; + Heap_Block *prev = block->prev; + + prev->next = next; + next->prev = prev; +} + +RTEMS_INLINE_ROUTINE void _Heap_Free_list_replace( + Heap_Block *old_block, + Heap_Block *new_block +) +{ + Heap_Block *next = old_block->next; + Heap_Block *prev = old_block->prev; + + new_block->next = next; + new_block->prev = prev; + + next->prev = new_block; + prev->next = new_block; +} + +RTEMS_INLINE_ROUTINE void _Heap_Free_list_insert_after( + Heap_Block *block_before, + Heap_Block *new_block +) +{ + Heap_Block *next = block_before->next; + + new_block->next = next; + new_block->prev = block_before; + block_before->next = new_block; + next->prev = new_block; +} + +RTEMS_INLINE_ROUTINE void _Heap_Free_list_insert_before( + Heap_Block *block_next, + Heap_Block *new_block +) +{ + Heap_Block *prev = block_next->prev; + + new_block->next = block_next; + new_block->prev = prev; + prev->next = new_block; + block_next->prev = new_block; +} + +RTEMS_INLINE_ROUTINE bool _Heap_Is_aligned( + uintptr_t value, + uintptr_t alignment +) +{ + return (value % alignment) == 0; +} + +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Align_down( + uintptr_t value, + uintptr_t alignment +) +{ + return value - (value % alignment); +} + +/** + * @brief Returns the block which is @a offset away from @a block. + */ +RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Block_at( + const Heap_Block *block, + uintptr_t offset +) +{ + return (Heap_Block *) ((uintptr_t) block + offset); +} + +RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Prev_block( + const Heap_Block *block +) +{ + return (Heap_Block *) ((uintptr_t) block - block->prev_size); +} + +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Alloc_area_of_block( + const Heap_Block *block +) +{ + return (uintptr_t) block + HEAP_BLOCK_HEADER_SIZE; +} + +RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Block_of_alloc_area( + uintptr_t alloc_begin, + uintptr_t page_size +) +{ + return (Heap_Block *) (_Heap_Align_down( alloc_begin, page_size ) + - HEAP_BLOCK_HEADER_SIZE); +} + +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Block_size( const Heap_Block *block ) +{ + return block->size_and_flag & ~HEAP_PREV_BLOCK_USED; +} + +RTEMS_INLINE_ROUTINE void _Heap_Block_set_size( + Heap_Block *block, + uintptr_t size +) +{ + uintptr_t flag = block->size_and_flag & HEAP_PREV_BLOCK_USED; + + block->size_and_flag = size | flag; +} + +RTEMS_INLINE_ROUTINE bool _Heap_Is_prev_used( const Heap_Block *block ) +{ + return block->size_and_flag & HEAP_PREV_BLOCK_USED; +} + +RTEMS_INLINE_ROUTINE bool _Heap_Is_used( + const Heap_Block *block +) +{ + const Heap_Block *const next_block = + _Heap_Block_at( block, _Heap_Block_size( block ) ); + + return _Heap_Is_prev_used( next_block ); +} + +RTEMS_INLINE_ROUTINE bool _Heap_Is_free( + const Heap_Block *block +) +{ + return !_Heap_Is_used( block ); +} + +RTEMS_INLINE_ROUTINE bool _Heap_Is_block_in_heap( + const Heap_Control *heap, + const Heap_Block *block +) +{ + return (uintptr_t) block >= (uintptr_t) heap->first_block + && (uintptr_t) block <= (uintptr_t) heap->last_block; +} + +/** + * @brief Sets the size of the last block for heap @a heap. + * + * The next block of the last block will be the first block. Since the first + * block indicates that the previous block is used, this ensures that the last + * block appears as used for the _Heap_Is_used() and _Heap_Is_free() + * functions. + * + * This feature will be used to terminate the scattered heap area list. See + * also _Heap_Extend(). + */ +RTEMS_INLINE_ROUTINE void _Heap_Set_last_block_size( Heap_Control *heap ) +{ + _Heap_Block_set_size( + heap->last_block, + (uintptr_t) heap->first_block - (uintptr_t) heap->last_block + ); +} + +/** + * @brief Returns the size of the allocatable area in bytes. + * + * This value is an integral multiple of the page size. + */ +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Get_size( const Heap_Control *heap ) +{ + return heap->stats.size; +} + +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Max( uintptr_t a, uintptr_t b ) +{ + return a > b ? a : b; +} + +RTEMS_INLINE_ROUTINE uintptr_t _Heap_Min( uintptr_t a, uintptr_t b ) +{ + return a < b ? a : b; +} + +#ifdef RTEMS_DEBUG + #define RTEMS_HEAP_DEBUG +#endif + +#ifdef RTEMS_HEAP_DEBUG + #include + #define _HAssert( cond ) \ + do { \ + if ( !(cond) ) { \ + __assert( __FILE__, __LINE__, #cond ); \ + } \ + } while (0) +#else + #define _HAssert( cond ) ((void) 0) +#endif + +/** @} */ + +#ifdef __cplusplus +} +#endif + +#endif +/* end of include file */ diff --git a/cpukit/score/include/rtems/score/protectedheap.h b/cpukit/score/include/rtems/score/protectedheap.h index 29ee62dbfb..1cfef21efb 100644 --- a/cpukit/score/include/rtems/score/protectedheap.h +++ b/cpukit/score/include/rtems/score/protectedheap.h @@ -18,7 +18,7 @@ #ifndef _RTEMS_SCORE_PROTECTED_HEAP_H #define _RTEMS_SCORE_PROTECTED_HEAP_H -#include +#include #include #ifdef __cplusplus diff --git a/cpukit/score/inline/rtems/score/heap.inl b/cpukit/score/inline/rtems/score/heap.inl deleted file mode 100644 index 4a346bdf21..0000000000 --- a/cpukit/score/inline/rtems/score/heap.inl +++ /dev/null @@ -1,238 +0,0 @@ -/** - * @file - * - * @brief Heap Handler API - */ - -/* - * COPYRIGHT (c) 1989-2008. - * On-Line Applications Research Corporation (OAR). - * - * The license and distribution terms for this file may be - * found in the file LICENSE in this distribution or at - * http://www.rtems.com/license/LICENSE. - */ - -#ifndef _RTEMS_SCORE_HEAP_H -# error "Never use directly; include instead." -#endif - -#ifndef _RTEMS_SCORE_HEAP_INL -#define _RTEMS_SCORE_HEAP_INL - -#include - -/** - * @addtogroup ScoreHeap - */ -/**@{**/ - -RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_head( Heap_Control *heap ) -{ - return &heap->free_list; -} - -RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_tail( Heap_Control *heap ) -{ - return &heap->free_list; -} - -RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_first( Heap_Control *heap ) -{ - return _Heap_Free_list_head(heap)->next; -} - -RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Free_list_last( Heap_Control *heap ) -{ - return _Heap_Free_list_tail(heap)->prev; -} - -RTEMS_INLINE_ROUTINE void _Heap_Free_list_remove( Heap_Block *block ) -{ - Heap_Block *next = block->next; - Heap_Block *prev = block->prev; - - prev->next = next; - next->prev = prev; -} - -RTEMS_INLINE_ROUTINE void _Heap_Free_list_replace( - Heap_Block *old_block, - Heap_Block *new_block -) -{ - Heap_Block *next = old_block->next; - Heap_Block *prev = old_block->prev; - - new_block->next = next; - new_block->prev = prev; - - next->prev = new_block; - prev->next = new_block; -} - -RTEMS_INLINE_ROUTINE void _Heap_Free_list_insert_after( - Heap_Block *block_before, - Heap_Block *new_block -) -{ - Heap_Block *next = block_before->next; - - new_block->next = next; - new_block->prev = block_before; - block_before->next = new_block; - next->prev = new_block; -} - -RTEMS_INLINE_ROUTINE void _Heap_Free_list_insert_before( - Heap_Block *block_next, - Heap_Block *new_block -) -{ - Heap_Block *prev = block_next->prev; - - new_block->next = block_next; - new_block->prev = prev; - prev->next = new_block; - block_next->prev = new_block; -} - -RTEMS_INLINE_ROUTINE bool _Heap_Is_aligned( - uintptr_t value, - uintptr_t alignment -) -{ - return (value % alignment) == 0; -} - -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Align_down( - uintptr_t value, - uintptr_t alignment -) -{ - return value - (value % alignment); -} - -/** - * @brief Returns the block which is @a offset away from @a block. - */ -RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Block_at( - const Heap_Block *block, - uintptr_t offset -) -{ - return (Heap_Block *) ((uintptr_t) block + offset); -} - -RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Prev_block( - const Heap_Block *block -) -{ - return (Heap_Block *) ((uintptr_t) block - block->prev_size); -} - -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Alloc_area_of_block( - const Heap_Block *block -) -{ - return (uintptr_t) block + HEAP_BLOCK_HEADER_SIZE; -} - -RTEMS_INLINE_ROUTINE Heap_Block *_Heap_Block_of_alloc_area( - uintptr_t alloc_begin, - uintptr_t page_size -) -{ - return (Heap_Block *) (_Heap_Align_down( alloc_begin, page_size ) - - HEAP_BLOCK_HEADER_SIZE); -} - -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Block_size( const Heap_Block *block ) -{ - return block->size_and_flag & ~HEAP_PREV_BLOCK_USED; -} - -RTEMS_INLINE_ROUTINE void _Heap_Block_set_size( - Heap_Block *block, - uintptr_t size -) -{ - uintptr_t flag = block->size_and_flag & HEAP_PREV_BLOCK_USED; - - block->size_and_flag = size | flag; -} - -RTEMS_INLINE_ROUTINE bool _Heap_Is_prev_used( const Heap_Block *block ) -{ - return block->size_and_flag & HEAP_PREV_BLOCK_USED; -} - -RTEMS_INLINE_ROUTINE bool _Heap_Is_used( - const Heap_Block *block -) -{ - const Heap_Block *const next_block = - _Heap_Block_at( block, _Heap_Block_size( block ) ); - - return _Heap_Is_prev_used( next_block ); -} - -RTEMS_INLINE_ROUTINE bool _Heap_Is_free( - const Heap_Block *block -) -{ - return !_Heap_Is_used( block ); -} - -RTEMS_INLINE_ROUTINE bool _Heap_Is_block_in_heap( - const Heap_Control *heap, - const Heap_Block *block -) -{ - return (uintptr_t) block >= (uintptr_t) heap->first_block - && (uintptr_t) block <= (uintptr_t) heap->last_block; -} - -/** - * @brief Sets the size of the last block for heap @a heap. - * - * The next block of the last block will be the first block. Since the first - * block indicates that the previous block is used, this ensures that the last - * block appears as used for the _Heap_Is_used() and _Heap_Is_free() - * functions. - * - * This feature will be used to terminate the scattered heap area list. See - * also _Heap_Extend(). - */ -RTEMS_INLINE_ROUTINE void _Heap_Set_last_block_size( Heap_Control *heap ) -{ - _Heap_Block_set_size( - heap->last_block, - (uintptr_t) heap->first_block - (uintptr_t) heap->last_block - ); -} - -/** - * @brief Returns the size of the allocatable area in bytes. - * - * This value is an integral multiple of the page size. - */ -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Get_size( const Heap_Control *heap ) -{ - return heap->stats.size; -} - -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Max( uintptr_t a, uintptr_t b ) -{ - return a > b ? a : b; -} - -RTEMS_INLINE_ROUTINE uintptr_t _Heap_Min( uintptr_t a, uintptr_t b ) -{ - return a < b ? a : b; -} - -/** @} */ - -#endif -/* end of include file */ diff --git a/cpukit/score/preinstall.am b/cpukit/score/preinstall.am index 73d088c665..fe19329646 100644 --- a/cpukit/score/preinstall.am +++ b/cpukit/score/preinstall.am @@ -107,6 +107,10 @@ $(PROJECT_INCLUDE)/rtems/score/heap.h: include/rtems/score/heap.h $(PROJECT_INCL $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/heap.h PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/heap.h +$(PROJECT_INCLUDE)/rtems/score/heapimpl.h: include/rtems/score/heapimpl.h $(PROJECT_INCLUDE)/rtems/score/$(dirstamp) + $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/heapimpl.h +PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/heapimpl.h + $(PROJECT_INCLUDE)/rtems/score/protectedheap.h: include/rtems/score/protectedheap.h $(PROJECT_INCLUDE)/rtems/score/$(dirstamp) $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/protectedheap.h PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/protectedheap.h @@ -299,10 +303,6 @@ $(PROJECT_INCLUDE)/rtems/score/schedulersimplesmp.h: include/rtems/score/schedul $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/schedulersimplesmp.h PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/schedulersimplesmp.h endif -$(PROJECT_INCLUDE)/rtems/score/heap.inl: inline/rtems/score/heap.inl $(PROJECT_INCLUDE)/rtems/score/$(dirstamp) - $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/heap.inl -PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/heap.inl - $(PROJECT_INCLUDE)/rtems/score/object.inl: inline/rtems/score/object.inl $(PROJECT_INCLUDE)/rtems/score/$(dirstamp) $(INSTALL_DATA) $< $(PROJECT_INCLUDE)/rtems/score/object.inl PREINSTALL_FILES += $(PROJECT_INCLUDE)/rtems/score/object.inl diff --git a/cpukit/score/src/heap.c b/cpukit/score/src/heap.c index 89dcd34fa6..6773f2ac52 100644 --- a/cpukit/score/src/heap.c +++ b/cpukit/score/src/heap.c @@ -18,15 +18,14 @@ */ #if HAVE_CONFIG_H -#include "config.h" + #include "config.h" #endif -#include - -#include -#include +#include #include +#include + #if CPU_ALIGNMENT == 0 || CPU_ALIGNMENT % 2 != 0 #error "invalid CPU_ALIGNMENT value" #endif diff --git a/cpukit/score/src/heapallocate.c b/cpukit/score/src/heapallocate.c index a912644d80..6367fac426 100644 --- a/cpukit/score/src/heapallocate.c +++ b/cpukit/score/src/heapallocate.c @@ -23,7 +23,7 @@ #include #include -#include +#include #ifndef HEAP_PROTECTION #define _Heap_Protection_free_delayed_blocks( heap, alloc_begin ) false diff --git a/cpukit/score/src/heapextend.c b/cpukit/score/src/heapextend.c index aaaabf4236..571bba8428 100644 --- a/cpukit/score/src/heapextend.c +++ b/cpukit/score/src/heapextend.c @@ -23,7 +23,7 @@ #include #include -#include +#include static void _Heap_Free_block( Heap_Control *heap, Heap_Block *block ) { diff --git a/cpukit/score/src/heapfree.c b/cpukit/score/src/heapfree.c index bd85cad9fc..d15094ce77 100644 --- a/cpukit/score/src/heapfree.c +++ b/cpukit/score/src/heapfree.c @@ -20,7 +20,7 @@ #endif #include -#include +#include #ifndef HEAP_PROTECTION #define _Heap_Protection_determine_block_free( heap, block ) true diff --git a/cpukit/score/src/heapgetfreeinfo.c b/cpukit/score/src/heapgetfreeinfo.c index be0bfd883a..de6e3dc555 100644 --- a/cpukit/score/src/heapgetfreeinfo.c +++ b/cpukit/score/src/heapgetfreeinfo.c @@ -21,7 +21,7 @@ #include #include -#include +#include void _Heap_Get_free_information( Heap_Control *the_heap, diff --git a/cpukit/score/src/heapgetinfo.c b/cpukit/score/src/heapgetinfo.c index d796ba44e4..ded488b560 100644 --- a/cpukit/score/src/heapgetinfo.c +++ b/cpukit/score/src/heapgetinfo.c @@ -21,7 +21,7 @@ #include -#include +#include static bool _Heap_Get_information_visitor( const Heap_Block *block __attribute__((unused)), diff --git a/cpukit/score/src/heapgreedy.c b/cpukit/score/src/heapgreedy.c index b5c61a4e64..833a80ea34 100644 --- a/cpukit/score/src/heapgreedy.c +++ b/cpukit/score/src/heapgreedy.c @@ -24,7 +24,7 @@ #include "config.h" #endif -#include +#include Heap_Block *_Heap_Greedy_allocate( Heap_Control *heap, diff --git a/cpukit/score/src/heapiterate.c b/cpukit/score/src/heapiterate.c index b5c900a81f..893bcc1f80 100644 --- a/cpukit/score/src/heapiterate.c +++ b/cpukit/score/src/heapiterate.c @@ -24,7 +24,7 @@ #include "config.h" #endif -#include +#include void _Heap_Iterate( Heap_Control *heap, diff --git a/cpukit/score/src/heapnoextend.c b/cpukit/score/src/heapnoextend.c index 1652f59e17..ef7a2a7243 100644 --- a/cpukit/score/src/heapnoextend.c +++ b/cpukit/score/src/heapnoextend.c @@ -24,7 +24,7 @@ #include "config.h" #endif -#include +#include uintptr_t _Heap_No_extend( Heap_Control *unused_0 __attribute__((unused)), diff --git a/cpukit/score/src/heapresizeblock.c b/cpukit/score/src/heapresizeblock.c index 742e03fa8f..f791efee44 100644 --- a/cpukit/score/src/heapresizeblock.c +++ b/cpukit/score/src/heapresizeblock.c @@ -23,7 +23,7 @@ #include #include -#include +#include static Heap_Resize_status _Heap_Resize_block_checked( Heap_Control *heap, diff --git a/cpukit/score/src/heapsizeofuserarea.c b/cpukit/score/src/heapsizeofuserarea.c index 5c1ce69acd..7c4d9f3e2e 100644 --- a/cpukit/score/src/heapsizeofuserarea.c +++ b/cpukit/score/src/heapsizeofuserarea.c @@ -21,7 +21,7 @@ #include #include -#include +#include bool _Heap_Size_of_alloc_area( Heap_Control *heap, diff --git a/cpukit/score/src/heapwalk.c b/cpukit/score/src/heapwalk.c index c84f1282de..9e8557ae97 100644 --- a/cpukit/score/src/heapwalk.c +++ b/cpukit/score/src/heapwalk.c @@ -22,7 +22,7 @@ #include #include #include -#include +#include #include #include diff --git a/cpukit/score/src/wkspace.c b/cpukit/score/src/wkspace.c index 72712456fa..b9482960ac 100644 --- a/cpukit/score/src/wkspace.c +++ b/cpukit/score/src/wkspace.c @@ -15,13 +15,13 @@ */ #if HAVE_CONFIG_H -#include "config.h" + #include "config.h" #endif -#include -#include #include +#include #include +#include #include /* for memset */ diff --git a/testsuites/libtests/heapwalk/init.c b/testsuites/libtests/heapwalk/init.c index 3565570429..4e0142839d 100644 --- a/testsuites/libtests/heapwalk/init.c +++ b/testsuites/libtests/heapwalk/init.c @@ -15,7 +15,6 @@ #include "config.h" #endif -#define __RTEMS_VIOLATE_KERNEL_VISIBILITY__ #define CONFIGURE_INIT #include "system.h" @@ -23,7 +22,7 @@ #include #include #include -#include +#include #include #define TEST_HEAP_SIZE 1024 diff --git a/testsuites/sptests/sp63/init.c b/testsuites/sptests/sp63/init.c index 040f510d75..a5e8eb560f 100644 --- a/testsuites/sptests/sp63/init.c +++ b/testsuites/sptests/sp63/init.c @@ -13,6 +13,8 @@ #include +#include + /* forward declarations to avoid warnings */ rtems_task Init(rtems_task_argument argument); void test_case_one(void); diff --git a/testsuites/sptests/spheapprot/init.c b/testsuites/sptests/spheapprot/init.c index d48703faa4..aaea75dd79 100644 --- a/testsuites/sptests/spheapprot/init.c +++ b/testsuites/sptests/spheapprot/init.c @@ -20,12 +20,10 @@ #include #include -#define __RTEMS_VIOLATE_KERNEL_VISIBILITY__ - -#include - #include +#include + #ifdef HEAP_PROTECTION static void test_heap_block_error(Heap_Control *heap, Heap_Block *block) { diff --git a/testsuites/sptests/spstkalloc02/init.c b/testsuites/sptests/spstkalloc02/init.c index 8c1db21339..46880c7f74 100644 --- a/testsuites/sptests/spstkalloc02/init.c +++ b/testsuites/sptests/spstkalloc02/init.c @@ -31,7 +31,7 @@ #include #include -#include +#include #define TASK_COUNT 5 -- cgit v1.2.3