Files
gps/tools/local/circt/include/llvm/MC/MCGOFFObjectWriter.h
T
2026-07-12 11:01:51 +03:00

116 lines
3.9 KiB
C++

//===- MCGOFFObjectWriter.h - GOFF Object Writer ----------------*- C++ -*-===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//
#ifndef LLVM_MC_MCGOFFOBJECTWRITER_H
#define LLVM_MC_MCGOFFOBJECTWRITER_H
#include "llvm/BinaryFormat/GOFF.h"
#include "llvm/MC/MCObjectWriter.h"
#include "llvm/MC/MCValue.h"
#include <memory>
#include <vector>
namespace llvm {
class MCObjectWriter;
class MCSectionGOFF;
class MCSymbolGOFF;
class raw_pwrite_stream;
class MCGOFFObjectTargetWriter : public MCObjectTargetWriter {
protected:
MCGOFFObjectTargetWriter() = default;
public:
enum RLDRelocationType {
Reloc_Type_ACon = 0x1, // General address.
Reloc_Type_RICon = 0x2, // Relative-immediate address.
Reloc_Type_QCon = 0x3, // Offset of symbol in class.
Reloc_Type_VCon = 0x4, // Address of external symbol.
Reloc_Type_RCon = 0x5, // PSECT of symbol.
};
~MCGOFFObjectTargetWriter() override = default;
virtual unsigned getRelocType(const MCValue &Target,
const MCFixup &Fixup) const = 0;
Triple::ObjectFormatType getFormat() const override { return Triple::GOFF; }
static bool classof(const MCObjectTargetWriter *W) {
return W->getFormat() == Triple::GOFF;
}
};
// A GOFFRelocationEntry describes a single relocation.
// For the naming, see
// https://www.ibm.com/docs/en/zos/3.1.0?topic=record-relocation-directory-data-item.
struct GOFFRelocationEntry {
const MCSymbolGOFF *Rptr; // The R pointer.
const MCSectionGOFF *Pptr; // The P pointer.
uint32_t REsdId = 0; // The R pointer id.
uint32_t PEsdId = 0; // The P pointer id.
uint64_t POffset; // The offset within the element described by the P pointer.
uint32_t TargetLength; // The byte length of the target field.
// Details of the relocation.
GOFF::RLDReferenceType ReferenceType : 4;
GOFF::RLDReferentType ReferentType : 2;
GOFF::RLDAction Action : 1;
GOFF::RLDFetchStore FetchStore : 1;
GOFFRelocationEntry(const MCSectionGOFF *Pptr, const MCSymbolGOFF *Rptr,
GOFF::RLDReferenceType ReferenceType,
GOFF::RLDReferentType ReferentType,
GOFF::RLDAction Action, GOFF::RLDFetchStore FetchStore,
uint64_t POffset, uint32_t TargetLength)
: Rptr(Rptr), Pptr(Pptr), POffset(POffset), TargetLength(TargetLength),
ReferenceType(ReferenceType), ReferentType(ReferentType),
Action(Action), FetchStore(FetchStore) {}
};
class LLVM_ABI GOFFObjectWriter : public MCObjectWriter {
// The target specific GOFF writer instance.
std::unique_ptr<MCGOFFObjectTargetWriter> TargetObjectWriter;
// The stream used to write the GOFF records.
raw_pwrite_stream &OS;
// The RootSD section.
MCSectionGOFF *RootSD = nullptr;
// Saved relocation data.
std::vector<GOFFRelocationEntry> Relocations;
public:
GOFFObjectWriter(std::unique_ptr<MCGOFFObjectTargetWriter> MOTW,
raw_pwrite_stream &OS);
~GOFFObjectWriter() override;
void reset() override;
void setRootSD(MCSectionGOFF *RootSD) { this->RootSD = RootSD; }
// Implementation of the MCObjectWriter interface.
void recordRelocation(const MCFragment &F, const MCFixup &Fixup,
MCValue Target, uint64_t &FixedValue) override;
uint64_t writeObject() override;
};
/// \brief Construct a new GOFF writer instance.
///
/// \param MOTW - The target-specific GOFF writer subclass.
/// \param OS - The stream to write to.
/// \returns The constructed object writer.
LLVM_ABI std::unique_ptr<MCObjectWriter>
createGOFFObjectWriter(std::unique_ptr<MCGOFFObjectTargetWriter> MOTW,
raw_pwrite_stream &OS);
} // namespace llvm
#endif