From c233aaa76e53d3a0598628f210e389879eb258d1 Mon Sep 17 00:00:00 2001 From: Virgile Prevosto <virgile.prevosto@m4x.org> Date: Fri, 12 Mar 2021 11:21:52 +0100 Subject: [PATCH] [clang translation] avoid potential uninitialized uses + constify --- ClangVisitor.cpp | 220 +++++++++++++++++++++++------------------------ Clang_utils.cpp | 1 + RTTITable.cpp | 4 +- RTTITable.h | 14 +-- 4 files changed, 120 insertions(+), 119 deletions(-) diff --git a/ClangVisitor.cpp b/ClangVisitor.cpp index f4e34d8b..4e6ac540 100644 --- a/ClangVisitor.cpp +++ b/ClangVisitor.cpp @@ -5045,17 +5045,16 @@ void FramacVisitor::ensureVaListDeclaration(const clang::RecordDecl* decl) { body = opt_some_container(funContent); }; }; - + const clang::RecordDecl* current_class = decl; funkind kind; if (functionDecl->getCanonicalDecl()->getStorageClass() == clang::SC_Static) kind = funkind_FKFunction(); else { + const auto meth = + llvm::cast<const clang::CXXMethodDecl>(functionDecl); if (clang::CXXMethodDecl::classof(functionDecl)) { - const clang::CXXMethodDecl* meth - = static_cast<const clang::CXXMethodDecl*>(functionDecl); - kind = _clangUtils->cv_meth(meth); }; arg_decl cdecl = (arg_decl)malloc(sizeof(*cdecl)); prms = cons_container(cdecl,prms); @@ -5063,33 +5062,31 @@ void FramacVisitor::ensureVaListDeclaration(const clang::RecordDecl* decl) { clang::QualType typeClass(current_class->getTypeForDecl(), 0); qual_type this_type = _clangUtils->makeType(functionDecl->getLocation(), typeClass); - this_type->qualifier = - cv_this_ptr( - static_cast<const clang::CXXMethodDecl*>(functionDecl)); + this_type->qualifier = cv_this_ptr(meth); pkind pointerKind = pkind_PDataPointer(this_type); cdecl->arg_type = qual_type_cons(NULL, typ_Pointer(pointerKind)); cdecl->arg_loc = makeLocation(functionDecl->getSourceRange()); - }; - if (functionDecl->getKind() == clang::Decl::CXXConstructor) { - kind = funkind_FKConstructor(true); - if (strlen(name) == 0) { - free(const_cast<char*>(name)); - name = strdup("constructor-special"); - }; - if (body->is_some) { - list& contentBody = *(list*)&body->content.container; - insertConstructorPreambleIn( - *static_cast<const clang::CXXConstructorDecl*>(functionDecl), - contentBody,NULL); + if (llvm::isa<clang::CXXConstructorDecl>(meth)) { + kind = funkind_FKConstructor(true); + if (strlen(name) == 0) { + free(const_cast<char*>(name)); + name = strdup("constructor-special"); + } + if (body->is_some) { + list& contentBody = *(list*)&body->content.container; + insertConstructorPreambleIn( + *llvm::cast<const clang::CXXConstructorDecl>(meth), + contentBody,NULL); + } + } else if (llvm::isa<clang::CXXDestructorDecl>(meth)) { + kind = funkind_FKDestructor(true); + if (body->is_some) + insertDestructorPreambleIn( + *llvm::cast<const clang::CXXDestructorDecl>(meth), body); + } else { + kind = _clangUtils->cv_meth(meth); } - }; - if (functionDecl->getKind() == clang::Decl::CXXDestructor) { - kind = funkind_FKDestructor(true); - if (body->is_some) - insertDestructorPreambleIn( - *static_cast<const clang::CXXDestructorDecl*>(functionDecl), - body); - }; + } bool is_implicit = isImplicitFunction || functionDecl->isDefaulted(); bool is_variadic = functionDecl->isVariadic(); class_decl method = class_decl_CMethod( @@ -6923,11 +6920,12 @@ bool FramacVisitor::VisitFunctionDecl(clang::FunctionDecl* Decl) { } else { if (Decl->getDeclContext()->isRecord() /* _parents.isClass() */) { - assert(llvm::dyn_cast<clang::CXXRecordDecl>(Decl->getDeclContext())); const clang::CXXRecordDecl* current_class = - (const clang::CXXRecordDecl*) Decl->getDeclContext(); + llvm::cast<const clang::CXXRecordDecl>(Decl->getDeclContext()); /* need to resynchronize RTTI table if the definition is outside of the class body. */ + option /* statement list */ bodyref = delayedBody ? delayedBody : body; + option bodyBare = NULL; funkind kind; if (Decl->getCanonicalDecl()->getStorageClass() == clang::SC_Static || Decl->getNameAsString() == "operator new" || @@ -6936,11 +6934,88 @@ bool FramacVisitor::VisitFunctionDecl(clang::FunctionDecl* Decl) { Decl->getNameAsString() == "operator delete[]") kind = funkind_FKFunction(); else { - if (clang::CXXMethodDecl::classof(Decl)) { - clang::CXXMethodDecl* meth = static_cast<clang::CXXMethodDecl*>(Decl); - if (meth->isVirtual() - && Decl->getDeclContext() == Decl->getLexicalDeclContext()) - _rttiTable.addVirtualMethod(meth); + auto meth = llvm::cast<const clang::CXXMethodDecl>(Decl); + if (meth->isVirtual() + && Decl->getDeclContext() == Decl->getLexicalDeclContext()) + _rttiTable.addVirtualMethod(meth); + if (llvm::isa<clang::CXXConstructorDecl>(Decl)) { + kind = funkind_FKConstructor(true); + if (strlen(name) == 0) { + free(const_cast<char*>(name)); + name = strdup("constructor-special"); + }; + bool hasVirtualBaseClasses = + _rttiTable.hasVirtualBaseClasses(current_class); + if (bodyref->is_some) { + bool shouldDelay = false; + /* statement */ list bareResult = NULL; + ForwardReferenceList headerBare(bareResult); + if (hasVirtualBaseClasses && + _clangUtils->doesGenerateBareFunctions() && + (list) bodyref->content.container) { + list cursor = (list) bodyref->content.container; + headerBare.insertContainer((statement) cursor->element.container); + cursor = cursor->next; + while (cursor) { + headerBare.insertContainer( + (statement) cursor->element.container); + cursor = cursor->next; + } + } + insertConstructorPreambleIn( + *llvm::cast<const clang::CXXConstructorDecl>(Decl), + *(list*)&bodyref->content.container, &shouldDelay, + (hasVirtualBaseClasses&& _clangUtils->doesGenerateBareFunctions()) + ? &headerBare : NULL); + if ((shouldDelay || (hasVirtualBaseClasses + && _clangUtils->doesGenerateBareFunctions())) + && !delayedBody) { + delayedBody = body; + body = opt_none(); + }; + if (bareResult) + bodyBare = opt_some_container(bareResult); + } + else if (hasVirtualBaseClasses + && _clangUtils->doesGenerateBareFunctions()) + bodyBare = opt_none(); + } else if (llvm::isa<clang::CXXDestructorDecl>(Decl)) { + // the same as for FKCONSTRUCTOR + kind = funkind_FKDestructor(true); + if (bodyref->is_some) { + /* statement */ list bareResult = NULL; + bool hasVirtualBaseClasses = + _rttiTable.hasVirtualBaseClasses(current_class); + ForwardReferenceList headerBare(bareResult); + if (hasVirtualBaseClasses && (list) bodyref->content.container) { + list cursor = (list) bodyref->content.container; + headerBare.insertContainer((statement) cursor->element.container); + cursor = cursor->next; + while (cursor) { + headerBare.insertContainer( + (statement) cursor->element.container); + cursor = cursor->next; + }; + }; + insertDestructorPreambleIn( + *llvm::cast<const clang::CXXDestructorDecl>(Decl), + bodyref, + (hasVirtualBaseClasses && + _clangUtils->doesGenerateBareFunctions()) + ? &headerBare : NULL); + if (hasVirtualBaseClasses && + _clangUtils->doesGenerateBareFunctions()) + { bodyBare = opt_some_container(bareResult); + if (!delayedBody) { + delayedBody = body; + body = opt_none(); + }; + }; + } + else if (_clangUtils->doesGenerateBareFunctions() + && _rttiTable.hasVirtualBaseClasses(current_class)) + bodyBare = opt_none(); + } else { kind = _clangUtils->cv_meth(meth); }; arg_decl cdecl = (arg_decl)malloc(sizeof(*cdecl)); @@ -6954,82 +7029,7 @@ bool FramacVisitor::VisitFunctionDecl(clang::FunctionDecl* Decl) { pkind pointerKind = pkind_PDataPointer(this_type); cdecl->arg_type = qual_type_cons(NULL, typ_Pointer(pointerKind)); cdecl->arg_loc = makeLocation(Decl->getSourceRange()); - }; - option /* statement list */ bodyref = delayedBody ? delayedBody : body; - option bodyBare = NULL; - if (Decl->getKind() == clang::Decl::CXXConstructor) { - kind = funkind_FKConstructor(true); - if (strlen(name) == 0) { - free(const_cast<char*>(name)); - name = strdup("constructor-special"); - }; - bool hasVirtualBaseClasses = _rttiTable - .hasVirtualBaseClasses(current_class); - if (bodyref->is_some) { - bool shouldDelay = false; - /* statement */ list bareResult = NULL; - ForwardReferenceList headerBare(bareResult); - if (hasVirtualBaseClasses && _clangUtils->doesGenerateBareFunctions() - && (list) bodyref->content.container) { - list cursor = (list) bodyref->content.container; - headerBare.insertContainer((statement) cursor->element.container); - cursor = cursor->next; - while (cursor) { - headerBare.insertContainer((statement) cursor->element.container); - cursor = cursor->next; - }; - }; - insertConstructorPreambleIn( - *static_cast<const clang::CXXConstructorDecl*>(Decl), - *(list*)&bodyref->content.container, &shouldDelay, - (hasVirtualBaseClasses&& _clangUtils->doesGenerateBareFunctions()) - ? &headerBare : NULL); - if ((shouldDelay || (hasVirtualBaseClasses - && _clangUtils->doesGenerateBareFunctions())) - && !delayedBody) { - delayedBody = body; - body = opt_none(); - }; - if (bareResult) - bodyBare = opt_some_container(bareResult); - } - else if (hasVirtualBaseClasses - && _clangUtils->doesGenerateBareFunctions()) - bodyBare = opt_none(); - }; - if (Decl->getKind() == clang::Decl::CXXDestructor) { - // the same as for FKCONSTRUCTOR - kind = funkind_FKDestructor(true); - if (bodyref->is_some) { - /* statement */ list bareResult = NULL; - bool hasVirtualBaseClasses = _rttiTable - .hasVirtualBaseClasses(current_class); - ForwardReferenceList headerBare(bareResult); - if (hasVirtualBaseClasses && (list) bodyref->content.container) { - list cursor = (list) bodyref->content.container; - headerBare.insertContainer((statement) cursor->element.container); - cursor = cursor->next; - while (cursor) { - headerBare.insertContainer((statement) cursor->element.container); - cursor = cursor->next; - }; - }; - insertDestructorPreambleIn(*static_cast<const - clang::CXXDestructorDecl*>(Decl), bodyref, - (hasVirtualBaseClasses && _clangUtils->doesGenerateBareFunctions()) - ? &headerBare : NULL); - if (hasVirtualBaseClasses && _clangUtils->doesGenerateBareFunctions()) - { bodyBare = opt_some_container(bareResult); - if (!delayedBody) { - delayedBody = body; - body = opt_none(); - }; - }; - } - else if (_clangUtils->doesGenerateBareFunctions() - && _rttiTable.hasVirtualBaseClasses(current_class)) - bodyBare = opt_none(); - }; + } bool is_implicit = isImplicitFunction || Decl->isDefaulted(); bool is_variadic = Decl->isVariadic(); if (_parents.isClass()) { diff --git a/Clang_utils.cpp b/Clang_utils.cpp index b5318fbb..d1ac0e70 100644 --- a/Clang_utils.cpp +++ b/Clang_utils.cpp @@ -641,6 +641,7 @@ expression Intermediate_ast::makeFloatZero(const location loc, fkind k) { case FFLOAT: r = "0.0f"; break; case FDOUBLE: r = "0.0"; break; case FLONGDOUBLE: r = "0.0l"; break; + default: __builtin_unreachable(); } return makeFloatConstant(loc,k,r); } diff --git a/RTTITable.cpp b/RTTITable.cpp index bbf781ae..853aada9 100644 --- a/RTTITable.cpp +++ b/RTTITable.cpp @@ -183,7 +183,7 @@ bool RTTITable::ClassInfo::isSameMethod( } int -RTTITable::ClassInfo::addVirtualMethod(clang::CXXMethodDecl* method) +RTTITable::ClassInfo::addVirtualMethod(const clang::CXXMethodDecl* method) { typedef std::vector<VirtualMethodInfo>::iterator MethodIterator; MethodIterator iterEnd = _virtualMethodTable.end(); int result = 0, index = 0; @@ -213,7 +213,7 @@ RTTITable::ClassInfo::addVirtualMethod(clang::CXXMethodDecl* method) } int -RTTITable::ClassInfo::getIndexOfMethod(clang::CXXMethodDecl* method, +RTTITable::ClassInfo::getIndexOfMethod(const clang::CXXMethodDecl* method, const InheritancePath*& inheritancePath, const VirtualInheritancePath*& virtualInheritancePath) const { MethodIterator iterEnd = _virtualMethodTable.end(); diff --git a/RTTITable.h b/RTTITable.h index bb4cc49b..a38631a5 100644 --- a/RTTITable.h +++ b/RTTITable.h @@ -58,7 +58,7 @@ private: private: class VirtualMethodInfo { private: - clang::CXXMethodDecl* _method; + const clang::CXXMethodDecl* _method; InheritancePath _inheritancePath; VirtualInheritancePath _virtualInheritancePath; InheritancePath _parentInheritancePath; @@ -69,7 +69,7 @@ private: std::make_pair((const clang::CXXRecordDecl*) NULL, 0)) {} // shift for virtual base class access // _virtualInheritancePath.second is the index in _virtualMethodTable - VirtualMethodInfo(clang::CXXMethodDecl* method) + VirtualMethodInfo(const clang::CXXMethodDecl* method) : _method(method), _virtualInheritancePath( std::make_pair((const clang::CXXRecordDecl*) NULL, 0)) @@ -92,8 +92,8 @@ private: } bool isMethod() const { return _method != NULL; } bool isVirtualBaseAccess() const { return _method == NULL; } - clang::CXXMethodDecl* getMethod() const { return _method; } - void setMethod(clang::CXXMethodDecl* method) { _method = method; } + const clang::CXXMethodDecl* getMethod() const { return _method; } + void setMethod(const clang::CXXMethodDecl* method) { _method = method; } void addInherits(const clang::CXXRecordDecl* baseClass, int vmtPosition) { if (!_virtualInheritancePath.first) _inheritancePath.push_back( @@ -150,8 +150,8 @@ private: const std::vector<const clang::CXXRecordDecl*>& getVirtualBases() const { return _virtualBaseClassTable; } int numberOfMethods() const { return _virtualMethodTable.size(); } - int addVirtualMethod(clang::CXXMethodDecl* method); - int getIndexOfMethod(clang::CXXMethodDecl* method, + int addVirtualMethod(const clang::CXXMethodDecl* method); + int getIndexOfMethod(const clang::CXXMethodDecl* method, const InheritancePath*& inheritancePath, const VirtualInheritancePath*& virtualInheritancePath) const; int getBasePosition(const clang::CXXRecordDecl* base, bool& isVirtual) @@ -462,7 +462,7 @@ public: }; return result; } - void addVirtualMethod(clang::CXXMethodDecl* method) + void addVirtualMethod(const clang::CXXMethodDecl* method) { assert(!_currentClass.empty() && !_virtualTags.empty()); _currentClassInfo.front().addVirtualMethod(method); *_virtualTags.back() = true; -- GitLab