diff options
author | Noel Grandin <noel.grandin@collabora.co.uk> | 2017-08-17 11:35:37 +0200 |
---|---|---|
committer | Noel Grandin <noel.grandin@collabora.co.uk> | 2017-08-17 13:18:34 +0200 |
commit | b0d7b8fa63109117ec19864ddd2462683088d1e3 (patch) | |
tree | 48ef8f5c1809be477575562a5d02c84e3b0c7618 /compilerplugins/clang/convertuintptr.cxx | |
parent | d64a7f4ba80fa2a0a0ad2bddc6906ab6b78a23c8 (diff) |
new loplugin convertuintptr
an experiment to see if I can make the process of eliminating
sal_uIntPtr a little easier
Change-Id: I808185fbf18826cb9ab5612a7be4148d52045957
Diffstat (limited to 'compilerplugins/clang/convertuintptr.cxx')
-rw-r--r-- | compilerplugins/clang/convertuintptr.cxx | 105 |
1 files changed, 105 insertions, 0 deletions
diff --git a/compilerplugins/clang/convertuintptr.cxx b/compilerplugins/clang/convertuintptr.cxx new file mode 100644 index 000000000000..77eb1b4f8616 --- /dev/null +++ b/compilerplugins/clang/convertuintptr.cxx @@ -0,0 +1,105 @@ +/* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */ +/* + * This file is part of the LibreOffice project. + * + * This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at http://mozilla.org/MPL/2.0/. + */ + +#include <memory> +#include <cassert> +#include <string> +#include <iostream> +#include <fstream> +#include <set> +#include "plugin.hxx" +#include "check.hxx" + +/** + plugin to help to when converting code from sal_uIntPtr to something more precise. + */ +namespace { + +class ConvertUIntPtr: + public RecursiveASTVisitor<ConvertUIntPtr>, public loplugin::Plugin +{ +public: + explicit ConvertUIntPtr(InstantiationData const & data): Plugin(data) {} + + virtual void run() override + { + std::string fn( compiler.getSourceManager().getFileEntryForID( + compiler.getSourceManager().getMainFileID())->getName() ); + normalizeDotDotInFilePath(fn); + // using sal_uIntPtr as in-between type when converting void* to rtl_TextEncoding + if (fn == SRCDIR "/sal/osl/unx/thread.cxx") + return; + // too much magic + if (fn == SRCDIR "/sal/rtl/alloc_arena.cxx") + return; + if (fn == SRCDIR "/sal/rtl/alloc_cache.cxx") + return; + // TODO not sure what is going on here + if (fn == SRCDIR "/tools/source/generic/bigint.cxx") + return; + TraverseDecl(compiler.getASTContext().getTranslationUnitDecl()); + } + + bool VisitImplicitCastExpr(ImplicitCastExpr const *); +private: + bool isIntPtr(QualType qt); +}; + +bool ConvertUIntPtr::VisitImplicitCastExpr(ImplicitCastExpr const * castExpr) +{ + if (ignoreLocation(castExpr)) + return true; + + if (castExpr->getCastKind() == CK_LValueToRValue) + return true; + if (isa<IntegerLiteral>(castExpr->IgnoreCasts())) + return true; + // ignore literals like "-123" + if (isa<UnaryOperator>(castExpr->IgnoreCasts())) + return true; + + bool isSrcIntPtr = isIntPtr(castExpr->getSubExpr()->getType()); + bool isDestIntPtr = isIntPtr(castExpr->getType()); + + if (!isSrcIntPtr && !isDestIntPtr) + return true; + + // exclude casting between sal_uIntPtr <-> sal_IntPtr + if (isSrcIntPtr && isDestIntPtr) + return true; + + if (isSrcIntPtr && loplugin::TypeCheck(castExpr->getType()).AnyBoolean()) + return true; + + report( + DiagnosticsEngine::Warning, + "cast from %0 to %1", + castExpr->getExprLoc()) + << castExpr->getSubExpr()->getType() + << castExpr->getType() + << castExpr->getSourceRange(); + + return true; +} + +bool ConvertUIntPtr::isIntPtr(QualType qt) +{ + auto tc = loplugin::TypeCheck(qt); + if (!tc.Typedef()) + return false; + TypedefType const * typedefType = qt->getAs<TypedefType>(); + auto name = typedefType->getDecl()->getName(); + return name == "sal_uIntPtr" || name == "sal_IntPtr"; +} + +loplugin::Plugin::Registration< ConvertUIntPtr > X("convertuintptr", false); + +} + +/* vim:set shiftwidth=4 softtabstop=4 expandtab: */ |