a28210ba9543d132587947a184dc864b4ed2636d
[oota-llvm.git] / include / llvm / DerivedTypes.h
1 //===-- llvm/DerivedTypes.h - Classes for handling data types ----*- C++ -*--=//
2 //
3 // This file contains the declarations of classes that represent "derived 
4 // types".  These are things like "arrays of x" or "structure of x, y, z" or
5 // "method returning x taking (y,z) as parameters", etc...
6 //
7 // The implementations of these classes live in the Type.cpp file.
8 //
9 //===----------------------------------------------------------------------===//
10
11 #ifndef LLVM_DERIVED_TYPES_H
12 #define LLVM_DERIVED_TYPES_H
13
14 #include "llvm/Type.h"
15 #include "llvm/CodeGen/TargetMachine.h"
16 #include "vector"
17
18 class TargetMachine;
19
20
21 // Future derived types: SIMD packed format
22
23
24 class MethodType : public Type {
25 public:
26   typedef vector<const Type*> ParamTypes;
27 private:
28   const Type *ResultType;
29   ParamTypes ParamTys;
30
31   MethodType(const MethodType &);                   // Do not implement
32   const MethodType &operator=(const MethodType &);  // Do not implement
33 protected:
34   // This should really be private, but it squelches a bogus warning
35   // from GCC to make them protected:  warning: `class MethodType' only 
36   // defines private constructors and has no friends
37
38   // Private ctor - Only can be created by a static member...
39   MethodType(const Type *Result, const vector<const Type*> &Params, 
40              const string &Name);
41 public:
42
43   inline const Type *getReturnType() const { return ResultType; }
44   inline const ParamTypes &getParamTypes() const { return ParamTys; }
45
46   static const MethodType *getMethodType(const Type *Result, 
47                                          const ParamTypes &Params);
48   static const MethodType *get(const Type *Result, const ParamTypes &Params) {
49     return getMethodType(Result, Params);
50   }
51 };
52
53
54
55 class ArrayType : public Type {
56 private:
57   const Type *ElementType;
58   int NumElements;       // >= 0 for sized array, -1 for unbounded/unknown array
59
60   ArrayType(const ArrayType &);                   // Do not implement
61   const ArrayType &operator=(const ArrayType &);  // Do not implement
62 protected:
63   // This should really be private, but it squelches a bogus warning
64   // from GCC to make them protected:  warning: `class ArrayType' only 
65   // defines private constructors and has no friends
66
67
68   // Private ctor - Only can be created by a static member...
69   ArrayType(const Type *ElType, int NumEl, const string &Name);
70 public:
71
72   inline const Type *getElementType() const { return ElementType; }
73   inline int         getNumElements() const { return NumElements; }
74
75   inline bool isSized()   const { return NumElements >= 0; }
76   inline bool isUnsized() const { return NumElements == -1; }
77
78   static const ArrayType *getArrayType(const Type *ElementType, 
79                                        int NumElements = -1);
80   static const ArrayType *get(const Type *ElementType, int NumElements = -1) {
81     return getArrayType(ElementType, NumElements);
82   }
83 };
84
85 class StructType : public Type {
86 public:
87   typedef vector<const Type*> ElementTypes;
88
89 private:
90   ElementTypes ETypes;
91   struct StructSizeAndOffsetInfo {
92     int storageSize;                    // -1 until the value is computd
93     vector<int> memberOffsets;          // -1 until values are computed 
94     const TargetMachine* targetInfo;
95   }
96   *layoutCache;
97   
98 private:
99   StructType(const StructType &);                   // Do not implement
100   const StructType &operator=(const StructType &);  // Do not implement
101   
102 protected:
103   // This should really be private, but it squelches a bogus warning
104   // from GCC to make them protected:  warning: `class StructType' only 
105   // defines private constructors and has no friends
106
107   // Private ctor - Only can be created by a static member...
108   StructType(const vector<const Type*> &Types, const string &Name);
109   
110   // Reset cached info so it will be computed when first requested
111   void ResetCachedInfo() const;
112   
113 public:
114
115   inline const ElementTypes &getElementTypes() const { return ETypes; }
116   static const StructType *getStructType(const ElementTypes &Params);
117   static const StructType *get(const ElementTypes &Params) {
118     return getStructType(Params);
119   }
120   unsigned int             getStorageSize(const TargetMachine& tmi) const;
121   unsigned int             getElementOffset(int i, const TargetMachine& tmi) const;
122 };
123
124
125 inline unsigned int
126 StructType::getStorageSize(const TargetMachine& tmi) const
127 {
128   if (layoutCache->targetInfo != NULL && ! (* layoutCache->targetInfo == tmi))
129     {// target machine has changed (hey it could happen). discard cached info.
130       ResetCachedInfo();
131       layoutCache->targetInfo = &tmi;
132     }
133   
134   if (layoutCache->storageSize < 0)
135     {
136       layoutCache->storageSize = tmi.findOptimalStorageSize(this);
137       assert(layoutCache->storageSize >= 0);
138     }
139   
140   return layoutCache->storageSize;
141 }
142
143
144 inline unsigned int
145 StructType::getElementOffset(int i, const TargetMachine& tmi) const
146 {
147   if (layoutCache->targetInfo != NULL && ! (* layoutCache->targetInfo == tmi))
148     {// target machine has changed (hey it could happen). discard cached info.
149       ResetCachedInfo();
150     }
151   
152   if (layoutCache->memberOffsets[i] < 0)
153     {
154       layoutCache->targetInfo = &tmi;   // remember which target was used
155       
156       unsigned int* offsetVec = tmi.findOptimalMemberOffsets(this);
157       for (unsigned i=0, N=layoutCache->memberOffsets.size(); i < N; i++)
158         {
159           layoutCache->memberOffsets[i] = offsetVec[i];
160           assert(layoutCache->memberOffsets[i] >= 0);
161         }
162       delete[] offsetVec; 
163     }
164   
165   return layoutCache->memberOffsets[i];
166 }
167
168
169 inline void
170 StructType::ResetCachedInfo() const
171 {
172   layoutCache->storageSize = -1;
173   layoutCache->memberOffsets.insert(layoutCache->memberOffsets.begin(),
174                                     ETypes.size(), -1);
175   layoutCache->targetInfo = NULL;
176 }
177
178
179 class PointerType : public Type {
180 private:
181   const Type *ValueType;
182
183   PointerType(const PointerType &);                   // Do not implement
184   const PointerType &operator=(const PointerType &);  // Do not implement
185 protected:
186   // This should really be private, but it squelches a bogus warning
187   // from GCC to make them protected:  warning: `class PointerType' only 
188   // defines private constructors and has no friends
189
190
191   // Private ctor - Only can be created by a static member...
192   PointerType(const Type *ElType);
193 public:
194
195   inline const Type *getValueType() const { return ValueType; }
196
197
198   static const PointerType *getPointerType(const Type *ElementType);
199   static const PointerType *get(const Type *ElementType) {
200     return getPointerType(ElementType);
201   }
202 };
203
204 #endif