Author: Timm Baeder Date: 2023-10-19T08:20:53+02:00 New Revision: 59d2dc239b053d124ebc82937da2e7a38d0ec11e
URL: https://github.com/llvm/llvm-project/commit/59d2dc239b053d124ebc82937da2e7a38d0ec11e DIFF: https://github.com/llvm/llvm-project/commit/59d2dc239b053d124ebc82937da2e7a38d0ec11e.diff LOG: [clang][Interp] IntegralAP zero-initializers (#68081) Added: Modified: clang/lib/AST/Interp/ByteCodeExprGen.cpp clang/lib/AST/Interp/IntegralAP.h clang/lib/AST/Interp/Interp.h clang/lib/AST/Interp/Opcodes.td clang/test/AST/Interp/intap.cpp Removed: ################################################################################ diff --git a/clang/lib/AST/Interp/ByteCodeExprGen.cpp b/clang/lib/AST/Interp/ByteCodeExprGen.cpp index e9e20b222d5d34f..d9389e7b0033191 100644 --- a/clang/lib/AST/Interp/ByteCodeExprGen.cpp +++ b/clang/lib/AST/Interp/ByteCodeExprGen.cpp @@ -1665,9 +1665,9 @@ bool ByteCodeExprGen<Emitter>::visitZeroInitializer(PrimType T, QualType QT, case PT_Uint64: return this->emitZeroUint64(E); case PT_IntAP: + return this->emitZeroIntAP(Ctx.getBitWidth(QT), E); case PT_IntAPS: - assert(false); - return false; + return this->emitZeroIntAPS(Ctx.getBitWidth(QT), E); case PT_Ptr: return this->emitNullPtr(E); case PT_FnPtr: diff --git a/clang/lib/AST/Interp/IntegralAP.h b/clang/lib/AST/Interp/IntegralAP.h index fd120944a25043e..ebf362238ba09d5 100644 --- a/clang/lib/AST/Interp/IntegralAP.h +++ b/clang/lib/AST/Interp/IntegralAP.h @@ -78,7 +78,8 @@ template <bool Signed> class IntegralAP final { template <typename T> static IntegralAP from(T Value, unsigned NumBits = 0) { assert(NumBits > 0); - APSInt Copy = APSInt(APInt(NumBits, static_cast<int64_t>(Value), Signed), !Signed); + APSInt Copy = + APSInt(APInt(NumBits, static_cast<uint64_t>(Value), Signed), !Signed); return IntegralAP<Signed>(Copy); } @@ -97,16 +98,16 @@ template <bool Signed> class IntegralAP final { template <unsigned Bits, bool InputSigned> static IntegralAP from(Integral<Bits, InputSigned> I, unsigned BitWidth) { APSInt Copy = - APSInt(APInt(BitWidth, static_cast<int64_t>(I), InputSigned), !Signed); + APSInt(APInt(BitWidth, static_cast<uint64_t>(I), InputSigned), !Signed); Copy.setIsSigned(Signed); assert(Copy.isSigned() == Signed); return IntegralAP<Signed>(Copy); } - static IntegralAP zero() { - assert(false); - return IntegralAP(0); + static IntegralAP zero(int32_t BitWidth) { + APSInt V = APSInt(APInt(BitWidth, 0LL, Signed), !Signed); + return IntegralAP(V); } constexpr unsigned bitWidth() const { return V.getBitWidth(); } diff --git a/clang/lib/AST/Interp/Interp.h b/clang/lib/AST/Interp/Interp.h index 3d226a40f9cf608..4b081301655cfb2 100644 --- a/clang/lib/AST/Interp/Interp.h +++ b/clang/lib/AST/Interp/Interp.h @@ -1688,6 +1688,16 @@ bool Zero(InterpState &S, CodePtr OpPC) { return true; } +static inline bool ZeroIntAP(InterpState &S, CodePtr OpPC, uint32_t BitWidth) { + S.Stk.push<IntegralAP<false>>(IntegralAP<false>::zero(BitWidth)); + return true; +} + +static inline bool ZeroIntAPS(InterpState &S, CodePtr OpPC, uint32_t BitWidth) { + S.Stk.push<IntegralAP<true>>(IntegralAP<true>::zero(BitWidth)); + return true; +} + template <PrimType Name, class T = typename PrimConv<Name>::T> inline bool Null(InterpState &S, CodePtr OpPC) { S.Stk.push<T>(); diff --git a/clang/lib/AST/Interp/Opcodes.td b/clang/lib/AST/Interp/Opcodes.td index 9d390fed152417f..e1e7e5e2efbb059 100644 --- a/clang/lib/AST/Interp/Opcodes.td +++ b/clang/lib/AST/Interp/Opcodes.td @@ -72,6 +72,11 @@ def IntegerTypeClass : TypeClass { Uint32, Sint64, Uint64, IntAP, IntAPS]; } +def FixedSizeIntegralTypeClass : TypeClass { + let Types = [Sint8, Uint8, Sint16, Uint16, Sint32, + Uint32, Sint64, Uint64, Bool]; +} + def NumberTypeClass : TypeClass { let Types = !listconcat(IntegerTypeClass.Types, [Float]); } @@ -243,10 +248,18 @@ def ConstBool : ConstOpcode<Bool, ArgBool>; // [] -> [Integer] def Zero : Opcode { - let Types = [AluTypeClass]; + let Types = [FixedSizeIntegralTypeClass]; let HasGroup = 1; } +def ZeroIntAP : Opcode { + let Args = [ArgUint32]; +} + +def ZeroIntAPS : Opcode { + let Args = [ArgUint32]; +} + // [] -> [Pointer] def Null : Opcode { let Types = [PtrTypeClass]; diff --git a/clang/test/AST/Interp/intap.cpp b/clang/test/AST/Interp/intap.cpp index ef7a0d4f0dfdab0..27fae1b904351ce 100644 --- a/clang/test/AST/Interp/intap.cpp +++ b/clang/test/AST/Interp/intap.cpp @@ -17,6 +17,16 @@ constexpr MaxBitInt A_ = 0; constexpr MaxBitInt B_ = A_ + 1; static_assert(B_ == 1, ""); +constexpr MaxBitInt BitIntZero{}; +static_assert(BitIntZero == 0, ""); +constexpr unsigned _BitInt(128) UBitIntZero{}; +static_assert(UBitIntZero == 0, ""); + +constexpr _BitInt(2) BitIntZero2{}; +static_assert(BitIntZero2 == 0, ""); +constexpr unsigned _BitInt(1) UBitIntZero1{}; +static_assert(UBitIntZero1 == 0, ""); + #ifdef __SIZEOF_INT128__ namespace i128 { @@ -49,6 +59,11 @@ namespace i128 { constexpr uint128_t AllOnes = ~static_cast<uint128_t>(0); static_assert(AllOnes == UINT128_MAX, ""); + constexpr uint128_t i128Zero{}; + static_assert(i128Zero == 0, ""); + constexpr uint128_t ui128Zero{}; + static_assert(ui128Zero == 0, ""); + #if __cplusplus >= 201402L template <typename T> constexpr T CastFrom(__int128_t A) { _______________________________________________ cfe-commits mailing list cfe-commits@lists.llvm.org https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits