Skip to content

Instantly share code, notes, and snippets.

@iamalbert
Last active June 5, 2022 04:51
Show Gist options
  • Save iamalbert/de463e388173ca6f862c2a730fb64cee to your computer and use it in GitHub Desktop.
Save iamalbert/de463e388173ca6f862c2a730fb64cee to your computer and use it in GitHub Desktop.
C++ SMART ASSERT
#define __ASSERT1__(x) __REPORT__(x).__ASSERT2__
#define __ASSERT2__(x) __REPORT__(x).__ASSERT1__
#define __REPORT__(x) report(#x,(x))
#define ASSERT(cond, msg) if(!(cond)) Assert(#cond,msg,__FILE__,__LINE__).__ASSERT1__
#include <iostream>
struct Assert {
template<class T>
Assert(const char * cond, T && msg, const char * file, int line) {
std::cerr << "Assertion Failed: " << cond << "\n";
std::cerr << "Message : " << msg << "\n";
std::cerr << "File : " << file << ", line " << line << "\n";
}
template<class T>
Assert & report(const char * name, T&& value){
std::cerr << " " << name << ": " << value << "\n";
return *this;
}
struct Empty {};
static constexpr Empty __ASSERT1__ {}, __ASSERT2__ {};
~Assert(){ exit(-1); }
};
#include "Assert.hpp"
int main(){
int a = 1, b = 2;
std::cout << sizeof(Assert) << "\n";
ASSERT(a + b == 4, "addition")(a)(b);
}
@ChuckStarchaser
Copy link

ChuckStarchaser commented Apr 5, 2021

That's brilliant! I found this page by searching for smart_assert, since a very old backup of a suchly named boost folder that I have was not in the current boost, or at least I could not find it; but now I had a second look at that and it seems to be a totally different smart_assert by somebody else. I could not understand that other code either, but due to the sheer size of it, rather; I much prefer yours; and I think I'm going to use it. One feature I wish it had is a way to stop execution, like debug break, rather than abort.
A rather crazy thing I've been thinking about is having targets ALPHA and BETA, between DEBUG and RELEASE, that change the behavior of asserts to logging assertion failures and continue running (with or without "fixing" things). For example, if an addition should never overflow, but saturating the result would be a preferable compromise to shutting down the program, in DEBUG mode, the assert would stop execution; in ALPHA it would log the error to a file and ask the user whether to continue; in BETA it would log silently and continue; and in RELEASE mode it would just saturate the result and continue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment