diff options
Diffstat (limited to 'mbglib/common/words.h')
-rw-r--r-- | mbglib/common/words.h | 312 |
1 files changed, 195 insertions, 117 deletions
diff --git a/mbglib/common/words.h b/mbglib/common/words.h index 4216e17..c298755 100644 --- a/mbglib/common/words.h +++ b/mbglib/common/words.h @@ -1,7 +1,7 @@ /************************************************************************** * - * $Id: words.h 1.26 2011/04/06 10:23:03 martin REL_M $ + * $Id: words.h 1.34 2014/10/20 12:31:20 martin REL_M $ * * Copyright (c) Meinberg Funkuhren, Bad Pyrmont, Germany * @@ -10,6 +10,29 @@ * * ----------------------------------------------------------------------- * $Log: words.h $ + * Revision 1.34 2014/10/20 12:31:20 martin + * Moved macro _isdigit() here. + * Revision 1.33 2014/05/27 10:18:35Z martin + * Finer control of which types are required for or already + * available on particular target systems. + * Added macros helpful to simplify declarations of code/name tables. + * Revision 1.32 2014/01/07 15:43:52 martin + * Define __mbg_inline for ARM firmware targets. + * Revision 1.31 2012/11/29 11:54:39Z martin + * Removed #if sizeof() definitions which may cause build errors + * with some older compilers. + * Include stdbool.h for __ARMCC_VERSION targets. + * Moved _nop_macro_fnc() definition here. + * Revision 1.30 2012/11/02 09:12:29Z martin + * Moved most feature detection code to mbg_tgt.h. + * Tried to define missing features most flexibly and portably. + * Revision 1.29 2012/07/11 16:45:45Z martin + * New macros to access individual bytes of long constants. + * Revision 1.28 2012/04/05 14:36:18Z martin + * Support CVI 2010 compiler which provides C99 types. + * Revision 1.27 2011/07/18 10:21:38Z martin + * Added definition for MBG_CODE_NAME_TABLE_ENTRY which can + * be used to define tables assigning strings to numeric codes. * Revision 1.26 2011/04/06 10:23:03 martin * Added FBYTE_OF() and FWORD_OF() macros. * Modifications required for *BSD. @@ -82,23 +105,33 @@ #if !defined( _IS_MBG_FIRMWARE ) -#if defined( _C166 ) || \ - defined( _CC51 ) || \ - defined( __ARM ) || \ - defined( __ARMCC_VERSION ) - #define _IS_MBG_FIRMWARE 1 -#else - #define _IS_MBG_FIRMWARE 0 -#endif - + #if defined( _C166 ) || \ + defined( _CC51 ) || \ + defined( __ARM ) || \ + defined( __ARMCC_VERSION ) + #define _IS_MBG_FIRMWARE 1 + #else + #define _IS_MBG_FIRMWARE 0 + #endif #endif + #if !_IS_MBG_FIRMWARE #include <mbg_tgt.h> +#else + #if defined( __ARMCC_VERSION ) // Keil RealView Compiler for ARM + #define __mbg_inline __inline + #include <stdint.h> + #include <stdbool.h> + #define MBG_TGT_HAS_EXACT_SIZE_TYPES 1 + #else + #define MBG_TGT_MISSING_64_BIT_TYPES 1 + #endif #endif + #ifdef _WORDS #define _ext #else @@ -108,117 +141,60 @@ /* Start of header body */ - -// The compilers below support native bit types. - -#if defined( _C166 ) || defined( _CC51 ) - #define _BIT_DEFINED 1 +#if defined( _C166 ) \ + || defined( _CC51 ) + #define _BIT_DEFINED 1 // these compilers natively support the "bit" type + #define USE_LONG_FOR_INT32 1 #endif -// Check whether the target system supports C99 fixed-size types. - -#if defined( MBG_TGT_LINUX ) // any Linux target - - #if defined( __KERNEL__ ) - #include <linux/types.h> - #else - #include <stdint.h> - #include <sys/types.h> - #endif - - #define _C99_BIT_TYPES_DEFINED 1 - -#elif defined( MBG_TGT_BSD ) +#if !defined( MBG_TGT_HAS_EXACT_SIZE_TYPES ) - #include <sys/types.h> + #if defined( MBG_TGT_HAS_INT_8_16_32 ) - #define _C99_BIT_TYPES_DEFINED 1 + // Define C99 exact size types using non-standard exact-size types + typedef __int8 int8_t; + typedef unsigned __int8 uint8_t; - // avoid inclusion of stdbool.h later - #define bit int - #define _BIT_DEFINED 1 - -#elif defined( MBG_TGT_QNX ) // QNX 4.x or QNX 6.x - - #if defined( MBG_TGT_QNX_NTO ) // QNX 6.x (Neutrino) with gcc - #include <stdint.h> - #else // QNX 4.x with Watcom C 10.6 - #include <sys/types.h> // 64 bit types not supported - #endif - - #define _C99_BIT_TYPES_DEFINED 1 - -#endif + typedef __int16 int16_t; + typedef unsigned __int16 uint16_t; + typedef __int32 int32_t; + typedef unsigned __int32 uint32_t; + #else -// If it's not yet clear whether fixed-size types are supported, -// check the build environment which may be multi-platform. + // Assume a 16 or 32 bit compiler which doesn't + // support exact-size types. -#if !defined( _C99_BIT_TYPES_DEFINED ) + typedef char int8_t; + typedef unsigned char uint8_t; - #if defined( __WATCOMC__ ) - #if __WATCOMC__ > 1230 // Open Watcom C 1.3 and above - #include <stdint.h> - #define _C99_BIT_TYPES_DEFINED 1 - #elif defined( __WATCOM_INT64__ ) // Watcom C 11, non-QNX - typedef __int64 int64_t; - typedef unsigned __int64 uint64_t; + typedef short int16_t; + typedef unsigned short uint16_t; - #define _C99_BIT_TYPES_DEFINED 1 - #endif - #endif + // Using #if sizeof() to determine the size of a type may not + // be supported by all preprocessors, and may even result in + // build errors if used in a conditional preprocessor section, + // so we can't use this here without compatibility problems. - #if defined( __BORLANDC__ ) - #if ( __BORLANDC__ >= 0x570 ) // at least Borland Developer Studio 2006 - #define _C99_BIT_TYPES_DEFINED 1 + #if defined( USE_LONG_FOR_INT32 ) + typedef long int32_t; + typedef unsigned long uint32_t; + #elif defined( USE_INT_FOR_INT32 ) + typedef int int32_t; + typedef unsigned int uint32_t; + #else + #error Need to define int32_t and uint32_t #endif - #endif - - #if defined( __GNUC__ ) - #include <stdint.h> - #define _C99_BIT_TYPES_DEFINED 1 - #endif - #if defined( __ARMCC_VERSION ) // Keil RealView Compiler for ARM - #include <stdint.h> - #define _C99_BIT_TYPES_DEFINED 1 #endif -#endif - - -// If neither the target system nor the build environment define C99 fixed-size -// types define those types based on standard types with the proper sizes -// commonly used in 16/32 bit environments. - -#if defined( _C99_BIT_TYPES_DEFINED ) - - #define MBG_TGT_HAS_64BIT_TYPES 1 - -#else - - typedef char int8_t; - typedef unsigned char uint8_t; - - typedef short int16_t; - typedef unsigned short uint16_t; - - typedef long int32_t; - typedef unsigned long uint32_t; + #if defined( MBG_TGT_MISSING_64_BIT_TYPES ) - - #if defined( MBG_TGT_WIN32 ) - - typedef __int64 int64_t; - typedef unsigned __int64 uint64_t; - - #define MBG_TGT_HAS_64BIT_TYPES 1 - - #else - // The types below are required to avoid build errors + // The build environment does not support 64 bit types. However, + // 64 bit types need to be defined to avoid build errors // if these types are formally used in function prototypes. // We explicitely use abnormal data types to hopefully // cause compiler errors in case these types are @@ -226,45 +202,102 @@ // platform which does not support 64 bit types. typedef void *int64_t; typedef void *uint64_t; + + #else + + // Define C99 types using non-standard exact-size types + // which are usually supported by build envonronments + // supporting 64 bit types but no C99 types. + typedef __int64 int64_t; + typedef unsigned __int64 uint64_t; + #endif #endif -#if !defined( MBG_TGT_HAS_64BIT_TYPES ) +#if defined( MBG_TGT_MISSING_64_BIT_TYPES ) #define MBG_TGT_HAS_64BIT_TYPES 0 +#else + + #define MBG_TGT_HAS_64BIT_TYPES 1 + #endif // Some commonly used types -typedef unsigned char uchar; +#if !defined( _UCHAR_DEFINED ) + typedef unsigned char uchar; + #define uchar uchar +#endif -#if !defined( MBG_TGT_LINUX ) && !( defined ( MBG_TGT_NETBSD ) && defined ( MBG_TGT_KERNEL ) ) +#if !defined( _USHORT_DEFINED ) typedef unsigned short ushort; + #define ushort ushort +#endif + +#if !defined( _UINT_DEFINED ) typedef unsigned int uint; + #define uint uint +#endif + +#if !defined( _ULONG_DEFINED ) typedef unsigned long ulong; + #define ulong ulong +#endif + +#if !defined( _UDOUBLE_DEFINED ) + typedef double udouble; + #define udouble udouble +#endif + +#if !defined( _BYTE_DEFINED ) + typedef unsigned char byte; + #define byte byte +#endif + +#if !defined( _WORD_DEFINED ) + typedef unsigned short word; + #define word word #endif -typedef double udouble; +#if !defined( _LONGWORD_DEFINED ) + typedef unsigned long longword; + #define longword longword +#endif + +#if !defined( _DWORD_DEFINED ) +// typedef unsigned long dword; +// #define dword dword +#endif -typedef unsigned char byte; -typedef unsigned short word; -typedef unsigned long longword; -typedef unsigned long dword; #if !defined( _BIT_DEFINED ) - #if _C99_BIT_TYPES_DEFINED - #include <stdbool.h> + // We need to implement a "bit" type. Preferably we use "bool" + // to do this, but this is only supported by C++ compilers, and + // by C compilers supporting the C99 standard. + + #if !defined( MBG_TGT_MISSING_BOOL_TYPE ) && \ + ( defined( __cplusplus ) || defined( __bool_true_false_are_defined ) ) typedef bool bit; - #else + #define bit bit + + #else // C99 types not supported + + // Falling back to use "int" for "bit". This prevents error + // messages if "bit" is used in function prototypes, but may + // yield unexpected results for code like: + // return (bit) ( val & 0x10 ); typedef int bit; + #define bit bit + #endif #define _BIT_REDEFINED 1 @@ -272,11 +305,17 @@ typedef unsigned long dword; #endif -#define HI_BYTE( _x ) ( (_x) >> 8 ) -#define LO_BYTE( _x ) ( (_x) & 0xFF ) +#define BYTE_0( _x ) ( (uint8_t ) ( (_x) & 0xFF ) ) +#define BYTE_1( _x ) ( (uint8_t ) ( ( ( (uint16_t) (_x) ) >> 8 ) & 0xFF ) ) +#define BYTE_2( _x ) ( (uint8_t ) ( ( ( (uint32_t) (_x) ) >> 16 ) & 0xFF ) ) +#define BYTE_3( _x ) ( (uint8_t ) ( ( ( (uint32_t) (_x) ) >> 24 ) & 0xFF ) ) -#define HI_WORD( _x ) ( (_x) >> 16 ) -#define LO_WORD( _x ) ( (_x) & 0xFFFF ) + +#define HI_BYTE( _x ) ( (uint8_t ) ( (_x) >> 8 ) ) +#define LO_BYTE( _x ) ( (uint8_t ) ( (_x) & 0xFF ) ) + +#define HI_WORD( _x ) ( (uint16_t ) ( (_x) >> 16 ) ) +#define LO_WORD( _x ) ( (uint16_t ) ( (_x) & 0xFFFF ) ) // the macros below assume little endianess // these macros expect the name of a variable @@ -332,6 +371,45 @@ typedef unsigned long dword; #define _hilo_32( _x ) (_x) #endif + +#define _isdigit( _c ) ( (_c) >= '0' && (_c) <= '9' ) + + +// A macro function which can safely be used without +// side effects as a macro doing nothing. +// This is useful to define debug macros away in +// release builds, etc. +#if !defined( _nop_macro_fnc ) + #define _nop_macro_fnc() do {} while (0) +#endif + + +/** + * @brief A table entry which can be used to map codes to names. + */ +typedef struct +{ + ulong code; + const char *name; +} MBG_CODE_NAME_TABLE_ENTRY; + +/** + * @brief A macro defining a ::MBG_CODE_NAME_TABLE_ENTRY + * + * The stringified parameter is used for the name. + * + * @param _n The symbolic name of the numeric code + */ +#define _mbg_cn_table_entry( _n ) { _n, #_n } + +/** + * @brief A macro defining an empty ::MBG_CODE_NAME_TABLE_ENTRY + * + * This is used to terminate a table. + */ +#define _mbg_cn_table_end() { 0, NULL } + + /* End of header body */ #undef _ext |