================ @@ -0,0 +1,182 @@ +//===--- InvalidEnumDefaultInitializationCheck.cpp - clang-tidy -----------===// +// +// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. +// See https://llvm.org/LICENSE.txt for license information. +// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception +// +//===----------------------------------------------------------------------===// + +#include "InvalidEnumDefaultInitializationCheck.h" +#include "clang/AST/ASTContext.h" +#include "clang/AST/TypeVisitor.h" +#include "clang/ASTMatchers/ASTMatchFinder.h" +#include <algorithm> + +using namespace clang::ast_matchers; + +namespace clang::tidy::bugprone { + +namespace { + +bool isCompleteAndHasNoZeroValue(const EnumDecl *D) { + const EnumDecl *Definition = D->getDefinition(); + return Definition && Definition->isComplete() && + !Definition->enumerators().empty() && + std::none_of(Definition->enumerator_begin(), + Definition->enumerator_end(), + [](const EnumConstantDecl *Value) { + return Value->getInitVal().isZero(); + }); +} + +AST_MATCHER(EnumDecl, isCompleteAndHasNoZeroValue) { + return isCompleteAndHasNoZeroValue(&Node); +} + +// Find an initialization which initializes the value (if it has enum type) to a +// default zero value. +AST_MATCHER(Expr, isEmptyInit) { + if (isa<CXXScalarValueInitExpr>(&Node)) + return true; + if (isa<ImplicitValueInitExpr>(&Node)) + return true; + if (const auto *Init = dyn_cast<InitListExpr>(&Node)) { + if (Init->getNumInits() == 0) + return true; + } + return false; +} + +AST_MATCHER(InitListExpr, hasArrayFiller) { return Node.hasArrayFiller(); } + +// Check if any type has a "child" type that is an enum without zero value. +// The "child" type can be an array element type or member type of a record +// type (or a recursive combination of these). In this case, if the "root" type +// is statically initialized, the enum component is initialized to zero. +class FindEnumMember : public TypeVisitor<FindEnumMember, bool> { +public: + const EnumType *FoundEnum = nullptr; + + bool VisitType(const Type *T) { + const Type *DesT = T->getUnqualifiedDesugaredType(); + if (DesT != T) + return Visit(DesT); + return false; + } + bool VisitArrayType(const ArrayType *T) { + return Visit(T->getElementType()->getUnqualifiedDesugaredType()); ---------------- balazske wrote:
It looks redundant, I have removed `getUnqualifiedDesugaredType` when `Visit` is called (but `getTypePtr` is needed instead). https://github.com/llvm/llvm-project/pull/136823 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits