using namespace llvm;
MCObjectStreamer::MCObjectStreamer(MCContext &Context, MCAsmBackend &TAB,
- raw_ostream &OS, MCCodeEmitter *Emitter_)
+ raw_pwrite_stream &OS,
+ MCCodeEmitter *Emitter_)
: MCStreamer(Context),
Assembler(new MCAssembler(Context, TAB, *Emitter_,
*TAB.createObjectWriter(OS), OS)),
CurSectionData(nullptr), EmitEHFrame(true), EmitDebugFrame(false) {}
-MCObjectStreamer::MCObjectStreamer(MCContext &Context, MCAsmBackend &TAB,
- raw_ostream &OS, MCCodeEmitter *Emitter_,
- MCAssembler *Assembler)
- : MCStreamer(Context), Assembler(Assembler), CurSectionData(nullptr),
- EmitEHFrame(true), EmitDebugFrame(false) {}
-
MCObjectStreamer::~MCObjectStreamer() {
delete &Assembler->getBackend();
delete &Assembler->getEmitter();
delete Assembler;
}
-void MCObjectStreamer::flushPendingLabels(MCFragment *F) {
+void MCObjectStreamer::flushPendingLabels(MCFragment *F, uint64_t FOffset) {
if (PendingLabels.size()) {
if (!F) {
F = new MCDataFragment();
}
for (MCSymbolData *SD : PendingLabels) {
SD->setFragment(F);
- SD->setOffset(0);
+ SD->setOffset(FOffset);
}
PendingLabels.clear();
}
MCDataFragment *F = dyn_cast_or_null<MCDataFragment>(getCurrentFragment());
// When bundling is enabled, we don't want to add data to a fragment that
// already has instructions (see MCELFStreamer::EmitInstToData for details)
- if (!F || (Assembler->isBundlingEnabled() && F->hasInstructions())) {
+ if (!F || (Assembler->isBundlingEnabled() && !Assembler->getRelaxAll() &&
+ F->hasInstructions())) {
F = new MCDataFragment();
insert(F);
}
return;
}
DF->getFixups().push_back(
- MCFixup::Create(DF->getContents().size(), Value,
+ MCFixup::create(DF->getContents().size(), Value,
MCFixup::getKindForSize(Size, false), Loc));
DF->getContents().resize(DF->getContents().size() + Size, 0);
}
void MCObjectStreamer::EmitCFIStartProcImpl(MCDwarfFrameInfo &Frame) {
// We need to create a local symbol to avoid relocations.
- Frame.Begin = getContext().CreateTempSymbol();
+ Frame.Begin = getContext().createTempSymbol();
EmitLabel(Frame.Begin);
}
void MCObjectStreamer::EmitCFIEndProcImpl(MCDwarfFrameInfo &Frame) {
- Frame.End = getContext().CreateTempSymbol();
+ Frame.End = getContext().createTempSymbol();
EmitLabel(Frame.End);
}
// If there is a current fragment, mark the symbol as pointing into it.
// Otherwise queue the label and set its fragment pointer when we emit the
// next fragment.
- if (auto *F = dyn_cast_or_null<MCDataFragment>(getCurrentFragment())) {
+ auto *F = dyn_cast_or_null<MCDataFragment>(getCurrentFragment());
+ if (F && !(getAssembler().isBundlingEnabled() &&
+ getAssembler().getRelaxAll())) {
SD.setFragment(F);
SD.setOffset(F->getContents().size());
} else {
void MCObjectStreamer::ChangeSection(const MCSection *Section,
const MCExpr *Subsection) {
+ changeSectionImpl(Section, Subsection);
+}
+
+bool MCObjectStreamer::changeSectionImpl(const MCSection *Section,
+ const MCExpr *Subsection) {
assert(Section && "Cannot switch to a null section!");
flushPendingLabels(nullptr);
- CurSectionData = &getAssembler().getOrCreateSectionData(*Section);
+ bool Created;
+ CurSectionData = &getAssembler().getOrCreateSectionData(*Section, &Created);
int64_t IntSubsection = 0;
if (Subsection &&
report_fatal_error("Subsection number out of range");
CurInsertionPoint =
CurSectionData->getSubsectionInsertionPoint(unsigned(IntSubsection));
+ return Created;
}
void MCObjectStreamer::EmitAssignment(MCSymbol *Symbol, const MCExpr *Value) {
void MCObjectStreamer::EmitInstToFragment(const MCInst &Inst,
const MCSubtargetInfo &STI) {
+ if (getAssembler().getRelaxAll() && getAssembler().isBundlingEnabled())
+ llvm_unreachable("All instructions should have already been relaxed");
+
// Always create a new, separate fragment here, because its size can change
// during relaxation.
MCRelaxableFragment *IF = new MCRelaxableFragment(Inst, STI);
SmallString<128> Code;
raw_svector_ostream VecOS(Code);
- getAssembler().getEmitter().EncodeInstruction(Inst, VecOS, IF->getFixups(),
+ getAssembler().getEmitter().encodeInstruction(Inst, VecOS, IF->getFixups(),
STI);
VecOS.flush();
IF->getContents().append(Code.begin(), Code.end());
return false;
}
- MCSymbol *CurrentPos = getContext().CreateTempSymbol();
+ MCSymbol *CurrentPos = getContext().createTempSymbol();
EmitLabel(CurrentPos);
MCSymbolRefExpr::VariantKind Variant = MCSymbolRefExpr::VK_None;
const MCExpr *Ref =
void MCObjectStreamer::EmitGPRel32Value(const MCExpr *Value) {
MCDataFragment *DF = getOrCreateDataFragment();
- DF->getFixups().push_back(MCFixup::Create(DF->getContents().size(),
+ DF->getFixups().push_back(MCFixup::create(DF->getContents().size(),
Value, FK_GPRel_4));
DF->getContents().resize(DF->getContents().size() + 4, 0);
}
void MCObjectStreamer::EmitGPRel64Value(const MCExpr *Value) {
MCDataFragment *DF = getOrCreateDataFragment();
- DF->getFixups().push_back(MCFixup::Create(DF->getContents().size(),
+ DF->getFixups().push_back(MCFixup::create(DF->getContents().size(),
Value, FK_GPRel_4));
DF->getContents().resize(DF->getContents().size() + 8, 0);
}