aboutsummaryrefslogtreecommitdiff
path: root/clang
diff options
context:
space:
mode:
authorTimm Baeder <tbaeder@redhat.com>2023-11-16 06:24:04 +0100
committerGitHub <noreply@github.com>2023-11-16 06:24:04 +0100
commit0f8c51a5230b37331bd62d3e4ad73ac4a5deb106 (patch)
tree0291ee5942976a5b43dc6067c09e8e13055d1bd8 /clang
parent6416b2d0a81abdce0819961b9d12609e34916098 (diff)
downloadllvm-0f8c51a5230b37331bd62d3e4ad73ac4a5deb106.zip
llvm-0f8c51a5230b37331bd62d3e4ad73ac4a5deb106.tar.gz
llvm-0f8c51a5230b37331bd62d3e4ad73ac4a5deb106.tar.bz2
[clang][Interp] Implement __builtin_parity (#71662)
Diffstat (limited to 'clang')
-rw-r--r--clang/lib/AST/Interp/InterpBuiltin.cpp16
-rw-r--r--clang/test/AST/Interp/builtin-functions.cpp17
2 files changed, 32 insertions, 1 deletions
diff --git a/clang/lib/AST/Interp/InterpBuiltin.cpp b/clang/lib/AST/Interp/InterpBuiltin.cpp
index f26d298..0536fe4 100644
--- a/clang/lib/AST/Interp/InterpBuiltin.cpp
+++ b/clang/lib/AST/Interp/InterpBuiltin.cpp
@@ -439,6 +439,15 @@ static bool interp__builtin_popcount(InterpState &S, CodePtr OpPC,
return true;
}
+static bool interp__builtin_parity(InterpState &S, CodePtr OpPC,
+ const InterpFrame *Frame,
+ const Function *Func, const CallExpr *Call) {
+ PrimType ArgT = *S.getContext().classify(Call->getArg(0)->getType());
+ APSInt Val = peekToAPSInt(S.Stk, ArgT);
+ pushInt(S, Val.popcount() % 2);
+ return true;
+}
+
bool InterpretBuiltin(InterpState &S, CodePtr OpPC, const Function *F,
const CallExpr *Call) {
InterpFrame *Frame = S.Current;
@@ -576,6 +585,13 @@ bool InterpretBuiltin(InterpState &S, CodePtr OpPC, const Function *F,
return retInt(S, OpPC, Dummy);
break;
+ case Builtin::BI__builtin_parity:
+ case Builtin::BI__builtin_parityl:
+ case Builtin::BI__builtin_parityll:
+ if (interp__builtin_parity(S, OpPC, Frame, F, Call))
+ return retInt(S, OpPC, Dummy);
+ break;
+
default:
return false;
}
diff --git a/clang/test/AST/Interp/builtin-functions.cpp b/clang/test/AST/Interp/builtin-functions.cpp
index a78a0fb..14604a2b 100644
--- a/clang/test/AST/Interp/builtin-functions.cpp
+++ b/clang/test/AST/Interp/builtin-functions.cpp
@@ -274,6 +274,7 @@ namespace SourceLocation {
}
}
+#define BITSIZE(x) (sizeof(x) * 8)
namespace popcount {
static_assert(__builtin_popcount(~0u) == __CHAR_BIT__ * sizeof(unsigned int), "");
static_assert(__builtin_popcount(0) == 0, "");
@@ -283,7 +284,6 @@ namespace popcount {
static_assert(__builtin_popcountll(0) == 0, "");
/// From test/Sema/constant-builtins-2.c
-#define BITSIZE(x) (sizeof(x) * 8)
char popcount1[__builtin_popcount(0) == 0 ? 1 : -1];
char popcount2[__builtin_popcount(0xF0F0) == 8 ? 1 : -1];
char popcount3[__builtin_popcount(~0) == BITSIZE(int) ? 1 : -1];
@@ -295,3 +295,18 @@ namespace popcount {
char popcount9[__builtin_popcountll(0xF0F0LL) == 8 ? 1 : -1];
char popcount10[__builtin_popcountll(~0LL) == BITSIZE(long long) ? 1 : -1];
}
+
+namespace parity {
+ /// From test/Sema/constant-builtins-2.c
+ char parity1[__builtin_parity(0) == 0 ? 1 : -1];
+ char parity2[__builtin_parity(0xb821) == 0 ? 1 : -1];
+ char parity3[__builtin_parity(0xb822) == 0 ? 1 : -1];
+ char parity4[__builtin_parity(0xb823) == 1 ? 1 : -1];
+ char parity5[__builtin_parity(0xb824) == 0 ? 1 : -1];
+ char parity6[__builtin_parity(0xb825) == 1 ? 1 : -1];
+ char parity7[__builtin_parity(0xb826) == 1 ? 1 : -1];
+ char parity8[__builtin_parity(~0) == 0 ? 1 : -1];
+ char parity9[__builtin_parityl(1L << (BITSIZE(long) - 1)) == 1 ? 1 : -1];
+ char parity10[__builtin_parityll(1LL << (BITSIZE(long long) - 1)) == 1 ? 1 : -1];
+}
+