@@ -14168,18 +14168,39 @@ static QualType getCommonSugarTypeNode(ASTContext &Ctx, const Type *X,
1416814168 llvm_unreachable("Unhandled Type Class");
1416914169}
1417014170
14171+ /// Returns element type of the array, probably multidimensional, specified by
14172+ /// the given ArrayType.
14173+ /// \returns Canonical type of the array element.
14174+ static QualType getNonArrayElementType(const ArrayType* ATy) {
14175+ QualType ElTy = ATy->getElementType().getCanonicalType();
14176+ while (auto *SubArr = dyn_cast<ArrayType>(ElTy.getTypePtr()))
14177+ ElTy = SubArr->getElementType();
14178+ return ElTy;
14179+ }
14180+
14181+ /// Given a qualified type, returns an equivalent type, which has cv-qualifiers
14182+ /// only at array element type.
14183+ static SplitQualType normalizeArrayQualifiers(const SplitQualType &T) {
14184+ if (const auto *ATy = dyn_cast<ArrayType>(T.Ty)) {
14185+ // C++ 9.3.3.4p3: Any type of the form "cv-qualifier-seq array of N U" is
14186+ // adjusted to "array of N cv-qualifier-seq U".
14187+ // C23 6.7.3p10: If the specification of an array type includes any type
14188+ // qualifiers, both the array and the element type are so-qualified.
14189+ //
14190+ // If cv-qualifier is present in both array and element type, remove the
14191+ // redundant qualifiers from the array.
14192+ QualType ElTy = getNonArrayElementType(ATy);
14193+ unsigned Quals =
14194+ ElTy.getCVRQualifiers() & (Qualifiers::Const | Qualifiers::Volatile);
14195+ return SplitQualType(ATy, Qualifiers::fromCVRMask(Quals));
14196+ }
14197+ return T;
14198+ }
14199+
1417114200static auto unwrapSugar(SplitQualType &T, Qualifiers &QTotal) {
1417214201 SmallVector<SplitQualType, 8> R;
1417314202 while (true) {
14174- if (const auto *ATy = dyn_cast<ArrayType>(T.Ty)) {
14175- // C++ 9.3.3.4p3: Any type of the form "cv-qualifier-seq array of N U" is
14176- // adjusted to "array of N cv-qualifier-seq U".
14177- // C23 6.7.3p10: If the specification of an array type includes any type
14178- // qualifiers, both the array and the element type are so-qualified.
14179- //
14180- // To simplify comparison remove the redundant qualifiers from the array.
14181- T.Quals.removeCVRQualifiers(Qualifiers::Const | Qualifiers::Volatile);
14182- }
14203+ T = normalizeArrayQualifiers(T);
1418314204 QTotal.addConsistentQualifiers(T.Quals);
1418414205 QualType NT = T.Ty->getLocallyUnqualifiedSingleStepDesugaredType();
1418514206 if (NT == QualType(T.Ty, 0))
0 commit comments