struct inject_site {
const char *name;
const char *desc;
enum inject_kind kind;
_Atomic bool armed;
_Atomic uint32_t seed;
_Atomic uint32_t nth;
_Atomic uint32_t counter;
};
enum inject_kind {
INJECT_KIND_DELAY = 1,
INJECT_KIND_FAIL = 1 << 1,
};
void inject_arm(struct inject_site *s, uint32_t seed, uint32_t nth);
void inject_disarm(struct inject_site *s);
void inject_delay_impl(struct inject_site *s);
#define INJECT_SITE_ATTRIBUTE \
__attribute__((section(".kernel_inject_sites"), used))
#define INJECT_SITE_DECLARE(id, injkind, description) \
INJECT_SITE_ATTRIBUTE struct inject_site __inject_site_##id = { \
.name = #id, .desc = (description), .kind = (injkind)}
#define INJECT_SITE_DEFINE(id) extern struct inject_site __inject_site_##id
#define INJECT_SITE(id) (&__inject_site_##id)
#define INJECT_DELAY(id) \
do { \
if (unlikely(atomic_load_explicit(&INJECT_SITE(id)->armed, \
memory_order_relaxed))) \
inject_delay_impl(INJECT_SITE(id)); \
} while (0)
#define INJECT_FAIL(id) \
(unlikely(atomic_load_explicit(&INJECT_SITE(id)->armed, \
memory_order_relaxed)) && \
inject_fail_impl(INJECT_SITE(id)))
#define INJECT_DELAY(id) ((void) 0)
#define INJECT_FAIL(id) (false)