From f26f5fc12446e8e35bdcf0da30d271896a62a946 Mon Sep 17 00:00:00 2001 From: Sebastian Huber Date: Tue, 23 Jul 2013 15:30:16 +0200 Subject: score: Merge address API into one file --- cpukit/score/include/rtems/score/address.h | 165 ++++++++++++++++++++++++++++- 1 file changed, 160 insertions(+), 5 deletions(-) (limited to 'cpukit/score/include/rtems/score/address.h') diff --git a/cpukit/score/include/rtems/score/address.h b/cpukit/score/include/rtems/score/address.h index 85658b55b0..9b22b3c72a 100644 --- a/cpukit/score/include/rtems/score/address.h +++ b/cpukit/score/include/rtems/score/address.h @@ -19,6 +19,12 @@ #ifndef _RTEMS_SCORE_ADDRESS_H #define _RTEMS_SCORE_ADDRESS_H +#include + +#ifdef __cplusplus +extern "C" { +#endif + /** * @defgroup ScoreAddress Address Handler * @@ -29,17 +35,166 @@ */ /**@{*/ -#ifdef __cplusplus -extern "C" { -#endif +/** + * @brief Add offset to an address. + * + * This function is used to add an @a offset to a @a base address. + * It returns the resulting address. This address is typically + * converted to an access type before being used further. + * + * @param[in] base is the base address. + * @param[in] offset is the offset to add to @a base. + * + * @return This method returns the resulting address. + */ +RTEMS_INLINE_ROUTINE void *_Addresses_Add_offset ( + const void *base, + uintptr_t offset +) +{ + return (void *)((uintptr_t)base + offset); +} + +/** + * @brief Subtract offset from offset. + * + * This function is used to subtract an @a offset from a @a base + * address. It returns the resulting address. This address is + * typically converted to an access type before being used further. + * + * @param[in] base is the base address. + * @param[in] offset is the offset to subtract to @a base. + * + * @return This method returns the resulting address. + */ -#include +RTEMS_INLINE_ROUTINE void *_Addresses_Subtract_offset ( + const void *base, + uintptr_t offset +) +{ + return (void *)((uintptr_t)base - offset); +} -#ifdef __cplusplus +/** + * @brief Subtract two offsets. + * + * This function is used to subtract two addresses. It returns the + * resulting offset. + * + * @param[in] left is the address on the left hand side of the subtraction. + * @param[in] right is the address on the right hand side of the subtraction. + * + * @return This method returns the resulting address. + * + * @note The cast of an address to an uint32_t makes this code + * dependent on an addresses being thirty two bits. + */ +RTEMS_INLINE_ROUTINE int32_t _Addresses_Subtract ( + const void *left, + const void *right +) +{ + return (int32_t) ((const char *) left - (const char *) right); } + +/** + * @brief Is address aligned. + * + * This function returns true if the given address is correctly + * aligned for this processor and false otherwise. Proper alignment + * is based on correctness and efficiency. + * + * @param[in] address is the address being checked for alignment. + * + * @retval true The @a address is aligned. + * @retval false The @a address is not aligned. + */ +RTEMS_INLINE_ROUTINE bool _Addresses_Is_aligned ( + const void *address +) +{ +#if (CPU_ALIGNMENT == 0) + return true; +#else + return (((uintptr_t)address % CPU_ALIGNMENT) == 0); #endif +} + +/** + * @brief Is address in range. + * + * This function returns true if the given address is within the + * memory range specified and false otherwise. base is the address + * of the first byte in the memory range and limit is the address + * of the last byte in the memory range. The base address is + * assumed to be lower than the limit address. + * + * @param[in] address is the address to check. + * @param[in] base is the lowest address of the range to check against. + * @param[in] limit is the highest address of the range to check against. + * + * @retval true The @a address is within the memory range specified + * @retval false The @a address is not within the memory range specified. + */ +RTEMS_INLINE_ROUTINE bool _Addresses_Is_in_range ( + const void *address, + const void *base, + const void *limit +) +{ + return (address >= base && address <= limit); +} + +/** + * @brief Align address to nearest multiple of alignment, rounding up. + * + * This function returns the given address aligned to the given alignment. + * If the address already is aligned, or if alignment is 0, the address is + * returned as is. The returned address is greater than or equal to the + * given address. + * + * @param[in] address is the address to align. + * @param[in] alignment is the boundary for alignment and must be a power of 2 + * + * @return Returns the aligned address. + */ +RTEMS_INLINE_ROUTINE void *_Addresses_Align_up( + void *address, + size_t alignment +) +{ + uintptr_t mask = alignment - (uintptr_t)1; + return (void*)(((uintptr_t)address + mask) & ~mask); +} + +/** + * @brief Align address to nearest multiple of alignment, truncating. + * + * This function returns the given address aligned to the given alignment. + * If the address already is aligned, or if alignment is 0, the address is + * returned as is. The returned address is less than or equal to the + * given address. + * + * @param[in] address is the address to align. + * @param[in] alignment is the boundary for alignment and must be a power of 2. + * + * @return Returns the aligned address. + */ +RTEMS_INLINE_ROUTINE void *_Addresses_Align_down( + void *address, + size_t alignment +) +{ + uintptr_t mask = alignment - (uintptr_t)1; + return (void*)((uintptr_t)address & ~mask); +} /**@}*/ +#ifdef __cplusplus +} +#endif + #endif /* end of include file */ -- cgit v1.2.3