1*2b15cb3dSCy Schubert /* 2*2b15cb3dSCy Schubert * ntp_assert.h - design by contract stuff 3*2b15cb3dSCy Schubert * 4*2b15cb3dSCy Schubert * example: 5*2b15cb3dSCy Schubert * 6*2b15cb3dSCy Schubert * int foo(char *a) { 7*2b15cb3dSCy Schubert * int result; 8*2b15cb3dSCy Schubert * int value; 9*2b15cb3dSCy Schubert * 10*2b15cb3dSCy Schubert * REQUIRE(a != NULL); 11*2b15cb3dSCy Schubert * ... 12*2b15cb3dSCy Schubert * bar(&value); 13*2b15cb3dSCy Schubert * INSIST(value > 2); 14*2b15cb3dSCy Schubert * ... 15*2b15cb3dSCy Schubert * 16*2b15cb3dSCy Schubert * ENSURE(result != 12); 17*2b15cb3dSCy Schubert * return result; 18*2b15cb3dSCy Schubert * } 19*2b15cb3dSCy Schubert * 20*2b15cb3dSCy Schubert * open question: when would we use INVARIANT()? 21*2b15cb3dSCy Schubert * 22*2b15cb3dSCy Schubert * For cases where the overhead for non-debug builds is deemed too high, 23*2b15cb3dSCy Schubert * use DEBUG_REQUIRE(), DEBUG_INSIST(), DEBUG_ENSURE(), and/or 24*2b15cb3dSCy Schubert * DEBUG_INVARIANT(). 25*2b15cb3dSCy Schubert */ 26*2b15cb3dSCy Schubert 27*2b15cb3dSCy Schubert #ifndef NTP_ASSERT_H 28*2b15cb3dSCy Schubert #define NTP_ASSERT_H 29*2b15cb3dSCy Schubert 30*2b15cb3dSCy Schubert # ifdef CALYSTO 31*2b15cb3dSCy Schubert /* see: http://www.domagoj-babic.com/index.php/ResearchProjects/Calysto */ 32*2b15cb3dSCy Schubert 33*2b15cb3dSCy Schubert extern void calysto_assume(unsigned char cnd); /* assume this always holds */ 34*2b15cb3dSCy Schubert extern void calysto_assert(unsigned char cnd); /* check whether this holds */ 35*2b15cb3dSCy Schubert #define ALWAYS_REQUIRE(x) calysto_assert(x) 36*2b15cb3dSCy Schubert #define ALWAYS_INSIST(x) calysto_assume(x) /* DLH calysto_assert()? */ 37*2b15cb3dSCy Schubert #define ALWAYS_INVARIANT(x) calysto_assume(x) 38*2b15cb3dSCy Schubert #define ALWAYS_ENSURE(x) calysto_assert(x) 39*2b15cb3dSCy Schubert 40*2b15cb3dSCy Schubert /* # elif defined(__COVERITY__) */ 41*2b15cb3dSCy Schubert /* 42*2b15cb3dSCy Schubert * DH: try letting coverity scan our actual assertion macros, now that 43*2b15cb3dSCy Schubert * isc_assertioncallback_t is marked __attribute__ __noreturn__. 44*2b15cb3dSCy Schubert */ 45*2b15cb3dSCy Schubert 46*2b15cb3dSCy Schubert /* 47*2b15cb3dSCy Schubert * Coverity has special knowledge that assert(x) terminates the process 48*2b15cb3dSCy Schubert * if x is not true. Rather than teach it about our assertion macros, 49*2b15cb3dSCy Schubert * just use the one it knows about for Coverity Prevent scans. This 50*2b15cb3dSCy Schubert * means our assertion code (and ISC's) escapes Coverity analysis, but 51*2b15cb3dSCy Schubert * that seems to be a reasonable trade-off. 52*2b15cb3dSCy Schubert */ 53*2b15cb3dSCy Schubert 54*2b15cb3dSCy Schubert /* 55*2b15cb3dSCy Schubert #define ALWAYS_REQUIRE(x) assert(x) 56*2b15cb3dSCy Schubert #define ALWAYS_INSIST(x) assert(x) 57*2b15cb3dSCy Schubert #define ALWAYS_INVARIANT(x) assert(x) 58*2b15cb3dSCy Schubert #define ALWAYS_ENSURE(x) assert(x) 59*2b15cb3dSCy Schubert */ 60*2b15cb3dSCy Schubert 61*2b15cb3dSCy Schubert 62*2b15cb3dSCy Schubert #elif defined(__FLEXELINT__) 63*2b15cb3dSCy Schubert 64*2b15cb3dSCy Schubert #include <assert.h> 65*2b15cb3dSCy Schubert 66*2b15cb3dSCy Schubert #define ALWAYS_REQUIRE(x) assert(x) 67*2b15cb3dSCy Schubert #define ALWAYS_INSIST(x) assert(x) 68*2b15cb3dSCy Schubert #define ALWAYS_INVARIANT(x) assert(x) 69*2b15cb3dSCy Schubert #define ALWAYS_ENSURE(x) assert(x) 70*2b15cb3dSCy Schubert 71*2b15cb3dSCy Schubert # else /* neither Calysto, Coverity or FlexeLint */ 72*2b15cb3dSCy Schubert 73*2b15cb3dSCy Schubert #include "isc/assertions.h" 74*2b15cb3dSCy Schubert 75*2b15cb3dSCy Schubert #define ALWAYS_REQUIRE(x) ISC_REQUIRE(x) 76*2b15cb3dSCy Schubert #define ALWAYS_INSIST(x) ISC_INSIST(x) 77*2b15cb3dSCy Schubert #define ALWAYS_INVARIANT(x) ISC_INVARIANT(x) 78*2b15cb3dSCy Schubert #define ALWAYS_ENSURE(x) ISC_ENSURE(x) 79*2b15cb3dSCy Schubert 80*2b15cb3dSCy Schubert # endif /* neither Coverity nor Calysto */ 81*2b15cb3dSCy Schubert 82*2b15cb3dSCy Schubert #define REQUIRE(x) ALWAYS_REQUIRE(x) 83*2b15cb3dSCy Schubert #define INSIST(x) ALWAYS_INSIST(x) 84*2b15cb3dSCy Schubert #define INVARIANT(x) ALWAYS_INVARIANT(x) 85*2b15cb3dSCy Schubert #define ENSURE(x) ALWAYS_ENSURE(x) 86*2b15cb3dSCy Schubert 87*2b15cb3dSCy Schubert /* 88*2b15cb3dSCy Schubert * We initially used NTP_REQUIRE() instead of REQUIRE() etc, but that 89*2b15cb3dSCy Schubert * is unneccesarily verbose, as libisc use of REQUIRE() etc shows. 90*2b15cb3dSCy Schubert */ 91*2b15cb3dSCy Schubert 92*2b15cb3dSCy Schubert # ifdef DEBUG 93*2b15cb3dSCy Schubert #define DEBUG_REQUIRE(x) REQUIRE(x) 94*2b15cb3dSCy Schubert #define DEBUG_INSIST(x) INSIST(x) 95*2b15cb3dSCy Schubert #define DEBUG_INVARIANT(x) INVARIANT(x) 96*2b15cb3dSCy Schubert #define DEBUG_ENSURE(x) ENSURE(x) 97*2b15cb3dSCy Schubert # else 98*2b15cb3dSCy Schubert #define DEBUG_REQUIRE(x) do {} while (FALSE) 99*2b15cb3dSCy Schubert #define DEBUG_INSIST(x) do {} while (FALSE) 100*2b15cb3dSCy Schubert #define DEBUG_INVARIANT(x) do {} while (FALSE) 101*2b15cb3dSCy Schubert #define DEBUG_ENSURE(x) do {} while (FALSE) 102*2b15cb3dSCy Schubert # endif 103*2b15cb3dSCy Schubert 104*2b15cb3dSCy Schubert #endif /* NTP_ASSERT_H */ 105