Support implicitly closing on 'this' in a block.  Fixed PR7165.

(the codegen works here, too, but that's annoying to test without execution)



git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@104202 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/CodeGen/CGBlocks.h b/lib/CodeGen/CGBlocks.h
index 5646d00..067dfc7 100644
--- a/lib/CodeGen/CGBlocks.h
+++ b/lib/CodeGen/CGBlocks.h
@@ -160,8 +160,12 @@
     /// into this block.
     llvm::SmallVector<const BlockDeclRefExpr *, 8> DeclRefs;
 
+    /// CXXThisRef - An expression referring to the required 'this'
+    /// expression.
+    const CXXThisExpr *CXXThisRef;
+
     BlockInfo(const llvm::Type *blt, const char *n)
-      : BlockLiteralTy(blt), Name(n) {
+      : BlockLiteralTy(blt), Name(n), CXXThisRef(0) {
       // Skip asm prefix, if any.
       if (Name && Name[0] == '\01')
         ++Name;
@@ -179,19 +183,31 @@
   /// characters.
   CharUnits BlockAlign;
 
-  /// getBlockOffset - Allocate an offset for the ValueDecl from a
-  /// BlockDeclRefExpr in a block literal (BlockExpr).
-  CharUnits getBlockOffset(const BlockDeclRefExpr *E);
+  /// getBlockOffset - Allocate a location within the block's storage
+  /// for a value with the given size and alignment requirements.
+  CharUnits getBlockOffset(CharUnits Size, CharUnits Align);
 
   /// BlockHasCopyDispose - True iff the block uses copy/dispose.
   bool BlockHasCopyDispose;
 
-  /// BlockDeclRefDecls - Decls from BlockDeclRefExprs in apperance order
-  /// in a block literal.  Decls without names are used for padding.
-  llvm::SmallVector<const Expr *, 8> BlockDeclRefDecls;
+  /// BlockLayout - The layout of the block's storage, represented as
+  /// a sequence of expressions which require such storage.  The
+  /// expressions can be:
+  /// - a BlockDeclRefExpr, indicating that the given declaration
+  ///   from an enclosing scope is needed by the block;
+  /// - a DeclRefExpr, which always wraps an anonymous VarDecl with
+  ///   array type, used to insert padding into the block; or
+  /// - a CXXThisExpr, indicating that the C++ 'this' value should
+  ///   propagate from the parent to the block.
+  /// This is a really silly representation.
+  llvm::SmallVector<const Expr *, 8> BlockLayout;
 
   /// BlockDecls - Offsets for all Decls in BlockDeclRefExprs.
-  std::map<const Decl*, CharUnits> BlockDecls;
+  llvm::DenseMap<const Decl*, CharUnits> BlockDecls;
+
+  /// BlockCXXThisOffset - The offset of the C++ 'this' value within
+  /// the block structure.
+  CharUnits BlockCXXThisOffset;
 
   ImplicitParamDecl *BlockStructDecl;
   ImplicitParamDecl *getBlockStructDecl() { return BlockStructDecl; }