1 /* ----------------------------------------------------------------------------
2 * $Id: Closures.h,v 1.28 2001/10/03 13:57:42 simonmar Exp $
4 * (c) The GHC Team, 1998-1999
8 * -------------------------------------------------------------------------- */
14 * The Layout of a closure header depends on which kind of system we're
15 * compiling for: profiling, parallel, ticky, etc.
18 /* -----------------------------------------------------------------------------
20 -------------------------------------------------------------------------- */
26 /* -----------------------------------------------------------------------------
28 -------------------------------------------------------------------------- */
31 /* StgWord ga; */ /* nope! global addresses are managed via a hash table */
34 /* -----------------------------------------------------------------------------
36 -------------------------------------------------------------------------- */
39 StgWord procs; /* bitmask indicating on which PEs this closure resides */
42 /* -----------------------------------------------------------------------------
43 The ticky-ticky header
45 Comment from old Ticky.h:
47 This is used to record if a closure has been updated but not yet
48 entered. It is set when the closure is updated and cleared when
51 NB: It is {\em not} an ``entry count'', it is an
52 ``entries-after-update count.''
54 The commoning up of @CONST@, @CHARLIKE@ and @INTLIKE@ closures is
55 turned off(?) if this is required. This has only been done for 2s
56 collection. It is done using a nasty hack which defines the
57 @_Evacuate@ and @_Scavenge@ code for @CONST@, @CHARLIKE@ and @INTLIKE@
58 info tables to be @_Evacuate_1@ and @_Scavenge_1_0@.
59 -------------------------------------------------------------------------- */
62 /* old: W_ updated; */
65 /* -----------------------------------------------------------------------------
66 The full fixed-size closure header
68 The size of the fixed header is the sum of the optional parts plus a single
69 word for the entry code pointer.
70 -------------------------------------------------------------------------- */
73 const struct _StgInfoTable* info;
88 #define FIXED_HS (sizeof(StgHeader))
90 /* -----------------------------------------------------------------------------
93 For any given closure type (defined in InfoTables.h), there is a
94 corresponding structure defined below. The name of the structure
95 is obtained by concatenating the closure type with '_closure'
96 -------------------------------------------------------------------------- */
98 /* All closures follow the generic format */
102 struct StgClosure_ *payload[FLEXIBLE_ARRAY];
105 /* What a stroke of luck - all our mutable closures follow the same
106 * basic layout, with the mutable link field as the second field after
107 * the header. This means the following structure is the supertype of
111 typedef struct StgMutClosure_ {
114 struct StgMutClosure_ *mut_link;
115 struct StgClosure_ *payload[FLEXIBLE_ARRAY];
120 StgClosure *selectee;
127 StgClosure *payload[FLEXIBLE_ARRAY];
134 StgClosure *payload[FLEXIBLE_ARRAY];
139 StgClosure *indirectee;
144 StgClosure *indirectee;
145 StgMutClosure *mut_link;
150 StgClosure *indirectee;
151 StgClosure *static_link;
152 struct _StgInfoTable *saved_info;
158 StgWord payload[FLEXIBLE_ARRAY];
164 StgMutClosure *mut_link; /* mutable list */
165 StgClosure *payload[FLEXIBLE_ARRAY];
171 StgMutClosure *mut_link;
176 StgArrWords *instrs; /* a pointer to an ArrWords */
177 StgArrWords *literals; /* a pointer to an ArrWords */
178 StgMutArrPtrs *ptrs; /* a pointer to a MutArrPtrs */
179 StgArrWords *itbls; /* a pointer to an ArrWords */
183 A collective typedef for all linkable stack frames i.e.
184 StgUpdateFrame, StgSeqFrame, StgCatchFrame
186 typedef struct _StgFrame {
188 struct _StgFrame *link;
191 typedef struct _StgUpdateFrame {
193 struct _StgUpdateFrame *link;
199 struct _StgUpdateFrame *link;
204 struct _StgUpdateFrame *link;
205 StgInt exceptions_blocked;
221 } StgIntCharlikeClosure;
223 /* statically allocated */
228 typedef struct _StgForeignObj {
230 StgAddr data; /* pointer to data in non-haskell-land */
233 typedef struct _StgStableName {
238 typedef struct _StgWeak { /* Weak v */
241 StgClosure *value; /* v */
242 StgClosure *finalizer;
243 struct _StgWeak *link;
246 typedef struct _StgDeadWeak { /* Weak v */
248 struct _StgWeak *link;
251 /* Dynamic stack frames - these have a liveness mask in the object
252 * itself, rather than in the info table. Useful for generic heap
257 const struct _StgInfoTable* info;
260 StgWord payload[FLEXIBLE_ARRAY];
263 /* Concurrent communication objects */
267 struct StgTSO_ *head;
268 StgMutClosure *mut_link;
269 struct StgTSO_ *tail;
273 #if defined(PAR) || defined(GRAN)
275 StgBlockingQueueElement is a ``collective type'' representing the types
276 of closures that can be found on a blocking queue: StgTSO, StgRBHSave,
277 StgBlockedFetch. (StgRBHSave can only appear at the end of a blocking
278 queue). Logically, this is a union type, but defining another struct
279 with a common layout is easier to handle in the code (same as for
281 Note that in the standard setup only StgTSOs can be on a blocking queue.
282 This is one of the main reasons for slightly different code in files
285 typedef struct StgBlockingQueueElement_ {
287 struct StgBlockingQueueElement_ *link; /* next elem in BQ */
288 StgMutClosure *mut_link; /* next elem in mutable list */
289 struct StgClosure_ *payload[FLEXIBLE_ARRAY];/* contents of the closure */
290 } StgBlockingQueueElement;
292 /* only difference to std code is type of the elem in the BQ */
293 typedef struct StgBlockingQueue_ {
295 struct StgBlockingQueueElement_ *blocking_queue; /* start of the BQ */
296 StgMutClosure *mut_link; /* next elem in mutable list */
299 /* this closure is hanging at the end of a blocking queue in (see RBH.c) */
300 typedef struct StgRBHSave_ {
302 StgClosure *payload[FLEXIBLE_ARRAY]; /* 2 words ripped out of the guts of the */
303 } StgRBHSave; /* closure holding the blocking queue */
305 typedef struct StgRBH_ {
307 struct StgBlockingQueueElement_ *blocking_queue; /* start of the BQ */
308 StgMutClosure *mut_link; /* next elem in mutable list */
313 typedef struct StgBlockingQueue_ {
315 struct StgTSO_ *blocking_queue;
316 StgMutClosure *mut_link;
322 /* global indirections aka FETCH_ME closures */
323 typedef struct StgFetchMe_ {
325 globalAddr *ga; /* ptr to unique id for a closure */
326 StgMutClosure *mut_link; /* next elem in mutable list */
329 /* same contents as an ordinary StgBlockingQueue */
330 typedef struct StgFetchMeBlockingQueue_ {
332 struct StgBlockingQueueElement_ *blocking_queue; /* start of the BQ */
333 StgMutClosure *mut_link; /* next elem in mutable list */
334 } StgFetchMeBlockingQueue;
336 /* This is an entry in a blocking queue. It indicates a fetch request from a
337 TSO on another PE demanding the value of this closur. Note that a
338 StgBlockedFetch can only occur in a BQ. Once the node is evaluated and
339 updated with the result, the result will be sent back (the PE is encoded
340 in the globalAddr) and the StgBlockedFetch closure will be nuked.
342 typedef struct StgBlockedFetch_ {
344 struct StgBlockingQueueElement_ *link; /* next elem in the BQ */
345 StgMutClosure *mut_link; /* next elem in mutable list */
346 StgClosure *node; /* node to fetch */
347 globalAddr ga; /* where to send the result to */
348 } StgBlockedFetch; /* NB: not just a ptr to a GA */
351 #endif /* CLOSURES_H */