Make loplugin:defaultparams work for multiple default params per function
Change-Id: I0aa3841e1ac3375f519384f3012450bc683d1c51
This commit is contained in:
@@ -32,51 +32,61 @@ bool DefaultParams::VisitCallExpr(CallExpr * callExpr) {
|
|||||||
if (ignoreLocation(callExpr)) {
|
if (ignoreLocation(callExpr)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (callExpr->getNumArgs() == 0) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
if (callExpr->getDirectCallee() == nullptr) {
|
if (callExpr->getDirectCallee() == nullptr) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
const FunctionDecl* functionDecl = callExpr->getDirectCallee()->getCanonicalDecl();
|
const FunctionDecl* functionDecl = callExpr->getDirectCallee()->getCanonicalDecl();
|
||||||
unsigned i = callExpr->getNumArgs() - 1;
|
auto n = functionDecl->getNumParams();
|
||||||
Expr* arg = callExpr->getArg(i);
|
if (n == 0 || !functionDecl->getParamDecl(n - 1)->hasDefaultArg()) {
|
||||||
// variadic functions
|
|
||||||
if (i >= functionDecl->getNumParams()) {
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (arg->isDefaultArgument()) {
|
if(callExpr->getNumArgs()>n){
|
||||||
|
report(
|
||||||
|
DiagnosticsEngine::Warning, "TODO %0 != %1", callExpr->getLocStart())
|
||||||
|
<< callExpr->getNumArgs() << n << callExpr->getSourceRange();
|
||||||
|
callExpr->dump();
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
|
assert(callExpr->getNumArgs() <= n); // can be < in template code
|
||||||
|
for (unsigned i = callExpr->getNumArgs(); i != 0;) {
|
||||||
|
--i;
|
||||||
|
Expr* arg = callExpr->getArg(i);
|
||||||
|
if (arg->isDefaultArgument()) {
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
// ignore this, it seems to trigger an infinite recursion
|
// ignore this, it seems to trigger an infinite recursion
|
||||||
if (isa<UnaryExprOrTypeTraitExpr>(arg))
|
if (isa<UnaryExprOrTypeTraitExpr>(arg))
|
||||||
return true;
|
break;
|
||||||
const ParmVarDecl* parmVarDecl = functionDecl->getParamDecl(i);
|
const ParmVarDecl* parmVarDecl = functionDecl->getParamDecl(i);
|
||||||
if (!parmVarDecl->hasDefaultArg()
|
if (!parmVarDecl->hasDefaultArg()
|
||||||
|| parmVarDecl->hasUninstantiatedDefaultArg())
|
|| parmVarDecl->hasUninstantiatedDefaultArg())
|
||||||
{
|
{
|
||||||
return true;
|
break;
|
||||||
}
|
}
|
||||||
const Expr* defaultArgExpr = parmVarDecl->getDefaultArg();
|
const Expr* defaultArgExpr = parmVarDecl->getDefaultArg();
|
||||||
if (defaultArgExpr &&
|
if (!(defaultArgExpr &&
|
||||||
defaultArgExpr->getType()->isIntegralType(compiler.getASTContext()))
|
defaultArgExpr->getType()->isIntegralType(
|
||||||
|
compiler.getASTContext())))
|
||||||
{
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
APSInt x1, x2;
|
APSInt x1, x2;
|
||||||
if (arg->EvaluateAsInt(x1, compiler.getASTContext()) &&
|
if (!(arg->EvaluateAsInt(x1, compiler.getASTContext()) &&
|
||||||
defaultArgExpr->EvaluateAsInt(x2, compiler.getASTContext()) &&
|
defaultArgExpr->EvaluateAsInt(x2, compiler.getASTContext()) &&
|
||||||
x1 == x2)
|
x1 == x2))
|
||||||
{
|
{
|
||||||
|
break;
|
||||||
|
}
|
||||||
report(
|
report(
|
||||||
DiagnosticsEngine::Warning,
|
DiagnosticsEngine::Warning,
|
||||||
"not necessary to pass this argument, it defaults to the same value",
|
"not necessary to pass this argument, it defaults to the same value",
|
||||||
arg->getSourceRange().getBegin())
|
arg->getSourceRange().getBegin())
|
||||||
<< arg->getSourceRange();
|
<< arg->getSourceRange();
|
||||||
/*report(
|
report(
|
||||||
DiagnosticsEngine::Warning,
|
DiagnosticsEngine::Note,
|
||||||
"default method parameter declaration here",
|
"default method parameter declaration here",
|
||||||
parmVarDecl->getSourceRange().getBegin())
|
parmVarDecl->getSourceRange().getBegin())
|
||||||
<< parmVarDecl->getSourceRange();*/
|
<< parmVarDecl->getSourceRange();
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
Reference in New Issue
Block a user