MCObjectStreamer.cpp revision 8067adc271d7ccfcd28a238d73942b21a5e2bc62
18dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar//===- lib/MC/MCObjectStreamer.cpp - Object File MCStreamer Interface -----===//
28dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar//
38dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar//                     The LLVM Compiler Infrastructure
48dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar//
58dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar// This file is distributed under the University of Illinois Open Source
68dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar// License. See LICENSE.TXT for details.
78dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar//
88dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar//===----------------------------------------------------------------------===//
98dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar
108dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar#include "llvm/MC/MCObjectStreamer.h"
118dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar
128067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer#include "llvm/Support/ErrorHandling.h"
138dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar#include "llvm/MC/MCAssembler.h"
148067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer#include "llvm/MC/MCExpr.h"
158dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbarusing namespace llvm;
168dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar
178dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel DunbarMCObjectStreamer::MCObjectStreamer(MCContext &Context, TargetAsmBackend &TAB,
188dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar                                   raw_ostream &_OS, MCCodeEmitter *_Emitter)
1983b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar  : MCStreamer(Context), Assembler(new MCAssembler(Context, TAB,
2083b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar                                                   *_Emitter, _OS)),
2183b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar    CurSectionData(0)
228dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar{
238dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar}
248dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar
258dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel DunbarMCObjectStreamer::~MCObjectStreamer() {
268dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar  delete Assembler;
278dc68ab931e0f0a7c5caf9cd341b2ec855733863Daniel Dunbar}
2883b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar
298067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. SpencerMCFragment *MCObjectStreamer::getCurrentFragment() const {
308067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  assert(getCurrentSectionData() && "No current section!");
318067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
328067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  if (!getCurrentSectionData()->empty())
338067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    return &getCurrentSectionData()->getFragmentList().back();
348067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
358067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  return 0;
368067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer}
378067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
388067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. SpencerMCDataFragment *MCObjectStreamer::getOrCreateDataFragment() const {
398067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  MCDataFragment *F = dyn_cast_or_null<MCDataFragment>(getCurrentFragment());
408067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  if (!F)
418067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    F = new MCDataFragment(getCurrentSectionData());
428067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  return F;
438067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer}
448067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
458067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencerconst MCExpr *MCObjectStreamer::AddValueSymbols(const MCExpr *Value) {
468067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  switch (Value->getKind()) {
478067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  case MCExpr::Target: llvm_unreachable("Can't handle target exprs yet!");
488067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  case MCExpr::Constant:
498067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    break;
508067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
518067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  case MCExpr::Binary: {
528067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    const MCBinaryExpr *BE = cast<MCBinaryExpr>(Value);
538067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    AddValueSymbols(BE->getLHS());
548067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    AddValueSymbols(BE->getRHS());
558067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    break;
568067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  }
578067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
588067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  case MCExpr::SymbolRef:
598067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    Assembler->getOrCreateSymbolData(cast<MCSymbolRefExpr>(Value)->getSymbol());
608067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    break;
618067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
628067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  case MCExpr::Unary:
638067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    AddValueSymbols(cast<MCUnaryExpr>(Value)->getSubExpr());
648067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer    break;
658067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  }
668067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
678067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer  return Value;
688067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer}
698067adc271d7ccfcd28a238d73942b21a5e2bc62Michael J. Spencer
7083b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbarvoid MCObjectStreamer::SwitchSection(const MCSection *Section) {
7183b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar  assert(Section && "Cannot switch to a null section!");
7283b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar
7383b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar  // If already in this section, then this is a noop.
7483b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar  if (Section == CurSection) return;
7583b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar
7683b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar  CurSection = Section;
7783b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar  CurSectionData = &getAssembler().getOrCreateSectionData(*Section);
7883b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar}
7983b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar
8083b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbarvoid MCObjectStreamer::Finish() {
8183b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar  getAssembler().Finish();
8283b467178a8295048f3ee7b44ff9c7ea244a96ccDaniel Dunbar}
83