Add support for global constants, and for initializers for constants
[oota-llvm.git] / lib / VMCore / Function.cpp
index 550c4f0ad66c66123950f4a0f6cbe0127034f723..47a85395a3f70a91b88479895ea297f99ced83a8 100644 (file)
@@ -1,6 +1,7 @@
 //===-- Method.cpp - Implement the Method class ------------------*- C++ -*--=//
 //
-// This file implements the Method class for the VMCore library.
+// This file implements the Method & GlobalVariable classes for the VMCore
+// library.
 //
 //===----------------------------------------------------------------------===//
 
 #include "llvm/SymbolTable.h"
 #include "llvm/Module.h"
 #include "llvm/Method.h"
+#include "llvm/GlobalVariable.h"
 #include "llvm/BasicBlock.h"
 #include "llvm/iOther.h"
 
+//===----------------------------------------------------------------------===//
+// Method Implementation
+//===----------------------------------------------------------------------===//
+
+
 // Instantiate Templates - This ugliness is the price we have to pay
 // for having a ValueHolderImpl.h file seperate from ValueHolder.h!  :(
 //
-template class ValueHolder<MethodArgument, Method>;
-template class ValueHolder<BasicBlock    , Method>;
+template class ValueHolder<MethodArgument, Method, Method>;
+template class ValueHolder<BasicBlock    , Method, Method>;
 
 Method::Method(const MethodType *Ty, const string &name) 
-  : SymTabValue(Ty, Value::MethodVal, name), BasicBlocks(this), 
+  : Value(Ty, Value::MethodVal, name), SymTabValue(this), BasicBlocks(this), 
     ArgumentList(this, this) {
   assert(Ty->isMethodType() && "Method signature must be of method type!");
   Parent = 0;
@@ -29,8 +36,8 @@ Method::~Method() {
   dropAllReferences();    // After this it is safe to delete instructions.
 
   // TODO: Should remove from the end, not the beginning of vector!
-  BasicBlocksType::iterator BI = BasicBlocks.begin();
-  while ((BI = BasicBlocks.begin()) != BasicBlocks.end())
+  iterator BI = begin();
+  while ((BI = begin()) != end())
     delete BasicBlocks.remove(BI);
 
   // Delete all of the method arguments and unlink from symbol table...
@@ -39,8 +46,10 @@ Method::~Method() {
 }
 
 // Specialize setName to take care of symbol table majik
-void Method::setName(const string &name) {
+void Method::setName(const string &name, SymbolTable *ST) {
   Module *P;
+  assert((ST == 0 || (!getParent() || ST == getParent()->getSymbolTable())) &&
+        "Invalid symtab argument!");
   if ((P = getParent()) && hasName()) P->getSymbolTable()->remove(this);
   Value::setName(name);
   if (P && getName() != "") P->getSymbolTableSure()->insert(this);
@@ -57,10 +66,6 @@ const Type *Method::getReturnType() const {
   return ((const MethodType *)getType())->getReturnType(); 
 }
 
-const MethodType *Method::getMethodType() const { 
-  return (const MethodType *)getType();
-}
-
 // dropAllReferences() - This function causes all the subinstructions to "let
 // go" of all references that they are maintaining.  This allows one to
 // 'delete' a whole class at a time, even though there may be circular
@@ -70,6 +75,33 @@ const MethodType *Method::getMethodType() const {
 // delete.
 //
 void Method::dropAllReferences() {
-  for_each(BasicBlocks.begin(), BasicBlocks.end(), 
-          std::mem_fun(&BasicBlock::dropAllReferences));
+  for_each(begin(), end(), std::mem_fun(&BasicBlock::dropAllReferences));
+}
+
+//===----------------------------------------------------------------------===//
+// GlobalVariable Implementation
+//===----------------------------------------------------------------------===//
+
+GlobalVariable::GlobalVariable(const Type *Ty, bool isConstant,
+                              ConstPoolVal *Initializer = 0, 
+                              const string &Name = "")
+  : User(Ty, Value::GlobalVal, Name), Parent(0), Constant(isConstant) {
+  assert(Ty->isPointerType() &&                   // No unsized array pointers
+        (!Ty->castPointerType()->isArrayType() ||
+         Ty->castPointerType()->castArrayType()->isSized()) &&
+        "Global Variables must be pointers to a sized type!");
+  if (Initializer) Operands.push_back(Use((Value*)Initializer, this));
+
+  assert(!isConstant || hasInitializer() &&
+        "Globals Constants must have an initializer!"); 
+}
+
+// Specialize setName to take care of symbol table majik
+void GlobalVariable::setName(const string &name, SymbolTable *ST) {
+  Module *P;
+  assert((ST == 0 || (!getParent() || ST == getParent()->getSymbolTable())) &&
+        "Invalid symtab argument!");
+  if ((P = getParent()) && hasName()) P->getSymbolTable()->remove(this);
+  Value::setName(name);
+  if (P && getName() != "") P->getSymbolTableSure()->insert(this);
 }