Kaydet (Commit) a6358f1c authored tarafından Noel Grandin's avatar Noel Grandin

improve loplugin constparams

Change-Id: Ic1833dbd030044011e7ee5f89dc35737e5469f05
Reviewed-on: https://gerrit.libreoffice.org/66586
Tested-by: Jenkins
Reviewed-by: 's avatarNoel Grandin <noel.grandin@collabora.co.uk>
üst fc2a8bf0
...@@ -76,11 +76,12 @@ public: ...@@ -76,11 +76,12 @@ public:
{ {
continue; continue;
} }
std::string fname = functionDecl->getQualifiedNameAsString();
report( report(
DiagnosticsEngine::Warning, DiagnosticsEngine::Warning,
"this parameter can be const", "this parameter can be const %0",
compat::getBeginLoc(pParmVarDecl)) compat::getBeginLoc(pParmVarDecl))
<< pParmVarDecl->getSourceRange(); << fname << pParmVarDecl->getSourceRange();
if (canonicalDecl->getLocation() != functionDecl->getLocation()) { if (canonicalDecl->getLocation() != functionDecl->getLocation()) {
unsigned idx = pParmVarDecl->getFunctionScopeIndex(); unsigned idx = pParmVarDecl->getFunctionScopeIndex();
const ParmVarDecl* pOther = canonicalDecl->getParamDecl(idx); const ParmVarDecl* pOther = canonicalDecl->getParamDecl(idx);
...@@ -150,16 +151,8 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl) ...@@ -150,16 +151,8 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl)
if (isInUnoIncludeFile(functionDecl)) { if (isInUnoIncludeFile(functionDecl)) {
return false; return false;
} }
// TODO ignore template stuff for now
if (functionDecl->getTemplatedKind() != FunctionDecl::TK_NonTemplate) {
return false;
}
if (functionDecl->isDeleted()) if (functionDecl->isDeleted())
return false; return false;
if (isa<CXXMethodDecl>(functionDecl)
&& dyn_cast<CXXMethodDecl>(functionDecl)->getParent()->getDescribedClassTemplate() != nullptr ) {
return false;
}
// ignore virtual methods // ignore virtual methods
if (isa<CXXMethodDecl>(functionDecl) if (isa<CXXMethodDecl>(functionDecl)
&& dyn_cast<CXXMethodDecl>(functionDecl)->isVirtual() ) { && dyn_cast<CXXMethodDecl>(functionDecl)->isVirtual() ) {
...@@ -210,10 +203,19 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl) ...@@ -210,10 +203,19 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl)
|| name == "Read_And" || name == "Read_And"
// passed as a LINK<> to another method // passed as a LINK<> to another method
|| name == "GlobalBasicErrorHdl_Impl" || name == "GlobalBasicErrorHdl_Impl"
// template
|| name == "extract_throw" || name == "readProp"
) )
return false; return false;
} }
std::string fqn = functionDecl->getQualifiedNameAsString();
if ( fqn == "connectivity::jdbc::GlobalRef::set"
|| fqn == "(anonymous namespace)::ReorderNotifier::operator()"
|| fqn == "static_txtattr_cast")
return false;
// calculate the ones we want to check // calculate the ones we want to check
bool foundInterestingParam = false; bool foundInterestingParam = false;
for (const ParmVarDecl *pParmVarDecl : functionDecl->parameters()) { for (const ParmVarDecl *pParmVarDecl : functionDecl->parameters()) {
...@@ -222,11 +224,8 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl) ...@@ -222,11 +224,8 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl)
|| pParmVarDecl->hasAttr<UnusedAttr>()) || pParmVarDecl->hasAttr<UnusedAttr>())
continue; continue;
auto const type = loplugin::TypeCheck(pParmVarDecl->getType()); auto const type = loplugin::TypeCheck(pParmVarDecl->getType());
if (!type.Pointer() && !type.LvalueReference()) if (!( type.Pointer().NonConst()
continue; || type.LvalueReference().NonConst()))
if (type.Pointer().Const())
continue;
if (type.LvalueReference().Const())
continue; continue;
// since we normally can't change typedefs, just ignore them // since we normally can't change typedefs, just ignore them
if (isa<TypedefType>(pParmVarDecl->getType())) if (isa<TypedefType>(pParmVarDecl->getType()))
...@@ -240,11 +239,6 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl) ...@@ -240,11 +239,6 @@ bool ConstParams::CheckTraverseFunctionDecl(FunctionDecl * functionDecl)
// const is meaningless when applied to function pointer types // const is meaningless when applied to function pointer types
if (pParmVarDecl->getType()->isFunctionPointerType()) if (pParmVarDecl->getType()->isFunctionPointerType())
continue; continue;
// ignore things with template params
if (pParmVarDecl->getType()->isInstantiationDependentType())
continue;
if (functionDecl->getIdentifier() && functionDecl->getName() == "WW8TransCol")
pParmVarDecl->getType()->dump();
interestingParamSet.insert(pParmVarDecl); interestingParamSet.insert(pParmVarDecl);
parmToFunction[pParmVarDecl] = functionDecl; parmToFunction[pParmVarDecl] = functionDecl;
foundInterestingParam = true; foundInterestingParam = true;
...@@ -281,12 +275,23 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar ...@@ -281,12 +275,23 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar
{ {
for ( auto cxxCtorInitializer : cxxConstructorDecl->inits()) for ( auto cxxCtorInitializer : cxxConstructorDecl->inits())
{ {
if (cxxCtorInitializer->isAnyMemberInitializer() && cxxCtorInitializer->getInit() == stmt) if ( cxxCtorInitializer->getInit() == stmt)
{ {
// if the member is not pointer or ref to-const, we cannot make the param const if (cxxCtorInitializer->isAnyMemberInitializer())
auto fieldDecl = cxxCtorInitializer->getAnyMember(); {
auto tc = loplugin::TypeCheck(fieldDecl->getType()); // if the member is not pointer-to-const or ref-to-const or value, we cannot make the param const
return tc.Pointer().Const() || tc.LvalueReference().Const(); auto fieldDecl = cxxCtorInitializer->getAnyMember();
auto tc = loplugin::TypeCheck(fieldDecl->getType());
if (tc.Pointer() || tc.LvalueReference())
return tc.Pointer().Const() || tc.LvalueReference().Const();
else
return true;
}
else
{
// probably base initialiser, but no simple way to look up the relevant constructor decl
return false;
}
} }
} }
} }
...@@ -392,6 +397,7 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar ...@@ -392,6 +397,7 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar
} }
} }
} }
return false;
} else if (auto callExpr = dyn_cast<CallExpr>(parent)) { } else if (auto callExpr = dyn_cast<CallExpr>(parent)) {
QualType functionType = callExpr->getCallee()->getType(); QualType functionType = callExpr->getCallee()->getType();
if (functionType->isFunctionPointerType()) { if (functionType->isFunctionPointerType()) {
...@@ -437,6 +443,7 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar ...@@ -437,6 +443,7 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar
} }
} }
} }
return false;
} else if (auto callExpr = dyn_cast<ObjCMessageExpr>(parent)) { } else if (auto callExpr = dyn_cast<ObjCMessageExpr>(parent)) {
if (callExpr->getInstanceReceiver() == stmt) { if (callExpr->getInstanceReceiver() == stmt) {
return true; return true;
...@@ -526,7 +533,7 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar ...@@ -526,7 +533,7 @@ bool ConstParams::checkIfCanBeConst(const Stmt* stmt, const ParmVarDecl* parmVar
} else if (isa<CXXTypeidExpr>(parent)) { } else if (isa<CXXTypeidExpr>(parent)) {
return true; return true;
} else if (isa<ParenListExpr>(parent)) { } else if (isa<ParenListExpr>(parent)) {
return true; return false; // could be improved, seen in constructors when calling base class constructor
} else if (isa<CXXUnresolvedConstructExpr>(parent)) { } else if (isa<CXXUnresolvedConstructExpr>(parent)) {
return false; return false;
} else if (isa<UnresolvedMemberExpr>(parent)) { } else if (isa<UnresolvedMemberExpr>(parent)) {
......
...@@ -12,7 +12,7 @@ ...@@ -12,7 +12,7 @@
struct Class1 struct Class1
{ {
int const * m_f1; int const * m_f1;
Class1(int * f1) : m_f1(f1) {} // expected-error {{this parameter can be const [loplugin:constparams]}} Class1(int * f1) : m_f1(f1) {} // expected-error {{this parameter can be const Class1::Class1 [loplugin:constparams]}}
}; };
struct Class2 struct Class2
...@@ -38,7 +38,7 @@ void g() { ...@@ -38,7 +38,7 @@ void g() {
P2 p2; P2 p2;
p2 = (P2) (f3); p2 = (P2) (f3);
} }
int const * f1(int * p) { // expected-error {{this parameter can be const [loplugin:constparams]}} int const * f1(int * p) { // expected-error {{this parameter can be const f1 [loplugin:constparams]}}
return p; return p;
} }
void f4(std::string * p) { void f4(std::string * p) {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment