Add include needed for MSVC.
[clang/acc.git] / lib / CodeGen / CGBlocks.h
blob5a0af04b24d7bcead76ce6adafe25dceaf94b9ca
1 //===-- CGBlocks.h - state for LLVM CodeGen for blocks ----------*- 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 is the internal state used for llvm translation for block literals.
12 //===----------------------------------------------------------------------===//
14 #ifndef CLANG_CODEGEN_CGBLOCKS_H
15 #define CLANG_CODEGEN_CGBLOCKS_H
17 #include "CodeGenTypes.h"
18 #include "clang/AST/Type.h"
19 #include "llvm/Module.h"
20 #include "llvm/ADT/DenseMap.h"
21 #include "llvm/ADT/SmallVector.h"
22 #include "clang/Basic/TargetInfo.h"
23 #include "clang/AST/Expr.h"
24 #include "clang/AST/ExprCXX.h"
25 #include "clang/AST/ExprObjC.h"
27 #include <vector>
28 #include <map>
30 #include "CGBuilder.h"
31 #include "CGCall.h"
32 #include "CGValue.h"
34 namespace llvm {
35 class Module;
36 class Constant;
37 class Function;
38 class GlobalValue;
39 class TargetData;
40 class FunctionType;
41 class Value;
42 class LLVMContext;
45 namespace clang {
47 namespace CodeGen {
48 class CodeGenModule;
50 class BlockBase {
51 public:
52 enum {
53 BLOCK_NEEDS_FREE = (1 << 24),
54 BLOCK_HAS_COPY_DISPOSE = (1 << 25),
55 BLOCK_HAS_CXX_OBJ = (1 << 26),
56 BLOCK_IS_GC = (1 << 27),
57 BLOCK_IS_GLOBAL = (1 << 28),
58 BLOCK_HAS_DESCRIPTOR = (1 << 29)
62 class BlockModule : public BlockBase {
63 ASTContext &Context;
64 llvm::Module &TheModule;
65 const llvm::TargetData &TheTargetData;
66 CodeGenTypes &Types;
67 CodeGenModule &CGM;
68 llvm::LLVMContext &VMContext;
70 ASTContext &getContext() const { return Context; }
71 llvm::Module &getModule() const { return TheModule; }
72 CodeGenTypes &getTypes() { return Types; }
73 const llvm::TargetData &getTargetData() const { return TheTargetData; }
74 public:
75 llvm::Constant *getNSConcreteGlobalBlock();
76 llvm::Constant *getNSConcreteStackBlock();
77 int getGlobalUniqueCount() { return ++Block.GlobalUniqueCount; }
78 const llvm::Type *getBlockDescriptorType();
80 const llvm::Type *getGenericBlockLiteralType();
81 const llvm::Type *getGenericExtendedBlockLiteralType();
83 llvm::Constant *GetAddrOfGlobalBlock(const BlockExpr *BE, const char *);
85 /// NSConcreteGlobalBlock - Cached reference to the class pointer for global
86 /// blocks.
87 llvm::Constant *NSConcreteGlobalBlock;
89 /// NSConcreteStackBlock - Cached reference to the class poinnter for stack
90 /// blocks.
91 llvm::Constant *NSConcreteStackBlock;
93 const llvm::Type *BlockDescriptorType;
94 const llvm::Type *GenericBlockLiteralType;
95 const llvm::Type *GenericExtendedBlockLiteralType;
96 struct {
97 int GlobalUniqueCount;
98 } Block;
100 llvm::Value *BlockObjectAssign;
101 llvm::Value *BlockObjectDispose;
102 const llvm::Type *PtrToInt8Ty;
104 std::map<uint64_t, llvm::Constant *> AssignCache;
105 std::map<uint64_t, llvm::Constant *> DestroyCache;
107 BlockModule(ASTContext &C, llvm::Module &M, const llvm::TargetData &TD,
108 CodeGenTypes &T, CodeGenModule &CodeGen)
109 : Context(C), TheModule(M), TheTargetData(TD), Types(T),
110 CGM(CodeGen), VMContext(M.getContext()),
111 NSConcreteGlobalBlock(0), NSConcreteStackBlock(0), BlockDescriptorType(0),
112 GenericBlockLiteralType(0), GenericExtendedBlockLiteralType(0),
113 BlockObjectAssign(0), BlockObjectDispose(0) {
114 Block.GlobalUniqueCount = 0;
115 PtrToInt8Ty = llvm::PointerType::getUnqual(llvm::Type::Int8Ty);
119 class BlockFunction : public BlockBase {
120 CodeGenModule &CGM;
121 CodeGenFunction &CGF;
122 ASTContext &getContext() const;
124 protected:
125 llvm::LLVMContext &VMContext;
127 public:
128 const llvm::Type *PtrToInt8Ty;
129 struct HelperInfo {
130 int index;
131 int flag;
132 bool RequiresCopying;
135 enum {
136 BLOCK_FIELD_IS_OBJECT = 3, /* id, NSObject, __attribute__((NSObject)),
137 block, ... */
138 BLOCK_FIELD_IS_BLOCK = 7, /* a block variable */
139 BLOCK_FIELD_IS_BYREF = 8, /* the on stack structure holding the __block
140 variable */
141 BLOCK_FIELD_IS_WEAK = 16, /* declared __weak, only used in byref copy
142 helpers */
143 BLOCK_BYREF_CALLER = 128, /* called from __block (byref) copy/dispose
144 support routines */
145 BLOCK_BYREF_CURRENT_MAX = 256
148 /// BlockInfo - Information to generate a block literal.
149 struct BlockInfo {
150 /// BlockLiteralTy - The type of the block literal.
151 const llvm::Type *BlockLiteralTy;
153 /// Name - the name of the function this block was created for, if any.
154 const char *Name;
156 /// ByCopyDeclRefs - Variables from parent scopes that have been imported
157 /// into this block.
158 llvm::SmallVector<const BlockDeclRefExpr *, 8> ByCopyDeclRefs;
160 // ByRefDeclRefs - __block variables from parent scopes that have been
161 // imported into this block.
162 llvm::SmallVector<const BlockDeclRefExpr *, 8> ByRefDeclRefs;
164 BlockInfo(const llvm::Type *blt, const char *n)
165 : BlockLiteralTy(blt), Name(n) {
166 // Skip asm prefix, if any.
167 if (Name && Name[0] == '\01')
168 ++Name;
172 CGBuilderTy &Builder;
174 BlockFunction(CodeGenModule &cgm, CodeGenFunction &cgf, CGBuilderTy &B);
176 /// BlockOffset - The offset in bytes for the next allocation of an
177 /// imported block variable.
178 uint64_t BlockOffset;
179 /// BlockAlign - Maximal alignment needed for the Block expressed in bytes.
180 uint64_t BlockAlign;
182 /// getBlockOffset - Allocate an offset for the ValueDecl from a
183 /// BlockDeclRefExpr in a block literal (BlockExpr).
184 uint64_t getBlockOffset(const BlockDeclRefExpr *E);
186 /// BlockHasCopyDispose - True iff the block uses copy/dispose.
187 bool BlockHasCopyDispose;
189 /// BlockDeclRefDecls - Decls from BlockDeclRefExprs in apperance order
190 /// in a block literal. Decls without names are used for padding.
191 llvm::SmallVector<const Expr *, 8> BlockDeclRefDecls;
193 /// BlockDecls - Offsets for all Decls in BlockDeclRefExprs.
194 std::map<const Decl*, uint64_t> BlockDecls;
196 ImplicitParamDecl *BlockStructDecl;
197 ImplicitParamDecl *getBlockStructDecl() { return BlockStructDecl; }
199 llvm::Constant *GenerateCopyHelperFunction(bool, const llvm::StructType *,
200 std::vector<HelperInfo> *);
201 llvm::Constant *GenerateDestroyHelperFunction(bool, const llvm::StructType *,
202 std::vector<HelperInfo> *);
204 llvm::Constant *BuildCopyHelper(const llvm::StructType *,
205 std::vector<HelperInfo> *);
206 llvm::Constant *BuildDestroyHelper(const llvm::StructType *,
207 std::vector<HelperInfo> *);
209 llvm::Constant *GeneratebyrefCopyHelperFunction(const llvm::Type *, int flag);
210 llvm::Constant *GeneratebyrefDestroyHelperFunction(const llvm::Type *T, int);
212 llvm::Constant *BuildbyrefCopyHelper(const llvm::Type *T, int flag,
213 unsigned Align);
214 llvm::Constant *BuildbyrefDestroyHelper(const llvm::Type *T, int flag,
215 unsigned Align);
217 llvm::Value *getBlockObjectAssign();
218 llvm::Value *getBlockObjectDispose();
219 void BuildBlockRelease(llvm::Value *DeclPtr, int flag = BLOCK_FIELD_IS_BYREF);
221 bool BlockRequiresCopying(QualType Ty) {
222 if (Ty->isBlockPointerType())
223 return true;
224 if (getContext().isObjCNSObjectType(Ty))
225 return true;
226 if (Ty->isObjCObjectPointerType())
227 return true;
228 return false;
232 } // end namespace CodeGen
233 } // end namespace clang
235 #endif