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

Nikita Popov via llvm-commits llvm-commits at lists.llvm.org
Thu Feb 19 08:00:36 PST 2026


================
@@ -276,6 +276,157 @@ 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;
+
+  /// 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(); }
+
+  /// A helper method that can be used to determine if the constant contained
+  /// within is equal to a constant.  This only works for very small values,
+  /// because this is all that can be represented with all types.
+  /// Determine if this constant's value is same as an unsigned char.
+  bool equalsByte(uint64_t V) const { return Val == V; }
+
+  /// Variant of the getType() method to always return a ByteType, which
+  /// reduces the amount of casting needed in parts of the compiler.
+  inline ByteType *getByteType() const {
+    return cast<ByteType>(Value::getType());
+  }
+
+  bool isNegative() const { return Val.isNegative(); }
+
+  /// This is just a convenience method to make client code smaller for a
+  /// common code. It also correctly performs the comparison without the
+  /// potential for an assertion from getZExtValue().
+  bool isZero() const { return Val.isZero(); }
+
+  /// This is just a convenience method to make client code smaller for a
+  /// common case. It also correctly performs the comparison without the
+  /// potential for an assertion from getZExtValue().
+  /// Determine if the value is one.
+  bool isOne() const { return Val.isOne(); }
+
+  /// This function will return true iff every bit in this constant is set
+  /// to true.
+  /// @returns true iff this constant's bits are all set to true.
+  /// Determine if the value is all ones.
+  bool isMinusOne() const { return Val.isAllOnes(); }
+
+  /// This function will return true iff this constant represents the largest
+  /// value that may be represented by the constant's type.
+  /// @returns true iff this is the largest value that may be represented
+  /// by this type.
+  /// Determine if the value is maximal.
+  bool isMaxValue(bool IsSigned) const {
+    if (IsSigned)
+      return Val.isMaxSignedValue();
+    else
+      return Val.isMaxValue();
+  }
+
+  /// This function will return true iff this constant represents the smallest
+  /// value that may be represented by this constant's type.
+  /// @returns true if this is the smallest value that may be represented by
+  /// this type.
+  /// Determine if the value is minimal.
+  bool isMinValue(bool IsSigned) const {
+    if (IsSigned)
+      return Val.isMinSignedValue();
+    else
+      return Val.isMinValue();
+  }
+
+  /// This function will return true iff this constant represents a value with
+  /// active bits bigger than 64 bits or a value greater than the given uint64_t
+  /// value.
+  /// @returns true iff this constant is greater or equal to the given number.
+  /// Determine if the value is greater or equal to the given number.
+  bool uge(uint64_t Num) const { return Val.uge(Num); }
----------------
nikic wrote:

I'd drop this as well.

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


More information about the llvm-commits mailing list