Home | History | Annotate | Download | only in MC
      1 //===- ConstantPools.cpp - ConstantPool class --*- C++ -*---------===//
      2 //
      3 //                     The LLVM Compiler Infrastructure
      4 //
      5 // This file is distributed under the University of Illinois Open Source
      6 // License. See LICENSE.TXT for details.
      7 //
      8 //===----------------------------------------------------------------------===//
      9 //
     10 // This file implements the ConstantPool and  AssemblerConstantPools classes.
     11 //
     12 //===----------------------------------------------------------------------===//
     13 #include "llvm/ADT/MapVector.h"
     14 #include "llvm/MC/MCContext.h"
     15 #include "llvm/MC/MCExpr.h"
     16 #include "llvm/MC/MCStreamer.h"
     17 #include "llvm/MC/ConstantPools.h"
     18 
     19 using namespace llvm;
     20 //
     21 // ConstantPool implementation
     22 //
     23 // Emit the contents of the constant pool using the provided streamer.
     24 void ConstantPool::emitEntries(MCStreamer &Streamer) {
     25   if (Entries.empty())
     26     return;
     27   Streamer.EmitCodeAlignment(4); // align to 4-byte address
     28   Streamer.EmitDataRegion(MCDR_DataRegion);
     29   for (EntryVecTy::const_iterator I = Entries.begin(), E = Entries.end();
     30        I != E; ++I) {
     31     Streamer.EmitLabel(I->first);
     32     Streamer.EmitValue(I->second, 4);
     33   }
     34   Streamer.EmitDataRegion(MCDR_DataRegionEnd);
     35   Entries.clear();
     36 }
     37 
     38 const MCExpr *ConstantPool::addEntry(const MCExpr *Value, MCContext &Context) {
     39   MCSymbol *CPEntryLabel = Context.CreateTempSymbol();
     40 
     41   Entries.push_back(std::make_pair(CPEntryLabel, Value));
     42   return MCSymbolRefExpr::Create(CPEntryLabel, Context);
     43 }
     44 
     45 bool ConstantPool::empty() { return Entries.empty(); }
     46 
     47 //
     48 // AssemblerConstantPools implementation
     49 //
     50 ConstantPool *
     51 AssemblerConstantPools::getConstantPool(const MCSection *Section) {
     52   ConstantPoolMapTy::iterator CP = ConstantPools.find(Section);
     53   if (CP == ConstantPools.end())
     54     return nullptr;
     55 
     56   return &CP->second;
     57 }
     58 
     59 ConstantPool &
     60 AssemblerConstantPools::getOrCreateConstantPool(const MCSection *Section) {
     61   return ConstantPools[Section];
     62 }
     63 
     64 static void emitConstantPool(MCStreamer &Streamer, const MCSection *Section,
     65                              ConstantPool &CP) {
     66   if (!CP.empty()) {
     67     Streamer.SwitchSection(Section);
     68     CP.emitEntries(Streamer);
     69   }
     70 }
     71 
     72 void AssemblerConstantPools::emitAll(MCStreamer &Streamer) {
     73   // Dump contents of assembler constant pools.
     74   for (ConstantPoolMapTy::iterator CPI = ConstantPools.begin(),
     75                                    CPE = ConstantPools.end();
     76        CPI != CPE; ++CPI) {
     77     const MCSection *Section = CPI->first;
     78     ConstantPool &CP = CPI->second;
     79 
     80     emitConstantPool(Streamer, Section, CP);
     81   }
     82 }
     83 
     84 void AssemblerConstantPools::emitForCurrentSection(MCStreamer &Streamer) {
     85   const MCSection *Section = Streamer.getCurrentSection().first;
     86   if (ConstantPool *CP = getConstantPool(Section)) {
     87     emitConstantPool(Streamer, Section, *CP);
     88   }
     89 }
     90 
     91 const MCExpr *AssemblerConstantPools::addEntry(MCStreamer &Streamer,
     92                                                const MCExpr *Expr) {
     93   const MCSection *Section = Streamer.getCurrentSection().first;
     94   return getOrCreateConstantPool(Section).addEntry(Expr, Streamer.getContext());
     95 }
     96