Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit 814ed93

Browse files
authoredDec 3, 2024··
[clang] constexpr built-in elementwise bitreverse function. (#118177)
Part of #51787. This patch adds constexpr support for the built-in elementwise bitreverse function.
1 parent 7907292 commit 814ed93

File tree

6 files changed

+25
-8
lines changed

6 files changed

+25
-8
lines changed
 

‎clang/docs/LanguageExtensions.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -648,7 +648,7 @@ elementwise to the input.
648648
Unless specified otherwise operation(±0) = ±0 and operation(±infinity) = ±infinity
649649

650650
The integer elementwise intrinsics, including ``__builtin_elementwise_popcount``,
651-
can be called in a ``constexpr`` context.
651+
``__builtin_elementwise_bitreverse``, can be called in a ``constexpr`` context.
652652

653653
============================================== ====================================================================== =========================================
654654
Name Operation Supported element types

‎clang/docs/ReleaseNotes.rst

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -404,6 +404,7 @@ Non-comprehensive list of changes in this release
404404
- ``__builtin_reduce_and`` function can now be used in constant expressions.
405405
- ``__builtin_reduce_or`` and ``__builtin_reduce_xor`` functions can now be used in constant expressions.
406406
- ``__builtin_elementwise_popcount`` function can now be used in constant expressions.
407+
- ``__builtin_elementwise_bitreverse`` function can now be used in constant expressions.
407408

408409
New Compiler Flags
409410
------------------

‎clang/include/clang/Basic/Builtins.td

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1270,7 +1270,7 @@ def ElementwiseATan2 : Builtin {
12701270

12711271
def ElementwiseBitreverse : Builtin {
12721272
let Spellings = ["__builtin_elementwise_bitreverse"];
1273-
let Attributes = [NoThrow, Const, CustomTypeChecking];
1273+
let Attributes = [NoThrow, Const, CustomTypeChecking, Constexpr];
12741274
let Prototype = "void(...)";
12751275
}
12761276

‎clang/lib/AST/ExprConstant.cpp

Lines changed: 16 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -11310,7 +11310,8 @@ bool VectorExprEvaluator::VisitCallExpr(const CallExpr *E) {
1131011310
switch (E->getBuiltinCallee()) {
1131111311
default:
1131211312
return false;
11313-
case Builtin::BI__builtin_elementwise_popcount: {
11313+
case Builtin::BI__builtin_elementwise_popcount:
11314+
case Builtin::BI__builtin_elementwise_bitreverse: {
1131411315
APValue Source;
1131511316
if (!EvaluateAsRValue(Info, E->getArg(0), Source))
1131611317
return false;
@@ -11322,9 +11323,18 @@ bool VectorExprEvaluator::VisitCallExpr(const CallExpr *E) {
1132211323

1132311324
for (unsigned EltNum = 0; EltNum < SourceLen; ++EltNum) {
1132411325
APSInt Elt = Source.getVectorElt(EltNum).getInt();
11325-
ResultElements.push_back(
11326-
APValue(APSInt(APInt(Info.Ctx.getIntWidth(DestEltTy), Elt.popcount()),
11327-
DestEltTy->isUnsignedIntegerOrEnumerationType())));
11326+
switch (E->getBuiltinCallee()) {
11327+
case Builtin::BI__builtin_elementwise_popcount:
11328+
ResultElements.push_back(APValue(
11329+
APSInt(APInt(Info.Ctx.getIntWidth(DestEltTy), Elt.popcount()),
11330+
DestEltTy->isUnsignedIntegerOrEnumerationType())));
11331+
break;
11332+
case Builtin::BI__builtin_elementwise_bitreverse:
11333+
ResultElements.push_back(
11334+
APValue(APSInt(Elt.reverseBits(),
11335+
DestEltTy->isUnsignedIntegerOrEnumerationType())));
11336+
break;
11337+
}
1132811338
}
1132911339

1133011340
return Success(APValue(ResultElements.data(), ResultElements.size()), E);
@@ -12833,7 +12843,8 @@ bool IntExprEvaluator::VisitBuiltinCallExpr(const CallExpr *E,
1283312843
case Builtin::BI__builtin_bitreverse8:
1283412844
case Builtin::BI__builtin_bitreverse16:
1283512845
case Builtin::BI__builtin_bitreverse32:
12836-
case Builtin::BI__builtin_bitreverse64: {
12846+
case Builtin::BI__builtin_bitreverse64:
12847+
case Builtin::BI__builtin_elementwise_bitreverse: {
1283712848
APSInt Val;
1283812849
if (!EvaluateInteger(E->getArg(0), Val, Info))
1283912850
return false;

‎clang/test/CodeGen/builtins-elementwise-math.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -443,7 +443,7 @@ void test_builtin_elementwise_bitreverse(si8 vi1, si8 vi2,
443443
// CHECK-NEXT: call i32 @llvm.bitreverse.i32(i32 [[IA1]])
444444
b = __builtin_elementwise_bitreverse(int_as_one);
445445

446-
// CHECK: call i32 @llvm.bitreverse.i32(i32 -10)
446+
// CHECK: store i32 1879048191, ptr @b, align 4
447447
b = __builtin_elementwise_bitreverse(-10);
448448

449449
// CHECK: [[SI:%.+]] = load i16, ptr %si.addr, align 2

‎clang/test/Sema/constant_builtins_vector.cpp

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -817,3 +817,8 @@ static_assert(__builtin_elementwise_popcount(~0U) == 8 * sizeof(int));
817817
static_assert(__builtin_elementwise_popcount(0L) == 0);
818818
static_assert(__builtin_elementwise_popcount(0xF0F0L) == 8);
819819
static_assert(__builtin_elementwise_popcount(~0LL) == 8 * sizeof(long long));
820+
821+
static_assert(__builtin_elementwise_bitreverse(0x12345678) == 0x1E6A2C48);
822+
static_assert(__builtin_elementwise_bitreverse(0x0123456789ABCDEFULL) == 0xF7B3D591E6A2C480);
823+
static_assert(__builtin_bit_cast(unsigned, __builtin_elementwise_bitreverse((vector4char){1, 2, 4, 8})) == (LITTLE_END ? 0x10204080 : 0x80402010));
824+
static_assert(__builtin_bit_cast(unsigned long long, __builtin_elementwise_bitreverse((vector4short){1, 2, 4, 8})) == (LITTLE_END ? 0x1000200040008000 : 0x8000400020001000));

0 commit comments

Comments
 (0)
Please sign in to comment.