[llvm] [IR] Add initial support for the byte type (PR #178666)

Pedro Lobo via llvm-commits llvm-commits at lists.llvm.org
Sat Feb 14 08:45:48 PST 2026


================
@@ -276,6 +276,199 @@ class ConstantInt final : public ConstantData {
   }
 };
 
+//===----------------------------------------------------------------------===//
+/// Class for constant bytes.
+class ConstantByte final : public ConstantData {
+  friend class Constant;
+  friend class ConstantVector;
+
+  APInt Val;
+
+  ConstantByte(Type *Ty, const APInt &V);
+
+  void destroyConstantImpl();
+
+  /// Return a ConstantByte with the specified value and an implied Type. The
+  /// type is the vector type whose byte element type corresponds to the bit
+  /// width of the value.
+  static ConstantByte *get(LLVMContext &Context, ElementCount EC,
+                           const APInt &V);
+
+public:
+  ConstantByte(const ConstantByte &) = delete;
+
+  LLVM_ABI static ConstantByte *getTrue(LLVMContext &Context);
+  LLVM_ABI static ConstantByte *getFalse(LLVMContext &Context);
+  LLVM_ABI static ConstantByte *getBool(LLVMContext &Context, bool V);
+  LLVM_ABI static Constant *getTrue(Type *Ty);
+  LLVM_ABI static Constant *getFalse(Type *Ty);
+  LLVM_ABI static Constant *getBool(Type *Ty, bool V);
+
+  /// If Ty is a vector type, return a Constant with a splat of the given
+  /// value. Otherwise return a ConstantByte for the given value.
+  /// \param ImplicitTrunc Whether to allow implicit truncation of the value.
+  LLVM_ABI static Constant *get(Type *Ty, uint64_t V, bool isSigned = false,
+                                bool ImplicitTrunc = false);
+
+  /// Return a ConstantByte with the specified byte value for the specified
+  /// type. If the type is wider than 64 bits, the value will be zero-extended
+  /// to fit the type, unless IsSigned is true, in which case the value will
+  /// be interpreted as a 64-bit signed byte and sign-extended to fit
+  /// the type.
+  /// \param ImplicitTrunc Whether to allow implicit truncation of the value.
+  LLVM_ABI static ConstantByte *get(ByteType *Ty, uint64_t V,
+                                    bool isSigned = false,
+                                    bool ImplicitTrunc = false);
+
+  /// Return a ConstantByte with the specified value for the specified type. The
+  /// value V will be canonicalized to an unsigned APInt. Accessing it with
+  /// either getSExtValue() or getZExtValue() will yield a correctly sized and
+  /// signed value for the type Ty.
+  /// Get a ConstantByte for a specific signed value.
+  /// \param ImplicitTrunc Whether to allow implicit truncation of the value.
+  static ConstantByte *getSigned(ByteType *Ty, int64_t V,
+                                 bool ImplicitTrunc = false) {
+    return get(Ty, V, /*IsSigned=*/true, ImplicitTrunc);
+  }
+  static Constant *getSigned(Type *Ty, int64_t V, bool ImplicitTrunc = false) {
+    return get(Ty, V, /*IsSigned=*/true, ImplicitTrunc);
+  }
+
+  /// Return a ConstantByte with the specified value and an implied Type. The
+  /// type is the byte type that corresponds to the bit width of the value.
+  LLVM_ABI static ConstantByte *get(LLVMContext &Context, const APInt &V);
+
+  /// Return a ConstantByte constructed from the string strStart with the given
+  /// radix.
+  LLVM_ABI static ConstantByte *get(ByteType *Ty, StringRef Str, uint8_t Radix);
+
+  /// If Ty is a vector type, return a Constant with a splat of the given
+  /// value. Otherwise return a ConstantByte for the given value.
+  LLVM_ABI static Constant *get(Type *Ty, const APInt &V);
+
+  /// Return the constant as an APInt value reference. This allows clients to
+  /// obtain a full-precision copy of the value.
+  /// Return the constant's value.
+  inline const APInt &getValue() const { return Val; }
+
+  /// getBitWidth - Return the scalar bitwidth of this constant.
+  unsigned getBitWidth() const { return Val.getBitWidth(); }
+
+  /// Return the constant as a 64-bit byte value after it
+  /// has been zero extended as appropriate for the type of this constant. Note
+  /// that this method can assert if the value does not fit in 64 bits.
+  /// Return the zero extended value.
+  inline uint64_t getZExtValue() const { return Val.getZExtValue(); }
+
+  /// Return the constant as a 64-bit byte value after it has been sign
+  /// extended as appropriate for the type of this constant. Note that
+  /// this method can assert if the value does not fit in 64 bits.
+  /// Return the sign extended value.
+  inline int64_t getSExtValue() const { return Val.getSExtValue(); }
+
+  /// Return the constant as an llvm::MaybeAlign.
+  /// Note that this method can assert if the value does not fit in 64 bits or
+  /// is not a power of two.
+  inline MaybeAlign getMaybeAlignValue() const {
----------------
pedroclobo wrote:

Not sure what to remove here, apart from the alignment methods. Most of these methods are not used in the old implementation. However, I suspect that some optimizations (e.g., InstCombine) could benefit from them in the future.

The following don't seem that useful and I think could be removed:
- `getTrue`, `getFalse` and `getBool`.
- `isValueValidForType`.
- Perhaps `getLimitedValue`.

Let me know that you think.

https://github.com/llvm/llvm-project/pull/178666


More information about the llvm-commits mailing list