================ @@ -3250,26 +3285,17 @@ static void mergeParamDeclAttributes(ParmVarDecl *newDecl, diag::note_carries_dependency_missing_first_decl) << 1/*Param*/; } - if (!oldDecl->hasAttrs()) - return; - - bool foundAny = newDecl->hasAttrs(); - - // Ensure that any moving of objects within the allocated map is - // done before we process them. - if (!foundAny) newDecl->setAttrs(AttrVec()); - - for (const auto *I : oldDecl->specific_attrs<InheritableParamAttr>()) { - if (!DeclHasAttr(newDecl, I)) { - InheritableAttr *newAttr = - cast<InheritableParamAttr>(I->clone(S.Context)); - newAttr->setInherited(true); - newDecl->addAttr(newAttr); - foundAny = true; - } - } - - if (!foundAny) newDecl->dropAttrs(); + propagateAttributes( + newDecl, oldDecl, [&S](ParmVarDecl *toDecl, const ParmVarDecl *fromDecl) { + unsigned found = 0; + found += propagateAttribute<InheritableParamAttr>(toDecl, fromDecl, S); + // Propagate the lifetimebound attribute from parameters to the + // most recent declaration. Note that this doesn't include the implicit + // 'this' parameter, as the attribute is applied to the function type in + // that case. + found += propagateAttribute<LifetimeBoundAttr>(toDecl, fromDecl, S); ---------------- ilya-biryukov wrote:
It feels that LifetimeBoundAttr might need to be an `InheritableParamAttr` itself, which would allow to avoid having a template altogether. Are there any downsides to that? (I'm assuming that `InheritableParamAttr` represents the attributes that should be added from redeclarations, not just from the base methods of overridden members) https://github.com/llvm/llvm-project/pull/107627 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits