[cfe-commits] r98676 - /cfe/trunk/docs/BlockImplementation.txt

Blaine Garst blaine at apple.com
Tue Mar 16 14:21:07 PDT 2010

Author: blaine
Date: Tue Mar 16 16:21:07 2010
New Revision: 98676

URL: http://llvm.org/viewvc/llvm-project?rev=98676&view=rev
rev existing doc to account for recent ABI changes


Modified: cfe/trunk/docs/BlockImplementation.txt
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/docs/BlockImplementation.txt?rev=98676&r1=98675&r2=98676&view=diff
--- cfe/trunk/docs/BlockImplementation.txt (original)
+++ cfe/trunk/docs/BlockImplementation.txt Tue Mar 16 16:21:07 2010
@@ -30,10 +30,17 @@
 2008/10/30 - revise new layout to have invoke function in same place
 2008/10/30 - add __weak support
+2010/3/16  - rev for stret return, signature field
 This document describes the Apple ABI implementation specification of Blocks.
+The first shipping version of this ABI is found in Mac OS X 10.6, and shall be referred to as 10.6.ABI. Proposals have been made to enhance the blocks compiler and runtime, and these changes would form a new ABI called post-10.6.ABI if these changes were ever shipped in a product, which is purely speculative.
+Since the Apple ABI references symbols from other elements of the system, any attempt to use this ABI on systems prior to SnowLeopard is undefined.
 1. High Level
+The ABI of blocks consist of their layout and the runtime functions required by the compiler.
 A Block consists of a structure of the following form:
 struct Block_literal_1 {
@@ -43,23 +50,37 @@
     void (*invoke)(void *, ...);
     struct Block_descriptor_1 {
 	unsigned long int reserved;	// NULL
-    	unsigned long int size;  // sizeof(struct Block_literal_1)
+    	unsigned long int size;         // sizeof(struct Block_literal_1)
 	// optional helper functions
-    	void (*copy_helper)(void *dst, void *src);
-    	void (*dispose_helper)(void *src); 
+    	void (*copy_helper)(void *dst, void *src);     // IFF (1<<25)
+    	void (*dispose_helper)(void *src);             // IFF (1<<25)
+        // required post 10.6.ABI
+        const char *signature;                         // IFF (1<<30)
     } *descriptor;
     // imported variables
-The following flags bits are used by the compiler:
+The following flags bits are in use thusly for a possible post.10.6.ABI:
 enum {
     BLOCK_HAS_COPY_DISPOSE =  (1 << 25),
     BLOCK_HAS_CTOR =          (1 << 26), // helpers have C++ code
     BLOCK_IS_GLOBAL =         (1 << 28),
-    BLOCK_HAS_DESCRIPTOR =    (1 << 29), // interim until complete world build is accomplished
+    BLOCK_HAS_STRET =         (1 << 29),
+    BLOCK_HAS_SIGNATURE =     (1 << 30), 
+In 10.6.ABI the (1<<29) was unconditionally set and ignored by the runtime - it was a transitional marker that did not get deleted after the transition. This bit is now paired with (1<<30), and represented as the pair (3<<30), for the following combinations of valid bit settings, and their meanings.
+switch (flags & (3<<29)) {
+  case (0<<29):  <unused>    , error
+  case (1<<29):      10.6.ABI, no signature field available
+  case (2<<29): post-10.6.ABI, regular calling convention, presence of signature field
+  case (3<<29): post-10.6.ABI, street calling convention, presence of signature field,
+The following discussions are presented as 10.6.ABI otherwise.
 Block literals may occur within functions where the structure is created in stack local memory.  They may also appear as initialization expressions for Block variables of global or static local variables.
 When a Block literal expression is evaluated the stack based structure is initialized as follows:
@@ -72,6 +93,7 @@
 2a) the isa field is set to the address of the external _NSConcreteStackBlock, which is a block of uninitialized memory supplied in libSystem, or _NSConcreteGlobalBlock if this is a static or file level block literal.
 2) The flags field is set to zero unless there are variables imported into the block that need helper functions for program level Block_copy() and Block_release() operations, in which case the (1<<25) flags bit is set.
 As an example, the Block literal expression
    ^ { printf("hello world\n"); }
 would cause to be created on a 32-bit system:

More information about the cfe-commits mailing list