[e16e8f2] | 1 | #ifndef COMPILER_H |
---|
| 2 | #define COMPILER_H |
---|
| 3 | |
---|
| 4 | /* |
---|
| 5 | * Doxygen can't cope with some of the more esoteric areas of C, so we |
---|
| 6 | * make its life simpler. |
---|
| 7 | * |
---|
| 8 | */ |
---|
| 9 | #ifdef DOXYGEN |
---|
| 10 | #define __attribute__(x) |
---|
| 11 | #endif |
---|
| 12 | |
---|
| 13 | /** @file |
---|
| 14 | * |
---|
| 15 | * Global compiler definitions. |
---|
| 16 | * |
---|
| 17 | * This file is implicitly included by every @c .c file in Etherboot. |
---|
| 18 | * It defines global macros such as DBG(). |
---|
| 19 | * |
---|
| 20 | * We arrange for each object to export the symbol @c obj_OBJECT |
---|
| 21 | * (where @c OBJECT is the object name, e.g. @c rtl8139) as a global |
---|
| 22 | * symbol, so that the linker can drag in selected object files from |
---|
| 23 | * the library using <tt> -u obj_OBJECT </tt>. |
---|
| 24 | * |
---|
| 25 | */ |
---|
| 26 | |
---|
| 27 | /* Force visibility of all symbols to "hidden", i.e. inform gcc that |
---|
| 28 | * all symbol references resolve strictly within our final binary. |
---|
| 29 | * This avoids unnecessary PLT/GOT entries on x86_64. |
---|
| 30 | * |
---|
| 31 | * This is a stronger claim than specifying "-fvisibility=hidden", |
---|
| 32 | * since it also affects symbols marked with "extern". |
---|
| 33 | */ |
---|
| 34 | #ifndef ASSEMBLY |
---|
| 35 | #if __GNUC__ >= 4 |
---|
| 36 | #pragma GCC visibility push(hidden) |
---|
| 37 | #endif |
---|
| 38 | #endif /* ASSEMBLY */ |
---|
| 39 | |
---|
| 40 | #undef _S1 |
---|
| 41 | #undef _S2 |
---|
| 42 | #undef _C1 |
---|
| 43 | #undef _C2 |
---|
| 44 | |
---|
| 45 | /** Concatenate non-expanded arguments */ |
---|
| 46 | #define _C1( x, y ) x ## y |
---|
| 47 | /** Concatenate expanded arguments */ |
---|
| 48 | #define _C2( x, y ) _C1 ( x, y ) |
---|
| 49 | |
---|
| 50 | /** Stringify non-expanded argument */ |
---|
| 51 | #define _S1( x ) #x |
---|
| 52 | /** Stringify expanded argument */ |
---|
| 53 | #define _S2( x ) _S1 ( x ) |
---|
| 54 | |
---|
| 55 | /** |
---|
| 56 | * @defgroup symmacros Macros to provide or require explicit symbols |
---|
| 57 | * @{ |
---|
| 58 | */ |
---|
| 59 | |
---|
| 60 | /** Provide a symbol within this object file */ |
---|
| 61 | #ifdef ASSEMBLY |
---|
| 62 | #define PROVIDE_SYMBOL( _sym ) \ |
---|
| 63 | .globl _sym ; \ |
---|
| 64 | .comm _sym, 0 |
---|
| 65 | #else /* ASSEMBLY */ |
---|
| 66 | #define PROVIDE_SYMBOL( _sym ) \ |
---|
| 67 | char _sym[0] |
---|
| 68 | #endif /* ASSEMBLY */ |
---|
| 69 | |
---|
| 70 | /** Require a symbol within this object file |
---|
| 71 | * |
---|
| 72 | * The symbol is referenced by a relocation in a discarded section, so |
---|
| 73 | * if it is not available at link time the link will fail. |
---|
| 74 | */ |
---|
| 75 | #ifdef ASSEMBLY |
---|
| 76 | #define REQUIRE_SYMBOL( _sym ) \ |
---|
| 77 | .section ".discard", "a", @progbits ; \ |
---|
| 78 | .extern _sym ; \ |
---|
| 79 | .long _sym ; \ |
---|
| 80 | .previous |
---|
| 81 | #else /* ASSEMBLY */ |
---|
| 82 | #define REQUIRE_SYMBOL( _sym ) \ |
---|
| 83 | extern char _sym; \ |
---|
| 84 | static char * _C2 ( _C2 ( __require_, _sym ), _C2 ( _, __LINE__ ) ) \ |
---|
| 85 | __attribute__ (( section ( ".discard" ), used )) \ |
---|
| 86 | = &_sym |
---|
| 87 | #endif |
---|
| 88 | |
---|
| 89 | /** Request that a symbol be available at runtime |
---|
| 90 | * |
---|
| 91 | * The requested symbol is entered as undefined into the symbol table |
---|
| 92 | * for this object, so the linker will pull in other object files as |
---|
| 93 | * necessary to satisfy the reference. However, the undefined symbol |
---|
| 94 | * is not referenced in any relocations, so the link can still succeed |
---|
| 95 | * if no file contains it. |
---|
| 96 | * |
---|
| 97 | * A symbol passed to this macro may not be referenced anywhere |
---|
| 98 | * else in the file. If you want to do that, see IMPORT_SYMBOL(). |
---|
| 99 | */ |
---|
| 100 | #ifdef ASSEMBLY |
---|
| 101 | #define REQUEST_SYMBOL( _sym ) \ |
---|
| 102 | .equ __need_ ## _sym, _sym |
---|
| 103 | #else /* ASSEMBLY */ |
---|
| 104 | #define REQUEST_SYMBOL( _sym ) \ |
---|
| 105 | __asm__ ( ".equ\t__need_" #_sym ", " #_sym ) |
---|
| 106 | #endif /* ASSEMBLY */ |
---|
| 107 | |
---|
| 108 | /** Set up a symbol to be usable in another file by IMPORT_SYMBOL() |
---|
| 109 | * |
---|
| 110 | * The symbol must already be marked as global. |
---|
| 111 | */ |
---|
| 112 | #define EXPORT_SYMBOL( _sym ) PROVIDE_SYMBOL ( __export_ ## _sym ) |
---|
| 113 | |
---|
| 114 | /** Make a symbol usable to this file if available at link time |
---|
| 115 | * |
---|
| 116 | * If no file passed to the linker contains the symbol, it will have |
---|
| 117 | * @c NULL value to future uses. Keep in mind that the symbol value is |
---|
| 118 | * really the @e address of a variable or function; see the code |
---|
| 119 | * snippet below. |
---|
| 120 | * |
---|
| 121 | * In C using IMPORT_SYMBOL, you must specify the declaration as the |
---|
| 122 | * second argument, for instance |
---|
| 123 | * |
---|
| 124 | * @code |
---|
| 125 | * IMPORT_SYMBOL ( my_func, int my_func ( int arg ) ); |
---|
| 126 | * IMPORT_SYMBOL ( my_var, int my_var ); |
---|
| 127 | * |
---|
| 128 | * void use_imports ( void ) { |
---|
| 129 | * if ( my_func && &my_var ) |
---|
| 130 | * my_var = my_func ( my_var ); |
---|
| 131 | * } |
---|
| 132 | * @endcode |
---|
| 133 | * |
---|
| 134 | * GCC considers a weak declaration to override a strong one no matter |
---|
| 135 | * which comes first, so it is safe to include a header file declaring |
---|
| 136 | * the imported symbol normally, but providing the declaration to |
---|
| 137 | * IMPORT_SYMBOL is still required. |
---|
| 138 | * |
---|
| 139 | * If no EXPORT_SYMBOL declaration exists for the imported symbol in |
---|
| 140 | * another file, the behavior will be most likely be identical to that |
---|
| 141 | * for an unavailable symbol. |
---|
| 142 | */ |
---|
| 143 | #ifdef ASSEMBLY |
---|
| 144 | #define IMPORT_SYMBOL( _sym ) \ |
---|
| 145 | REQUEST_SYMBOL ( __export_ ## _sym ) ; \ |
---|
| 146 | .weak _sym |
---|
| 147 | #else /* ASSEMBLY */ |
---|
| 148 | #define IMPORT_SYMBOL( _sym, _decl ) \ |
---|
| 149 | REQUEST_SYMBOL ( __export_ ## _sym ) ; \ |
---|
| 150 | extern _decl __attribute__ (( weak )) |
---|
| 151 | #endif |
---|
| 152 | |
---|
| 153 | /** @} */ |
---|
| 154 | |
---|
| 155 | /** |
---|
| 156 | * @defgroup objmacros Macros to provide or require explicit objects |
---|
| 157 | * @{ |
---|
| 158 | */ |
---|
| 159 | |
---|
| 160 | #define PREFIX_OBJECT( _prefix ) _C2 ( _prefix, OBJECT ) |
---|
| 161 | #define OBJECT_SYMBOL PREFIX_OBJECT ( obj_ ) |
---|
| 162 | #define REQUEST_EXPANDED( _sym ) REQUEST_SYMBOL ( _sym ) |
---|
| 163 | #define CONFIG_SYMBOL PREFIX_OBJECT ( obj_config_ ) |
---|
| 164 | |
---|
| 165 | /** Always provide the symbol for the current object (defined by -DOBJECT) */ |
---|
| 166 | PROVIDE_SYMBOL ( OBJECT_SYMBOL ); |
---|
| 167 | |
---|
| 168 | /** Pull in an object-specific configuration file if available */ |
---|
| 169 | REQUEST_EXPANDED ( CONFIG_SYMBOL ); |
---|
| 170 | |
---|
| 171 | /** Explicitly require another object */ |
---|
| 172 | #define REQUIRE_OBJECT( _obj ) REQUIRE_SYMBOL ( obj_ ## _obj ) |
---|
| 173 | |
---|
| 174 | /** Pull in another object if it exists */ |
---|
| 175 | #define REQUEST_OBJECT( _obj ) REQUEST_SYMBOL ( obj_ ## _obj ) |
---|
| 176 | |
---|
| 177 | /** @} */ |
---|
| 178 | |
---|
| 179 | /** Select file identifier for errno.h (if used) */ |
---|
| 180 | #define ERRFILE PREFIX_OBJECT ( ERRFILE_ ) |
---|
| 181 | |
---|
| 182 | /** |
---|
| 183 | * @defgroup weakmacros Macros to manage weak symbol definitions |
---|
| 184 | * |
---|
| 185 | * Weak symbols allow one to reference a function in another file |
---|
| 186 | * without necessarily requiring that file to be linked in. In their |
---|
| 187 | * native form, the function will be @c NULL if its file is not linked |
---|
| 188 | * in; these macros provide an inline wrapper that returns an |
---|
| 189 | * appropriate error indication or default value. |
---|
| 190 | * |
---|
| 191 | * @{ |
---|
| 192 | */ |
---|
| 193 | #ifndef ASSEMBLY |
---|
| 194 | |
---|
| 195 | /** Mangle @a name into its weakly-referenced implementation */ |
---|
| 196 | #define __weak_impl( name ) _w_ ## name |
---|
| 197 | |
---|
| 198 | /** |
---|
| 199 | * Declare a weak function with inline safety wrapper |
---|
| 200 | * |
---|
| 201 | * @v ret Return type of weak function |
---|
| 202 | * @v name Name of function to expose |
---|
| 203 | * @v proto Parenthesized list of arguments with types |
---|
| 204 | * @v args Parenthesized list of argument names |
---|
| 205 | * @v dfl Value to return if weak function is not available |
---|
| 206 | */ |
---|
| 207 | #define __weak_decl( ret, name, proto, args, dfl ) \ |
---|
| 208 | ret __weak_impl( name ) proto __attribute__ (( weak )); \ |
---|
| 209 | static inline ret name proto { \ |
---|
| 210 | if ( __weak_impl( name ) ) \ |
---|
| 211 | return __weak_impl( name ) args; \ |
---|
| 212 | return dfl; \ |
---|
| 213 | } |
---|
| 214 | |
---|
| 215 | #endif |
---|
| 216 | /** @} */ |
---|
| 217 | |
---|
| 218 | /** @defgroup dbg Debugging infrastructure |
---|
| 219 | * @{ |
---|
| 220 | */ |
---|
| 221 | #ifndef ASSEMBLY |
---|
| 222 | |
---|
| 223 | /** @def DBG |
---|
| 224 | * |
---|
| 225 | * Print a debugging message. |
---|
| 226 | * |
---|
| 227 | * The debug level is set at build time by specifying the @c DEBUG= |
---|
| 228 | * parameter on the @c make command line. For example, to enable |
---|
| 229 | * debugging for the PCI bus functions (in pci.c) in a @c .dsk image |
---|
| 230 | * for the @c rtl8139 card, you could use the command line |
---|
| 231 | * |
---|
| 232 | * @code |
---|
| 233 | * |
---|
| 234 | * make bin/rtl8139.dsk DEBUG=pci |
---|
| 235 | * |
---|
| 236 | * @endcode |
---|
| 237 | * |
---|
| 238 | * This will enable the debugging statements (DBG()) in pci.c. If |
---|
| 239 | * debugging is not enabled, DBG() statements will be ignored. |
---|
| 240 | * |
---|
| 241 | * You can enable debugging in several objects simultaneously by |
---|
| 242 | * separating them with commas, as in |
---|
| 243 | * |
---|
| 244 | * @code |
---|
| 245 | * |
---|
| 246 | * make bin/rtl8139.dsk DEBUG=pci,buffer,heap |
---|
| 247 | * |
---|
| 248 | * @endcode |
---|
| 249 | * |
---|
| 250 | * You can increase the debugging level for an object by specifying it |
---|
| 251 | * with @c :N, where @c N is the level, as in |
---|
| 252 | * |
---|
| 253 | * @code |
---|
| 254 | * |
---|
| 255 | * make bin/rtl8139.dsk DEBUG=pci,buffer:2,heap |
---|
| 256 | * |
---|
| 257 | * @endcode |
---|
| 258 | * |
---|
| 259 | * which would enable debugging for the PCI, buffer-handling and |
---|
| 260 | * heap-allocation code, with the buffer-handling code at level 2. |
---|
| 261 | * |
---|
| 262 | */ |
---|
| 263 | |
---|
| 264 | /* |
---|
| 265 | * If debug_OBJECT is set to a true value, the macro DBG(...) will |
---|
| 266 | * expand to printf(...) when compiling OBJECT, and the symbol |
---|
| 267 | * DEBUG_LEVEL will be inserted into the object file. |
---|
| 268 | * |
---|
| 269 | */ |
---|
| 270 | #define DEBUG_SYMBOL PREFIX_OBJECT ( debug_ ) |
---|
| 271 | |
---|
| 272 | /** printf() for debugging |
---|
| 273 | * |
---|
| 274 | * This function exists so that the DBG() macros can expand to |
---|
| 275 | * printf() calls without dragging the printf() prototype into scope. |
---|
| 276 | * |
---|
| 277 | * As far as the compiler is concerned, dbg_printf() and printf() are |
---|
| 278 | * completely unrelated calls; it's only at the assembly stage that |
---|
| 279 | * references to the dbg_printf symbol are collapsed into references |
---|
| 280 | * to the printf symbol. |
---|
| 281 | */ |
---|
| 282 | extern int __attribute__ (( format ( printf, 1, 2 ) )) |
---|
| 283 | dbg_printf ( const char *fmt, ... ) asm ( "printf" ); |
---|
| 284 | |
---|
| 285 | extern void dbg_autocolourise ( unsigned long id ); |
---|
| 286 | extern void dbg_decolourise ( void ); |
---|
| 287 | extern void dbg_hex_dump_da ( unsigned long dispaddr, |
---|
| 288 | const void *data, unsigned long len ); |
---|
| 289 | |
---|
| 290 | #if DEBUG_SYMBOL |
---|
| 291 | #define DBGLVL_MAX DEBUG_SYMBOL |
---|
| 292 | #else |
---|
| 293 | #define DBGLVL_MAX 0 |
---|
| 294 | #endif |
---|
| 295 | |
---|
| 296 | /* Allow for selective disabling of enabled debug levels */ |
---|
| 297 | #if DBGLVL_MAX |
---|
| 298 | int __debug_disable; |
---|
| 299 | #define DBGLVL ( DBGLVL_MAX & ~__debug_disable ) |
---|
| 300 | #define DBG_DISABLE( level ) do { \ |
---|
| 301 | __debug_disable |= ( (level) & DBGLVL_MAX ); \ |
---|
| 302 | } while ( 0 ) |
---|
| 303 | #define DBG_ENABLE( level ) do { \ |
---|
| 304 | __debug_disable &= ~( (level) & DBGLVL_MAX ); \ |
---|
| 305 | } while ( 0 ) |
---|
| 306 | #else |
---|
| 307 | #define DBGLVL 0 |
---|
| 308 | #define DBG_DISABLE( level ) do { } while ( 0 ) |
---|
| 309 | #define DBG_ENABLE( level ) do { } while ( 0 ) |
---|
| 310 | #endif |
---|
| 311 | |
---|
| 312 | #define DBGLVL_LOG 1 |
---|
| 313 | #define DBG_LOG ( DBGLVL & DBGLVL_LOG ) |
---|
| 314 | #define DBGLVL_EXTRA 2 |
---|
| 315 | #define DBG_EXTRA ( DBGLVL & DBGLVL_EXTRA ) |
---|
| 316 | #define DBGLVL_PROFILE 4 |
---|
| 317 | #define DBG_PROFILE ( DBGLVL & DBGLVL_PROFILE ) |
---|
| 318 | #define DBGLVL_IO 8 |
---|
| 319 | #define DBG_IO ( DBGLVL & DBGLVL_IO ) |
---|
| 320 | |
---|
| 321 | /** |
---|
| 322 | * Print debugging message if we are at a certain debug level |
---|
| 323 | * |
---|
| 324 | * @v level Debug level |
---|
| 325 | * @v ... printf() argument list |
---|
| 326 | */ |
---|
| 327 | #define DBG_IF( level, ... ) do { \ |
---|
| 328 | if ( DBG_ ## level ) { \ |
---|
| 329 | dbg_printf ( __VA_ARGS__ ); \ |
---|
| 330 | } \ |
---|
| 331 | } while ( 0 ) |
---|
| 332 | |
---|
| 333 | /** |
---|
| 334 | * Print a hex dump if we are at a certain debug level |
---|
| 335 | * |
---|
| 336 | * @v level Debug level |
---|
| 337 | * @v dispaddr Display address |
---|
| 338 | * @v data Data to print |
---|
| 339 | * @v len Length of data |
---|
| 340 | */ |
---|
| 341 | #define DBG_HDA_IF( level, dispaddr, data, len ) do { \ |
---|
| 342 | if ( DBG_ ## level ) { \ |
---|
| 343 | union { \ |
---|
| 344 | unsigned long ul; \ |
---|
| 345 | typeof ( dispaddr ) raw; \ |
---|
| 346 | } da; \ |
---|
| 347 | da.raw = dispaddr; \ |
---|
| 348 | dbg_hex_dump_da ( da.ul, data, len ); \ |
---|
| 349 | } \ |
---|
| 350 | } while ( 0 ) |
---|
| 351 | |
---|
| 352 | /** |
---|
| 353 | * Print a hex dump if we are at a certain debug level |
---|
| 354 | * |
---|
| 355 | * @v level Debug level |
---|
| 356 | * @v data Data to print |
---|
| 357 | * @v len Length of data |
---|
| 358 | */ |
---|
| 359 | #define DBG_HD_IF( level, data, len ) do { \ |
---|
| 360 | const void *_data = data; \ |
---|
| 361 | DBG_HDA_IF ( level, _data, _data, len ); \ |
---|
| 362 | } while ( 0 ) |
---|
| 363 | |
---|
| 364 | /** |
---|
| 365 | * Select colour for debug messages if we are at a certain debug level |
---|
| 366 | * |
---|
| 367 | * @v level Debug level |
---|
| 368 | * @v id Message stream ID |
---|
| 369 | */ |
---|
| 370 | #define DBG_AC_IF( level, id ) do { \ |
---|
| 371 | if ( DBG_ ## level ) { \ |
---|
| 372 | union { \ |
---|
| 373 | unsigned long ul; \ |
---|
| 374 | typeof ( id ) raw; \ |
---|
| 375 | } dbg_stream; \ |
---|
| 376 | dbg_stream.raw = id; \ |
---|
| 377 | dbg_autocolourise ( dbg_stream.ul ); \ |
---|
| 378 | } \ |
---|
| 379 | } while ( 0 ) |
---|
| 380 | |
---|
| 381 | /** |
---|
| 382 | * Revert colour for debug messages if we are at a certain debug level |
---|
| 383 | * |
---|
| 384 | * @v level Debug level |
---|
| 385 | */ |
---|
| 386 | #define DBG_DC_IF( level ) do { \ |
---|
| 387 | if ( DBG_ ## level ) { \ |
---|
| 388 | dbg_decolourise(); \ |
---|
| 389 | } \ |
---|
| 390 | } while ( 0 ) |
---|
| 391 | |
---|
| 392 | /* Autocolourising versions of the DBGxxx_IF() macros */ |
---|
| 393 | |
---|
| 394 | #define DBGC_IF( level, id, ... ) do { \ |
---|
| 395 | DBG_AC_IF ( level, id ); \ |
---|
| 396 | DBG_IF ( level, __VA_ARGS__ ); \ |
---|
| 397 | DBG_DC_IF ( level ); \ |
---|
| 398 | } while ( 0 ) |
---|
| 399 | |
---|
| 400 | #define DBGC_HDA_IF( level, id, ... ) do { \ |
---|
| 401 | DBG_AC_IF ( level, id ); \ |
---|
| 402 | DBG_HDA_IF ( level, __VA_ARGS__ ); \ |
---|
| 403 | DBG_DC_IF ( level ); \ |
---|
| 404 | } while ( 0 ) |
---|
| 405 | |
---|
| 406 | #define DBGC_HD_IF( level, id, ... ) do { \ |
---|
| 407 | DBG_AC_IF ( level, id ); \ |
---|
| 408 | DBG_HD_IF ( level, __VA_ARGS__ ); \ |
---|
| 409 | DBG_DC_IF ( level ); \ |
---|
| 410 | } while ( 0 ) |
---|
| 411 | |
---|
| 412 | /* Versions of the DBGxxx_IF() macros that imply DBGxxx_IF( LOG, ... )*/ |
---|
| 413 | |
---|
| 414 | #define DBG( ... ) DBG_IF ( LOG, __VA_ARGS__ ) |
---|
| 415 | #define DBG_HDA( ... ) DBG_HDA_IF ( LOG, __VA_ARGS__ ) |
---|
| 416 | #define DBG_HD( ... ) DBG_HD_IF ( LOG, __VA_ARGS__ ) |
---|
| 417 | #define DBGC( ... ) DBGC_IF ( LOG, __VA_ARGS__ ) |
---|
| 418 | #define DBGC_HDA( ... ) DBGC_HDA_IF ( LOG, __VA_ARGS__ ) |
---|
| 419 | #define DBGC_HD( ... ) DBGC_HD_IF ( LOG, __VA_ARGS__ ) |
---|
| 420 | |
---|
| 421 | /* Versions of the DBGxxx_IF() macros that imply DBGxxx_IF( EXTRA, ... )*/ |
---|
| 422 | |
---|
| 423 | #define DBG2( ... ) DBG_IF ( EXTRA, __VA_ARGS__ ) |
---|
| 424 | #define DBG2_HDA( ... ) DBG_HDA_IF ( EXTRA, __VA_ARGS__ ) |
---|
| 425 | #define DBG2_HD( ... ) DBG_HD_IF ( EXTRA, __VA_ARGS__ ) |
---|
| 426 | #define DBGC2( ... ) DBGC_IF ( EXTRA, __VA_ARGS__ ) |
---|
| 427 | #define DBGC2_HDA( ... ) DBGC_HDA_IF ( EXTRA, __VA_ARGS__ ) |
---|
| 428 | #define DBGC2_HD( ... ) DBGC_HD_IF ( EXTRA, __VA_ARGS__ ) |
---|
| 429 | |
---|
| 430 | /* Versions of the DBGxxx_IF() macros that imply DBGxxx_IF( PROFILE, ... )*/ |
---|
| 431 | |
---|
| 432 | #define DBGP( ... ) DBG_IF ( PROFILE, __VA_ARGS__ ) |
---|
| 433 | #define DBGP_HDA( ... ) DBG_HDA_IF ( PROFILE, __VA_ARGS__ ) |
---|
| 434 | #define DBGP_HD( ... ) DBG_HD_IF ( PROFILE, __VA_ARGS__ ) |
---|
| 435 | #define DBGCP( ... ) DBGC_IF ( PROFILE, __VA_ARGS__ ) |
---|
| 436 | #define DBGCP_HDA( ... ) DBGC_HDA_IF ( PROFILE, __VA_ARGS__ ) |
---|
| 437 | #define DBGCP_HD( ... ) DBGC_HD_IF ( PROFILE, __VA_ARGS__ ) |
---|
| 438 | |
---|
| 439 | /* Versions of the DBGxxx_IF() macros that imply DBGxxx_IF( IO, ... )*/ |
---|
| 440 | |
---|
| 441 | #define DBGIO( ... ) DBG_IF ( IO, __VA_ARGS__ ) |
---|
| 442 | #define DBGIO_HDA( ... ) DBG_HDA_IF ( IO, __VA_ARGS__ ) |
---|
| 443 | #define DBGIO_HD( ... ) DBG_HD_IF ( IO, __VA_ARGS__ ) |
---|
| 444 | #define DBGCIO( ... ) DBGC_IF ( IO, __VA_ARGS__ ) |
---|
| 445 | #define DBGCIO_HDA( ... ) DBGC_HDA_IF ( IO, __VA_ARGS__ ) |
---|
| 446 | #define DBGCIO_HD( ... ) DBGC_HD_IF ( IO, __VA_ARGS__ ) |
---|
| 447 | |
---|
| 448 | |
---|
| 449 | #if DEBUG_SYMBOL == 0 |
---|
| 450 | #define NDEBUG |
---|
| 451 | #endif |
---|
| 452 | |
---|
| 453 | #endif /* ASSEMBLY */ |
---|
| 454 | /** @} */ |
---|
| 455 | |
---|
| 456 | /** @defgroup attrs Miscellaneous attributes |
---|
| 457 | * @{ |
---|
| 458 | */ |
---|
| 459 | #ifndef ASSEMBLY |
---|
| 460 | |
---|
| 461 | /** Declare a data structure as packed. */ |
---|
| 462 | #define PACKED __attribute__ (( packed )) |
---|
| 463 | |
---|
| 464 | /** Declare a variable or data structure as unused. */ |
---|
| 465 | #define __unused __attribute__ (( unused )) |
---|
| 466 | |
---|
| 467 | /** |
---|
| 468 | * Declare a function as pure - i.e. without side effects |
---|
| 469 | */ |
---|
| 470 | #define __pure __attribute__ (( pure )) |
---|
| 471 | |
---|
| 472 | /** |
---|
| 473 | * Declare a function as const - i.e. it does not access global memory |
---|
| 474 | * (including dereferencing pointers passed to it) at all. |
---|
| 475 | * Must also not call any non-const functions. |
---|
| 476 | */ |
---|
| 477 | #define __const __attribute__ (( const )) |
---|
| 478 | |
---|
| 479 | /** |
---|
| 480 | * Declare a function's pointer parameters as non-null - i.e. force |
---|
| 481 | * compiler to check pointers at compile time and enable possible |
---|
| 482 | * optimizations based on that fact |
---|
| 483 | */ |
---|
| 484 | #define __nonnull __attribute__ (( nonnull )) |
---|
| 485 | |
---|
| 486 | /** |
---|
| 487 | * Declare a pointer returned by a function as a unique memory address |
---|
| 488 | * as returned by malloc-type functions. |
---|
| 489 | */ |
---|
| 490 | #define __malloc __attribute__ (( malloc )) |
---|
| 491 | |
---|
| 492 | /** |
---|
| 493 | * Declare a function as used. |
---|
| 494 | * |
---|
| 495 | * Necessary only if the function is called only from assembler code. |
---|
| 496 | */ |
---|
| 497 | #define __used __attribute__ (( used )) |
---|
| 498 | |
---|
| 499 | /** Declare a data structure to be aligned with 16-byte alignment */ |
---|
| 500 | #define __aligned __attribute__ (( aligned ( 16 ) )) |
---|
| 501 | |
---|
| 502 | /** Declare a function to be always inline */ |
---|
| 503 | #define __always_inline __attribute__ (( always_inline )) |
---|
| 504 | |
---|
| 505 | /** |
---|
| 506 | * Shared data. |
---|
| 507 | * |
---|
| 508 | * To save space in the binary when multiple-driver images are |
---|
| 509 | * compiled, uninitialised data areas can be shared between drivers. |
---|
| 510 | * This will typically be used to share statically-allocated receive |
---|
| 511 | * and transmit buffers between drivers. |
---|
| 512 | * |
---|
| 513 | * Use as e.g. |
---|
| 514 | * |
---|
| 515 | * @code |
---|
| 516 | * |
---|
| 517 | * struct { |
---|
| 518 | * char rx_buf[NUM_RX_BUF][RX_BUF_SIZE]; |
---|
| 519 | * char tx_buf[TX_BUF_SIZE]; |
---|
| 520 | * } my_static_data __shared; |
---|
| 521 | * |
---|
| 522 | * @endcode |
---|
| 523 | * |
---|
| 524 | */ |
---|
| 525 | #define __shared __asm__ ( "_shared_bss" ) __aligned |
---|
| 526 | |
---|
| 527 | #endif /* ASSEMBLY */ |
---|
| 528 | /** @} */ |
---|
| 529 | |
---|
| 530 | /** |
---|
| 531 | * Optimisation barrier |
---|
| 532 | */ |
---|
| 533 | #ifndef ASSEMBLY |
---|
| 534 | #define barrier() __asm__ __volatile__ ( "" : : : "memory" ) |
---|
| 535 | #endif /* ASSEMBLY */ |
---|
| 536 | |
---|
| 537 | /** |
---|
| 538 | * @defgroup licences Licence declarations |
---|
| 539 | * |
---|
| 540 | * For reasons that are partly historical, various different files |
---|
| 541 | * within the gPXE codebase have differing licences. |
---|
| 542 | * |
---|
| 543 | * @{ |
---|
| 544 | */ |
---|
| 545 | |
---|
| 546 | /** Declare a file as being in the public domain |
---|
| 547 | * |
---|
| 548 | * This licence declaration is applicable when a file states itself to |
---|
| 549 | * be in the public domain. |
---|
| 550 | */ |
---|
| 551 | #define FILE_LICENCE_PUBLIC_DOMAIN \ |
---|
| 552 | PROVIDE_SYMBOL ( __licence_public_domain ) |
---|
| 553 | |
---|
| 554 | /** Declare a file as being under version 2 (or later) of the GNU GPL |
---|
| 555 | * |
---|
| 556 | * This licence declaration is applicable when a file states itself to |
---|
| 557 | * be licensed under the GNU GPL; "either version 2 of the License, or |
---|
| 558 | * (at your option) any later version". |
---|
| 559 | */ |
---|
| 560 | #define FILE_LICENCE_GPL2_OR_LATER \ |
---|
| 561 | PROVIDE_SYMBOL ( __licence_gpl2_or_later ) |
---|
| 562 | |
---|
| 563 | /** Declare a file as being under version 2 of the GNU GPL |
---|
| 564 | * |
---|
| 565 | * This licence declaration is applicable when a file states itself to |
---|
| 566 | * be licensed under version 2 of the GPL, and does not include the |
---|
| 567 | * "or, at your option, any later version" clause. |
---|
| 568 | */ |
---|
| 569 | #define FILE_LICENCE_GPL2_ONLY \ |
---|
| 570 | PROVIDE_SYMBOL ( __licence_gpl2_only ) |
---|
| 571 | |
---|
| 572 | /** Declare a file as being under any version of the GNU GPL |
---|
| 573 | * |
---|
| 574 | * This licence declaration is applicable when a file states itself to |
---|
| 575 | * be licensed under the GPL, but does not specify a version. |
---|
| 576 | * |
---|
| 577 | * According to section 9 of the GPLv2, "If the Program does not |
---|
| 578 | * specify a version number of this License, you may choose any |
---|
| 579 | * version ever published by the Free Software Foundation". |
---|
| 580 | */ |
---|
| 581 | #define FILE_LICENCE_GPL_ANY \ |
---|
| 582 | PROVIDE_SYMBOL ( __licence_gpl_any ) |
---|
| 583 | |
---|
| 584 | /** Declare a file as being under the three-clause BSD licence |
---|
| 585 | * |
---|
| 586 | * This licence declaration is applicable when a file states itself to |
---|
| 587 | * be licensed under terms allowing redistribution in source and |
---|
| 588 | * binary forms (with or without modification) provided that: |
---|
| 589 | * |
---|
| 590 | * redistributions of source code retain the copyright notice, |
---|
| 591 | * list of conditions and any attached disclaimers |
---|
| 592 | * |
---|
| 593 | * redistributions in binary form reproduce the copyright notice, |
---|
| 594 | * list of conditions and any attached disclaimers in the |
---|
| 595 | * documentation and/or other materials provided with the |
---|
| 596 | * distribution |
---|
| 597 | * |
---|
| 598 | * the name of the author is not used to endorse or promote |
---|
| 599 | * products derived from the software without specific prior |
---|
| 600 | * written permission |
---|
| 601 | * |
---|
| 602 | * It is not necessary for the file to explicitly state that it is |
---|
| 603 | * under a "BSD" licence; only that the licensing terms be |
---|
| 604 | * functionally equivalent to the standard three-clause BSD licence. |
---|
| 605 | */ |
---|
| 606 | #define FILE_LICENCE_BSD3 \ |
---|
| 607 | PROVIDE_SYMBOL ( __licence_bsd3 ) |
---|
| 608 | |
---|
| 609 | /** Declare a file as being under the two-clause BSD licence |
---|
| 610 | * |
---|
| 611 | * This licence declaration is applicable when a file states itself to |
---|
| 612 | * be licensed under terms allowing redistribution in source and |
---|
| 613 | * binary forms (with or without modification) provided that: |
---|
| 614 | * |
---|
| 615 | * redistributions of source code retain the copyright notice, |
---|
| 616 | * list of conditions and any attached disclaimers |
---|
| 617 | * |
---|
| 618 | * redistributions in binary form reproduce the copyright notice, |
---|
| 619 | * list of conditions and any attached disclaimers in the |
---|
| 620 | * documentation and/or other materials provided with the |
---|
| 621 | * distribution |
---|
| 622 | * |
---|
| 623 | * It is not necessary for the file to explicitly state that it is |
---|
| 624 | * under a "BSD" licence; only that the licensing terms be |
---|
| 625 | * functionally equivalent to the standard two-clause BSD licence. |
---|
| 626 | */ |
---|
| 627 | #define FILE_LICENCE_BSD2 \ |
---|
| 628 | PROVIDE_SYMBOL ( __licence_bsd2 ) |
---|
| 629 | |
---|
| 630 | /** Declare a file as being under the one-clause MIT-style licence |
---|
| 631 | * |
---|
| 632 | * This licence declaration is applicable when a file states itself to |
---|
| 633 | * be licensed under terms allowing redistribution for any purpose |
---|
| 634 | * with or without fee, provided that the copyright notice and |
---|
| 635 | * permission notice appear in all copies. |
---|
| 636 | */ |
---|
| 637 | #define FILE_LICENCE_MIT \ |
---|
| 638 | PROVIDE_SYMBOL ( __licence_mit ) |
---|
| 639 | |
---|
| 640 | /** Declare a particular licence as applying to a file */ |
---|
| 641 | #define FILE_LICENCE( _licence ) FILE_LICENCE_ ## _licence |
---|
| 642 | |
---|
| 643 | /** @} */ |
---|
| 644 | |
---|
| 645 | /* This file itself is under GPLv2-or-later */ |
---|
| 646 | FILE_LICENCE ( GPL2_OR_LATER ); |
---|
| 647 | |
---|
| 648 | #include <bits/compiler.h> |
---|
| 649 | |
---|
| 650 | #endif /* COMPILER_H */ |
---|