From aa69e15c6909c3b162b15f5326f0a72ba9bb7163 Mon Sep 17 00:00:00 2001 From: Richard-Qin-X Date: Thu, 13 Aug 2026 23:55:38 +0800 Subject: [CodeGen] Unify scalar low-level types --- .../include/rcc/CodeGen/InstructionDescriptor.h | 18 +++-- backend/include/rcc/CodeGen/LowLevelType.h | 89 +++++++--------------- backend/include/rcc/CodeGen/MachineMemOperand.h | 2 +- backend/include/rcc/CodeGen/MachineRegisterInfo.h | 6 +- backend/include/rcc/CodeGen/TargetCallLowering.h | 17 ++++- 5 files changed, 55 insertions(+), 77 deletions(-) (limited to 'backend/include/rcc') diff --git a/backend/include/rcc/CodeGen/InstructionDescriptor.h b/backend/include/rcc/CodeGen/InstructionDescriptor.h index 15d2162..ddc42e8 100644 --- a/backend/include/rcc/CodeGen/InstructionDescriptor.h +++ b/backend/include/rcc/CodeGen/InstructionDescriptor.h @@ -67,24 +67,24 @@ private: std::uint32_t Mask = 0; }; -class LLTKindSet final { +class LowLevelTypeKindSet final { public: - static_assert(static_cast(LLT::Kind::VectorPointer) < 16); + static_assert(static_cast(LowLevelType::Kind::VectorPointer) < 16); - constexpr LLTKindSet() noexcept = default; + constexpr LowLevelTypeKindSet() noexcept = default; - LLTKindSet(std::initializer_list Kinds) noexcept; + LowLevelTypeKindSet(std::initializer_list Kinds) noexcept; [[nodiscard]] constexpr bool empty() const noexcept { return Mask == 0; } - [[nodiscard]] constexpr bool contains(LLT::Kind Kind) const noexcept { + [[nodiscard]] constexpr bool contains(LowLevelType::Kind Kind) const noexcept { const auto Index = static_cast(Kind); return Index < 16 && (Mask & (std::uint16_t{1} << Index)) != 0; } - constexpr void add(LLT::Kind Kind) noexcept { + constexpr void add(LowLevelType::Kind Kind) noexcept { const auto Index = static_cast(Kind); if (Index < 16) Mask |= std::uint16_t{1} << Index; @@ -94,7 +94,8 @@ public: return Mask; } - friend constexpr bool operator==(LLTKindSet Left, LLTKindSet Right) noexcept = default; + friend constexpr bool operator==(LowLevelTypeKindSet Left, + LowLevelTypeKindSet Right) noexcept = default; private: std::uint16_t Mask = 0; @@ -117,7 +118,7 @@ enum class MemoryOperandRole : std::uint8_t { }; struct OperandTypeConstraint final { - LLTKindSet Kinds; + LowLevelTypeKindSet Kinds; std::optional EqualityGroup; }; @@ -141,6 +142,7 @@ enum class InstructionFlag : std::uint8_t { NotDuplicable, Convergent, UnmodeledSideEffects, + MayRaiseFPException, Phi, FakeUse, Generic, diff --git a/backend/include/rcc/CodeGen/LowLevelType.h b/backend/include/rcc/CodeGen/LowLevelType.h index e6ff174..d35d30d 100644 --- a/backend/include/rcc/CodeGen/LowLevelType.h +++ b/backend/include/rcc/CodeGen/LowLevelType.h @@ -3,7 +3,6 @@ #ifndef RCC_CODEGEN_LOWLEVELTYPE_H #define RCC_CODEGEN_LOWLEVELTYPE_H -#include "rcc/ADT/APFloat.h" #include "rcc/Support/Error.h" #include @@ -16,18 +15,14 @@ namespace rcc { -class LLT final { +class LowLevelType final { public: enum class Kind : std::uint8_t { Invalid, Token, - AnyScalar, - Integer, - Float, + CategoryNeutralScalar, Pointer, - VectorAny, - VectorInteger, - VectorFloat, + Vector, VectorPointer, }; @@ -35,20 +30,19 @@ public: static constexpr std::uint32_t MaxElementCount = (std::uint32_t{1} << 16) - 1; static constexpr std::uint32_t MaxAddressSpace = (std::uint32_t{1} << 24) - 1; - constexpr LLT() noexcept = default; + constexpr LowLevelType() noexcept = default; - [[nodiscard]] static constexpr LLT token() noexcept { - return LLT(encode(Kind::Token, 0, 0, 0, false)); + [[nodiscard]] static constexpr LowLevelType token() noexcept { + return LowLevelType(encode(Kind::Token, 0, 0, 0, false)); } - [[nodiscard]] static Expected makeAnyScalar(std::uint64_t BitWidth); - [[nodiscard]] static Expected makeInteger(std::uint64_t BitWidth); - [[nodiscard]] static Expected makeFloat(FloatSemantics Semantics); - [[nodiscard]] static Expected makePointer(std::uint64_t AddressSpace, - std::uint64_t BitWidth); - [[nodiscard]] static Expected makeFixedVector(std::uint64_t ElementCount, LLT ElementType); - [[nodiscard]] static Expected makeScalableVector(std::uint64_t MinimumElementCount, - LLT ElementType); + [[nodiscard]] static Expected makeCategoryNeutralScalar(std::uint64_t BitWidth); + [[nodiscard]] static Expected makePointer(std::uint64_t AddressSpace, + std::uint64_t BitWidth); + [[nodiscard]] static Expected makeFixedVector(std::uint64_t ElementCount, + LowLevelType ElementType); + [[nodiscard]] static Expected makeScalableVector(std::uint64_t MinimumElementCount, + LowLevelType ElementType); [[nodiscard]] constexpr Kind kind() const noexcept { return static_cast((RawValue >> KindShift) & KindMask); @@ -62,53 +56,28 @@ public: return kind() == Kind::Token; } - [[nodiscard]] constexpr bool isAnyScalar() const noexcept { - return kind() == Kind::AnyScalar; - } - - [[nodiscard]] constexpr bool isInteger() const noexcept { - return kind() == Kind::Integer; - } - - [[nodiscard]] constexpr bool isFloat() const noexcept { - return kind() == Kind::Float; + [[nodiscard]] constexpr bool isCategoryNeutralScalar() const noexcept { + return kind() == Kind::CategoryNeutralScalar; } [[nodiscard]] constexpr bool isPointer() const noexcept { return kind() == Kind::Pointer; } - [[nodiscard]] constexpr bool isAnyVector() const noexcept { - return kind() == Kind::VectorAny; - } - - [[nodiscard]] constexpr bool isIntegerVector() const noexcept { - return kind() == Kind::VectorInteger; - } - - [[nodiscard]] constexpr bool isFloatVector() const noexcept { - return kind() == Kind::VectorFloat; + [[nodiscard]] constexpr bool isVectorValue() const noexcept { + return kind() == Kind::Vector; } [[nodiscard]] constexpr bool isPointerVector() const noexcept { return kind() == Kind::VectorPointer; } - [[nodiscard]] constexpr bool isIntegerOrIntegerVector() const noexcept { - return isInteger() || isIntegerVector(); - } - - [[nodiscard]] constexpr bool isFloatOrFloatVector() const noexcept { - return isFloat() || isFloatVector(); - } - [[nodiscard]] constexpr bool isPointerOrPointerVector() const noexcept { return isPointer() || isPointerVector(); } [[nodiscard]] constexpr bool isVector() const noexcept { - return kind() == Kind::VectorAny || kind() == Kind::VectorInteger || - kind() == Kind::VectorFloat || kind() == Kind::VectorPointer; + return kind() == Kind::Vector || kind() == Kind::VectorPointer; } [[nodiscard]] constexpr bool isScalableVector() const noexcept { @@ -116,7 +85,7 @@ public: } [[nodiscard]] constexpr bool isScalarValue() const noexcept { - return isAnyScalar() || isInteger() || isFloat() || isPointer(); + return isCategoryNeutralScalar() || isPointer(); } [[nodiscard]] constexpr std::uint32_t scalarBitWidth() const noexcept { @@ -130,8 +99,7 @@ public: } [[nodiscard]] std::optional addressSpace() const noexcept; - [[nodiscard]] std::optional floatSemantics() const noexcept; - [[nodiscard]] std::optional scalarElementType() const noexcept; + [[nodiscard]] std::optional scalarElementType() const noexcept; [[nodiscard]] constexpr std::uint64_t rawValue() const noexcept { return RawValue; @@ -139,7 +107,7 @@ public: [[nodiscard]] std::string toString() const; - friend constexpr bool operator==(LLT Left, LLT Right) noexcept = default; + friend constexpr bool operator==(LowLevelType Left, LowLevelType Right) noexcept = default; private: static constexpr unsigned BitWidthShift = 0; @@ -153,7 +121,7 @@ private: static constexpr std::uint64_t AuxiliaryMask = (std::uint64_t{1} << 24) - 1; static constexpr std::uint64_t KindMask = (std::uint64_t{1} << 4) - 1; - explicit constexpr LLT(std::uint64_t RawValue) noexcept : RawValue(RawValue) {} + explicit constexpr LowLevelType(std::uint64_t RawValue) noexcept : RawValue(RawValue) {} [[nodiscard]] static constexpr std::uint64_t encode(Kind TypeKind, std::uint32_t BitWidth, std::uint32_t ElementCount, @@ -166,9 +134,8 @@ private: (static_cast(BitWidth) << BitWidthShift); } - [[nodiscard]] static Expected makeScalar(Kind TypeKind, std::uint64_t BitWidth); - [[nodiscard]] static Expected makeVector(std::uint64_t ElementCount, bool IsScalable, - LLT ElementType); + [[nodiscard]] static Expected makeVector(std::uint64_t ElementCount, + bool IsScalable, LowLevelType ElementType); [[nodiscard]] constexpr std::uint32_t auxiliaryValue() const noexcept { return static_cast((RawValue >> AuxiliaryShift) & AuxiliaryMask); @@ -177,13 +144,13 @@ private: std::uint64_t RawValue = 0; }; -static_assert(sizeof(LLT) == sizeof(std::uint64_t)); -static_assert(std::is_trivially_copyable_v); +static_assert(sizeof(LowLevelType) == sizeof(std::uint64_t)); +static_assert(std::is_trivially_copyable_v); } // namespace rcc -template <> struct std::hash { - [[nodiscard]] std::size_t operator()(rcc::LLT Type) const noexcept { +template <> struct std::hash { + [[nodiscard]] std::size_t operator()(rcc::LowLevelType Type) const noexcept { return std::hash{}(Type.rawValue()); } }; diff --git a/backend/include/rcc/CodeGen/MachineMemOperand.h b/backend/include/rcc/CodeGen/MachineMemOperand.h index d236fd3..0ddd1b5 100644 --- a/backend/include/rcc/CodeGen/MachineMemOperand.h +++ b/backend/include/rcc/CodeGen/MachineMemOperand.h @@ -197,7 +197,7 @@ struct MachineMemOperandDesc final { AtomicOrdering FailureOrdering = AtomicOrdering::NotAtomic; SyncScopeID SyncScope; MemorySize Size; - std::optional MemoryType; + std::optional MemoryType; Alignment Align; std::optional BaseAlign; std::uint32_t AddressSpace = 0; diff --git a/backend/include/rcc/CodeGen/MachineRegisterInfo.h b/backend/include/rcc/CodeGen/MachineRegisterInfo.h index 524ee77..e0538d3 100644 --- a/backend/include/rcc/CodeGen/MachineRegisterInfo.h +++ b/backend/include/rcc/CodeGen/MachineRegisterInfo.h @@ -81,7 +81,7 @@ private: struct VirtualRegisterInfo final { std::optional Name; - std::optional Type; + std::optional Type; std::optional Bank; std::optional RegClass; std::vector AllocationHints; @@ -107,7 +107,7 @@ public: ~MachineRegisterInfo(); [[nodiscard]] Expected createVirtualRegister(); - [[nodiscard]] Expected createVirtualRegister(LLT Type); + [[nodiscard]] Expected createVirtualRegister(LowLevelType Type); [[nodiscard]] Expected eraseVirtualRegister(Register Reg); [[nodiscard]] bool isKnownVirtualRegister(Register Reg) const noexcept; @@ -119,7 +119,7 @@ public: [[nodiscard]] Expected> virtualRegisterInfo(Register Reg) const; - [[nodiscard]] Expected setType(Register Reg, LLT Type); + [[nodiscard]] Expected setType(Register Reg, LowLevelType Type); [[nodiscard]] Expected clearType(Register Reg); [[nodiscard]] Expected setRegisterBank(Register Reg, RegisterBankID Bank); [[nodiscard]] Expected clearRegisterBank(Register Reg); diff --git a/backend/include/rcc/CodeGen/TargetCallLowering.h b/backend/include/rcc/CodeGen/TargetCallLowering.h index 9d9b98b..21b5407 100644 --- a/backend/include/rcc/CodeGen/TargetCallLowering.h +++ b/backend/include/rcc/CodeGen/TargetCallLowering.h @@ -33,6 +33,14 @@ enum class ABIExtensionKind : std::uint8_t { Count, }; +enum class ABIValueCategory : std::uint8_t { + Invalid, + Integer, + FloatingPoint, + Pointer, + Count, +}; + enum class ABIValueFlag : std::uint8_t { ByVal, StructReturn, @@ -71,7 +79,8 @@ private: struct ABIValue final { Register Value; - LLT Type; + LowLevelType Type; + ABIValueCategory Category = ABIValueCategory::Invalid; std::uint32_t OriginalValue = 0; std::uint16_t FragmentIndex = 0; std::uint16_t FragmentCount = 1; @@ -222,8 +231,8 @@ struct CCAssignment final { std::uint32_t OriginalValueIndex = 0; std::uint16_t FragmentIndex = 0; std::uint16_t FragmentCount = 1; - LLT ValueType; - LLT LocationType; + LowLevelType ValueType; + LowLevelType LocationType; CCLocationKind LocationKind = CCLocationKind::Register; std::optional LocationRegister; std::optional StackOffsetBytes; @@ -279,7 +288,7 @@ struct VarArgLoweringState final { struct ByValCopyAssignment final { std::size_t ArgumentAssignmentIndex = 0; Register Source; - LLT PointerType; + LowLevelType PointerType; std::uint64_t StackOffsetBytes = 0; std::uint64_t SizeBytes = 0; Alignment Align; -- cgit v1.2.3