diff options
| author | c8ef <c8ef@outlook.com> | 2024-11-26 20:31:29 +0800 |
|---|---|---|
| committer | GitHub <noreply@github.com> | 2024-11-26 20:31:29 +0800 |
| commit | 827ebf84e9af7c93a30daf4ed17e99ccef4cf94a (patch) | |
| tree | fc5e1effe817a2f1a6e8381c55e092c872bf648e /clang/lib/AST/ExprConstant.cpp | |
| parent | 90df66455b2ff6a3b3754a56afafc05935a05e15 (diff) | |
| download | llvm-827ebf84e9af7c93a30daf4ed17e99ccef4cf94a.zip llvm-827ebf84e9af7c93a30daf4ed17e99ccef4cf94a.tar.gz llvm-827ebf84e9af7c93a30daf4ed17e99ccef4cf94a.tar.bz2 | |
[clang] constexpr built-in elementwise popcount function. (#117473)
Part of #51787.
This patch adds constexpr support for the built-in elementwise popcount
function.
Diffstat (limited to 'clang/lib/AST/ExprConstant.cpp')
| -rw-r--r-- | clang/lib/AST/ExprConstant.cpp | 31 |
1 files changed, 31 insertions, 0 deletions
diff --git a/clang/lib/AST/ExprConstant.cpp b/clang/lib/AST/ExprConstant.cpp index c6d0030..bb5ab67 100644 --- a/clang/lib/AST/ExprConstant.cpp +++ b/clang/lib/AST/ExprConstant.cpp @@ -11005,6 +11005,7 @@ namespace { bool VisitUnaryImag(const UnaryOperator *E); bool VisitBinaryOperator(const BinaryOperator *E); bool VisitUnaryOperator(const UnaryOperator *E); + bool VisitCallExpr(const CallExpr *E); bool VisitConvertVectorExpr(const ConvertVectorExpr *E); bool VisitShuffleVectorExpr(const ShuffleVectorExpr *E); @@ -11302,6 +11303,35 @@ static bool handleVectorElementCast(EvalInfo &Info, const FPOptions FPO, return false; } +bool VectorExprEvaluator::VisitCallExpr(const CallExpr *E) { + if (!IsConstantEvaluatedBuiltinCall(E)) + return ExprEvaluatorBaseTy::VisitCallExpr(E); + + switch (E->getBuiltinCallee()) { + default: + return false; + case Builtin::BI__builtin_elementwise_popcount: { + APValue Source; + if (!EvaluateAsRValue(Info, E->getArg(0), Source)) + return false; + + QualType DestEltTy = E->getType()->castAs<VectorType>()->getElementType(); + unsigned SourceLen = Source.getVectorLength(); + SmallVector<APValue, 4> ResultElements; + ResultElements.reserve(SourceLen); + + for (unsigned EltNum = 0; EltNum < SourceLen; ++EltNum) { + APSInt Elt = Source.getVectorElt(EltNum).getInt(); + ResultElements.push_back( + APValue(APSInt(APInt(Info.Ctx.getIntWidth(DestEltTy), Elt.popcount()), + DestEltTy->isUnsignedIntegerOrEnumerationType()))); + } + + return Success(APValue(ResultElements.data(), ResultElements.size()), E); + } + } +} + bool VectorExprEvaluator::VisitConvertVectorExpr(const ConvertVectorExpr *E) { APValue Source; QualType SourceVecType = E->getSrcExpr()->getType(); @@ -13118,6 +13148,7 @@ bool IntExprEvaluator::VisitBuiltinCallExpr(const CallExpr *E, case Builtin::BI__builtin_popcountl: case Builtin::BI__builtin_popcountll: case Builtin::BI__builtin_popcountg: + case Builtin::BI__builtin_elementwise_popcount: case Builtin::BI__popcnt16: // Microsoft variants of popcount case Builtin::BI__popcnt: case Builtin::BI__popcnt64: { |
