169de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//===-- llvm/CodeGen/PseudoSourceValue.cpp ----------------------*- C++ -*-===//
269de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//
369de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//                     The LLVM Compiler Infrastructure
469de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//
569de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman// This file is distributed under the University of Illinois Open Source
669de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman// License. See LICENSE.TXT for details.
769de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//
869de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//===----------------------------------------------------------------------===//
969de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//
1069de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman// This file implements the PseudoSourceValue class.
1169de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//
1269de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman//===----------------------------------------------------------------------===//
1369de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman
146d69ba8a6901c69d78488cbc41f8dbf080618fdeDan Gohman#include "llvm/CodeGen/MachineFrameInfo.h"
1569de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman#include "llvm/CodeGen/PseudoSourceValue.h"
1669de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman#include "llvm/DerivedTypes.h"
1775c478a96a542dc386152e00518441e63d22058dChris Lattner#include "llvm/LLVMContext.h"
18c25e7581b9b8088910da31702d4ca21c4734c6d7Torok Edwin#include "llvm/Support/ErrorHandling.h"
1969de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman#include "llvm/Support/ManagedStatic.h"
2040ab164d3ae6fddb279ae49ab2f9756b466c640aEvan Cheng#include "llvm/Support/raw_ostream.h"
211f6efa3996dd1929fbc129203ce5009b620e6969Michael J. Spencer#include "llvm/Support/Mutex.h"
22a54cf176613f9ae8301519a61b8935652c0fb8aeDan Gohman#include <map>
23edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattnerusing namespace llvm;
2469de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman
25e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskinnamespace {
26e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskinstruct PSVGlobalsTy {
27e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  // PseudoSourceValues are immutable so don't need locking.
28e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  const PseudoSourceValue PSVs[4];
29e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  sys::Mutex Lock;  // Guards FSValues, but not the values inside it.
30e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  std::map<int, const PseudoSourceValue *> FSValues;
31e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin
32e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  PSVGlobalsTy() : PSVs() {}
33e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  ~PSVGlobalsTy() {
34e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin    for (std::map<int, const PseudoSourceValue *>::iterator
35e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin           I = FSValues.begin(), E = FSValues.end(); I != E; ++I) {
36e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin      delete I->second;
37e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin    }
38e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  }
39e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin};
40e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin
41e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskinstatic ManagedStatic<PSVGlobalsTy> PSVGlobals;
42e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin
43e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin}  // anonymous namespace
4469de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman
45edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattnerconst PseudoSourceValue *PseudoSourceValue::getStack()
46e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin{ return &PSVGlobals->PSVs[0]; }
47edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattnerconst PseudoSourceValue *PseudoSourceValue::getGOT()
48e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin{ return &PSVGlobals->PSVs[1]; }
49edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattnerconst PseudoSourceValue *PseudoSourceValue::getJumpTable()
50e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin{ return &PSVGlobals->PSVs[2]; }
51edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattnerconst PseudoSourceValue *PseudoSourceValue::getConstantPool()
52e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin{ return &PSVGlobals->PSVs[3]; }
5369de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman
54edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattnerstatic const char *const PSVNames[] = {
55edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  "Stack",
56edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  "GOT",
57edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  "JumpTable",
58edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  "ConstantPool"
59edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner};
6069de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman
611d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson// FIXME: THIS IS A HACK!!!!
621d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson// Eventually these should be uniqued on LLVMContext rather than in a managed
631d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson// static.  For now, we can safely use the global context for the time being to
641d0be15f89cb5056e20e2d24faa8d6afb1573bcaOwen Anderson// squeak by.
65cf62632d835313b720b68669bd1e5682d4d52d0dDavid GreenePseudoSourceValue::PseudoSourceValue(enum ValueTy Subclass) :
66ac53a0b272452013124bfc70480aea5e41b60f40Duncan Sands  Value(Type::getInt8PtrTy(getGlobalContext()),
67cf62632d835313b720b68669bd1e5682d4d52d0dDavid Greene        Subclass) {}
6869de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman
69cd26ec5f3c089b3b24f80ff200e94e681eb9e1eeDan Gohmanvoid PseudoSourceValue::printCustom(raw_ostream &O) const {
70e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  O << PSVNames[this - PSVGlobals->PSVs];
71edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner}
72a54cf176613f9ae8301519a61b8935652c0fb8aeDan Gohman
736553155172a2e74feff1253837daa608123de54aEvan Chengconst PseudoSourceValue *PseudoSourceValue::getFixedStack(int FI) {
74e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  PSVGlobalsTy &PG = *PSVGlobals;
75e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  sys::ScopedLock locked(PG.Lock);
76e8cfa63e4ec3eb5dde44c8f30dee136b20f8195dJeffrey Yasskin  const PseudoSourceValue *&V = PG.FSValues[FI];
77edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  if (!V)
786553155172a2e74feff1253837daa608123de54aEvan Cheng    V = new FixedStackPseudoSourceValue(FI);
79edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  return V;
80edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner}
816d69ba8a6901c69d78488cbc41f8dbf080618fdeDan Gohman
82edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattnerbool PseudoSourceValue::isConstant(const MachineFrameInfo *) const {
83edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  if (this == getStack())
846d69ba8a6901c69d78488cbc41f8dbf080618fdeDan Gohman    return false;
85edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  if (this == getGOT() ||
86edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner      this == getConstantPool() ||
87edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner      this == getJumpTable())
88edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner    return true;
89c23197a26f34f559ea9797de51e187087c039c42Torok Edwin  llvm_unreachable("Unknown PseudoSourceValue!");
90edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner}
916d69ba8a6901c69d78488cbc41f8dbf080618fdeDan Gohman
9238bdfc69cbe370ce5f623df4449afa32cda97422Evan Chengbool PseudoSourceValue::isAliased(const MachineFrameInfo *MFI) const {
93ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng  if (this == getStack() ||
94ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng      this == getGOT() ||
95ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng      this == getConstantPool() ||
96ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng      this == getJumpTable())
97ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng    return false;
98ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng  llvm_unreachable("Unknown PseudoSourceValue!");
99ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng}
100ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng
101f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Chengbool PseudoSourceValue::mayAlias(const MachineFrameInfo *MFI) const {
102f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng  if (this == getGOT() ||
103f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng      this == getConstantPool() ||
104f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng      this == getJumpTable())
105f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng    return false;
106f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng  return true;
107f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng}
108f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng
1096553155172a2e74feff1253837daa608123de54aEvan Chengbool FixedStackPseudoSourceValue::isConstant(const MachineFrameInfo *MFI) const{
110edfb72c6288118ab9c900a560ded89dfaa107296Chris Lattner  return MFI && MFI->isImmutableObjectIndex(FI);
11169de1932b350d7cdfc0ed1f4198d6f78c7822a02Dan Gohman}
112ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng
11338bdfc69cbe370ce5f623df4449afa32cda97422Evan Chengbool FixedStackPseudoSourceValue::isAliased(const MachineFrameInfo *MFI) const {
114ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng  // Negative frame indices are used for special things that don't
115ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng  // appear in LLVM IR. Non-negative indices may be used for things
116ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng  // like static allocas.
11738bdfc69cbe370ce5f623df4449afa32cda97422Evan Cheng  if (!MFI)
11838bdfc69cbe370ce5f623df4449afa32cda97422Evan Cheng    return FI >= 0;
11938bdfc69cbe370ce5f623df4449afa32cda97422Evan Cheng  // Spill slots should not alias others.
12038bdfc69cbe370ce5f623df4449afa32cda97422Evan Cheng  return !MFI->isFixedObjectIndex(FI) && !MFI->isSpillSlotObjectIndex(FI);
121ff89dcb06fbd103373436e2d0ae85f252fae2254Evan Cheng}
122f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng
123f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Chengbool FixedStackPseudoSourceValue::mayAlias(const MachineFrameInfo *MFI) const {
124f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng  if (!MFI)
125f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng    return true;
126f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng  // Spill slots will not alias any LLVM IR value.
127f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng  return !MFI->isSpillSlotObjectIndex(FI);
128f57b1baa441e3bbce7f264d8bb5054e50fe8ee1cEvan Cheng}
129b3bc115a2414a922caa40d5536d8a35ca54e40e3David Greene
130b3bc115a2414a922caa40d5536d8a35ca54e40e3David Greenevoid FixedStackPseudoSourceValue::printCustom(raw_ostream &OS) const {
131b3bc115a2414a922caa40d5536d8a35ca54e40e3David Greene  OS << "FixedStack" << FI;
132b3bc115a2414a922caa40d5536d8a35ca54e40e3David Greene}
133