7

I have a macro which instantiates a global variable. And thus clang-tidy will correctly issue an "Initialization of ... with static storage duration may throw an exception which cannot be caught".

Can I disable this warning on a per-macro basis? Preferable inline where the macro is defined.

That is, let's say I have:

// header.h
#define UGLY_MACRO(X)  SomeClass X(#X)

// source.cpp
UGLY_MACRO(SomeName); // clang-tidy complains here

And I want clang-tidy to stop complaining about this.

I want to be as specific as possible. I only want to turn of this warning for this macro. I do not want to turn of the warning globally, then someone might add more of this kind of macros into the code unnoticed. Also, I don’t want to add something (like a //NOLNT(...)) at every place where the macro is used, that would be too much of a hassle.

Or am I approaching this from the wrong direction? I have worked with pc-lint before, where this is possible.

pablo285
  • 2,460
  • 4
  • 14
  • 38
Johan W
  • 71
  • 1
  • 4

2 Answers2

5

I have the same problem. I have found two ways to do this, none of which are perfect, sadly.

Option 1 by using the --line-filter command-line argument for clang-tidy:

clang-tidy --line-filter='["name":"header.h"]' source.cpp

Notes:

  • Sadly this doesn't selectively work on one warning only, it disables all of them.
  • Unlike --filter-regex, this works even for macro expansion.
  • You can be more specific and specify the range of line numbers in header.h you want to disable the warnings for (see the help text for --line-filter)

Option 2 by wrapping the macro:

#define UGLY_MACRO_NOLINT(...) UGLY_MACRO(__VA_ARGS__) //NOLINT(...)

Notes:

  • Requires modifying your source code to use the nolint version
  • Does not work if UGLY_MACRO is multi-line
Dan Nestor
  • 2,441
  • 1
  • 24
  • 45
  • In option 2 is the "comment" ("// ... ") really stored as part of the macro, or is a comment that is ignored in the first place? – alfC Aug 31 '21 at 03:10
  • 1
    I'm no expert, but according to the standard (for both C and C++), comments are removed during translation phase 3, and macros expanded in phase 4. That would mean the comments in general are never "part" of any macro. I suspect though that clang-tidy has an extra pass to identify such comments that are meant to affect its behaviour. – Dan Nestor Sep 07 '21 at 14:23
  • ok, so, in conclusion, is not completely useless to try to add NOLINT suppression in macro definitions that would act on its expansion later on? Clang tidy could, if it wants, have different rules than C++ preprocessor. – alfC Sep 07 '21 at 14:24
  • 1
    No, it's not useless; indeed, that is the second solution presented in my answer. It does come with its own drawbacks, as explained. – Dan Nestor Sep 08 '21 at 15:18
  • 1
    Thanks, actually, I just tried and if you put the `NOLINT` in c-style comments `/* NOLINT ... */` you can make it work in multiline macros. – alfC Sep 08 '21 at 16:49
  • Oh, really? That's really helpful, thanks! I would appreciate it if you could edit my answer or perhaps add your own, showing exactly how that works. – Dan Nestor Sep 08 '21 at 17:29
1

As far as I know this is not possible. The check in question (cert-err58-cpp) doesn't have configurable options which means it can't be disabled on a per-macro basis, only globally.

Save for modifying the check's source the only option you have here is // NOLINT(cert-err58-cpp) and // NOLINTNEXTLINE(cert-err58-cpp). The latter is a little easier to use for text search and replace as you only need to catch a newline followed by the macro name.

alfC
  • 14,261
  • 4
  • 67
  • 118
pablo285
  • 2,460
  • 4
  • 14
  • 38