From 379ff50dcc7ccf977379aee68fa9d10f69065d23 Mon Sep 17 00:00:00 2001 From: Richard-Qin-X Date: Sun, 9 Aug 2026 18:31:49 +0800 Subject: [MC] Implement RV64GC assembly emission --- backend/include/rcc/MC/MCInst.h | 174 ++++++++++++++++++++++++++++++++++++++++ 1 file changed, 174 insertions(+) create mode 100644 backend/include/rcc/MC/MCInst.h (limited to 'backend/include/rcc/MC/MCInst.h') diff --git a/backend/include/rcc/MC/MCInst.h b/backend/include/rcc/MC/MCInst.h new file mode 100644 index 0000000..c6da93b --- /dev/null +++ b/backend/include/rcc/MC/MCInst.h @@ -0,0 +1,174 @@ +// SPDX-License-Identifier: GPL-3.0-or-later + +#ifndef RCC_MC_MCINST_H +#define RCC_MC_MCINST_H + +#include "rcc/MC/MCExpr.h" + +#include +#include +#include +#include +#include +#include + +namespace rcc::mc { + +class MCRegister final { +public: + constexpr MCRegister() noexcept = default; + + [[nodiscard]] static constexpr MCRegister fromValue(std::uint32_t Value) noexcept { + return MCRegister(Value); + } + + [[nodiscard]] constexpr std::uint32_t value() const noexcept { + return Value; + } + + [[nodiscard]] constexpr bool isValid() const noexcept { + return Value != 0; + } + + friend constexpr bool operator==(MCRegister Left, MCRegister Right) noexcept = default; + +private: + explicit constexpr MCRegister(std::uint32_t Value) noexcept : Value(Value) {} + + std::uint32_t Value = 0; +}; + +class MCOpcode final { +public: + constexpr MCOpcode() noexcept = default; + + [[nodiscard]] static constexpr MCOpcode fromValue(std::uint32_t Value) noexcept { + return MCOpcode(Value); + } + + [[nodiscard]] constexpr std::uint32_t value() const noexcept { + return Value; + } + + [[nodiscard]] constexpr bool isValid() const noexcept { + return Value != 0; + } + + friend constexpr bool operator==(MCOpcode Left, MCOpcode Right) noexcept = default; + +private: + explicit constexpr MCOpcode(std::uint32_t Value) noexcept : Value(Value) {} + + std::uint32_t Value = 0; +}; + +class MCOperand final { +public: + enum class Kind : std::uint8_t { + Register, + Immediate, + Float32Bits, + Float64Bits, + Expression, + }; + + [[nodiscard]] static MCOperand registerOperand(MCRegister Register) noexcept { + return MCOperand(Kind::Register, Register); + } + + [[nodiscard]] static MCOperand immediate(std::int64_t Value) noexcept { + return MCOperand(Kind::Immediate, Value); + } + + [[nodiscard]] static MCOperand float32Bits(std::uint32_t Value) noexcept { + return MCOperand(Kind::Float32Bits, Value); + } + + [[nodiscard]] static MCOperand float64Bits(std::uint64_t Value) noexcept { + return MCOperand(Kind::Float64Bits, Value); + } + + [[nodiscard]] static MCOperand expression(MCExprRef Value) { + return MCOperand(Kind::Expression, std::move(Value)); + } + + [[nodiscard]] Kind kind() const noexcept { + return OperandKind; + } + + [[nodiscard]] const MCRegister *registerValue() const noexcept { + return std::get_if(&Storage); + } + + [[nodiscard]] const std::int64_t *immediateValue() const noexcept { + return std::get_if(&Storage); + } + + [[nodiscard]] const std::uint32_t *float32BitsValue() const noexcept { + return std::get_if(&Storage); + } + + [[nodiscard]] const std::uint64_t *float64BitsValue() const noexcept { + return std::get_if(&Storage); + } + + [[nodiscard]] const MCExprRef *expressionValue() const noexcept { + return std::get_if(&Storage); + } + +private: + using StorageT = std::variant; + + MCOperand(Kind OperandKind, StorageT Storage) + : OperandKind(OperandKind), Storage(std::move(Storage)) {} + + Kind OperandKind; + StorageT Storage; +}; + +class MCInst final { +public: + explicit MCInst(MCOpcode InstructionOpcode) : InstructionOpcode(InstructionOpcode) {} + + [[nodiscard]] MCOpcode opcode() const noexcept { + return InstructionOpcode; + } + + void setFlags(std::uint32_t NewFlags) noexcept { + Flags = NewFlags; + } + + [[nodiscard]] std::uint32_t flags() const noexcept { + return Flags; + } + + void setSourceIdentity(std::uint64_t Identity) noexcept { + SourceIdentity = Identity; + } + + [[nodiscard]] std::uint64_t sourceIdentity() const noexcept { + return SourceIdentity; + } + + void reserveOperands(std::size_t Count) { + Operands.reserve(Count); + } + + void addOperand(MCOperand Operand) { + Operands.push_back(std::move(Operand)); + } + + [[nodiscard]] std::span operands() const noexcept { + return Operands; + } + +private: + MCOpcode InstructionOpcode; + std::uint32_t Flags = 0; + std::uint64_t SourceIdentity = 0; + std::vector Operands; +}; + +} // namespace rcc::mc + +#endif // RCC_MC_MCINST_H -- cgit v1.2.3