[cfe-dev] Q: Custom Assertion Handlers
Jordan Rose
jordan_rose at apple.com
Mon Jun 10 09:42:44 PDT 2013
Hi, Jeffrey. You're not going to be able to pass the assertion handler on the command line, but there are several well-established techniques for adding compiler-specific source annotations. The usual one looks something like this (from LLVM itself):
#ifdef __GNUC__
#define LLVM_ATTRIBUTE_NORETURN __attribute__((noreturn))
#elif defined(_MSC_VER)
#define LLVM_ATTRIBUTE_NORETURN __declspec(noreturn)
#else
#define LLVM_ATTRIBUTE_NORETURN
#endif
The analyzer actually has its own specific guard macro, __clang_analyzer__, so you could do something like this:
#ifdef __clang_analyzer__
#define ANALYZER_NORETURN __attribute__((analyzer_noreturn))
#else
#define ANALYZER_NORETURN
#endif
As for termination, neither 'noreturn' nor 'analyzer_noreturn' actually relies on the program immediately terminating. The former just promises that the function, well, won't return, and SIGTRAP to get into a debugger (and then terminating from the debugger later) is a perfectly reasonable way to accomplish that.
Still, if you aren't sure 'noreturn' fully describes your situation, just use 'analyzer_noreturn'. This tells the analyzer to stop analyzing this particular path (as if the program had terminated), but does not affect compilation in any way.
Hope that helps,
Jordan
On Jun 7, 2013, at 18:54 , Jeffrey Walton <noloader at gmail.com> wrote:
> Hi All,
>
> According to http://clang-analyzer.llvm.org/annotations.html#custom_assertions:
>
> <QUOTE>
> void foo(int *p) {
> assert(p != NULL);
> }
>
> When this code is preprocessed on Mac OS X it expands to the following:
>
> void foo(int *p) {
> (__builtin_expect(!(p != NULL), 0) ? __assert_rtn(__func__, "t.c",
> 4, "p != NULL") : (void)0);
> }
>
> In this example, the assertion handler is __assert_rtn. When called,
> most assertion handlers typically print an error and terminate the
> program. The analyzer can exploit such semantics by ending the
> analysis of a path once it hits a call to an assertion handler....
>
> The analyzer knows about several well-known assertion handlers, but
> can automatically infer if a function should be treated as an
> assertion handler if it is annotated with the 'noreturn' attribute or
> the (Clang-specific) 'analyzer_noreturn' attribute. Note that,
> currently, clang does not support these attributes on Objective-C
> methods and C++ methods.
> </QUOTE>
>
> I work with source files compiled under a number of compilers,
> including GCC, ICC/ICPC, MSVC, and Clang. Some of the compilers don't
> support GCC notations.
>
> (1) Is there a way to pass the assertion handler to Clang on the
> command line? (I typically use `ASSERT` rather than `assert`).
>
> (2) Is there a way to indicate the failed assertion does *not*
> terminate? (Calling abort() is useless behavior during development
> (i.e., Debug builds), so my ASSERT raises a SIGTRAP on *nix. Plus,
> Release builds don't include 'diagnostics' such as assert, so they are
> not present in release builds).
>
> Jeff
> _______________________________________________
> cfe-dev mailing list
> cfe-dev at cs.uiuc.edu
> http://lists.cs.uiuc.edu/mailman/listinfo/cfe-dev
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.llvm.org/pipermail/cfe-dev/attachments/20130610/c4ad9825/attachment.html>
More information about the cfe-dev
mailing list