solidc
Robust collection of general-purpose cross-platform C libraries and data structures designed for rapid and safe development in C
Loading...
Searching...
No Matches
Macros
macros.h File Reference

Portable utility macros for assertions, memory, math, iteration, timing, and platform compatibility. More...

#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
Include dependency graph for macros.h:
This graph shows which files directly or indirectly include this file:

Go to the source code of this file.

Macros

#define LIKELY(x)   (x)
 
#define WARN_UNUSED_RESULT
 
#define PRINTF_FORMAT(fmt, va)
 
#define NORETURN
 
#define UNUSED(x)   ((void)(x))
 
#define STATIC_ASSERT(cond, msg)   typedef char _static_assert_##__LINE__[(cond) ? 1 : -1]
 
#define ASSERT(cond)
 
#define ASSERT_TRUE(cond)   ASSERT(cond)
 
#define ASSERT_NULL(ptr)
 
#define ASSERT_NOT_NULL(ptr)
 
#define ASSERT_STR_EQ(a, b)
 
#define ASSERT_FLOAT_EQ(a, b, epsilon)
 
#define IS_POWER_OF_2(n)   ((n) > 0 && (((n) & ((n) - 1)) == 0))
 
#define STATIC_CHECK_POWER_OF_2(n)   STATIC_ASSERT(IS_POWER_OF_2(n), #n " must be a power of 2")
 
#define ARRAY_SIZE(arr)   (sizeof(arr) / sizeof((arr)[0]))
 
#define ZERO_MEMORY(ptr, size)   memset((ptr), 0, (size))
 
#define ZERO_STRUCT(s)   memset(&(s), 0, sizeof(s))
 
#define ZERO_ARRAY(arr)   memset((arr), 0, sizeof(arr))
 
#define MIN(a, b)   ((a) < (b) ? (a) : (b))
 
#define MAX(a, b)   ((a) > (b) ? (a) : (b))
 
#define ABS(x)   ((x) < 0 ? -(x) : (x))
 
#define CLAMP(x, lo, hi)   (MIN(MAX((x), (lo)), (hi)))
 
#define SET_BIT(v, pos)   ((v) |= (1ULL << (pos)))
 
#define CLEAR_BIT(v, pos)   ((v) &= ~(1ULL << (pos)))
 
#define TOGGLE_BIT(v, pos)   ((v) ^= (1ULL << (pos)))
 
#define CHECK_BIT(v, pos)   (((v) >> (pos)) & 1U)
 
#define ALIGN_UP(x, align)   (((x) + (align) - 1) & ~((align) - 1))
 
#define ALIGN_DOWN(x, align)   ((x) & ~((align) - 1))
 
#define IS_ALIGNED(x, align)   (((x) & ((align) - 1)) == 0)
 
#define STREQ(a, b)   (strcmp((a), (b)) == 0)
 
#define STRNEQ(a, b, n)   (strncmp((a), (b), (n)) == 0)
 
#define STR_EMPTY(s)   ((s) == NULL || (s)[0] == '\0')
 
#define STR_NOT_EMPTY(s)   ((s) != NULL && (s)[0] != '\0')
 
#define DEBUG_PRINT(fmt, ...)   printf("[DEBUG] %s:%d: " fmt "\n", __FILE__, __LINE__, ##__VA_ARGS__)
 
#define DEBUG_VAR(var)   printf("[DEBUG] %s:%d: %s = %td\n", __FILE__, __LINE__, #var, (ptrdiff_t)(var))
 
#define DEBUG_STR(str)   printf("[DEBUG] %s:%d: %s = \"%s\"\n", __FILE__, __LINE__, #str, (str) ? (str) : "(null)")
 
#define LOG_ERROR(fmt, ...)    fprintf(stderr, "[ERROR] %s:%d [%s]: " fmt "\n", __FILE__, __LINE__, __func__, ##__VA_ARGS__)
 
#define LOG_WARN(fmt, ...)   fprintf(stderr, "[WARN] %s:%d [%s]: " fmt "\n", __FILE__, __LINE__, __func__, ##__VA_ARGS__)
 
#define LOG_INFO(fmt, ...)   printf("[INFO] %s:%d [%s]: " fmt "\n", __FILE__, __LINE__, __func__, ##__VA_ARGS__)
 
#define FOR_EACH_ARRAY(item, array)
 
#define TIME_DIFF(start, end)    ((double)((end).tv_sec - (start).tv_sec) + (double)((end).tv_nsec - (start).tv_nsec) / 1.0e9)
 
#define TIME_DIFF_MS(start, end)    ((double)((end).tv_sec - (start).tv_sec) * 1000.0 + (double)((end).tv_nsec - (start).tv_nsec) / 1.0e6)
 

Detailed Description

Portable utility macros for assertions, memory, math, iteration, timing, and platform compatibility.

Supports: GCC, Clang, MSVC (C11 / C17). All macros are safe for use in C and C++ translation units.

Portability notes:

Definition in file macros.h.

Macro Definition Documentation

◆ ABS

#define ABS (   x)    ((x) < 0 ? -(x) : (x))

ABS(x) — absolute value without pulling in <math.h>.

Definition at line 388 of file macros.h.

◆ ALIGN_DOWN

#define ALIGN_DOWN (   x,
  align 
)    ((x) & ~((align) - 1))

ALIGN_DOWN(x, align) — round x down to the previous multiple of align.

Definition at line 419 of file macros.h.

◆ ALIGN_UP

#define ALIGN_UP (   x,
  align 
)    (((x) + (align) - 1) & ~((align) - 1))

ALIGN_UP(x, align) — round x up to the next multiple of align.

Definition at line 416 of file macros.h.

◆ ARRAY_SIZE

#define ARRAY_SIZE (   arr)    (sizeof(arr) / sizeof((arr)[0]))

ARRAY_SIZE(arr) — number of elements in a stack-allocated array.

Definition at line 366 of file macros.h.

◆ ASSERT

#define ASSERT (   cond)
Value:
do { \
if (UNLIKELY(!(cond))) { \
fprintf(stderr, "%s:%d [%s]: Assertion '%s' failed.\n", __FILE__, __LINE__, __func__, #cond); \
exit(1); \
} \
} while (0)

ASSERT(cond) — abort if cond is false.

Definition at line 138 of file macros.h.

◆ ASSERT_FLOAT_EQ

#define ASSERT_FLOAT_EQ (   a,
  b,
  epsilon 
)
Value:
do { \
double _afe_a = (double)(a); \
double _afe_b = (double)(b); \
double _afe_eps = (double)(epsilon); \
double _afe_d = _afe_a - _afe_b; \
/* Use manual abs to avoid pulling in <math.h> for fabs. */ \
if ((_afe_d > _afe_eps) || (-_afe_d > _afe_eps)) { \
fprintf(stderr, \
"%s:%d [%s]: Float '%s == %s' failed" \
" (%.6f != %.6f, eps=%.6f).\n", \
__FILE__, __LINE__, __func__, #a, #b, _afe_a, _afe_b, _afe_eps); \
exit(1); \
} \
} while (0)

ASSERT_FLOAT_EQ(a, b, epsilon) — abort if |a - b| > epsilon. Both operands are promoted to double for the comparison.

Definition at line 192 of file macros.h.

◆ ASSERT_NOT_NULL

#define ASSERT_NOT_NULL (   ptr)
Value:
do { \
if (UNLIKELY((ptr) == NULL)) { \
fprintf(stderr, "%s:%d [%s]: Expected '%s' to not be NULL.\n", __FILE__, __LINE__, __func__, #ptr); \
exit(1); \
} \
} while (0)

ASSERT_NOT_NULL(ptr) — abort if ptr is NULL.

Definition at line 159 of file macros.h.

◆ ASSERT_NULL

#define ASSERT_NULL (   ptr)
Value:
do { \
if (UNLIKELY((ptr) != NULL)) { \
fprintf(stderr, "%s:%d [%s]: Expected '%s' to be NULL.\n", __FILE__, __LINE__, __func__, #ptr); \
exit(1); \
} \
} while (0)

ASSERT_NULL(ptr) — abort if ptr is not NULL.

Definition at line 150 of file macros.h.

◆ ASSERT_STR_EQ

#define ASSERT_STR_EQ (   a,
 
)
Value:
do { \
const char* _ase_a = (a); \
const char* _ase_b = (b); \
if (_ase_a == NULL || _ase_b == NULL) { \
if (_ase_a != _ase_b) { \
fprintf(stderr, "%s:%d [%s]: '%s == %s' failed (one is NULL).\n", __FILE__, __LINE__, __func__, #a, \
#b); \
exit(1); \
} \
} else if (strcmp(_ase_a, _ase_b) != 0) { \
fprintf(stderr, "%s:%d [%s]: '%s == %s' failed (\"%s\" != \"%s\").\n", __FILE__, __LINE__, __func__, #a, \
#b, _ase_a, _ase_b); \
exit(1); \
} \
} while (0)

ASSERT_STR_EQ(a, b) — abort if two C strings are not equal. Handles NULL on either side gracefully.

Definition at line 171 of file macros.h.

◆ ASSERT_TRUE

#define ASSERT_TRUE (   cond)    ASSERT(cond)

ASSERT_TRUE(cond) — alias for ASSERT; documents boolean intent.

Definition at line 147 of file macros.h.

◆ CHECK_BIT

#define CHECK_BIT (   v,
  pos 
)    (((v) >> (pos)) & 1U)

CHECK_BIT(v, pos) — evaluate to 1 if bit pos is set in v, else 0.

Definition at line 407 of file macros.h.

◆ CLAMP

#define CLAMP (   x,
  lo,
  hi 
)    (MIN(MAX((x), (lo)), (hi)))

CLAMP(x, lo, hi) — constrain x to [lo, hi].

Definition at line 391 of file macros.h.

◆ CLEAR_BIT

#define CLEAR_BIT (   v,
  pos 
)    ((v) &= ~(1ULL << (pos)))

CLEAR_BIT(v, pos) — clear bit at position pos in v.

Definition at line 401 of file macros.h.

◆ DEBUG_PRINT

#define DEBUG_PRINT (   fmt,
  ... 
)    printf("[DEBUG] %s:%d: " fmt "\n", __FILE__, __LINE__, ##__VA_ARGS__)

DEBUG_PRINT(fmt, ...) — print a formatted debug message with source location.

Definition at line 450 of file macros.h.

◆ DEBUG_STR

#define DEBUG_STR (   str)    printf("[DEBUG] %s:%d: %s = \"%s\"\n", __FILE__, __LINE__, #str, (str) ? (str) : "(null)")

DEBUG_STR(str) — print a string variable's name and value, handling NULL.

Definition at line 456 of file macros.h.

◆ DEBUG_VAR

#define DEBUG_VAR (   var)    printf("[DEBUG] %s:%d: %s = %td\n", __FILE__, __LINE__, #var, (ptrdiff_t)(var))

DEBUG_VAR(var) — print a scalar variable's name and value as a signed integer.

Definition at line 453 of file macros.h.

◆ FOR_EACH_ARRAY

#define FOR_EACH_ARRAY (   item,
  array 
)
Value:
for (void *item = (void*)(array), *_fea_end = (void*)((char*)(array) + sizeof(array)); item < _fea_end; \
item = (char*)item + (sizeof((array)[0])))

FOR_EACH_ARRAY — MSVC fallback using size_t index. item is a void* pointing to the current element; cast before use.

Example: FOR_EACH_ARRAY(i, arr, sizeof(arr[0])) { int n = (int)item; }

Prefer the three-argument variant when element size is not obvious.

Definition at line 516 of file macros.h.

◆ IS_ALIGNED

#define IS_ALIGNED (   x,
  align 
)    (((x) & ((align) - 1)) == 0)

IS_ALIGNED(x, align) — evaluate to 1 if x is a multiple of align.

Definition at line 422 of file macros.h.

◆ IS_POWER_OF_2

#define IS_POWER_OF_2 (   n)    ((n) > 0 && (((n) & ((n) - 1)) == 0))

IS_POWER_OF_2(n) — evaluates to 1 if n is a power of two, 0 otherwise.

Definition at line 321 of file macros.h.

◆ LIKELY

#define LIKELY (   x)    (x)

Hint that a condition is likely true (branch prediction).

Definition at line 66 of file macros.h.

◆ LOG_ERROR

#define LOG_ERROR (   fmt,
  ... 
)     fprintf(stderr, "[ERROR] %s:%d [%s]: " fmt "\n", __FILE__, __LINE__, __func__, ##__VA_ARGS__)

LOG_ERROR(fmt, ...) — print an error message to stderr (always active).

Definition at line 467 of file macros.h.

◆ LOG_INFO

#define LOG_INFO (   fmt,
  ... 
)    printf("[INFO] %s:%d [%s]: " fmt "\n", __FILE__, __LINE__, __func__, ##__VA_ARGS__)

LOG_INFO(fmt, ...) — print an informational message to stdout (always active).

Definition at line 474 of file macros.h.

◆ LOG_WARN

#define LOG_WARN (   fmt,
  ... 
)    fprintf(stderr, "[WARN] %s:%d [%s]: " fmt "\n", __FILE__, __LINE__, __func__, ##__VA_ARGS__)

LOG_WARN(fmt, ...) — print a warning to stderr (always active).

Definition at line 471 of file macros.h.

◆ MAX

#define MAX (   a,
 
)    ((a) > (b) ? (a) : (b))

MAX(a, b) — maximum of two scalar values (evaluates each argument once).

Definition at line 385 of file macros.h.

◆ MIN

#define MIN (   a,
 
)    ((a) < (b) ? (a) : (b))

MIN(a, b) — minimum of two scalar values (evaluates each argument once).

Definition at line 382 of file macros.h.

◆ NORETURN

#define NORETURN

NORETURN — annotate functions that never return (abort, exit wrappers).

Definition at line 99 of file macros.h.

◆ PRINTF_FORMAT

#define PRINTF_FORMAT (   fmt,
  va 
)

PRINTF_FORMAT(fmt_idx, va_idx) — validate printf-style format strings at compile time (1-based argument indices). Example: void log(const char *fmt, ...) PRINTF_FORMAT(1, 2);

Definition at line 90 of file macros.h.

◆ SET_BIT

#define SET_BIT (   v,
  pos 
)    ((v) |= (1ULL << (pos)))

SET_BIT(v, pos) — set bit at position pos in v (0 = LSB).

Definition at line 398 of file macros.h.

◆ STATIC_ASSERT

#define STATIC_ASSERT (   cond,
  msg 
)    typedef char _static_assert_##__LINE__[(cond) ? 1 : -1]

STATIC_ASSERT(cond, msg) — compile-time assertion with a descriptive message.

Definition at line 125 of file macros.h.

◆ STATIC_CHECK_POWER_OF_2

#define STATIC_CHECK_POWER_OF_2 (   n)    STATIC_ASSERT(IS_POWER_OF_2(n), #n " must be a power of 2")

STATIC_CHECK_POWER_OF_2(n) — compile-time assertion that n is a power of two.

Definition at line 324 of file macros.h.

◆ STR_EMPTY

#define STR_EMPTY (   s)    ((s) == NULL || (s)[0] == '\0')

STR_EMPTY(s) — true if s is NULL or the empty string.

Definition at line 435 of file macros.h.

◆ STR_NOT_EMPTY

#define STR_NOT_EMPTY (   s)    ((s) != NULL && (s)[0] != '\0')

STR_NOT_EMPTY(s) — true if s is non-NULL and non-empty.

Definition at line 438 of file macros.h.

◆ STREQ

#define STREQ (   a,
 
)    (strcmp((a), (b)) == 0)

STREQ(a, b) — true if two C strings are equal.

Definition at line 429 of file macros.h.

◆ STRNEQ

#define STRNEQ (   a,
  b,
 
)    (strncmp((a), (b), (n)) == 0)

STRNEQ(a, b, n) — true if first n bytes of two C strings are equal.

Definition at line 432 of file macros.h.

◆ TIME_DIFF

#define TIME_DIFF (   start,
  end 
)     ((double)((end).tv_sec - (start).tv_sec) + (double)((end).tv_nsec - (start).tv_nsec) / 1.0e9)

TIME_DIFF(start, end) — elapsed seconds between two struct timespec values.

Definition at line 581 of file macros.h.

◆ TIME_DIFF_MS

#define TIME_DIFF_MS (   start,
  end 
)     ((double)((end).tv_sec - (start).tv_sec) * 1000.0 + (double)((end).tv_nsec - (start).tv_nsec) / 1.0e6)

TIME_DIFF_MS(start, end) — elapsed milliseconds between two struct timespec values.

Definition at line 588 of file macros.h.

◆ TOGGLE_BIT

#define TOGGLE_BIT (   v,
  pos 
)    ((v) ^= (1ULL << (pos)))

TOGGLE_BIT(v, pos) — flip bit at position pos in v.

Definition at line 404 of file macros.h.

◆ UNUSED

#define UNUSED (   x)    ((void)(x))

UNUSED — silence "unused variable/parameter" warnings.

Definition at line 103 of file macros.h.

◆ WARN_UNUSED_RESULT

#define WARN_UNUSED_RESULT

WARN_UNUSED_RESULT — emit a compiler diagnostic if the return value of a function annotated with this attribute is discarded by the caller.

Definition at line 79 of file macros.h.

◆ ZERO_ARRAY

#define ZERO_ARRAY (   arr)    memset((arr), 0, sizeof(arr))

ZERO_ARRAY(arr) — zero an entire stack-allocated array.

Definition at line 375 of file macros.h.

◆ ZERO_MEMORY

#define ZERO_MEMORY (   ptr,
  size 
)    memset((ptr), 0, (size))

ZERO_MEMORY(ptr, size) — zero size bytes starting at ptr.

Definition at line 369 of file macros.h.

◆ ZERO_STRUCT

#define ZERO_STRUCT (   s)    memset(&(s), 0, sizeof(s))

ZERO_STRUCT(s) — zero every byte of a struct variable s.

Definition at line 372 of file macros.h.