 |
|
 |
|
| Files: |
1 |
|
Branches Taken: |
75.0% |
3 / 4 |
| Generated: |
2010-02-10 01:31 |
|
Branches Executed: |
100.0% |
4 / 4 |
| |
|
Line Coverage: |
91.3% |
21 / 23 |
| |
 |
|
 |
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.
11 : //
12 : //===----------------------------------------------------------------------===//
13 :
14 : #ifndef CLANG_CODEGEN_CGBLOCKS_H
15 : #define CLANG_CODEGEN_CGBLOCKS_H
16 :
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/CharUnits.h"
24 : #include "clang/AST/Expr.h"
25 : #include "clang/AST/ExprCXX.h"
26 : #include "clang/AST/ExprObjC.h"
27 :
28 : #include <vector>
29 : #include <map>
30 :
31 : #include "CGBuilder.h"
32 : #include "CGCall.h"
33 : #include "CGValue.h"
34 :
35 : namespace llvm {
36 : class Module;
37 : class Constant;
38 : class Function;
39 : class GlobalValue;
40 : class TargetData;
41 : class FunctionType;
42 : class Value;
43 : class LLVMContext;
44 : }
45 :
46 : namespace clang {
47 :
48 : namespace CodeGen {
49 : class CodeGenModule;
50 :
51 3701: class BlockBase {
52 : public:
53 : enum {
54 : BLOCK_NEEDS_FREE = (1 << 24),
55 : BLOCK_HAS_COPY_DISPOSE = (1 << 25),
56 : BLOCK_HAS_CXX_OBJ = (1 << 26),
57 : BLOCK_IS_GC = (1 << 27),
58 : BLOCK_IS_GLOBAL = (1 << 28),
59 : BLOCK_HAS_DESCRIPTOR = (1 << 29),
60 : BLOCK_HAS_OBJC_TYPE = (1 << 30)
61 : };
62 : };
63 :
64 599: class BlockModule : public BlockBase {
65 : ASTContext &Context;
66 : llvm::Module &TheModule;
67 : const llvm::TargetData &TheTargetData;
68 : CodeGenTypes &Types;
69 : CodeGenModule &CGM;
70 : llvm::LLVMContext &VMContext;
71 :
72 37: ASTContext &getContext() const { return Context; }
73 40: llvm::Module &getModule() const { return TheModule; }
74 37: CodeGenTypes &getTypes() { return Types; }
75 : const llvm::TargetData &getTargetData() const { return TheTargetData; }
76 : public:
77 : llvm::Constant *getNSConcreteGlobalBlock();
78 : llvm::Constant *getNSConcreteStackBlock();
79 12: int getGlobalUniqueCount() { return ++Block.GlobalUniqueCount; }
80 : const llvm::Type *getBlockDescriptorType();
81 :
82 : const llvm::Type *getGenericBlockLiteralType();
83 : const llvm::Type *getGenericExtendedBlockLiteralType();
84 :
85 : llvm::Constant *GetAddrOfGlobalBlock(const BlockExpr *BE, const char *);
86 :
87 : /// NSConcreteGlobalBlock - Cached reference to the class pointer for global
88 : /// blocks.
89 : llvm::Constant *NSConcreteGlobalBlock;
90 :
91 : /// NSConcreteStackBlock - Cached reference to the class poinnter for stack
92 : /// blocks.
93 : llvm::Constant *NSConcreteStackBlock;
94 :
95 : const llvm::Type *BlockDescriptorType;
96 : const llvm::Type *GenericBlockLiteralType;
97 : const llvm::Type *GenericExtendedBlockLiteralType;
98 : struct {
99 : int GlobalUniqueCount;
100 : } Block;
101 :
102 : llvm::Value *BlockObjectAssign;
103 : llvm::Value *BlockObjectDispose;
104 : const llvm::Type *PtrToInt8Ty;
105 :
106 : std::map<uint64_t, llvm::Constant *> AssignCache;
107 : std::map<uint64_t, llvm::Constant *> DestroyCache;
108 :
109 : BlockModule(ASTContext &C, llvm::Module &M, const llvm::TargetData &TD,
110 625: CodeGenTypes &T, CodeGenModule &CodeGen)
111 : : Context(C), TheModule(M), TheTargetData(TD), Types(T),
112 : CGM(CodeGen), VMContext(M.getContext()),
113 : NSConcreteGlobalBlock(0), NSConcreteStackBlock(0), BlockDescriptorType(0),
114 : GenericBlockLiteralType(0), GenericExtendedBlockLiteralType(0),
115 625: BlockObjectAssign(0), BlockObjectDispose(0) {
116 625: Block.GlobalUniqueCount = 0;
117 625: PtrToInt8Ty = llvm::Type::getInt8PtrTy(M.getContext());
118 625: }
119 :
120 0: bool BlockRequiresCopying(QualType Ty)
121 0: { return getContext().BlockRequiresCopying(Ty); }
122 : };
123 :
124 3076: class BlockFunction : public BlockBase {
125 : CodeGenModule &CGM;
126 : CodeGenFunction &CGF;
127 : ASTContext &getContext() const;
128 :
129 : protected:
130 : llvm::LLVMContext &VMContext;
131 :
132 : public:
133 : const llvm::Type *PtrToInt8Ty;
134 : struct HelperInfo {
135 : int index;
136 : int flag;
137 : bool RequiresCopying;
138 : };
139 :
140 : enum {
141 : BLOCK_FIELD_IS_OBJECT = 3, /* id, NSObject, __attribute__((NSObject)),
142 : block, ... */
143 : BLOCK_FIELD_IS_BLOCK = 7, /* a block variable */
144 : BLOCK_FIELD_IS_BYREF = 8, /* the on stack structure holding the __block
145 : variable */
146 : BLOCK_FIELD_IS_WEAK = 16, /* declared __weak, only used in byref copy
147 : helpers */
148 : BLOCK_BYREF_CALLER = 128, /* called from __block (byref) copy/dispose
149 : support routines */
150 : BLOCK_BYREF_CURRENT_MAX = 256
151 : };
152 :
153 : /// BlockInfo - Information to generate a block literal.
154 35: struct BlockInfo {
155 : /// BlockLiteralTy - The type of the block literal.
156 : const llvm::Type *BlockLiteralTy;
157 :
158 : /// Name - the name of the function this block was created for, if any.
159 : const char *Name;
160 :
161 : /// ByCopyDeclRefs - Variables from parent scopes that have been imported
162 : /// into this block.
163 : llvm::SmallVector<const BlockDeclRefExpr *, 8> DeclRefs;
164 :
165 35: BlockInfo(const llvm::Type *blt, const char *n)
166 35: : BlockLiteralTy(blt), Name(n) {
167 : // Skip asm prefix, if any.
35: branch 0 taken
0: branch 1 not taken
3: branch 2 taken
32: branch 3 taken
168 35: if (Name && Name[0] == '\01')
169 3: ++Name;
170 35: }
171 : };
172 :
173 : CGBuilderTy &Builder;
174 :
175 : BlockFunction(CodeGenModule &cgm, CodeGenFunction &cgf, CGBuilderTy &B);
176 :
177 : /// BlockOffset - The offset in bytes for the next allocation of an
178 : /// imported block variable.
179 : CharUnits BlockOffset;
180 : /// BlockAlign - Maximal alignment needed for the Block expressed in
181 : /// characters.
182 : CharUnits BlockAlign;
183 :
184 : /// getBlockOffset - Allocate an offset for the ValueDecl from a
185 : /// BlockDeclRefExpr in a block literal (BlockExpr).
186 : CharUnits getBlockOffset(const BlockDeclRefExpr *E);
187 :
188 : /// BlockHasCopyDispose - True iff the block uses copy/dispose.
189 : bool BlockHasCopyDispose;
190 :
191 : /// BlockDeclRefDecls - Decls from BlockDeclRefExprs in apperance order
192 : /// in a block literal. Decls without names are used for padding.
193 : llvm::SmallVector<const Expr *, 8> BlockDeclRefDecls;
194 :
195 : /// BlockDecls - Offsets for all Decls in BlockDeclRefExprs.
196 : std::map<const Decl*, CharUnits> BlockDecls;
197 :
198 : ImplicitParamDecl *BlockStructDecl;
199 36: ImplicitParamDecl *getBlockStructDecl() { return BlockStructDecl; }
200 :
201 : llvm::Constant *GenerateCopyHelperFunction(bool, const llvm::StructType *,
202 : std::vector<HelperInfo> *);
203 : llvm::Constant *GenerateDestroyHelperFunction(bool, const llvm::StructType *,
204 : std::vector<HelperInfo> *);
205 :
206 : llvm::Constant *BuildCopyHelper(const llvm::StructType *,
207 : std::vector<HelperInfo> *);
208 : llvm::Constant *BuildDestroyHelper(const llvm::StructType *,
209 : std::vector<HelperInfo> *);
210 :
211 : llvm::Constant *GeneratebyrefCopyHelperFunction(const llvm::Type *, int flag);
212 : llvm::Constant *GeneratebyrefDestroyHelperFunction(const llvm::Type *T, int);
213 :
214 : llvm::Constant *BuildbyrefCopyHelper(const llvm::Type *T, int flag,
215 : unsigned Align);
216 : llvm::Constant *BuildbyrefDestroyHelper(const llvm::Type *T, int flag,
217 : unsigned Align);
218 :
219 : llvm::Value *getBlockObjectAssign();
220 : llvm::Value *getBlockObjectDispose();
221 : void BuildBlockRelease(llvm::Value *DeclPtr, int flag = BLOCK_FIELD_IS_BYREF);
222 :
223 105: bool BlockRequiresCopying(QualType Ty)
224 105: { return getContext().BlockRequiresCopying(Ty); }
225 : };
226 :
227 : } // end namespace CodeGen
228 : } // end namespace clang
229 :
230 : #endif
Generated: 2010-02-10 01:31 by zcov