Hello @KUGA2,
First, I’d like to share that the rule cpp:S960 is not absolute. Even if function-like macros are usually something to avoid, in some cases, they can increase the readability of your code. In that case, marking them as Won’t fix (or Accept with latest versions of our products) is perfectly appropriate.
Let’s discuss if there are better alternatives in this case because I think that beyond this rule, the main question is one of error management.
The most significant element I see in this macro is ERR_INVALID_ARG
. The name refers to something that sounds like a programming error more than a normal condition, and I’m reluctant to clutter the main execution path with the handling of programming errors. If possible, I would prefer another mechanism, with the added advantage that the function return is now free to return meaningful values, instead of error codes.
Would it make sense for instance to abort
if your precondition is violated (and let a higher-level system perform some recovery)? In that case, you can replace the macro with a simple function.
If you are in C++ and they are not disabled, maybe raising an exception could also be an option (many people are not fond of exceptions for programming errors, but they may provide a good level of error recovery).
There are of course variants still based on return code, with things like std::expected
(C++23, but you can write your own). Those variants cannot be packaged in a function.
Now, another question is: Is the macro really worth it? The code it replaces is very simple, so why not simply write explicitly?
if (nullptr == pointer) { return ERR_INVALID_ARG; }
This comes with the added benefit of being able to test other conditions (if (value == 0)
for instance) or to return other, more accurate, error codes.
What do you think?