[llvm-branch-commits] [llvm] [SystemZ][z/OS] Show instruction encoding in HLASM output (PR #181904)
Kai Nacke via llvm-branch-commits
llvm-branch-commits at lists.llvm.org
Fri Jul 3 13:49:39 PDT 2026
https://github.com/redstar updated https://github.com/llvm/llvm-project/pull/181904
>From b71ec7c9b08a24f2ad6d579ba9a39e7402ab521f Mon Sep 17 00:00:00 2001
From: Kai Nacke <kai.peter.nacke at ibm.com>
Date: Wed, 25 Mar 2026 16:02:48 -0400
Subject: [PATCH 1/7] [MC] Move addEncodingComment() into new base class
MCAsmBaseStreamer
This is in preparation to use this functionality in the
SystemZHLASMAsmStreamer. No functional change.
---
llvm/include/llvm/MC/MCAsmStreamer.h | 33 +++-
llvm/lib/MC/MCAsmStreamer.cpp | 254 +++++++++++++--------------
2 files changed, 154 insertions(+), 133 deletions(-)
diff --git a/llvm/include/llvm/MC/MCAsmStreamer.h b/llvm/include/llvm/MC/MCAsmStreamer.h
index 651a0dc75fce9..71e004ca92fd7 100644
--- a/llvm/include/llvm/MC/MCAsmStreamer.h
+++ b/llvm/include/llvm/MC/MCAsmStreamer.h
@@ -14,15 +14,46 @@
#ifndef LLVM_MC_MCASMSTREAMER_H
#define LLVM_MC_MCASMSTREAMER_H
+#include "llvm/MC/MCAsmBackend.h"
+#include "llvm/MC/MCAssembler.h"
+#include "llvm/MC/MCCodeEmitter.h"
#include "llvm/MC/MCStreamer.h"
+#include "llvm/Support/raw_ostream.h"
+#include <memory>
namespace llvm {
+class MCAsmInfo;
class MCContext;
+class MCInst;
+class MCSubtargetInfo;
class MCAsmBaseStreamer : public MCStreamer {
protected:
- MCAsmBaseStreamer(MCContext &Context) : MCStreamer(Context) {}
+ std::unique_ptr<MCAssembler> Assembler;
+ SmallString<128> CommentToEmit;
+ raw_svector_ostream CommentStream;
+ raw_null_ostream NullStream;
+
+ MCAsmBaseStreamer(MCContext &Context, std::unique_ptr<MCCodeEmitter> Emitter,
+ std::unique_ptr<MCAsmBackend> AsmBackend);
+
+public:
+ /// Return a raw_ostream that comments can be written to.
+ /// Unlike AddComment, you are required to terminate comments with \n if you
+ /// use this method.
+ raw_ostream &getCommentOS() override {
+ if (!isVerboseAsm())
+ return nulls(); // Discard comments unless in verbose asm mode.
+ return CommentStream;
+ }
+
+ /// Add a comment showing the encoding of an instruction.
+ /// \param Inst - The instruction to encode.
+ /// \param STI - Subtarget information.
+ void addEncodingComment(const MCInst &Inst, const MCSubtargetInfo &STI);
+
+ MCAssembler &getAssembler() { return *Assembler; }
};
} // end namespace llvm
diff --git a/llvm/lib/MC/MCAsmStreamer.cpp b/llvm/lib/MC/MCAsmStreamer.cpp
index f3b4299575403..e993cd0dcafb6 100644
--- a/llvm/lib/MC/MCAsmStreamer.cpp
+++ b/llvm/lib/MC/MCAsmStreamer.cpp
@@ -42,6 +42,124 @@
using namespace llvm;
+MCAsmBaseStreamer::MCAsmBaseStreamer(MCContext &Context,
+ std::unique_ptr<MCCodeEmitter> Emitter,
+ std::unique_ptr<MCAsmBackend> AsmBackend)
+ : MCStreamer(Context),
+ Assembler(std::make_unique<MCAssembler>(
+ Context, std::move(AsmBackend), std::move(Emitter),
+ (AsmBackend) ? AsmBackend->createObjectWriter(NullStream) : nullptr)),
+ CommentStream(CommentToEmit) {}
+
+void MCAsmBaseStreamer::addEncodingComment(const MCInst &Inst,
+ const MCSubtargetInfo &STI) {
+ raw_ostream &OS = getCommentOS();
+ SmallString<256> Code;
+ SmallVector<MCFixup, 4> Fixups;
+
+ // If we have no code emitter, don't emit code.
+ if (!getAssembler().getEmitterPtr())
+ return;
+
+ getAssembler().getEmitter().encodeInstruction(Inst, Code, Fixups, STI);
+
+ // RISC-V instructions are always little-endian, even on BE systems.
+ bool ForceLE = getContext().getTargetTriple().isRISCV();
+
+ const MCAsmInfo *MAI = getContext().getAsmInfo();
+
+ // If we are showing fixups, create symbolic markers in the encoded
+ // representation. We do this by making a per-bit map to the fixup item index,
+ // then trying to display it as nicely as possible.
+ SmallVector<uint8_t, 64> FixupMap;
+ FixupMap.resize(Code.size() * 8);
+ for (unsigned I = 0, E = Code.size() * 8; I != E; ++I)
+ FixupMap[I] = 0;
+
+ for (unsigned I = 0, E = Fixups.size(); I != E; ++I) {
+ MCFixup &F = Fixups[I];
+ MCFixupKindInfo Info =
+ getAssembler().getBackend().getFixupKindInfo(F.getKind());
+ for (unsigned J = 0; J != Info.TargetSize; ++J) {
+ unsigned Index = F.getOffset() * 8 + Info.TargetOffset + J;
+ assert(Index < Code.size() * 8 && "Invalid offset in fixup!");
+ FixupMap[Index] = 1 + I;
+ }
+ }
+
+ // FIXME: Note the fixup comments for Thumb2 are completely bogus since the
+ // high order halfword of a 32-bit Thumb2 instruction is emitted first.
+ OS << "encoding: [";
+ for (unsigned I = 0, E = Code.size(); I != E; ++I) {
+ if (I)
+ OS << ',';
+
+ // See if all bits are the same map entry.
+ uint8_t MapEntry = FixupMap[I * 8 + 0];
+ for (unsigned J = 1; J != 8; ++J) {
+ if (FixupMap[I * 8 + J] == MapEntry)
+ continue;
+
+ MapEntry = uint8_t(~0U);
+ break;
+ }
+
+ if (MapEntry != uint8_t(~0U)) {
+ if (MapEntry == 0) {
+ OS << format("0x%02x", uint8_t(Code[I]));
+ } else {
+ if (Code[I]) {
+ // FIXME: Some of the 8 bits require fix up.
+ OS << format("0x%02x", uint8_t(Code[I])) << '\''
+ << char('A' + MapEntry - 1) << '\'';
+ } else
+ OS << char('A' + MapEntry - 1);
+ }
+ } else {
+ // Otherwise, write out in binary.
+ OS << "0b";
+ for (unsigned J = 8; J--;) {
+ unsigned Bit = (Code[I] >> J) & 1;
+
+ unsigned FixupBit;
+ // RISC-V instructions are always little-endian.
+ // The FixupMap is indexed by actual bit positions in the LE
+ // instruction.
+ if (MAI->isLittleEndian() || ForceLE)
+ FixupBit = I * 8 + J;
+ else
+ FixupBit = I * 8 + (7 - J);
+
+ if (uint8_t MapEntry = FixupMap[FixupBit]) {
+ assert(Bit == 0 && "Encoder wrote into fixed up bit!");
+ OS << char('A' + MapEntry - 1);
+ } else
+ OS << Bit;
+ }
+ }
+ }
+ OS << "]\n";
+
+ for (unsigned I = 0, E = Fixups.size(); I != E; ++I) {
+ MCFixup &F = Fixups[I];
+ OS << " fixup " << char('A' + I) << " - "
+ << "offset: " << F.getOffset() << ", value: ";
+ MAI->printExpr(OS, *F.getValue());
+ auto Kind = F.getKind();
+ if (mc::isRelocation(Kind))
+ OS << ", relocation type: " << Kind;
+ else {
+ OS << ", kind: ";
+ auto Info = getAssembler().getBackend().getFixupKindInfo(Kind);
+ if (F.isPCRel() && StringRef(Info.Name).starts_with("FK_Data_"))
+ OS << "FK_PCRel_" << (Info.TargetSize / 8);
+ else
+ OS << Info.Name;
+ }
+ OS << '\n';
+ }
+}
+
namespace {
class MCAsmStreamer final : public MCAsmBaseStreamer {
@@ -49,12 +167,8 @@ class MCAsmStreamer final : public MCAsmBaseStreamer {
formatted_raw_ostream &OS;
const MCAsmInfo *MAI;
std::unique_ptr<MCInstPrinter> InstPrinter;
- std::unique_ptr<MCAssembler> Assembler;
SmallString<128> ExplicitCommentToEmit;
- SmallString<128> CommentToEmit;
- raw_svector_ostream CommentStream;
- raw_null_ostream NullStream;
bool EmittedSectionDirective = false;
@@ -89,13 +203,9 @@ class MCAsmStreamer final : public MCAsmBaseStreamer {
std::unique_ptr<MCInstPrinter> printer,
std::unique_ptr<MCCodeEmitter> emitter,
std::unique_ptr<MCAsmBackend> asmbackend)
- : MCAsmBaseStreamer(Context), OSOwner(std::move(os)), OS(*OSOwner),
- MAI(&Context.getAsmInfo()), InstPrinter(std::move(printer)),
- Assembler(std::make_unique<MCAssembler>(
- Context, std::move(asmbackend), std::move(emitter),
- (asmbackend) ? asmbackend->createObjectWriter(NullStream)
- : nullptr)),
- CommentStream(CommentToEmit) {
+ : MCAsmBaseStreamer(Context, std::move(emitter), std::move(asmbackend)),
+ OSOwner(std::move(os)), OS(*OSOwner), MAI(&Context.getAsmInfo()),
+ InstPrinter(std::move(printer)) {
assert(InstPrinter);
if (Assembler->getBackendPtr())
setAllowAutoPadding(Assembler->getBackend().allowAutoPadding());
@@ -121,7 +231,6 @@ class MCAsmStreamer final : public MCAsmBaseStreamer {
}
}
- MCAssembler &getAssembler() { return *Assembler; }
MCAssembler *getAssemblerPtr() override { return nullptr; }
inline void EmitEOL() {
@@ -150,18 +259,6 @@ class MCAsmStreamer final : public MCAsmBaseStreamer {
/// and only when verbose assembly output is enabled.
void AddComment(const Twine &T, bool EOL = true) override;
- /// Add a comment showing the encoding of an instruction.
- void AddEncodingComment(const MCInst &Inst, const MCSubtargetInfo &);
-
- /// Return a raw_ostream that comments can be written to.
- /// Unlike AddComment, you are required to terminate comments with \n if you
- /// use this method.
- raw_ostream &getCommentOS() override {
- if (!IsVerboseAsm)
- return nulls(); // Discard comments unless in verbose asm mode.
- return CommentStream;
- }
-
void emitRawComment(const Twine &T, bool TabPrefix = true) override;
void addExplicitComment(const Twine &T) override;
@@ -2408,113 +2505,6 @@ void MCAsmStreamer::emitCGProfileEntry(const MCSymbolRefExpr *From,
EmitEOL();
}
-void MCAsmStreamer::AddEncodingComment(const MCInst &Inst,
- const MCSubtargetInfo &STI) {
- raw_ostream &OS = getCommentOS();
- SmallString<256> Code;
- SmallVector<MCFixup, 4> Fixups;
-
- // If we have no code emitter, don't emit code.
- if (!getAssembler().getEmitterPtr())
- return;
-
- getAssembler().getEmitter().encodeInstruction(Inst, Code, Fixups, STI);
-
- // RISC-V instructions are always little-endian, even on BE systems.
- bool ForceLE = getContext().getTargetTriple().isRISCV();
-
- // If we are showing fixups, create symbolic markers in the encoded
- // representation. We do this by making a per-bit map to the fixup item index,
- // then trying to display it as nicely as possible.
- SmallVector<uint8_t, 64> FixupMap;
- FixupMap.resize(Code.size() * 8);
- for (unsigned i = 0, e = Code.size() * 8; i != e; ++i)
- FixupMap[i] = 0;
-
- for (unsigned i = 0, e = Fixups.size(); i != e; ++i) {
- MCFixup &F = Fixups[i];
- MCFixupKindInfo Info =
- getAssembler().getBackend().getFixupKindInfo(F.getKind());
- for (unsigned j = 0; j != Info.TargetSize; ++j) {
- unsigned Index = F.getOffset() * 8 + Info.TargetOffset + j;
- assert(Index < Code.size() * 8 && "Invalid offset in fixup!");
- FixupMap[Index] = 1 + i;
- }
- }
-
- // FIXME: Note the fixup comments for Thumb2 are completely bogus since the
- // high order halfword of a 32-bit Thumb2 instruction is emitted first.
- OS << "encoding: [";
- for (unsigned i = 0, e = Code.size(); i != e; ++i) {
- if (i)
- OS << ',';
-
- // See if all bits are the same map entry.
- uint8_t MapEntry = FixupMap[i * 8 + 0];
- for (unsigned j = 1; j != 8; ++j) {
- if (FixupMap[i * 8 + j] == MapEntry)
- continue;
-
- MapEntry = uint8_t(~0U);
- break;
- }
-
- if (MapEntry != uint8_t(~0U)) {
- if (MapEntry == 0) {
- OS << format("0x%02x", uint8_t(Code[i]));
- } else {
- if (Code[i]) {
- // FIXME: Some of the 8 bits require fix up.
- OS << format("0x%02x", uint8_t(Code[i])) << '\''
- << char('A' + MapEntry - 1) << '\'';
- } else
- OS << char('A' + MapEntry - 1);
- }
- } else {
- // Otherwise, write out in binary.
- OS << "0b";
- for (unsigned j = 8; j--;) {
- unsigned Bit = (Code[i] >> j) & 1;
-
- unsigned FixupBit;
- // RISC-V instructions are always little-endian.
- // The FixupMap is indexed by actual bit positions in the LE
- // instruction.
- if (MAI->isLittleEndian() || ForceLE)
- FixupBit = i * 8 + j;
- else
- FixupBit = i * 8 + (7-j);
-
- if (uint8_t MapEntry = FixupMap[FixupBit]) {
- assert(Bit == 0 && "Encoder wrote into fixed up bit!");
- OS << char('A' + MapEntry - 1);
- } else
- OS << Bit;
- }
- }
- }
- OS << "]\n";
-
- for (unsigned i = 0, e = Fixups.size(); i != e; ++i) {
- MCFixup &F = Fixups[i];
- OS << " fixup " << char('A' + i) << " - "
- << "offset: " << F.getOffset() << ", value: ";
- MAI->printExpr(OS, *F.getValue());
- auto Kind = F.getKind();
- if (mc::isRelocation(Kind))
- OS << ", relocation type: " << Kind;
- else {
- OS << ", kind: ";
- auto Info = getAssembler().getBackend().getFixupKindInfo(Kind);
- if (F.isPCRel() && StringRef(Info.Name).starts_with("FK_Data_"))
- OS << "FK_PCRel_" << (Info.TargetSize / 8);
- else
- OS << Info.Name;
- }
- OS << '\n';
- }
-}
-
void MCAsmStreamer::emitInstruction(const MCInst &Inst,
const MCSubtargetInfo &STI) {
if (LFIRewriter && LFIRewriter->rewriteInst(Inst, *this, STI))
@@ -2531,7 +2521,7 @@ void MCAsmStreamer::emitInstruction(const MCInst &Inst,
MCDwarfLineEntry::make(this, getCurrentSectionOnly());
// Show the encoding in a comment if we have a code emitter.
- AddEncodingComment(Inst, STI);
+ addEncodingComment(Inst, STI);
// Show the MCInst if enabled.
if (ShowInst) {
>From 74a9e244277cd2b59c8d0d4d928d495c85f8b63b Mon Sep 17 00:00:00 2001
From: Kai Nacke <kai.peter.nacke at ibm.com>
Date: Fri, 10 Apr 2026 16:55:34 -0400
Subject: [PATCH 2/7] Reduce number of include files.
---
llvm/include/llvm/MC/MCAsmStreamer.h | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/llvm/include/llvm/MC/MCAsmStreamer.h b/llvm/include/llvm/MC/MCAsmStreamer.h
index 71e004ca92fd7..9ec81f3259f70 100644
--- a/llvm/include/llvm/MC/MCAsmStreamer.h
+++ b/llvm/include/llvm/MC/MCAsmStreamer.h
@@ -14,16 +14,16 @@
#ifndef LLVM_MC_MCASMSTREAMER_H
#define LLVM_MC_MCASMSTREAMER_H
-#include "llvm/MC/MCAsmBackend.h"
-#include "llvm/MC/MCAssembler.h"
-#include "llvm/MC/MCCodeEmitter.h"
#include "llvm/MC/MCStreamer.h"
#include "llvm/Support/raw_ostream.h"
#include <memory>
namespace llvm {
+class MCAsmBackend;
class MCAsmInfo;
+class MCAssembler;
+class MCCodeEmitter;
class MCContext;
class MCInst;
class MCSubtargetInfo;
>From a3f081dcdd4f5c7c0116cd03daffd09547499ffa Mon Sep 17 00:00:00 2001
From: Kai Nacke <kai.peter.nacke at ibm.com>
Date: Fri, 10 Apr 2026 18:39:48 -0400
Subject: [PATCH 3/7] Fix formatting
---
llvm/include/llvm/MC/MCAsmStreamer.h | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/llvm/include/llvm/MC/MCAsmStreamer.h b/llvm/include/llvm/MC/MCAsmStreamer.h
index 9ec81f3259f70..942e9e40b1274 100644
--- a/llvm/include/llvm/MC/MCAsmStreamer.h
+++ b/llvm/include/llvm/MC/MCAsmStreamer.h
@@ -36,7 +36,7 @@ class MCAsmBaseStreamer : public MCStreamer {
raw_null_ostream NullStream;
MCAsmBaseStreamer(MCContext &Context, std::unique_ptr<MCCodeEmitter> Emitter,
- std::unique_ptr<MCAsmBackend> AsmBackend);
+ std::unique_ptr<MCAsmBackend> AsmBackend);
public:
/// Return a raw_ostream that comments can be written to.
>From d7071b2bdee9fe89bece8ccc32408b98db4b430a Mon Sep 17 00:00:00 2001
From: Kai Nacke <kai.peter.nacke at ibm.com>
Date: Thu, 30 Apr 2026 10:40:08 -0400
Subject: [PATCH 4/7] Fix compile errors after rebase
---
llvm/lib/MC/MCAsmStreamer.cpp | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/llvm/lib/MC/MCAsmStreamer.cpp b/llvm/lib/MC/MCAsmStreamer.cpp
index e993cd0dcafb6..d36a6ee58b171 100644
--- a/llvm/lib/MC/MCAsmStreamer.cpp
+++ b/llvm/lib/MC/MCAsmStreamer.cpp
@@ -66,7 +66,7 @@ void MCAsmBaseStreamer::addEncodingComment(const MCInst &Inst,
// RISC-V instructions are always little-endian, even on BE systems.
bool ForceLE = getContext().getTargetTriple().isRISCV();
- const MCAsmInfo *MAI = getContext().getAsmInfo();
+ const MCAsmInfo &MAI = getContext().getAsmInfo();
// If we are showing fixups, create symbolic markers in the encoded
// representation. We do this by making a per-bit map to the fixup item index,
@@ -125,7 +125,7 @@ void MCAsmBaseStreamer::addEncodingComment(const MCInst &Inst,
// RISC-V instructions are always little-endian.
// The FixupMap is indexed by actual bit positions in the LE
// instruction.
- if (MAI->isLittleEndian() || ForceLE)
+ if (MAI.isLittleEndian() || ForceLE)
FixupBit = I * 8 + J;
else
FixupBit = I * 8 + (7 - J);
@@ -144,7 +144,7 @@ void MCAsmBaseStreamer::addEncodingComment(const MCInst &Inst,
MCFixup &F = Fixups[I];
OS << " fixup " << char('A' + I) << " - "
<< "offset: " << F.getOffset() << ", value: ";
- MAI->printExpr(OS, *F.getValue());
+ MAI.printExpr(OS, *F.getValue());
auto Kind = F.getKind();
if (mc::isRelocation(Kind))
OS << ", relocation type: " << Kind;
>From 1a06566eaa7106053d39761210ff5e696a919728 Mon Sep 17 00:00:00 2001
From: Kai Nacke <kai.peter.nacke at ibm.com>
Date: Wed, 25 Mar 2026 16:02:48 -0400
Subject: [PATCH 5/7] [MC] Move addEncodingComment() into new base class
MCAsmBaseStreamer
This is in preparation to use this functionality in the
SystemZHLASMAsmStreamer. No functional change.
---
llvm/include/llvm/MC/MCAsmStreamer.h | 3 +++
1 file changed, 3 insertions(+)
diff --git a/llvm/include/llvm/MC/MCAsmStreamer.h b/llvm/include/llvm/MC/MCAsmStreamer.h
index 942e9e40b1274..4780c7892bc12 100644
--- a/llvm/include/llvm/MC/MCAsmStreamer.h
+++ b/llvm/include/llvm/MC/MCAsmStreamer.h
@@ -14,6 +14,9 @@
#ifndef LLVM_MC_MCASMSTREAMER_H
#define LLVM_MC_MCASMSTREAMER_H
+#include "llvm/MC/MCAsmBackend.h"
+#include "llvm/MC/MCAssembler.h"
+#include "llvm/MC/MCCodeEmitter.h"
#include "llvm/MC/MCStreamer.h"
#include "llvm/Support/raw_ostream.h"
#include <memory>
>From bc0d6b77fe89e7c024a97c9cedb1273e29db8c64 Mon Sep 17 00:00:00 2001
From: Kai Nacke <kai.peter.nacke at ibm.com>
Date: Tue, 17 Feb 2026 14:32:24 -0500
Subject: [PATCH 6/7] [SystemZ][z/OS] Show instruction encoding in HLASM output
This change adds the support to show instruction encoding as a comment
when emitting HLASM text. With this, the last 2 LIT tests migrate to
HLASM syntax.
---
.../MCTargetDesc/SystemZHLASMAsmStreamer.cpp | 3 +
.../MCTargetDesc/SystemZHLASMAsmStreamer.h | 27 ++--
llvm/test/CodeGen/SystemZ/call-zos-02.ll | 12 +-
llvm/test/MC/SystemZ/insn-good-zos-pcrel.s | 140 +++++++++++-------
4 files changed, 103 insertions(+), 79 deletions(-)
diff --git a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.cpp b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.cpp
index b38bbb09fb8fa..ed5bcfc782d40 100644
--- a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.cpp
+++ b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.cpp
@@ -188,6 +188,9 @@ void SystemZHLASMAsmStreamer::emitBytes(StringRef Data) {
void SystemZHLASMAsmStreamer::emitInstruction(const MCInst &Inst,
const MCSubtargetInfo &STI) {
+ // Show the encoding in a comment if we have a code emitter.
+ addEncodingComment(Inst, STI);
+ EmitEOL();
InstPrinter->printInst(&Inst, 0, "", STI, OS);
EmitEOL();
diff --git a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.h b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.h
index ee7c5dcbf552c..27ca45423754f 100644
--- a/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.h
+++ b/llvm/lib/Target/SystemZ/MCTargetDesc/SystemZHLASMAsmStreamer.h
@@ -17,6 +17,7 @@
#include "llvm/ADT/StringRef.h"
#include "llvm/MC/MCAsmBackend.h"
#include "llvm/MC/MCAsmInfo.h"
+#include "llvm/MC/MCAsmStreamer.h"
#include "llvm/MC/MCAssembler.h"
#include "llvm/MC/MCCodeEmitter.h"
#include "llvm/MC/MCContext.h"
@@ -30,7 +31,7 @@
namespace llvm {
class MCSymbolGOFF;
-class SystemZHLASMAsmStreamer final : public MCStreamer {
+class SystemZHLASMAsmStreamer final : public MCAsmBaseStreamer {
constexpr static size_t InstLimit = 80;
constexpr static size_t ContIndicatorColumn = 72;
constexpr static size_t ContStartColumn = 15;
@@ -41,25 +42,17 @@ class SystemZHLASMAsmStreamer final : public MCStreamer {
raw_string_ostream OS;
const MCAsmInfo *MAI;
std::unique_ptr<MCInstPrinter> InstPrinter;
- std::unique_ptr<MCAssembler> Assembler;
- SmallString<128> CommentToEmit;
- raw_svector_ostream CommentStream;
- raw_null_ostream NullStream;
bool IsVerboseAsm = false;
public:
SystemZHLASMAsmStreamer(MCContext &Context,
- std::unique_ptr<formatted_raw_ostream> os,
- std::unique_ptr<MCInstPrinter> printer,
- std::unique_ptr<MCCodeEmitter> emitter,
- std::unique_ptr<MCAsmBackend> asmbackend)
- : MCStreamer(Context), FOSOwner(std::move(os)), FOS(*FOSOwner), OS(Str),
- MAI(&Context.getAsmInfo()), InstPrinter(std::move(printer)),
- Assembler(std::make_unique<MCAssembler>(
- Context, std::move(asmbackend), std::move(emitter),
- (asmbackend) ? asmbackend->createObjectWriter(NullStream)
- : nullptr)),
- CommentStream(CommentToEmit) {
+ std::unique_ptr<formatted_raw_ostream> OS,
+ std::unique_ptr<MCInstPrinter> Printer,
+ std::unique_ptr<MCCodeEmitter> Emitter,
+ std::unique_ptr<MCAsmBackend> AsmBackend)
+ : MCAsmBaseStreamer(Context, std::move(Emitter), std::move(AsmBackend)),
+ FOSOwner(std::move(OS)), FOS(*FOSOwner), OS(Str),
+ MAI(&Context.getAsmInfo()), InstPrinter(std::move(Printer)) {
assert(InstPrinter);
if (Assembler->getBackendPtr())
setAllowAutoPadding(Assembler->getBackend().allowAutoPadding());
@@ -70,8 +63,6 @@ class SystemZHLASMAsmStreamer final : public MCStreamer {
InstPrinter->setCommentStream(CommentStream);
}
- MCAssembler &getAssembler() { return *Assembler; }
-
void EmitEOL();
void EmitComment();
diff --git a/llvm/test/CodeGen/SystemZ/call-zos-02.ll b/llvm/test/CodeGen/SystemZ/call-zos-02.ll
index 4f1013fc8974d..7ddfda84ef4f6 100644
--- a/llvm/test/CodeGen/SystemZ/call-zos-02.ll
+++ b/llvm/test/CodeGen/SystemZ/call-zos-02.ll
@@ -1,4 +1,4 @@
-; RUN: llc --mtriple=s390x-ibm-zos --show-mc-encoding -emit-gnuas-syntax-on-zos=1 < %s | FileCheck %s
+; RUN: llc --mtriple=s390x-ibm-zos --show-mc-encoding < %s | FileCheck %s
define internal signext i32 @caller() {
entry:
@@ -8,10 +8,12 @@ entry:
define hidden signext i32 @caller2() {
entry:
-; CHECK-LABEL: caller2:
-; CHECK: brasl 7,caller * encoding: [0xc0,0x75,A,A,A,A]
-; CHECK-NEXT: * fixup A - offset: 2, value: caller+2, kind: FK_390_PC32DBL
-; CHECK-NEXT: bcr 0,3 * encoding: [0x07,0x03]
+; CHECK-LABEL: caller2 DS 0H
+; CHECK: * encoding: [0xc0,0x75,A,A,A,A]
+; CHECK-NEXT: * fixup A - offset: 2, value: caller+2, kind: FK_390_PC32DBL
+; CHECK-NEXT: brasl 7,caller
+; CHECK-NEXT: * encoding: [0x07,0x03]
+; CHECK-NEXT: bcr 0,3
%call = call signext i32 @caller()
ret i32 %call
}
diff --git a/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s b/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s
index ce3b7b5e6d410..50ec132f10723 100644
--- a/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s
+++ b/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s
@@ -1,102 +1,130 @@
* For z10 and above.
-* RUN: llvm-mc -triple s390x-ibm-zos -show-encoding -emit-gnuas-syntax-on-zos=1 --output-asm-variant=0 %s | FileCheck %s
-
-*CHECK: brcl 0, FOO * encoding: [0xc0,0x04,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnop FOO * encoding: [0xc0,0x04,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+* RUN: llvm-mc -triple s390x-ibm-zos -show-encoding %s | FileCheck %s
+
+*CHECK: * encoding: [0xc0,0x04,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: brcl 0, FOO
+*CHECK: * encoding: [0xc0,0x04,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnop FOO
brcl 0,FOO
jlnop FOO
-*CHECK: jge FOO * encoding: [0xc0,0x84,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jge FOO * encoding: [0xc0,0x84,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jge FOO
+*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jge FOO
jle FOO
brel FOO
-*CHECK: jgne FOO * encoding: [0xc0,0x74,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgne FOO * encoding: [0xc0,0x74,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgne FOO
+*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgne FOO
jlne FOO
brnel FOO
-*CHECK: jgh FOO * encoding: [0xc0,0x24,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgh FOO * encoding: [0xc0,0x24,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgh FOO
+*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgh FOO
jlh FOO
brhl FOO
-*CHECK: jgnh FOO * encoding: [0xc0,0xd4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnh FOO * encoding: [0xc0,0xd4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnh FOO
+*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnh FOO
jlnh FOO
brnhl FOO
-*CHECK: jgl FOO * encoding: [0xc0,0x44,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgl FOO * encoding: [0xc0,0x44,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
+*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgl FOO
+*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgl FOO
jll FOO
brll FOO
-*CHECK: jgnl FOO * encoding: [0xc0,0xb4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnl FOO * encoding: [0xc0,0xb4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnl FOO
+*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnl FOO
jlnl FOO
brnll FOO
-*CHECK: jgz FOO * encoding: [0xc0,0x84,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgz FOO * encoding: [0xc0,0x84,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgz FOO
+*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgz FOO
jlz FOO
brzl FOO
-*CHECK: jgnz FOO * encoding: [0xc0,0x74,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnz FOO * encoding: [0xc0,0x74,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnz FOO
+*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnz FOO
jlnz FOO
brnzl FOO
-*CHECK: jgp FOO * encoding: [0xc0,0x24,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgp FOO * encoding: [0xc0,0x24,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgp FOO
+*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgp FOO
jlp FOO
brpl FOO
-*CHECK: jgnp FOO * encoding: [0xc0,0xd4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnp FOO * encoding: [0xc0,0xd4,A,A,A,A]
+*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnp FOO
+*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnp FOO
jlnp FOO
brnpl FOO
-*CHECK: jgm FOO * encoding: [0xc0,0x44,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgm FOO * encoding: [0xc0,0x44,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgm FOO
+*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgm FOO
jlm FOO
brml FOO
-*CHECK: jgnm FOO * encoding: [0xc0,0xb4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnm FOO * encoding: [0xc0,0xb4,A,A,A,A]
+*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnm FOO
+*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jgnm FOO
jlnm FOO
brnml FOO
-*CHECK: jg FOO * encoding: [0xc0,0xf4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jg FOO * encoding: [0xc0,0xf4,A,A,A,A]
-*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: * encoding: [0xc0,0xf4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jg FOO
+*CHECK: * encoding: [0xc0,0xf4,A,A,A,A]
+*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
+*CHECK: jg FOO
jlu FOO
brul FOO
>From 457866e06a25293cafd9fec716d369a7a875add5 Mon Sep 17 00:00:00 2001
From: Kai Nacke <kai.peter.nacke at ibm.com>
Date: Fri, 10 Apr 2026 21:16:22 -0400
Subject: [PATCH 7/7] Fully translate test case to HLASM syntax dialect
This is a follow-up to 9d4436e3f4dfecd9503e90fb4cba907c86103e1e
which came in through the rebase.
---
llvm/test/MC/SystemZ/insn-good-zos-pcrel.s | 56 +++++++++++-----------
1 file changed, 28 insertions(+), 28 deletions(-)
diff --git a/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s b/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s
index 50ec132f10723..d769f6e6e3b4b 100644
--- a/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s
+++ b/llvm/test/MC/SystemZ/insn-good-zos-pcrel.s
@@ -3,128 +3,128 @@
*CHECK: * encoding: [0xc0,0x04,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: brcl 0, FOO
+*CHECK: brcl 0,FOO
*CHECK: * encoding: [0xc0,0x04,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnop FOO
+*CHECK: jlnop FOO
brcl 0,FOO
jlnop FOO
*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jge FOO
+*CHECK: jle FOO
*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jge FOO
+*CHECK: jle FOO
jle FOO
brel FOO
*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgne FOO
+*CHECK: jlne FOO
*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgne FOO
+*CHECK: jlne FOO
jlne FOO
brnel FOO
*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgh FOO
+*CHECK: jlh FOO
*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgh FOO
+*CHECK: jlh FOO
jlh FOO
brhl FOO
*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnh FOO
+*CHECK: jlnh FOO
*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnh FOO
+*CHECK: jlnh FOO
jlnh FOO
brnhl FOO
*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgl FOO
+*CHECK: jll FOO
*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgl FOO
+*CHECK: jll FOO
jll FOO
brll FOO
*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnl FOO
+*CHECK: jlnl FOO
*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnl FOO
+*CHECK: jlnl FOO
jlnl FOO
brnll FOO
*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgz FOO
+*CHECK: jlz FOO
*CHECK: * encoding: [0xc0,0x84,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgz FOO
+*CHECK: jlz FOO
jlz FOO
brzl FOO
*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnz FOO
+*CHECK: jlnz FOO
*CHECK: * encoding: [0xc0,0x74,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnz FOO
+*CHECK: jlnz FOO
jlnz FOO
brnzl FOO
*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgp FOO
+*CHECK: jlp FOO
*CHECK: * encoding: [0xc0,0x24,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgp FOO
+*CHECK: jlp FOO
jlp FOO
brpl FOO
*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnp FOO
+*CHECK: jlnp FOO
*CHECK: * encoding: [0xc0,0xd4,A,A,A,A]
*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnp FOO
+*CHECK: jlnp FOO
jlnp FOO
brnpl FOO
*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgm FOO
+*CHECK: jlm FOO
*CHECK: * encoding: [0xc0,0x44,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgm FOO
+*CHECK: jlm FOO
jlm FOO
brml FOO
*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnm FOO
+*CHECK: jlnm FOO
*CHECK: * encoding: [0xc0,0xb4,A,A,A,A]
*CHECK: fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jgnm FOO
+*CHECK: jlnm FOO
jlnm FOO
brnml FOO
*CHECK: * encoding: [0xc0,0xf4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jg FOO
+*CHECK: jlu FOO
*CHECK: * encoding: [0xc0,0xf4,A,A,A,A]
*CHECK: * fixup A - offset: 2, value: FOO+2, kind: FK_390_PC32DBL
-*CHECK: jg FOO
+*CHECK: jlu FOO
jlu FOO
brul FOO
More information about the llvm-branch-commits
mailing list