Add a clang-tidy configuration file

Also add some annotations to remove some false positives.

There remain some boost-related false positives, it’s unclear how to suppress
them.
master
Sébastien Villemot 2023-12-04 16:37:00 +01:00
parent b2e9ec205e
commit bffd68e0bf
No known key found for this signature in database
GPG Key ID: 2CECE9350ECEBE4A
8 changed files with 28 additions and 7 deletions

9
.clang-tidy Normal file
View File

@ -0,0 +1,9 @@
# TODO: add the following check families:
# - performance-*
# - bugprone-*
# - cppcoreguidelines-
# NB: as of clang-tidy 16, we get several false positives inside boost, notably this one:
# https://github.com/llvm/llvm-project/issues/40486
Checks: 'modernize-*,-modernize-use-trailing-return-type,-clang-diagnostic-unqualified-std-cast-call'

View File

@ -205,7 +205,7 @@ DataTree::AddPlus(expr_t iArg1, expr_t iArg2)
// To treat commutativity of "+"
// Nodes iArg1 and iArg2 are sorted by index
if (iArg1->idx > iArg2->idx && !no_commutativity)
if (iArg1->idx > iArg2->idx && !no_commutativity) // NOLINT(clang-analyzer-core.NullDereference)
swap(iArg1, iArg2);
return AddBinaryOp(iArg1, BinaryOpcode::plus, iArg2);
}
@ -283,7 +283,7 @@ DataTree::AddTimes(expr_t iArg1, expr_t iArg2)
// To treat commutativity of "*"
// Nodes iArg1 and iArg2 are sorted by index
if (iArg1->idx > iArg2->idx && !no_commutativity)
if (iArg1->idx > iArg2->idx && !no_commutativity) // NOLINT(clang-analyzer-core.NullDereference)
swap(iArg1, iArg2);
return AddBinaryOp(iArg1, BinaryOpcode::times, iArg2);
}

View File

@ -431,7 +431,7 @@ DataTree::AddUnaryOp(UnaryOpcode op_code, expr_t arg, int arg_exp_info_set, int
{
try
{
double argval = arg->eval({});
double argval = arg->eval({}); // NOLINT(clang-analyzer-core.CallAndMessage)
double val = UnaryOpNode::eval_opcode(op_code, argval);
return AddPossiblyNegativeConstant(val);
}
@ -460,8 +460,8 @@ DataTree::AddBinaryOp(expr_t arg1, BinaryOpcode op_code, expr_t arg2, int powerD
// Try to reduce to a constant
try
{
double argval1 = arg1->eval({});
double argval2 = arg2->eval({});
double argval1 = arg1->eval({}); // NOLINT(clang-analyzer-core.CallAndMessage)
double argval2 = arg2->eval({}); // NOLINT(clang-analyzer-core.CallAndMessage)
double val = BinaryOpNode::eval_opcode(argval1, op_code, argval2, powerDerivOrder);
return AddPossiblyNegativeConstant(val);
}

View File

@ -3727,7 +3727,7 @@ UnaryOpNode::substituteDiff(const lag_equivalence_table_t& nodes, subst_table_t&
if (vn)
symb_id = datatree.symbol_table.addDiffAuxiliaryVar(argsubst->idx, rit->second,
vn->symb_id, vn->lag);
else
else // NOLINTNEXTLINE(clang-analyzer-core.NullDereference)
symb_id = datatree.symbol_table.addDiffAuxiliaryVar(argsubst->idx, rit->second);
// make originating aux var & equation
@ -3745,8 +3745,10 @@ UnaryOpNode::substituteDiff(const lag_equivalence_table_t& nodes, subst_table_t&
for (int i = last_index; i > rit->first; i--)
{
if (i == last_index)
// NOLINTBEGIN(clang-analyzer-core.NullDereference)
symb_id = datatree.symbol_table.addDiffLagAuxiliaryVar(argsubst->idx, rit->second,
last_aux_var->symb_id, -1);
// NOLINTEND(clang-analyzer-core.NullDereference)
else
symb_id = datatree.symbol_table.addDiffLagAuxiliaryVar(
new_aux_var->idx, rit->second, last_aux_var->symb_id, -1);
@ -3884,6 +3886,7 @@ UnaryOpNode::substituteUnaryOpNodes(const lag_equivalence_table_t& nodes,
}
else
subst_table[rit->second]
// NOLINTNEXTLINE(clang-analyzer-core.CallAndMessage)
= dynamic_cast<VariableNode*>(aux_var->decreaseLeadsLags(base_index - rit->first));
assert(subst_table.contains(this));
@ -5692,6 +5695,7 @@ BinaryOpNode::getPacAREC(
vector<tuple<int, int, optional<int>, double>> linear_combination;
try
{
// NOLINTNEXTLINE(clang-analyzer-core.CallAndMessage)
auto [vid, lag, pid, constant] = term->matchVariableTimesConstantTimesParam(true);
linear_combination.emplace_back(vid.value(), lag, move(pid), constant);
}
@ -5773,6 +5777,7 @@ BinaryOpNode::isParamTimesEndogExpr() const
}
else
{
// NOLINTNEXTLINE(clang-analyzer-core.CallAndMessage)
arg1->collectDynamicVariables(SymbolType::endogenous, endogs);
arg1->collectDynamicVariables(SymbolType::exogenous, exogs);
arg1->collectVariables(SymbolType::parameter, params);
@ -9311,6 +9316,7 @@ BinaryOpNode::matchEndogenousTimesConstant() const
varg1 && varg1->get_type() == SymbolType::endogenous && arg2->isConstant())
return {varg1->symb_id, arg2};
if (auto varg2 = dynamic_cast<VariableNode*>(arg2);
// NOLINTNEXTLINE(clang-analyzer-core.CallAndMessage)
varg2 && varg2->get_type() == SymbolType::endogenous && arg1->isConstant())
return {varg2->symb_id, arg1};
}

View File

@ -393,7 +393,7 @@ ModelTree::evaluateAndReduceJacobian(const eval_context_t& eval_context) const
double val {[&] {
try
{
return d1->eval(eval_context);
return d1->eval(eval_context); // NOLINT(clang-analyzer-core.NullDereference)
}
catch (ExprNode::EvalExternalFunctionException& e)
{

View File

@ -751,6 +751,7 @@ ModelTree::writeTemporaryTerms(const temporary_terms_t& tt, temporary_terms_t& t
if (dynamic_cast<AbstractExternalFunctionNode*>(it))
it->writeExternalFunctionOutput(output, output_type, temp_term_union, tt_idxs, tef_terms);
// NOLINTNEXTLINE(clang-analyzer-core.CallAndMessage)
it->writeOutput(output, output_type, tt, tt_idxs, tef_terms);
output << " = ";
it->writeOutput(output, output_type, temp_term_union, tt_idxs, tef_terms);

View File

@ -184,6 +184,7 @@ OptionsList::writeOutput(ostream& output, const string& option_group) const
void
OptionsList::writeOutputCommon(ostream& output, const string& option_group) const
{
// NOLINTBEGIN(clang-analyzer-core.CallAndMessage)
for (const auto& [name, val] : options)
std::visit(
[&]<class T>(const T& v) {
@ -261,6 +262,7 @@ OptionsList::writeOutputCommon(ostream& output, const string& option_group) cons
}
},
val);
// NOLINTEND(clang-analyzer-core.CallAndMessage)
}
void

View File

@ -623,12 +623,15 @@ Range::eval(Environment& env) const
"the arguments must evaluate to reals");
vector<ExpressionPtr> arr;
// We do want a float counter, because thats the macro-language semantics
// NOLINTBEGIN(clang-analyzer-security.FloatLoopCounter)
if (*incdbl > 0 && *startdbl <= *enddbl)
for (double i = *startdbl; i <= *enddbl; i += *incdbl)
arr.emplace_back(make_shared<Real>(i));
else if (*startdbl >= *enddbl && *incdbl < 0)
for (double i = *startdbl; i >= *enddbl; i += *incdbl)
arr.emplace_back(make_shared<Real>(i));
// NOLINTEND(clang-analyzer-security.FloatLoopCounter)
return make_shared<Array>(arr, location);
}