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