#include "akerror.h" #include "err_capture.h" #include /* * akerr_release_error(NULL) is an API contract violation the library reports * rather than crashes on: it raises AKERR_NULLPOINTER against the internal * last-ditch context and hands that back, so the caller gets a describable * error instead of a dereferenced NULL. Nothing exercised that path. * * The last-ditch context deliberately lives outside AKERR_ARRAY_ERROR so * reporting this failure cannot consume a pool slot -- which is exactly what * akerr_valid_error_address() reports on, and what this test checks. */ int main(void) { akerr_capture_install(); /* akerr_init() sets up the last-ditch context's stacktrace cursor. */ akerr_init(); AKERR_CHECK(akerr_slots_in_use() == 0); akerr_ErrorContext *ret = akerr_release_error(NULL); AKERR_CHECK(ret != NULL); AKERR_CHECK(ret->status == AKERR_NULLPOINTER); AKERR_CHECK(strstr(ret->message, "NULL context pointer") != NULL); /* Reported through FAIL, so the stack trace names the error too. */ AKERR_CHECK(strstr(ret->stacktracebuf, "Null Pointer Error") != NULL); /* Not a pool slot, and no slot was checked out to report the failure. */ AKERR_CHECK(akerr_valid_error_address(ret) == 0); AKERR_CHECK(akerr_slots_in_use() == 0); /* The last-ditch context is a singleton: the same one comes back. */ akerr_ErrorContext *again = akerr_release_error(NULL); AKERR_CHECK(again == ret); AKERR_CHECK(akerr_slots_in_use() == 0); fprintf(stderr, "err_release_null ok\n"); return 0; }