#include "../../examples/processors.h" #include #include #include #include static int destroyed; static xtc_result fail(double r, size_t n, const float *v, size_t c, void **s) { (void)r; (void)n; (void)v; (void)c; *s = NULL; return XTC_ERR_OUT_OF_MEMORY; } static void cleanup(void *s) { assert(!s); ++destroyed; } static xtc_result process_fail(void *s, const xtc_native_block *b) { (void)s; b->output[0] = 99; return XTC_ERR_UNSUPPORTED; } int main(void) { xtc_processor_descriptor d = example_effect(), bad; xtc_processor *p = NULL, *restored = NULL; float out[16], input[16]; size_t i, size; unsigned char state[XTC_PROCESSOR_STATE_MAX], broken[XTC_PROCESSOR_STATE_MAX]; xtc_native_block b = {input, out, 16, 0, NULL, 0}; xtc_parameter_event e[] = {{0,1,.5f},{7,1,1},{7,1,2}}; for (i = 0; i < 16; ++i) input[i] = 1; bad = d; bad.abi_version = 99; assert(xtc_processor_validate(&bad) == XTC_ERR_UNSUPPORTED); bad = d; bad.parameters[0].default_value = NAN; assert(xtc_processor_validate(&bad) != XTC_OK); bad = d; bad.prepare = fail; bad.destroy = cleanup; assert(xtc_processor_create(&bad,48000,16,&p) == XTC_ERR_OUT_OF_MEMORY && !p && destroyed == 1); assert(xtc_processor_create(&d,48000,16,&p) == XTC_OK); assert(xtc_processor_process(p,&b,e,3) == XTC_OK); for (i = 0; i < 16; ++i) assert(out[i] == (i < 7 ? .5f : 2)); e[1].value = 3; out[0] = 123; assert(xtc_processor_process(p,&b,e,3) == XTC_ERR_INVALID_ARGUMENT && out[0] == 123); assert(xtc_processor_save(p,state,1,&size) == XTC_ERR_CAPACITY && size == 88); assert(xtc_processor_save(p,state,sizeof(state),&size) == XTC_OK); assert(xtc_processor_restore(&d,48000,16,state,size,&restored) == XTC_OK); b.input = out; for (i = 0; i < 16; ++i) out[i] = 1; assert(xtc_processor_process(restored,&b,NULL,0) == XTC_OK && out[15] == 2); xtc_processor_destroy(restored); restored = NULL; memcpy(broken,state,size); broken[8] = 'z'; assert(xtc_processor_restore(&d,48000,16,broken,size,&restored) != XTC_OK && !restored); memcpy(broken,state,size); broken[80] = 42; assert(xtc_processor_restore(&d,48000,16,broken,size,&restored) != XTC_OK); assert(xtc_processor_restore(&d,48000,16,state,size-1,&restored) != XTC_OK); xtc_processor_destroy(p); d.process = process_fail; assert(xtc_processor_create(&d,48000,16,&p) == XTC_OK); assert(xtc_processor_process(p,&b,NULL,0) == XTC_ERR_UNSUPPORTED); for (i = 0; i < 16; ++i) assert(out[i] == 0); xtc_processor_destroy(p); d = example_instrument(); assert(xtc_processor_create(&d,48000,16,&p) == XTC_OK); { xtc_midi_event midi[] = {{0,XTC_MIDI_NOTE_ON,0,69,127},{8,XTC_MIDI_NOTE_OFF,0,69,0}}; b.input = NULL; b.events = midi; b.event_count = 2; e[0].value = .25f; assert(xtc_processor_process(p,&b,e,1) == XTC_OK); assert(out[1] > 0 && out[1] < .25f); for (i = 8; i < 16; ++i) assert(out[i] == 0); xtc_processor_reset(p); b.events = NULL; b.event_count = 0; assert(xtc_processor_process(p,&b,NULL,0) == XTC_OK); for (i = 0; i < 16; ++i) assert(out[i] == 0); } xtc_processor_destroy(p); puts("Native parameter events, state, effect/instrument and lifecycle errors passed."); return 0; }