GithubHelp home page GithubHelp logo

leiless / assertf.h Goto Github PK

View Code? Open in Web Editor NEW
9.0 2.0 2.0 73 KB

🚀 C header-only formattable assert macros library

Home Page: https://leiless.github.io/assertf.h

License: BSD 2-Clause "Simplified" License

C 96.99% CMake 3.01%
c assert assertion header-only debug debugging test unittest cpp assertion-library misuse

assertf.h's Introduction

assertf.h

Try it online Codacy Badge License

assertf.h is a header-only formattable assert macros library, a possible alternative to the #include <assert.h>.

With enhanced assertions, we can debug/test code better.

Platform

Platform

assertf.h originally targets to embedded systems, it also can be used nearly all UNIX-like, including Windows systems.

Example

#include <stdio.h>
#include <unistd.h>
#include <errno.h>

#define ASSERTF_DEF_ONCE
#include "assertf.h"

int main(void)
{
    int e = rmdir("/tmp");
    assert_eqf(e, 0, %d, "rmdir(2) fail, errno: %d", errno);    /* Line 11 */
    // #define EACCES          13      /* Permission denied */
    return 0;
}

Sample assertion failure output(try it online)

Samplt output

Integration

In order to deploy assertf.h to your existing C/C++ project, you need:

  1. Download assertf.h to your source code directory

  2. In one of your C/C++ file(typically project main file), write:

    // Define ASSERTF_DEF_ONCE once and only once
    #define ASSERTF_DEF_ONCE
    #include "assertf.h"
  3. If other C/C++ files needs to use assertf.h, just type #include "assertf.h".

  4. If you want to disable assertf.h on release build, please specify -DASSERTF_DISABLE in Makefile, CMakeLists.txt, etc.

API

Nearly all assertf.h APIs prefixed with assert, the most basic API is the

  • assertf(expr, fmt, ...)

    When expr isn't true, it'll print out a message backed by fmt and ... to stderr and then crash the whole program(if assertf.h is enabled).

    Sample output:

    // assertf(e == 0, "unlink(2) errno: %d", errno);
    Assert (e == 0) failed: unlink(2) errno: 2 [test.c:12 (main)]
    [1]    62760 abort (core dumped)  ./test
  • panicf(fmt, ...)

    Alias call of assertf(0, fmt, ...).

  • assert_nonnull(ptr), assert_null(ptr)

    Assert nullability of ptr.

  • assert_eq(a, b, fs), assert_ne(), assert_lt(), assert_le(), assert_gt(), assert_ge()

    Check arithmetic relation of a and b, fs is the format specifier of a, b will use the same format specifier as a, double-quote in "%<type_specifier>" can be omitted.

    // assert_eq(e, 0, %d);
    Assert ((e) == (__type0(e)) (0)) failed: lhs: -1 rhs: 0 [test.c:13 (main)]
    [1]    65959 abort (core dumped)  ./test
  • assert_eqf(a, b, fs, fmt, ...), assert_nef(), assert_ltf(), assert_lef(), assert_gtf(), assert_gef()

    Like above version, fmt and ... can used for verbose assertion output once it failed.

    // assert_eqf(e, 0, %d, "unlink(2) errno: %d", errno);
    Assert ((e) == (__type0(e)) (0)) failed: lhs: -1 rhs: 0  unlink(2) errno: 2 [test.c:14 (main)]
    [1]    66800 abort (core dumped)  ./test
  • assert_true(x, fs), assert_truef(x, fs, fmt, ...), assert_false(), assert_falsef()

    Alias call of assert_ne(x, 0, fs, ...), assert_eq(x, 0, fs, ...).

  • assert_nonzero(x, fs), assert_zero(x, fs)

    Alias call of assert_true(x, fs), assert_false(x, fs).

  • BUILD_BUG_ON()

    Break compile if a condition is true at compile-time, taken from Linux kernel. It's useful with companion of assert*.

    If you have some code which relies on certain constants being true, or some other compile-time evaluated condition, you should use BUILD_BUG_ON() to detect if someone changes it unexpectedly.

Caveats

  • Do NOT #define ASSERTF_DISABLE in any part of your project source code, it'll break compilation semantics of assertf.h. Like aforementioned, define it in Makefile, CMakeLists.txt, etc.

  • Like #include <assert.h>, all assertf.h APIs isn't side-effect safe.

  • Like #include <assert.h>, when the expr not true, abort(3) will be called eventually.

  • Some C/C++ compilers may warns you implicit declaration of function 'typeof' is invalid in C99 [-Wimplicit-function-declaration], in such case, you may replace the typeof with __typeof__ and try again.

Pro tips

  • Do NOT misuse any assertion library, assertion is very useful in software development, many people rely on it heavily and some certainly misused it.

    Use assertion to assure code quality isn't a decent way to solve the problem.

    Most software have a very long life-time, sometimes keep running is better than simply crashed.

    SEE ALSO: Why does Go not have assertions?

  • Do NOT write side-effect unsafe code:

    // When you -DASSERTF_DISABLE, lseek(2) may optimized out by the compiler.
    assert_gt(lseek(fd, offset, SEEK_CUR), 0, %d);
    // The ++i will be evaluated twice when expanding assert_eq() macro
    // Again, -DASSERTF_DISABLE may cause ++i optimized out by the compiler
    assert_eq(++i, n, %d);
  • Use assertf.h heavily and confidently in your code base.

  • Replace #include <assert.h> with #include "assertf.h". 😌

FAQ

  • HOWTO check if assertf.h disabled on a certain build?

    • UNIX-like systems

      $ nm some_binary | grep assertf
      0000000000007709 T x_assertf_c21162d2

      If you see x_assertf_c21162d2, it means assertf.h is enabled in some_binary.

      Note that if you strip(1) the symbols, you have no way to determine whether assertf.h disabled or not.

    • Windows

      You need have to check the pdb(Program database) file.

assertf.h's People

Contributors

leiless avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar

assertf.h's Issues

-DASSERTF_DISABLE and assert_*() causes implicit declaration of function

Env

Ubuntu 20.04 LTS
gcc version 9.3.0 (Ubuntu 9.3.0-17ubuntu1~20.04)

HOWTO reproduce

  1. wget https://raw.githubusercontent.com/leiless/assertf.h/master/assertf.h
  2. Save the following code into foo.c
#include <stdio.h>

#define ASSERTF_DEF_ONCE
#include "assertf.h"

int main(void)
{
    assert_eq(1, 1, %d);
    return 0;
}
  1. gcc -Wall -DASSERTF_DISABLE foo.c (reproduced)
In file included from foo.c:4:
foo.c: In function ‘main’:
assertf.h:222:13: warning: implicit declaration of function ‘COL’ [-Wimplicit-function-declaration]
  222 |             COL(CYAN), (a), COL(RST),                                                       \
      |             ^~~
assertf.h:180:87: note: in definition of macro ‘assertf’
  180 | #define assertf(e, fmt, ...)        (void) __vunused((void *) (uintptr_t) (e), fmt, ##__VA_ARGS__)
      |                                                                                       ^~~~~~~~~~~
assertf.h:248:41: note: in expansion of macro ‘__assert_cmp0’
  248 | #define assert_eq(a, b, fs)             __assert_cmp0(a, b, fs, ==)
      |                                         ^~~~~~~~~~~~~
foo.c:8:5: note: in expansion of macro ‘assert_eq’
    8 |     assert_eq(1, 1, %d);
      |     ^~~~~~~~~
assertf.h:222:17: error: ‘CYAN’ undeclared (first use in this function)
  222 |             COL(CYAN), (a), COL(RST),                                                       \
      |                 ^~~~
...

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.