aboutsummaryrefslogtreecommitdiff
path: root/contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2024-07-27 23:34:35 +0000
committerDimitry Andric <dim@FreeBSD.org>2024-10-23 18:26:01 +0000
commit0fca6ea1d4eea4c934cfff25ac9ee8ad6fe95583 (patch)
tree6cf5ab1f05330c6773b1f3f64799d56a9c7a1faa /contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp
parent6b9f7133aba44189d9625c352bc2c2a59baf18ef (diff)
parentac9a064cb179f3425b310fa2847f8764ac970a4d (diff)
Diffstat (limited to 'contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp')
-rw-r--r--contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp151
1 files changed, 151 insertions, 0 deletions
diff --git a/contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp b/contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp
index 6ec4178053b2..11f0cba47afd 100644
--- a/contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp
+++ b/contrib/llvm-project/llvm/lib/Target/AMDGPU/AMDGPUMIRFormatter.cpp
@@ -17,6 +17,157 @@
using namespace llvm;
+void AMDGPUMIRFormatter::printImm(raw_ostream &OS, const MachineInstr &MI,
+ std::optional<unsigned int> OpIdx, int64_t Imm) const {
+
+ switch (MI.getOpcode()) {
+ case AMDGPU::S_DELAY_ALU:
+ assert(OpIdx == 0);
+ printSDelayAluImm(Imm, OS);
+ break;
+ default:
+ MIRFormatter::printImm(OS, MI, OpIdx, Imm);
+ break;
+ }
+}
+
+/// Implement target specific parsing of immediate mnemonics. The mnemonic is
+/// a string with a leading dot.
+bool AMDGPUMIRFormatter::parseImmMnemonic(const unsigned OpCode,
+ const unsigned OpIdx,
+ StringRef Src, int64_t &Imm,
+ ErrorCallbackType ErrorCallback) const
+{
+
+ switch (OpCode) {
+ case AMDGPU::S_DELAY_ALU:
+ return parseSDelayAluImmMnemonic(OpIdx, Imm, Src, ErrorCallback);
+ default:
+ break;
+ }
+ return true; // Don't know what this is
+}
+
+void AMDGPUMIRFormatter::printSDelayAluImm(int64_t Imm,
+ llvm::raw_ostream &OS) const {
+ // Construct an immediate string to represent the information encoded in the
+ // s_delay_alu immediate.
+ // .id0_<dep>[_skip_<count>_id1<dep>]
+ constexpr int64_t None = 0;
+ constexpr int64_t Same = 0;
+
+ uint64_t Id0 = (Imm & 0xF);
+ uint64_t Skip = ((Imm >> 4) & 0x7);
+ uint64_t Id1 = ((Imm >> 7) & 0xF);
+ auto Outdep = [&](uint64_t Id) {
+ if (Id == None)
+ OS << "NONE";
+ else if (Id < 5)
+ OS << "VALU_DEP_" << Id;
+ else if (Id < 8)
+ OS << "TRANS32_DEP_" << Id - 4;
+ else
+ OS << "SALU_CYCLE_" << Id - 8;
+ };
+
+ OS << ".id0_";
+ Outdep(Id0);
+
+ // If the second inst is "same" and "none", no need to print the rest of the
+ // string.
+ if (Skip == Same && Id1 == None)
+ return;
+
+ // Encode the second delay specification.
+ OS << "_skip_";
+ if (Skip == 0)
+ OS << "SAME";
+ else if (Skip == 1)
+ OS << "NEXT";
+ else
+ OS << "SKIP_" << Skip - 1;
+
+ OS << "_id1_";
+ Outdep(Id1);
+}
+
+bool AMDGPUMIRFormatter::parseSDelayAluImmMnemonic(
+ const unsigned int OpIdx, int64_t &Imm, llvm::StringRef &Src,
+ llvm::MIRFormatter::ErrorCallbackType &ErrorCallback) const
+{
+ assert(OpIdx == 0);
+
+ Imm = 0;
+ bool Expected = Src.consume_front(".id0_");
+ if (!Expected)
+ return ErrorCallback(Src.begin(), "Expected .id0_");
+
+ auto ExpectInt = [&](StringRef &Src, int64_t Offset) -> int64_t {
+ int64_t Dep;
+ if (!Src.consumeInteger(10, Dep))
+ return Dep + Offset;
+
+ return -1;
+ };
+
+ auto DecodeDelay = [&](StringRef &Src) -> int64_t {
+ if (Src.consume_front("NONE"))
+ return 0;
+ if (Src.consume_front("VALU_DEP_"))
+ return ExpectInt(Src, 0);
+ if (Src.consume_front("TRANS32_DEP_"))
+ return ExpectInt(Src, 4);
+ if (Src.consume_front("SALU_CYCLE_"))
+ return ExpectInt(Src, 8);
+
+ return -1;
+ };
+
+ int64_t Delay0 = DecodeDelay(Src);
+ int64_t Skip = 0;
+ int64_t Delay1 = 0;
+ if (Delay0 == -1)
+ return ErrorCallback(Src.begin(), "Could not decode delay0");
+
+
+ // Set the Imm so far, to that early return has the correct value.
+ Imm = Delay0;
+
+ // If that was the end of the string, the second instruction is "same" and
+ // "none"
+ if (Src.begin() == Src.end())
+ return false;
+
+ Expected = Src.consume_front("_skip_");
+ if (!Expected)
+ return ErrorCallback(Src.begin(), "Expected _skip_");
+
+
+ if (Src.consume_front("SAME")) {
+ Skip = 0;
+ } else if (Src.consume_front("NEXT")) {
+ Skip = 1;
+ } else if (Src.consume_front("SKIP_")) {
+ if (Src.consumeInteger(10, Skip)) {
+ return ErrorCallback(Src.begin(), "Expected integer Skip value");
+ }
+ Skip += 1;
+ } else {
+ ErrorCallback(Src.begin(), "Unexpected Skip Value");
+ }
+
+ Expected = Src.consume_front("_id1_");
+ if (!Expected)
+ return ErrorCallback(Src.begin(), "Expected _id1_");
+
+ Delay1 = DecodeDelay(Src);
+ if (Delay1 == -1)
+ return ErrorCallback(Src.begin(), "Could not decode delay1");
+
+ Imm = Imm | (Skip << 4) | (Delay1 << 7);
+ return false;
+}
+
bool AMDGPUMIRFormatter::parseCustomPseudoSourceValue(
StringRef Src, MachineFunction &MF, PerFunctionMIParsingState &PFS,
const PseudoSourceValue *&PSV, ErrorCallbackType ErrorCallback) const {