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