[project @ 2001-02-11 17:51:07 by simonmar]
[ghc-hetmet.git] / ghc / rts / StgMiscClosures.hc
1 /* -----------------------------------------------------------------------------
2  * $Id: StgMiscClosures.hc,v 1.64 2001/02/11 17:51:08 simonmar Exp $
3  *
4  * (c) The GHC Team, 1998-2000
5  *
6  * Entry code for various built-in closure types.
7  *
8  * ---------------------------------------------------------------------------*/
9
10 #include "Rts.h"
11 #include "RtsUtils.h"
12 #include "RtsFlags.h"
13 #include "StgMiscClosures.h"
14 #include "HeapStackCheck.h"   /* for stg_gen_yield */
15 #include "Storage.h"
16 #include "StoragePriv.h"
17 #include "Profiling.h"
18 #include "Prelude.h"
19 #include "Schedule.h"
20 #include "SMP.h"
21 #if defined(GRAN) || defined(PAR)
22 # include "GranSimRts.h"      /* for DumpRawGranEvent */
23 # include "StgRun.h"    /* for StgReturn and register saving */
24 #endif
25
26 #ifdef HAVE_STDIO_H
27 #include <stdio.h>
28 #endif
29
30 /* ToDo: make the printing of panics more win32-friendly, i.e.,
31  *       pop up some lovely message boxes (as well).
32  */
33 #define DUMP_ERRMSG(msg) STGCALL2(fprintf,stderr,msg)
34
35 /*
36   Template for the entry code of non-enterable closures.
37 */
38
39 #define NON_ENTERABLE_ENTRY_CODE(type)                                  \
40 STGFUN(stg_##type##_entry)                                                      \
41 {                                                                       \
42   FB_                                                                   \
43     DUMP_ERRMSG(#type " object entered!\n");                            \
44     STGCALL1(shutdownHaskellAndExit, EXIT_FAILURE);                     \
45     return NULL;                                                        \
46   FE_                                                                   \
47 }
48
49
50 /* -----------------------------------------------------------------------------
51    Support for the bytecode interpreter.
52    -------------------------------------------------------------------------- */
53
54 /* 9 bits of return code for constructors created by the interpreter. */
55 FN_(stg_interp_constr_entry) 
56
57   /* R1 points at the constructor */
58   FB_ 
59     /* STGCALL2(fprintf,stderr,"stg_interp_constr_entry (direct return)!\n"); */
60     /* Pointless, since SET_TAG doesn't do anything */
61     SET_TAG( GET_TAG(GET_INFO(R1.cl))); 
62     JMP_(ENTRY_CODE((P_)(*Sp))); 
63   FE_ 
64 }
65
66 FN_(stg_interp_constr1_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),0)); FE_ }
67 FN_(stg_interp_constr2_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),1)); FE_ }
68 FN_(stg_interp_constr3_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),2)); FE_ }
69 FN_(stg_interp_constr4_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),3)); FE_ }
70 FN_(stg_interp_constr5_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),4)); FE_ }
71 FN_(stg_interp_constr6_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),5)); FE_ }
72 FN_(stg_interp_constr7_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),6)); FE_ }
73 FN_(stg_interp_constr8_entry) { FB_ JMP_(RET_VEC((P_)(*Sp),7)); FE_ }
74  
75 /* Some info tables to be used when compiled code returns a value to
76    the interpreter, i.e. the interpreter pushes one of these onto the
77    stack before entering a value.  What the code does is to
78    impedance-match the compiled return convention (in R1p/R1n/F1/D1 etc) to
79    the interpreter's convention (returned value is on top of stack),
80    and then cause the scheduler to enter the interpreter.
81
82    On entry, the stack (growing down) looks like this:
83
84       ptr to BCO holding return continuation
85       ptr to one of these info tables.
86  
87    The info table code, both direct and vectored, must:
88       * push R1/F1/D1 on the stack, and its tag if necessary
89       * push the BCO (so it's now on the stack twice)
90       * Yield, ie, go to the scheduler.
91
92    Scheduler examines the t.o.s, discovers it is a BCO, and proceeds
93    directly to the bytecode interpreter.  That pops the top element
94    (the BCO, containing the return continuation), and interprets it.
95    Net result: return continuation gets interpreted, with the
96    following stack:
97
98       ptr to this BCO
99       ptr to the info table just jumped thru
100       return value
101
102    which is just what we want -- the "standard" return layout for the
103    interpreter.  Hurrah!
104
105    Don't ask me how unboxed tuple returns are supposed to work.  We
106    haven't got a good story about that yet.
107 */
108
109 /* When the returned value is in R1 and it is a pointer, so doesn't
110    need tagging ... */
111 #define STG_CtoI_RET_R1p_Template(label)        \
112    IFN_(label)                          \
113    {                                    \
114       StgPtr bco;                       \
115       FB_                               \
116       bco = ((StgPtr*)Sp)[1];           \
117       Sp -= 1;                          \
118       ((StgPtr*)Sp)[0] = R1.p;          \
119       Sp -= 1;                          \
120       ((StgPtr*)Sp)[0] = bco;           \
121       JMP_(stg_yield_to_interpreter);   \
122       FE_                               \
123    }
124
125 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_entry);
126 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_0_entry);
127 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_1_entry);
128 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_2_entry);
129 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_3_entry);
130 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_4_entry);
131 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_5_entry);
132 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_6_entry);
133 STG_CtoI_RET_R1p_Template(stg_ctoi_ret_R1p_7_entry);
134
135 VEC_POLY_INFO_TABLE(stg_ctoi_ret_R1p,0, NULL/*srt*/, 0/*srt_off*/, 0/*srt_len*/, RET_BCO,, EF_);
136
137
138
139 /* When the returned value is in R1 and it isn't a pointer. */
140 #define STG_CtoI_RET_R1n_Template(label)        \
141    IFN_(label)                          \
142    {                                    \
143       StgPtr bco;                       \
144       FB_                               \
145       bco = ((StgPtr*)Sp)[1];           \
146       Sp -= 1;                          \
147       ((StgPtr*)Sp)[0] = (StgPtr)R1.i;  \
148       Sp -= 1;                          \
149       ((StgPtr*)Sp)[0] = (StgPtr)1; /* tag */   \
150       Sp -= 1;                          \
151       ((StgPtr*)Sp)[0] = bco;           \
152       JMP_(stg_yield_to_interpreter);   \
153       FE_                               \
154    }
155
156 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_entry);
157 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_0_entry);
158 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_1_entry);
159 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_2_entry);
160 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_3_entry);
161 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_4_entry);
162 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_5_entry);
163 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_6_entry);
164 STG_CtoI_RET_R1n_Template(stg_ctoi_ret_R1n_7_entry);
165
166 VEC_POLY_INFO_TABLE(stg_ctoi_ret_R1n,0, NULL/*srt*/, 0/*srt_off*/, 0/*srt_len*/, RET_BCO,, EF_);
167
168
169
170 /* When the returned value is in F1 ... */
171 #define STG_CtoI_RET_F1_Template(label)         \
172    IFN_(label)                          \
173    {                                    \
174       StgPtr bco;                       \
175       FB_                               \
176       bco = ((StgPtr*)Sp)[1];           \
177       Sp -= sizeofW(StgFloat);          \
178       ASSIGN_FLT((W_*)Sp, F1);          \
179       Sp -= 1;                          \
180       ((StgPtr*)Sp)[0] = (StgPtr)sizeofW(StgFloat); \
181       Sp -= 1;                          \
182       ((StgPtr*)Sp)[0] = bco;           \
183       JMP_(stg_yield_to_interpreter);   \
184       FE_                               \
185    }
186
187 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_entry);
188 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_0_entry);
189 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_1_entry);
190 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_2_entry);
191 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_3_entry);
192 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_4_entry);
193 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_5_entry);
194 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_6_entry);
195 STG_CtoI_RET_F1_Template(stg_ctoi_ret_F1_7_entry);
196
197 VEC_POLY_INFO_TABLE(stg_ctoi_ret_F1,0, NULL/*srt*/, 0/*srt_off*/, 0/*srt_len*/, RET_BCO,, EF_);
198
199
200 /* When the returned value is in D1 ... */
201 #define STG_CtoI_RET_D1_Template(label)         \
202    IFN_(label)                          \
203    {                                    \
204       StgPtr bco;                       \
205       FB_                               \
206       bco = ((StgPtr*)Sp)[1];           \
207       Sp -= sizeofW(StgDouble);         \
208       ASSIGN_DBL((W_*)Sp, D1);          \
209       Sp -= 1;                          \
210       ((StgPtr*)Sp)[0] = (StgPtr)sizeofW(StgDouble); \
211       Sp -= 1;                          \
212       ((StgPtr*)Sp)[0] = bco;           \
213       JMP_(stg_yield_to_interpreter);   \
214       FE_                               \
215    }
216
217 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_entry);
218 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_0_entry);
219 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_1_entry);
220 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_2_entry);
221 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_3_entry);
222 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_4_entry);
223 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_5_entry);
224 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_6_entry);
225 STG_CtoI_RET_D1_Template(stg_ctoi_ret_D1_7_entry);
226
227 VEC_POLY_INFO_TABLE(stg_ctoi_ret_D1,0, NULL/*srt*/, 0/*srt_off*/, 0/*srt_len*/, RET_BCO,, EF_);
228
229 /* The other way round: when the interpreter returns a value to
230    compiled code.  The stack looks like this:
231
232       return info table (pushed by compiled code)
233       return value (pushed by interpreter)
234
235    If the value is ptr-rep'd, the interpreter simply returns to the
236    scheduler, instructing it to ThreadEnterGHC.
237
238    Otherwise (unboxed return value), we replace the top stack word,
239    which must be the tag, with stg_gc_unbx_r1_info (or f1_info or d1_info),
240    and return to the scheduler, instructing it to ThreadRunGHC.
241
242    No supporting code needed!
243 */
244
245
246 /* Entering a BCO.  Heave it on the stack and defer to the
247    scheduler. */
248 INFO_TABLE(stg_BCO_info,stg_BCO_entry,4,0,BCO,,EF_,"BCO","BCO");
249 STGFUN(stg_BCO_entry) {
250   FB_
251     Sp -= 1;
252     Sp[0] = R1.w;
253     JMP_(stg_yield_to_interpreter);
254   FE_
255 }
256
257
258 /* -----------------------------------------------------------------------------
259    Entry code for an indirection.
260    -------------------------------------------------------------------------- */
261
262 INFO_TABLE(stg_IND_info,stg_IND_entry,1,0,IND,,EF_,0,0);
263 STGFUN(stg_IND_entry)
264 {
265     FB_
266     TICK_ENT_IND(Node); /* tick */
267
268     R1.p = (P_) ((StgInd*)R1.p)->indirectee;
269     TICK_ENT_VIA_NODE();
270     JMP_(ENTRY_CODE(*R1.p));
271     FE_
272 }
273
274 INFO_TABLE(stg_IND_STATIC_info,stg_IND_STATIC_entry,1,0,IND_STATIC,,EF_,0,0);
275 STGFUN(stg_IND_STATIC_entry)
276 {
277     FB_
278     TICK_ENT_IND(Node); /* tick */
279     R1.p = (P_) ((StgIndStatic*)R1.p)->indirectee;
280     TICK_ENT_VIA_NODE();
281     JMP_(ENTRY_CODE(*R1.p));
282     FE_
283 }
284
285 INFO_TABLE(stg_IND_PERM_info,stg_IND_PERM_entry,1,1,IND_PERM,,EF_,"IND_PERM","IND_PERM");
286 STGFUN(stg_IND_PERM_entry)
287 {
288     FB_
289     /* Don't add INDs to granularity cost */
290     /* Dont: TICK_ENT_IND(Node); for ticky-ticky; this ind is here only to help profiling */
291
292 #if defined(TICKY_TICKY) && !defined(PROFILING)
293     /* TICKY_TICKY && !PROFILING means PERM_IND *replaces* an IND, rather than being extra  */
294     TICK_ENT_PERM_IND(R1.p); /* tick */
295 #endif
296
297     /* Enter PAP cost centre -- lexical scoping only */
298     ENTER_CCS_PAP_CL(R1.cl);
299
300     /* For ticky-ticky, change the perm_ind to a normal ind on first
301      * entry, so the number of ent_perm_inds is the number of *thunks*
302      * entered again, not the number of subsequent entries.
303      *
304      * Since this screws up cost centres, we die if profiling and
305      * ticky_ticky are on at the same time.  KSW 1999-01.
306      */
307
308 #ifdef TICKY_TICKY
309 #  ifdef PROFILING
310 #    error Profiling and ticky-ticky do not mix at present!
311 #  endif  /* PROFILING */
312     SET_INFO((StgInd*)R1.p,&stg_IND_info);
313 #endif /* TICKY_TICKY */
314
315     R1.p = (P_) ((StgInd*)R1.p)->indirectee;
316
317     /* Dont: TICK_ENT_VIA_NODE(); for ticky-ticky; as above */
318
319 #if defined(TICKY_TICKY) && !defined(PROFILING)
320     TICK_ENT_VIA_NODE();
321 #endif
322
323     JMP_(ENTRY_CODE(*R1.p));
324     FE_
325 }  
326
327 INFO_TABLE(stg_IND_OLDGEN_info,stg_IND_OLDGEN_entry,1,1,IND_OLDGEN,,EF_,0,0);
328 STGFUN(stg_IND_OLDGEN_entry)
329 {
330     FB_
331     TICK_ENT_IND(Node); /* tick */
332   
333     R1.p = (P_) ((StgInd*)R1.p)->indirectee;
334     TICK_ENT_VIA_NODE();
335     JMP_(ENTRY_CODE(*R1.p));
336     FE_
337 }
338
339 INFO_TABLE(stg_IND_OLDGEN_PERM_info,stg_IND_OLDGEN_PERM_entry,1,1,IND_OLDGEN_PERM,,EF_,0,0);
340 STGFUN(stg_IND_OLDGEN_PERM_entry)
341 {
342     FB_
343     /* Dont: TICK_ENT_IND(Node); for ticky-ticky; this ind is here only to help profiling */
344
345 #if defined(TICKY_TICKY) && !defined(PROFILING)
346     /* TICKY_TICKY && !PROFILING means PERM_IND *replaces* an IND, rather than being extra  */
347     TICK_ENT_PERM_IND(R1.p); /* tick */
348 #endif
349   
350     /* Enter PAP cost centre -- lexical scoping only */
351     ENTER_CCS_PAP_CL(R1.cl);
352
353     /* see comment in IND_PERM */
354 #ifdef TICKY_TICKY
355 #  ifdef PROFILING
356 #    error Profiling and ticky-ticky do not mix at present!
357 #  endif  /* PROFILING */
358     SET_INFO((StgInd*)R1.p,&stg_IND_OLDGEN_info);
359 #endif /* TICKY_TICKY */
360
361     R1.p = (P_) ((StgInd*)R1.p)->indirectee;
362     TICK_ENT_VIA_NODE();
363     JMP_(ENTRY_CODE(*R1.p));
364     FE_
365 }
366
367 /* -----------------------------------------------------------------------------
368    Entry code for a black hole.
369
370    Entering a black hole normally causes a cyclic data dependency, but
371    in the concurrent world, black holes are synchronization points,
372    and they are turned into blocking queues when there are threads
373    waiting for the evaluation of the closure to finish.
374    -------------------------------------------------------------------------- */
375
376 /* Note: a BLACKHOLE and BLACKHOLE_BQ must be big enough to be
377  * overwritten with an indirection/evacuee/catch.  Thus we claim it
378  * has 1 non-pointer word of payload (in addition to the pointer word
379  * for the blocking queue in a BQ), which should be big enough for an
380  * old-generation indirection. 
381  */
382
383 INFO_TABLE(stg_BLACKHOLE_info, stg_BLACKHOLE_entry,0,2,BLACKHOLE,,EF_,"BLACKHOLE","BLACKHOLE");
384 STGFUN(stg_BLACKHOLE_entry)
385 {
386   FB_
387 #if defined(GRAN)
388     /* Before overwriting TSO_LINK */
389     STGCALL3(GranSimBlock,CurrentTSO,CurrentProc,(StgClosure *)R1.p /*Node*/);
390 #endif
391
392 #ifdef SMP
393     {
394       bdescr *bd = Bdescr(R1.p);
395       if (bd->back != (bdescr *)BaseReg) {
396         if (bd->gen->no >= 1 || bd->step->no >= 1) {
397           CMPXCHG(R1.cl->header.info, &stg_BLACKHOLE_info, &stg_WHITEHOLE_info);
398         } else {
399           EXTFUN_RTS(stg_gc_enter_1_hponly);
400           JMP_(stg_gc_enter_1_hponly);
401         }
402       }
403     }
404 #endif
405     TICK_ENT_BH();
406
407     /* Put ourselves on the blocking queue for this black hole */
408 #if defined(GRAN) || defined(PAR)
409     /* in fact, only difference is the type of the end-of-queue marker! */
410     CurrentTSO->link = END_BQ_QUEUE;
411     ((StgBlockingQueue *)R1.p)->blocking_queue = (StgBlockingQueueElement *)CurrentTSO;
412 #else
413     CurrentTSO->link = END_TSO_QUEUE;
414     ((StgBlockingQueue *)R1.p)->blocking_queue = CurrentTSO;
415 #endif
416     /* jot down why and on what closure we are blocked */
417     CurrentTSO->why_blocked = BlockedOnBlackHole;
418     CurrentTSO->block_info.closure = R1.cl;
419     /* closure is mutable since something has just been added to its BQ */
420     recordMutable((StgMutClosure *)R1.cl);
421     /* Change the BLACKHOLE into a BLACKHOLE_BQ */
422     ((StgBlockingQueue *)R1.p)->header.info = &stg_BLACKHOLE_BQ_info;
423
424     /* PAR: dumping of event now done in blockThread -- HWL */
425
426     /* stg_gen_block is too heavyweight, use a specialised one */
427     BLOCK_NP(1);
428
429   FE_
430 }
431
432 INFO_TABLE(stg_BLACKHOLE_BQ_info, stg_BLACKHOLE_BQ_entry,1,1,BLACKHOLE_BQ,,EF_,"BLACKHOLE","BLACKHOLE");
433 STGFUN(stg_BLACKHOLE_BQ_entry)
434 {
435   FB_
436 #if defined(GRAN)
437     /* Before overwriting TSO_LINK */
438     STGCALL3(GranSimBlock,CurrentTSO,CurrentProc,(StgClosure *)R1.p /*Node*/);
439 #endif
440
441 #ifdef SMP
442     {
443       bdescr *bd = Bdescr(R1.p);
444       if (bd->back != (bdescr *)BaseReg) {
445         if (bd->gen->no >= 1 || bd->step->no >= 1) {
446           CMPXCHG(R1.cl->header.info, &stg_BLACKHOLE_info, &stg_WHITEHOLE_info);
447         } else {
448           EXTFUN_RTS(stg_gc_enter_1_hponly);
449           JMP_(stg_gc_enter_1_hponly);
450         }
451       }
452     }
453 #endif
454
455     TICK_ENT_BH();
456
457     /* Put ourselves on the blocking queue for this black hole */
458     CurrentTSO->link = ((StgBlockingQueue *)R1.p)->blocking_queue;
459     ((StgBlockingQueue *)R1.p)->blocking_queue = CurrentTSO;
460     /* jot down why and on what closure we are blocked */
461     CurrentTSO->why_blocked = BlockedOnBlackHole;
462     CurrentTSO->block_info.closure = R1.cl;
463 #ifdef SMP
464     ((StgBlockingQueue *)R1.p)->header.info = &stg_BLACKHOLE_BQ_info;
465 #endif
466
467     /* PAR: dumping of event now done in blockThread -- HWL */
468
469     /* stg_gen_block is too heavyweight, use a specialised one */
470     BLOCK_NP(1);
471   FE_
472 }
473
474 /*
475    Revertible black holes are needed in the parallel world, to handle
476    negative acknowledgements of messages containing updatable closures.
477    The idea is that when the original message is transmitted, the closure
478    is turned into a revertible black hole...an object which acts like a
479    black hole when local threads try to enter it, but which can be reverted
480    back to the original closure if necessary.
481
482    It's actually a lot like a blocking queue (BQ) entry, because revertible
483    black holes are initially set up with an empty blocking queue.
484 */
485
486 #if defined(PAR) || defined(GRAN)
487
488 INFO_TABLE(stg_RBH_info, stg_RBH_entry,1,1,RBH,,EF_,0,0);
489 STGFUN(stg_RBH_entry)
490 {
491   FB_
492 # if defined(GRAN)
493     /* mainly statistics gathering for GranSim simulation */
494     STGCALL3(GranSimBlock,CurrentTSO,CurrentProc,(StgClosure *)R1.p /*Node*/);
495 # endif
496
497     /* exactly the same as a BLACKHOLE_BQ_entry -- HWL */
498     /* Put ourselves on the blocking queue for this black hole */
499     CurrentTSO->link = ((StgBlockingQueue *)R1.p)->blocking_queue;
500     ((StgBlockingQueue *)R1.p)->blocking_queue = CurrentTSO;
501     /* jot down why and on what closure we are blocked */
502     CurrentTSO->why_blocked = BlockedOnBlackHole;
503     CurrentTSO->block_info.closure = R1.cl;
504
505     /* PAR: dumping of event now done in blockThread -- HWL */
506
507     /* stg_gen_block is too heavyweight, use a specialised one */
508     BLOCK_NP(1); 
509   FE_
510 }
511
512 INFO_TABLE(stg_RBH_Save_0_info, stg_RBH_Save_0_entry,0,2,CONSTR,,EF_,0,0);
513 NON_ENTERABLE_ENTRY_CODE(RBH_Save_0);
514
515 INFO_TABLE(stg_RBH_Save_1_info, stg_RBH_Save_1_entry,1,1,CONSTR,,EF_,0,0);
516 NON_ENTERABLE_ENTRY_CODE(RBH_Save_1);
517
518 INFO_TABLE(stg_RBH_Save_2_info, stg_RBH_Save_2_entry,2,0,CONSTR,,EF_,0,0);
519 NON_ENTERABLE_ENTRY_CODE(RBH_Save_2);
520 #endif /* defined(PAR) || defined(GRAN) */
521
522 /* identical to BLACKHOLEs except for the infotag */
523 INFO_TABLE(stg_CAF_BLACKHOLE_info, stg_CAF_BLACKHOLE_entry,0,2,CAF_BLACKHOLE,,EF_,"CAF_BLACKHOLE","CAF_BLACKHOLE");
524 STGFUN(stg_CAF_BLACKHOLE_entry)
525 {
526   FB_
527 #if defined(GRAN)
528     /* mainly statistics gathering for GranSim simulation */
529     STGCALL3(GranSimBlock,CurrentTSO,CurrentProc,(StgClosure *)R1.p /*Node*/);
530 #endif
531
532 #ifdef SMP
533     {
534       bdescr *bd = Bdescr(R1.p);
535       if (bd->back != (bdescr *)BaseReg) {
536         if (bd->gen->no >= 1 || bd->step->no >= 1) {
537           CMPXCHG(R1.cl->header.info, &stg_CAF_BLACKHOLE_info, &stg_WHITEHOLE_info);
538         } else {
539           EXTFUN_RTS(stg_gc_enter_1_hponly);
540           JMP_(stg_gc_enter_1_hponly);
541         }
542       }
543     }
544 #endif
545
546     TICK_ENT_BH();
547
548     /* Put ourselves on the blocking queue for this black hole */
549 #if defined(GRAN) || defined(PAR)
550     /* in fact, only difference is the type of the end-of-queue marker! */
551     CurrentTSO->link = END_BQ_QUEUE;
552     ((StgBlockingQueue *)R1.p)->blocking_queue = (StgBlockingQueueElement *)CurrentTSO;
553 #else
554     CurrentTSO->link = END_TSO_QUEUE;
555     ((StgBlockingQueue *)R1.p)->blocking_queue = CurrentTSO;
556 #endif
557     /* jot down why and on what closure we are blocked */
558     CurrentTSO->why_blocked = BlockedOnBlackHole;
559     CurrentTSO->block_info.closure = R1.cl;
560     /* closure is mutable since something has just been added to its BQ */
561     recordMutable((StgMutClosure *)R1.cl);
562     /* Change the CAF_BLACKHOLE into a BLACKHOLE_BQ_STATIC */
563     ((StgBlockingQueue *)R1.p)->header.info = &stg_BLACKHOLE_BQ_info;
564
565     /* PAR: dumping of event now done in blockThread -- HWL */
566
567     /* stg_gen_block is too heavyweight, use a specialised one */
568     BLOCK_NP(1);
569   FE_
570 }
571
572 #ifdef TICKY_TICKY
573 INFO_TABLE(stg_SE_BLACKHOLE_info, stg_SE_BLACKHOLE_entry,0,2,SE_BLACKHOLE,,EF_,0,0);
574 STGFUN(stg_SE_BLACKHOLE_entry)
575 {
576   FB_
577     STGCALL3(fprintf,stderr,"SE_BLACKHOLE at %p entered!\n",R1.p);
578     STGCALL1(shutdownHaskellAndExit,EXIT_FAILURE);
579   FE_
580 }
581
582 INFO_TABLE(SE_CAF_BLACKHOLE_info, SE_CAF_BLACKHOLE_entry,0,2,SE_CAF_BLACKHOLE,,EF_,0,0);
583 STGFUN(stg_SE_CAF_BLACKHOLE_entry)
584 {
585   FB_
586     STGCALL3(fprintf,stderr,"SE_CAF_BLACKHOLE at %p entered!\n",R1.p);
587     STGCALL1(shutdownHaskellAndExit,EXIT_FAILURE);
588   FE_
589 }
590 #endif
591
592 #ifdef SMP
593 INFO_TABLE(stg_WHITEHOLE_info, stg_WHITEHOLE_entry,0,2,CONSTR_NOCAF_STATIC,,EF_,0,0);
594 STGFUN(stg_WHITEHOLE_entry)
595 {
596   FB_
597      JMP_(GET_ENTRY(R1.cl));
598   FE_
599 }
600 #endif
601
602 /* -----------------------------------------------------------------------------
603    Some static info tables for things that don't get entered, and
604    therefore don't need entry code (i.e. boxed but unpointed objects)
605    NON_ENTERABLE_ENTRY_CODE now defined at the beginning of the file
606    -------------------------------------------------------------------------- */
607
608 INFO_TABLE(stg_TSO_info, stg_TSO_entry, 0,0,TSO,,EF_,"TSO","TSO");
609 NON_ENTERABLE_ENTRY_CODE(TSO);
610
611 /* -----------------------------------------------------------------------------
612    Evacuees are left behind by the garbage collector.  Any attempt to enter
613    one is a real bug.
614    -------------------------------------------------------------------------- */
615
616 INFO_TABLE(stg_EVACUATED_info,stg_EVACUATED_entry,1,0,EVACUATED,,EF_,0,0);
617 NON_ENTERABLE_ENTRY_CODE(EVACUATED);
618
619 /* -----------------------------------------------------------------------------
620    Weak pointers
621
622    Live weak pointers have a special closure type.  Dead ones are just
623    nullary constructors (although they live on the heap - we overwrite
624    live weak pointers with dead ones).
625    -------------------------------------------------------------------------- */
626
627 INFO_TABLE(stg_WEAK_info,stg_WEAK_entry,0,4,WEAK,,EF_,"WEAK","WEAK");
628 NON_ENTERABLE_ENTRY_CODE(WEAK);
629
630 INFO_TABLE_CONSTR(stg_DEAD_WEAK_info,stg_DEAD_WEAK_entry,0,1,0,CONSTR,,EF_,"DEAD_WEAK","DEAD_WEAK");
631 NON_ENTERABLE_ENTRY_CODE(DEAD_WEAK);
632
633 /* -----------------------------------------------------------------------------
634    NO_FINALIZER
635
636    This is a static nullary constructor (like []) that we use to mark an empty
637    finalizer in a weak pointer object.
638    -------------------------------------------------------------------------- */
639
640 INFO_TABLE_CONSTR(stg_NO_FINALIZER_info,stg_NO_FINALIZER_entry,0,0,0,CONSTR_NOCAF_STATIC,,EF_,0,0);
641 NON_ENTERABLE_ENTRY_CODE(NO_FINALIZER);
642
643 SET_STATIC_HDR(stg_NO_FINALIZER_closure,stg_NO_FINALIZER_info,0/*CC*/,,EI_)
644 , /*payload*/{} };
645
646 /* -----------------------------------------------------------------------------
647    Foreign Objects are unlifted and therefore never entered.
648    -------------------------------------------------------------------------- */
649
650 INFO_TABLE(stg_FOREIGN_info,stg_FOREIGN_entry,0,1,FOREIGN,,EF_,"FOREIGN","FOREIGN");
651 NON_ENTERABLE_ENTRY_CODE(FOREIGN);
652
653 /* -----------------------------------------------------------------------------
654    Stable Names are unlifted too.
655    -------------------------------------------------------------------------- */
656
657 INFO_TABLE(stg_STABLE_NAME_info,stg_STABLE_NAME_entry,0,1,STABLE_NAME,,EF_,"STABLE_NAME","STABLE_NAME");
658 NON_ENTERABLE_ENTRY_CODE(STABLE_NAME);
659
660 /* -----------------------------------------------------------------------------
661    MVars
662
663    There are two kinds of these: full and empty.  We need an info table
664    and entry code for each type.
665    -------------------------------------------------------------------------- */
666
667 INFO_TABLE(stg_FULL_MVAR_info,stg_FULL_MVAR_entry,4,0,MVAR,,EF_,"MVAR","MVAR");
668 NON_ENTERABLE_ENTRY_CODE(FULL_MVAR);
669
670 INFO_TABLE(stg_EMPTY_MVAR_info,stg_EMPTY_MVAR_entry,4,0,MVAR,,EF_,"MVAR","MVAR");
671 NON_ENTERABLE_ENTRY_CODE(EMPTY_MVAR);
672
673 /* -----------------------------------------------------------------------------
674    END_TSO_QUEUE
675
676    This is a static nullary constructor (like []) that we use to mark the
677    end of a linked TSO queue.
678    -------------------------------------------------------------------------- */
679
680 INFO_TABLE_CONSTR(stg_END_TSO_QUEUE_info,stg_END_TSO_QUEUE_entry,0,0,0,CONSTR_NOCAF_STATIC,,EF_,0,0);
681 NON_ENTERABLE_ENTRY_CODE(END_TSO_QUEUE);
682
683 SET_STATIC_HDR(stg_END_TSO_QUEUE_closure,stg_END_TSO_QUEUE_info,0/*CC*/,,EI_)
684 , /*payload*/{} };
685
686 /* -----------------------------------------------------------------------------
687    Mutable lists
688
689    Mutable lists (used by the garbage collector) consist of a chain of
690    StgMutClosures connected through their mut_link fields, ending in
691    an END_MUT_LIST closure.
692    -------------------------------------------------------------------------- */
693
694 INFO_TABLE_CONSTR(stg_END_MUT_LIST_info,stg_END_MUT_LIST_entry,0,0,0,CONSTR_NOCAF_STATIC,,EF_,0,0);
695 NON_ENTERABLE_ENTRY_CODE(END_MUT_LIST);
696
697 SET_STATIC_HDR(stg_END_MUT_LIST_closure,stg_END_MUT_LIST_info,0/*CC*/,,EI_)
698 , /*payload*/{} };
699
700 INFO_TABLE(stg_MUT_CONS_info, stg_MUT_CONS_entry, 1, 1, MUT_VAR, , EF_, 0, 0);
701 NON_ENTERABLE_ENTRY_CODE(MUT_CONS);
702
703 /* -----------------------------------------------------------------------------
704    Exception lists
705    -------------------------------------------------------------------------- */
706
707 INFO_TABLE_CONSTR(stg_END_EXCEPTION_LIST_info,stg_END_EXCEPTION_LIST_entry,0,0,0,CONSTR_NOCAF_STATIC,,EF_,0,0);
708 NON_ENTERABLE_ENTRY_CODE(END_EXCEPTION_LIST);
709
710 SET_STATIC_HDR(stg_END_EXCEPTION_LIST_closure,stg_END_EXCEPTION_LIST_info,0/*CC*/,,EI_)
711 , /*payload*/{} };
712
713 INFO_TABLE(stg_EXCEPTION_CONS_info, stg_EXCEPTION_CONS_entry, 1, 1, CONSTR, , EF_, 0, 0);
714 NON_ENTERABLE_ENTRY_CODE(EXCEPTION_CONS);
715
716 /* -----------------------------------------------------------------------------
717    Arrays
718
719    These come in two basic flavours: arrays of data (StgArrWords) and arrays of
720    pointers (StgArrPtrs).  They all have a similar layout:
721
722         ___________________________
723         | Info | No. of | data....
724         |  Ptr | Words  |
725         ---------------------------
726
727    These are *unpointed* objects: i.e. they cannot be entered.
728
729    -------------------------------------------------------------------------- */
730
731 #define ArrayInfo(type)                                 \
732 INFO_TABLE(stg_##type##_info, stg_##type##_entry, 0, 0, type, , EF_,"" # type "","" # type "");
733
734 ArrayInfo(ARR_WORDS);
735 NON_ENTERABLE_ENTRY_CODE(ARR_WORDS);
736 ArrayInfo(MUT_ARR_PTRS);
737 NON_ENTERABLE_ENTRY_CODE(MUT_ARR_PTRS);
738 ArrayInfo(MUT_ARR_PTRS_FROZEN);
739 NON_ENTERABLE_ENTRY_CODE(MUT_ARR_PTRS_FROZEN);
740
741 #undef ArrayInfo
742
743 /* -----------------------------------------------------------------------------
744    Mutable Variables
745    -------------------------------------------------------------------------- */
746
747 INFO_TABLE(stg_MUT_VAR_info, stg_MUT_VAR_entry, 1, 1, MUT_VAR, , EF_, "MUT_VAR", "MUT_VAR");
748 NON_ENTERABLE_ENTRY_CODE(MUT_VAR);
749
750 /* -----------------------------------------------------------------------------
751    Standard Error Entry.
752
753    This is used for filling in vector-table entries that can never happen,
754    for instance.
755    -------------------------------------------------------------------------- */
756 /* No longer used; we use NULL, because a) it never happens, right? and b)
757    Windows doesn't like DLL entry points being used as static initialisers
758 STGFUN(stg_error_entry)                                                 \
759 {                                                                       \
760   FB_                                                                   \
761     DUMP_ERRMSG("fatal: stg_error_entry");                              \
762     STGCALL1(shutdownHaskellAndExit, EXIT_FAILURE);                     \
763     return NULL;                                                        \
764   FE_                                                                   \
765 }
766 */
767 /* -----------------------------------------------------------------------------
768    Dummy return closure
769  
770    Entering this closure will just return to the address on the top of the
771    stack.  Useful for getting a thread in a canonical form where we can
772    just enter the top stack word to start the thread.  (see deleteThread)
773  * -------------------------------------------------------------------------- */
774
775 INFO_TABLE(stg_dummy_ret_info, stg_dummy_ret_entry, 0, 0, CONSTR_NOCAF_STATIC, , EF_, 0, 0);
776 STGFUN(stg_dummy_ret_entry)
777 {
778   W_ ret_addr;
779   FB_
780   ret_addr = Sp[0];
781   Sp++;
782   JMP_(ENTRY_CODE(ret_addr));
783   FE_
784 }
785 SET_STATIC_HDR(stg_dummy_ret_closure,stg_dummy_ret_info,CCS_DONT_CARE,,EI_)
786 , /*payload*/{} };
787
788 /* -----------------------------------------------------------------------------
789     Strict IO application - performing an IO action and entering its result.
790     
791     rts_evalIO() lets you perform Haskell IO actions from outside of Haskell-land,
792     returning back to you their result. Want this result to be evaluated to WHNF
793     by that time, so that we can easily get at the int/char/whatever using the
794     various get{Ty} functions provided by the RTS API.
795
796     forceIO takes care of this, performing the IO action and entering the
797     results that comes back.
798
799  * -------------------------------------------------------------------------- */
800
801 #ifdef REG_R1
802 INFO_TABLE_SRT_BITMAP(stg_forceIO_ret_info,stg_forceIO_ret_entry,0,0,0,0,RET_SMALL,,EF_,0,0);
803 STGFUN(stg_forceIO_ret_entry)
804 {
805   FB_
806   Sp++;
807   Sp -= sizeofW(StgSeqFrame);
808   PUSH_SEQ_FRAME(Sp);
809   JMP_(GET_ENTRY(R1.cl));
810 }
811 #else
812 INFO_TABLE_SRT_BITMAP(stg_forceIO_ret_info,stg_forceIO_ret_entry,0,0,0,0,RET_SMALL,,EF_,0,0);
813 STGFUN(stg_forceIO_ret_entry)
814 {
815   StgClosure *rval;
816   FB_
817   rval = (StgClosure *)Sp[0];
818   Sp += 2;
819   Sp -= sizeofW(StgSeqFrame);
820   PUSH_SEQ_FRAME(Sp);
821   R1.cl = rval;
822   JMP_(GET_ENTRY(R1.cl));
823 }
824 #endif
825
826 INFO_TABLE(stg_forceIO_info,stg_forceIO_entry,1,0,FUN_STATIC,,EF_,0,0);
827 FN_(stg_forceIO_entry)
828 {
829   FB_
830   /* Sp[0] contains the IO action we want to perform */
831   R1.p  = (P_)Sp[0];
832   /* Replace it with the return continuation that enters the result. */
833   Sp[0] = (W_)&stg_forceIO_ret_info;
834   Sp--;
835   /* Push the RealWorld# tag and enter */
836   Sp[0] =(W_)REALWORLD_TAG;
837   JMP_(GET_ENTRY(R1.cl));
838   FE_
839 }
840 SET_STATIC_HDR(stg_forceIO_closure,stg_forceIO_info,CCS_DONT_CARE,,EI_)
841 , /*payload*/{} };
842
843
844 /* -----------------------------------------------------------------------------
845    CHARLIKE and INTLIKE closures.  
846
847    These are static representations of Chars and small Ints, so that
848    we can remove dynamic Chars and Ints during garbage collection and
849    replace them with references to the static objects.
850    -------------------------------------------------------------------------- */
851
852 #if defined(INTERPRETER) || defined(ENABLE_WIN32_DLL_SUPPORT)
853 /*
854  * When sticking the RTS in a DLL, we delay populating the
855  * Charlike and Intlike tables until load-time, which is only
856  * when we've got the real addresses to the C# and I# closures.
857  *
858  */
859 static INFO_TBL_CONST StgInfoTable czh_static_info;
860 static INFO_TBL_CONST StgInfoTable izh_static_info;
861 #define Char_hash_static_info czh_static_info
862 #define Int_hash_static_info izh_static_info
863 #else
864 #define Char_hash_static_info PrelBase_Czh_static_info
865 #define Int_hash_static_info PrelBase_Izh_static_info
866 #endif
867
868 #define CHARLIKE_HDR(n)                                         \
869         {                                                       \
870           STATIC_HDR(Char_hash_static_info, /* C# */            \
871                          CCS_DONT_CARE),                        \
872           data : n                                              \
873         }
874                                              
875 #define INTLIKE_HDR(n)                                          \
876         {                                                       \
877           STATIC_HDR(Int_hash_static_info,  /* I# */            \
878                          CCS_DONT_CARE),                        \
879           data : n                                              \
880         }
881
882 /* put these in the *data* section, since the garbage collector relies
883  * on the fact that static closures live in the data section.
884  */
885
886 /* end the name with _closure, to convince the mangler this is a closure */
887
888 StgIntCharlikeClosure stg_CHARLIKE_closure[] = {
889     CHARLIKE_HDR(0),
890     CHARLIKE_HDR(1),
891     CHARLIKE_HDR(2),
892     CHARLIKE_HDR(3),
893     CHARLIKE_HDR(4),
894     CHARLIKE_HDR(5),
895     CHARLIKE_HDR(6),
896     CHARLIKE_HDR(7),
897     CHARLIKE_HDR(8),
898     CHARLIKE_HDR(9),
899     CHARLIKE_HDR(10),
900     CHARLIKE_HDR(11),
901     CHARLIKE_HDR(12),
902     CHARLIKE_HDR(13),
903     CHARLIKE_HDR(14),
904     CHARLIKE_HDR(15),
905     CHARLIKE_HDR(16),
906     CHARLIKE_HDR(17),
907     CHARLIKE_HDR(18),
908     CHARLIKE_HDR(19),
909     CHARLIKE_HDR(20),
910     CHARLIKE_HDR(21),
911     CHARLIKE_HDR(22),
912     CHARLIKE_HDR(23),
913     CHARLIKE_HDR(24),
914     CHARLIKE_HDR(25),
915     CHARLIKE_HDR(26),
916     CHARLIKE_HDR(27),
917     CHARLIKE_HDR(28),
918     CHARLIKE_HDR(29),
919     CHARLIKE_HDR(30),
920     CHARLIKE_HDR(31),
921     CHARLIKE_HDR(32),
922     CHARLIKE_HDR(33),
923     CHARLIKE_HDR(34),
924     CHARLIKE_HDR(35),
925     CHARLIKE_HDR(36),
926     CHARLIKE_HDR(37),
927     CHARLIKE_HDR(38),
928     CHARLIKE_HDR(39),
929     CHARLIKE_HDR(40),
930     CHARLIKE_HDR(41),
931     CHARLIKE_HDR(42),
932     CHARLIKE_HDR(43),
933     CHARLIKE_HDR(44),
934     CHARLIKE_HDR(45),
935     CHARLIKE_HDR(46),
936     CHARLIKE_HDR(47),
937     CHARLIKE_HDR(48),
938     CHARLIKE_HDR(49),
939     CHARLIKE_HDR(50),
940     CHARLIKE_HDR(51),
941     CHARLIKE_HDR(52),
942     CHARLIKE_HDR(53),
943     CHARLIKE_HDR(54),
944     CHARLIKE_HDR(55),
945     CHARLIKE_HDR(56),
946     CHARLIKE_HDR(57),
947     CHARLIKE_HDR(58),
948     CHARLIKE_HDR(59),
949     CHARLIKE_HDR(60),
950     CHARLIKE_HDR(61),
951     CHARLIKE_HDR(62),
952     CHARLIKE_HDR(63),
953     CHARLIKE_HDR(64),
954     CHARLIKE_HDR(65),
955     CHARLIKE_HDR(66),
956     CHARLIKE_HDR(67),
957     CHARLIKE_HDR(68),
958     CHARLIKE_HDR(69),
959     CHARLIKE_HDR(70),
960     CHARLIKE_HDR(71),
961     CHARLIKE_HDR(72),
962     CHARLIKE_HDR(73),
963     CHARLIKE_HDR(74),
964     CHARLIKE_HDR(75),
965     CHARLIKE_HDR(76),
966     CHARLIKE_HDR(77),
967     CHARLIKE_HDR(78),
968     CHARLIKE_HDR(79),
969     CHARLIKE_HDR(80),
970     CHARLIKE_HDR(81),
971     CHARLIKE_HDR(82),
972     CHARLIKE_HDR(83),
973     CHARLIKE_HDR(84),
974     CHARLIKE_HDR(85),
975     CHARLIKE_HDR(86),
976     CHARLIKE_HDR(87),
977     CHARLIKE_HDR(88),
978     CHARLIKE_HDR(89),
979     CHARLIKE_HDR(90),
980     CHARLIKE_HDR(91),
981     CHARLIKE_HDR(92),
982     CHARLIKE_HDR(93),
983     CHARLIKE_HDR(94),
984     CHARLIKE_HDR(95),
985     CHARLIKE_HDR(96),
986     CHARLIKE_HDR(97),
987     CHARLIKE_HDR(98),
988     CHARLIKE_HDR(99),
989     CHARLIKE_HDR(100),
990     CHARLIKE_HDR(101),
991     CHARLIKE_HDR(102),
992     CHARLIKE_HDR(103),
993     CHARLIKE_HDR(104),
994     CHARLIKE_HDR(105),
995     CHARLIKE_HDR(106),
996     CHARLIKE_HDR(107),
997     CHARLIKE_HDR(108),
998     CHARLIKE_HDR(109),
999     CHARLIKE_HDR(110),
1000     CHARLIKE_HDR(111),
1001     CHARLIKE_HDR(112),
1002     CHARLIKE_HDR(113),
1003     CHARLIKE_HDR(114),
1004     CHARLIKE_HDR(115),
1005     CHARLIKE_HDR(116),
1006     CHARLIKE_HDR(117),
1007     CHARLIKE_HDR(118),
1008     CHARLIKE_HDR(119),
1009     CHARLIKE_HDR(120),
1010     CHARLIKE_HDR(121),
1011     CHARLIKE_HDR(122),
1012     CHARLIKE_HDR(123),
1013     CHARLIKE_HDR(124),
1014     CHARLIKE_HDR(125),
1015     CHARLIKE_HDR(126),
1016     CHARLIKE_HDR(127),
1017     CHARLIKE_HDR(128),
1018     CHARLIKE_HDR(129),
1019     CHARLIKE_HDR(130),
1020     CHARLIKE_HDR(131),
1021     CHARLIKE_HDR(132),
1022     CHARLIKE_HDR(133),
1023     CHARLIKE_HDR(134),
1024     CHARLIKE_HDR(135),
1025     CHARLIKE_HDR(136),
1026     CHARLIKE_HDR(137),
1027     CHARLIKE_HDR(138),
1028     CHARLIKE_HDR(139),
1029     CHARLIKE_HDR(140),
1030     CHARLIKE_HDR(141),
1031     CHARLIKE_HDR(142),
1032     CHARLIKE_HDR(143),
1033     CHARLIKE_HDR(144),
1034     CHARLIKE_HDR(145),
1035     CHARLIKE_HDR(146),
1036     CHARLIKE_HDR(147),
1037     CHARLIKE_HDR(148),
1038     CHARLIKE_HDR(149),
1039     CHARLIKE_HDR(150),
1040     CHARLIKE_HDR(151),
1041     CHARLIKE_HDR(152),
1042     CHARLIKE_HDR(153),
1043     CHARLIKE_HDR(154),
1044     CHARLIKE_HDR(155),
1045     CHARLIKE_HDR(156),
1046     CHARLIKE_HDR(157),
1047     CHARLIKE_HDR(158),
1048     CHARLIKE_HDR(159),
1049     CHARLIKE_HDR(160),
1050     CHARLIKE_HDR(161),
1051     CHARLIKE_HDR(162),
1052     CHARLIKE_HDR(163),
1053     CHARLIKE_HDR(164),
1054     CHARLIKE_HDR(165),
1055     CHARLIKE_HDR(166),
1056     CHARLIKE_HDR(167),
1057     CHARLIKE_HDR(168),
1058     CHARLIKE_HDR(169),
1059     CHARLIKE_HDR(170),
1060     CHARLIKE_HDR(171),
1061     CHARLIKE_HDR(172),
1062     CHARLIKE_HDR(173),
1063     CHARLIKE_HDR(174),
1064     CHARLIKE_HDR(175),
1065     CHARLIKE_HDR(176),
1066     CHARLIKE_HDR(177),
1067     CHARLIKE_HDR(178),
1068     CHARLIKE_HDR(179),
1069     CHARLIKE_HDR(180),
1070     CHARLIKE_HDR(181),
1071     CHARLIKE_HDR(182),
1072     CHARLIKE_HDR(183),
1073     CHARLIKE_HDR(184),
1074     CHARLIKE_HDR(185),
1075     CHARLIKE_HDR(186),
1076     CHARLIKE_HDR(187),
1077     CHARLIKE_HDR(188),
1078     CHARLIKE_HDR(189),
1079     CHARLIKE_HDR(190),
1080     CHARLIKE_HDR(191),
1081     CHARLIKE_HDR(192),
1082     CHARLIKE_HDR(193),
1083     CHARLIKE_HDR(194),
1084     CHARLIKE_HDR(195),
1085     CHARLIKE_HDR(196),
1086     CHARLIKE_HDR(197),
1087     CHARLIKE_HDR(198),
1088     CHARLIKE_HDR(199),
1089     CHARLIKE_HDR(200),
1090     CHARLIKE_HDR(201),
1091     CHARLIKE_HDR(202),
1092     CHARLIKE_HDR(203),
1093     CHARLIKE_HDR(204),
1094     CHARLIKE_HDR(205),
1095     CHARLIKE_HDR(206),
1096     CHARLIKE_HDR(207),
1097     CHARLIKE_HDR(208),
1098     CHARLIKE_HDR(209),
1099     CHARLIKE_HDR(210),
1100     CHARLIKE_HDR(211),
1101     CHARLIKE_HDR(212),
1102     CHARLIKE_HDR(213),
1103     CHARLIKE_HDR(214),
1104     CHARLIKE_HDR(215),
1105     CHARLIKE_HDR(216),
1106     CHARLIKE_HDR(217),
1107     CHARLIKE_HDR(218),
1108     CHARLIKE_HDR(219),
1109     CHARLIKE_HDR(220),
1110     CHARLIKE_HDR(221),
1111     CHARLIKE_HDR(222),
1112     CHARLIKE_HDR(223),
1113     CHARLIKE_HDR(224),
1114     CHARLIKE_HDR(225),
1115     CHARLIKE_HDR(226),
1116     CHARLIKE_HDR(227),
1117     CHARLIKE_HDR(228),
1118     CHARLIKE_HDR(229),
1119     CHARLIKE_HDR(230),
1120     CHARLIKE_HDR(231),
1121     CHARLIKE_HDR(232),
1122     CHARLIKE_HDR(233),
1123     CHARLIKE_HDR(234),
1124     CHARLIKE_HDR(235),
1125     CHARLIKE_HDR(236),
1126     CHARLIKE_HDR(237),
1127     CHARLIKE_HDR(238),
1128     CHARLIKE_HDR(239),
1129     CHARLIKE_HDR(240),
1130     CHARLIKE_HDR(241),
1131     CHARLIKE_HDR(242),
1132     CHARLIKE_HDR(243),
1133     CHARLIKE_HDR(244),
1134     CHARLIKE_HDR(245),
1135     CHARLIKE_HDR(246),
1136     CHARLIKE_HDR(247),
1137     CHARLIKE_HDR(248),
1138     CHARLIKE_HDR(249),
1139     CHARLIKE_HDR(250),
1140     CHARLIKE_HDR(251),
1141     CHARLIKE_HDR(252),
1142     CHARLIKE_HDR(253),
1143     CHARLIKE_HDR(254),
1144     CHARLIKE_HDR(255)
1145 };
1146
1147 StgIntCharlikeClosure stg_INTLIKE_closure[] = {
1148     INTLIKE_HDR(-16),   /* MIN_INTLIKE == -16 */
1149     INTLIKE_HDR(-15),
1150     INTLIKE_HDR(-14),
1151     INTLIKE_HDR(-13),
1152     INTLIKE_HDR(-12),
1153     INTLIKE_HDR(-11),
1154     INTLIKE_HDR(-10),
1155     INTLIKE_HDR(-9),
1156     INTLIKE_HDR(-8),
1157     INTLIKE_HDR(-7),
1158     INTLIKE_HDR(-6),
1159     INTLIKE_HDR(-5),
1160     INTLIKE_HDR(-4),
1161     INTLIKE_HDR(-3),
1162     INTLIKE_HDR(-2),
1163     INTLIKE_HDR(-1),
1164     INTLIKE_HDR(0),
1165     INTLIKE_HDR(1),
1166     INTLIKE_HDR(2),
1167     INTLIKE_HDR(3),
1168     INTLIKE_HDR(4),
1169     INTLIKE_HDR(5),
1170     INTLIKE_HDR(6),
1171     INTLIKE_HDR(7),
1172     INTLIKE_HDR(8),
1173     INTLIKE_HDR(9),
1174     INTLIKE_HDR(10),
1175     INTLIKE_HDR(11),
1176     INTLIKE_HDR(12),
1177     INTLIKE_HDR(13),
1178     INTLIKE_HDR(14),
1179     INTLIKE_HDR(15),
1180     INTLIKE_HDR(16)     /* MAX_INTLIKE == 16 */
1181 };