#ifndef __MIDIMCAST_H__ #define __MIDIMCAST_H__ #include #include #include #include #include #include #define debug(FMT, ...) \ if (midimcast_debug) { \ fprintf(stderr, \ "[DEBUG] %s:%u:%s: " FMT "\n", \ __FILE__, \ __LINE__, \ __func__ __VA_OPT__(,) \ __VA_ARGS__); \ } #define warn(FMT, ...) \ fprintf(stderr, "[WARNING] %s:%u:%s: " FMT "\n", \ __FILE__, \ __LINE__, \ __func__ __VA_OPT__(,) \ __VA_ARGS__); #define err(FMT, ...) \ ({ \ fprintf(stderr, "[ERROR] %s:%u:%s: " FMT "\n", \ __FILE__, \ __LINE__, \ __func__ __VA_OPT__(,) \ __VA_ARGS__); \ exit(EXIT_FAILURE); \ }) #define err_std_nchk(CALLEE) \ ({ \ fprintf(stderr, "[ERROR] %s:%u:%s:%s: %s\n", \ __FILE__, \ __LINE__, \ __func__, \ #CALLEE, \ strerror(errno)); \ exit(EXIT_FAILURE); \ }) #define err_std(CALLEE, ...) \ if (CALLEE(__VA_ARGS__)) \ err_std_nchk(CALLEE); #define err_std_neg(CALLEE, ...) \ ({ \ const typeof(CALLEE(__VA_ARGS__)) ret = \ CALLEE(__VA_ARGS__); \ if (ret < 0) \ err_std_nchk(CALLEE); \ ret; \ }) #define err_std_null(CALLEE, ...) \ ({ \ const typeof(CALLEE(__VA_ARGS__)) ret = \ CALLEE(__VA_ARGS__); \ if (!ret) \ err_std_nchk(CALLEE); \ ret; \ }) #define err_snd_nchk(CALLEE, ERR) \ ({ \ fprintf(stderr, "[ERROR] %s:%u:%s:%s: %s\n", \ __FILE__, \ __LINE__, \ __func__, \ #CALLEE, \ snd_strerror(ERR)); \ exit(EXIT_FAILURE); \ }) #define err_snd(CALLEE, ...) \ ({ \ const int err = CALLEE(__VA_ARGS__); \ if (err) \ err_snd_nchk(CALLEE, err); \ }) #define err_snd_neg(CALLEE, ...) \ ({ \ const typeof(CALLEE(__VA_ARGS__)) ret \ = CALLEE(__VA_ARGS__); \ if (ret < 0) \ err_snd_nchk(CALLEE, ret); \ ret; \ }) struct msg { uint64_t ts; uint8_t midi[0x10]; // Large enough buffer } __attribute__((packed)); extern uint64_t now(); extern bool midimcast_debug; void env_read_common(const char **const mcast_group, uint16_t *const mcast_port); #endif