================ @@ -870,7 +870,29 @@ static bool IsStructurallyEquivalent(StructuralEquivalenceContext &Context, else if (T1->getTypeClass() == Type::FunctionNoProto && T2->getTypeClass() == Type::FunctionProto) TC = Type::FunctionNoProto; - else + else if (Context.LangOpts.C23 && !Context.StrictTypeSpelling && + (T1->getTypeClass() == Type::Enum || + T2->getTypeClass() == Type::Enum)) { + // In C23, if not being strict about token equivalence, we need to handle + // the case where one type is an enumeration and the other type is an + // integral type. + // + // C23 6.7.3.3p16: The enumerated type is compatible with the underlying + // type of the enumeration. + // + // Treat the enumeration as its underlying type and use the builtin type + // class comparison. + if (T1->getTypeClass() == Type::Enum) { + T1 = T1->getAs<EnumType>()->getDecl()->getIntegerType(); + if (!T2->isBuiltinType() || T1.isNull()) // Sanity check + return false; ---------------- AaronBallman wrote:
In general, yes, but given that I want to put this on the release branch with little time for finding fallout, I'd prefer to not assert; we mostly recover by using `int` as a type, but that's not a guarantee. How about this for an idea, leave it this way, land the changes, pick the changes to 21.x, once the pick is finished, make this an assert on main? https://github.com/llvm/llvm-project/pull/150282 _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits