[project @ 2002-12-19 17:57:39 by panne]
[ghc-hetmet.git] / ghc / includes / StgTicky.h
index 014569e..25b4c1b 100644 (file)
@@ -1,5 +1,8 @@
 /* ----------------------------------------------------------------------------
- * $Id: StgTicky.h,v 1.2 1999/02/02 14:21:28 simonm Exp $
+ * $Id: StgTicky.h,v 1.14 2002/12/18 01:13:37 mthomas Exp $
+ *
+ * (c) The AQUA project, Glasgow University, 1994-1997
+ * (c) The GHC Team, 1998-1999
  *
  * Ticky-ticky profiling macros.
  *
  * the allocations gives an indication of how many things we get per trip
  * to the well:
  */
-#define TICK_ALLOC_HEAP(n)     ALLOC_HEAP_ctr++; ALLOC_HEAP_tot += (n)
+#define TICK_ALLOC_HEAP(n, f_ct)               \
+  {                                            \
+    f_ct.allocs += (n);                                \
+    ALLOC_HEAP_ctr++;                          \
+    ALLOC_HEAP_tot += (n);                     \
+  }
+
+#define TICK_ALLOC_HEAP_NOCTR(n)               \
+  {                                            \
+    ALLOC_HEAP_ctr++;                          \
+    ALLOC_HEAP_tot += (n);                     \
+  }
 
 /* We count things every time we allocate something in the dynamic heap.
  * For each, we count the number of words of (1) ``admin'' (header),
        ALLOC_FUN_gds += (g);   ALLOC_FUN_slp += (s);   \
        TICK_ALLOC_HISTO(FUN,_HS,g,s)
 
-#define TICK_ALLOC_THK(g,s)                            \
-       ALLOC_THK_ctr++;        ALLOC_THK_adm += _HS;   \
+#define TICK_ALLOC_UP_THK(g,s)                          \
+       ALLOC_UP_THK_ctr++;     ALLOC_THK_adm += _HS;   \
+       ALLOC_THK_gds += (g);   ALLOC_THK_slp += (s);   \
+       TICK_ALLOC_HISTO(THK,_HS,g,s)
+
+#define TICK_ALLOC_SE_THK(g,s)                          \
+       ALLOC_SE_THK_ctr++;     ALLOC_THK_adm += _HS;   \
        ALLOC_THK_gds += (g);   ALLOC_THK_slp += (s);   \
        TICK_ALLOC_HISTO(THK,_HS,g,s)
 
        ALLOC_BH_gds += (g);    ALLOC_BH_slp += (s);    \
        TICK_ALLOC_HISTO(BH,_HS,g,s)
 
-#define TICK_ALLOC_UPD_PAP(g,s)                                        \
-       ALLOC_UPD_PAP_ctr++;    ALLOC_UPD_PAP_adm += sizeofW(StgPAP)-1; \
-       ALLOC_UPD_PAP_gds += (g); ALLOC_UPD_PAP_slp += (s);     \
-       TICK_ALLOC_HISTO(UPD_PAP,sizeofW(StgPAP)-1,g,s)
+#define TICK_ALLOC_PAP(g,s)                                    \
+       ALLOC_PAP_ctr++;      ALLOC_PAP_adm += sizeofW(StgPAP)-1; \
+       ALLOC_PAP_gds += (g); ALLOC_PAP_slp += (s);     \
+       TICK_ALLOC_HISTO(PAP,sizeofW(StgPAP)-1,g,s)
 
 #define TICK_ALLOC_TSO(g,s)                                            \
        ALLOC_TSO_ctr++;        ALLOC_TSO_adm += sizeofW(StgTSO);       \
 
 #define TICK_ENT_VIA_NODE()    ENT_VIA_NODE_ctr++
 
-#define TICK_ENT_THK()         ENT_THK_ctr++         /* thunk */
-#define TICK_ENT_FUN_STD()     ENT_FUN_STD_ctr++     /* std entry pt */
-#define TICK_ENT_FUN_DIRECT(n)         ENT_FUN_DIRECT_ctr++  /* fast entry pt */
-
-#define TICK_ENT_CON(n)                ENT_CON_ctr++         /* enter constructor */
-#define TICK_ENT_IND(n)                ENT_IND_ctr++         /* enter indirection */
+#define TICK_ENT_STATIC_THK()  ENT_STATIC_THK_ctr++ 
+#define TICK_ENT_DYN_THK()     ENT_DYN_THK_ctr++
+
+typedef struct _StgEntCounter {
+    unsigned   registeredp:16, /* 0 == no, 1 == yes */
+               arity:16,       /* arity (static info) */
+               stk_args:16;    /* # of args off stack */
+                               /* (rest of args are in registers) */
+    char       *str;           /* name of the thing */
+    char       *arg_kinds;     /* info about the args types */
+    I_         entry_count;      /* Trips to fast entry code */
+    I_          allocs;         /* number of allocations by this fun */
+    struct _StgEntCounter *link;/* link to chain them all together */
+} StgEntCounter;
+
+#define TICK_CTR(f_ct, str, arity, args, arg_kinds)    \
+   static StgEntCounter f_ct                   \
+       = { 0, arity, args,                     \
+           str, arg_kinds,                     \
+           0, 0, NULL };
+
+#define TICK_ENT_FUN_DIRECT_BODY(f_ct)                          \
+       {                                                       \
+         if ( ! f_ct.registeredp ) {                           \
+           /* hook this one onto the front of the list */      \
+           f_ct.link = ticky_entry_ctrs;                       \
+           ticky_entry_ctrs = & (f_ct);                        \
+           /* mark it as "registered" */                       \
+           f_ct.registeredp = 1;                               \
+         }                                                     \
+         f_ct.entry_count += 1;                                \
+       }
+
+#define TICK_ENT_STATIC_FUN_DIRECT(f_ct)                       \
+        TICK_ENT_FUN_DIRECT_BODY(f_ct)                          \
+       ENT_STATIC_FUN_DIRECT_ctr++ /* The static total one */
+
+#define TICK_ENT_DYN_FUN_DIRECT(f_ct)                          \
+        TICK_ENT_FUN_DIRECT_BODY(f_ct)                          \
+       ENT_DYN_FUN_DIRECT_ctr++ /* The dynamic total one */
+
+extern StgEntCounter top_ct;
+extern StgEntCounter *ticky_entry_ctrs;
+
+#define TICK_ENT_STATIC_CON(n) ENT_STATIC_CON_ctr++  /* enter static constructor */
+#define TICK_ENT_DYN_CON(n)    ENT_DYN_CON_ctr++     /* enter dynamic constructor */
+#define TICK_ENT_STATIC_IND(n) ENT_STATIC_IND_ctr++  /* enter static indirection */
+#define TICK_ENT_DYN_IND(n)    ENT_DYN_IND_ctr++     /* enter dynamic indirection */
+#define TICK_ENT_PERM_IND(n)    ENT_PERM_IND_ctr++    /* enter permanent indirection */
 #define TICK_ENT_PAP(n)                ENT_PAP_ctr++         /* enter PAP */
-#define TICK_ENT_AP_UPD(n)     ENT_AP_UPD_ctr++      /* enter AP_UPD */
+#define TICK_ENT_AP(n)                 ENT_AP_ctr++          /* enter AP_UPD */
+#define TICK_ENT_AP_STACK(n)    ENT_AP_STACK_ctr++    /* enter AP_STACK_UPD */
 #define TICK_ENT_BH()          ENT_BH_ctr++          /* enter BLACKHOLE */
 
+
+#define TICK_SLOW_HISTO(n)                             \
+ { unsigned __idx;                                     \
+   __idx = (n);                                                \
+   SLOW_CALL_hst[((__idx > 8) ? 8 : __idx)] += 1;      \
+ }
+
+// A slow call with n arguments
+#define TICK_SLOW_CALL(n)       SLOW_CALL_ctr++; \
+                                TICK_SLOW_HISTO(n)
+
+// A slow call to a FUN found insufficient arguments, and built a PAP
+#define TICK_SLOW_CALL_BUILT_PAP() SLOW_CALL_BUILT_PAP_ctr++
+
+// A slow call to a PAP found insufficient arguments, and build a new PAP
+#define TICK_SLOW_CALL_NEW_PAP()   SLOW_CALL_NEW_PAP_ctr++
+
 /* -----------------------------------------------------------------------------
    Returns
    -------------------------------------------------------------------------- */
 
-/* Whenever a ``return'' occurs, it is returning the constituent parts of
- * a data constructor.  The parts can be returned either in registers, or
- * by allocating some heap to put it in (the TICK_ALLOC_* macros account for
- * the allocation).  The constructor can either be an existing one
- * *OLD* or we could have {\em just} figured out this stuff
- * *NEW*.
- */
-
 #define TICK_RET_HISTO(categ,n)                                        \
        { I_ __idx;                                             \
          __idx = (n);                                          \
 #define TICK_RET_UNBOXED_TUP(n)  RET_UNBOXED_TUP_ctr++; \
                          TICK_RET_HISTO(UNBOXED_TUP,n)
 
-#define TICK_RET_SEMI(n) RET_SEMI_IN_HEAP_ctr++; \
-                        TICK_RET_HISTO(SEMI_IN_HEAP,n)
-
-#define TICK_RET_SEMI_BY_DEFAULT()/*???*/ RET_SEMI_BY_DEFAULT_ctr++
-
-#define TICK_RET_SEMI_FAILED(tag)      do {                            \
-                               if ((tag) == INFO_IND_TAG)              \
-                                   RET_SEMI_FAILED_IND_ctr++;          \
-                               else                                    \
-                                   RET_SEMI_FAILED_UNEVAL_ctr++;       \
-                               } while (0)
-
 #define TICK_VEC_RETURN(n)     VEC_RETURN_ctr++;           \
                                TICK_RET_HISTO(VEC_RETURN,n)
 
    Macro                          Counts
    ------------------              -------------------------------------------
    TICK_UPDF_PUSHED               Update frame pushed
-   TICK_SEQF_PUSHED               Seq frame pushed
    TICK_CATCHF_PUSHED             Catch frame pushed
    TICK_UPDF_OMITTED              A thunk decided not to push an update frame
    TICK_UPDF_RCC_PUSHED                   Cost Centre restore frame pushed
    -------------------------------------------------------------------------- */
 
 #define TICK_UPDF_OMITTED()    UPDF_OMITTED_ctr++
-#define TICK_UPDF_PUSHED()     UPDF_PUSHED_ctr++
-#define TICK_SEQF_PUSHED()      SEQF_PUSHED_ctr++
+#define TICK_UPDF_PUSHED(tgt,inf)      UPDF_PUSHED_ctr++ \
+/*                              ; fprintf(stderr,"UPDF_PUSHED:%p:%p\n",tgt,inf) */
 #define TICK_CATCHF_PUSHED()    CATCHF_PUSHED_ctr++
 #define TICK_UPDF_RCC_PUSHED() UPDF_RCC_PUSHED_ctr++
 #define TICK_UPDF_RCC_OMITTED()        UPDF_RCC_OMITTED_ctr++
    
    Macro                               Where
    -----------------------     --------------------------------------------
-   TICK_UPD_EXISTING           Updating with an indirection to something
-                               already in the heap
    TICK_UPD_SQUEEZED           Same as UPD_EXISTING but because
                                of stack-squeezing
    TICK_UPD_CON_IN_NEW         Allocating a new CON
+   TICK_UPD_CON_IN_PLACE       Updating with a PAP in place
    TICK_UPD_PAP_IN_NEW         Allocating a new PAP
    TICK_UPD_PAP_IN_PLACE       Updating with a PAP in place
 
          __idx = (n);                                           \
         UPD_##categ##_hst[((__idx > 8) ? 8 : __idx)] += 1;} 
 
-#define TICK_UPD_EXISTING()            UPD_EXISTING_ctr++
 #define TICK_UPD_SQUEEZED()            UPD_SQUEEZED_ctr++
 
 #define TICK_UPD_CON_IN_NEW(n)         UPD_CON_IN_NEW_ctr++ ; \
                                        TICK_UPD_HISTO(CON_IN_NEW,n)
 
+#define TICK_UPD_CON_IN_PLACE(n)       UPD_CON_IN_PLACE_ctr++; \
+                                       TICK_UPD_HISTO(CON_IN_PLACE,n)
+
 #define TICK_UPD_PAP_IN_NEW(n)         UPD_PAP_IN_NEW_ctr++ ; \
                                        TICK_UPD_HISTO(PAP_IN_NEW,n)
 
 /* For the generational collector: 
  */
 #define TICK_UPD_NEW_IND()             UPD_NEW_IND_ctr++
+#define TICK_UPD_NEW_PERM_IND(tgt)     UPD_NEW_PERM_IND_ctr++ \
+/*                                      ; fprintf(stderr,"UPD_NEW_PERM:%p\n",tgt) */
 #define TICK_UPD_OLD_IND()             UPD_OLD_IND_ctr++                       
+#define TICK_UPD_OLD_PERM_IND()                UPD_OLD_PERM_IND_ctr++                  
+
+/* Count blackholes:
+ */
+#define TICK_UPD_BH_UPDATABLE()         UPD_BH_UPDATABLE_ctr++
+#define TICK_UPD_BH_SINGLE_ENTRY()      UPD_BH_SINGLE_ENTRY_ctr++
+#define TICK_UPD_CAF_BH_UPDATABLE(s)                          \
+     UPD_CAF_BH_UPDATABLE_ctr++                               \
+/*   ; fprintf(stderr,"TICK_UPD_CAF_BH_UPDATABLE(%s)\n",s) */
+#define TICK_UPD_CAF_BH_SINGLE_ENTRY(s)                       \
+     UPD_CAF_BH_SINGLE_ENTRY_ctr++                            \
+/*   ; fprintf(stderr,"TICK_UPD_CAF_BH_SINGLE_ENTRY(%s)\n",s) */
+
 
 /* -----------------------------------------------------------------------------
    Garbage collection counters
@@ -280,7 +355,8 @@ EXTERN unsigned long ALLOC_FUN_hst[5]
 #endif
 ;
 
-EXTERN unsigned long ALLOC_THK_ctr INIT(0);
+EXTERN unsigned long ALLOC_UP_THK_ctr INIT(0);
+EXTERN unsigned long ALLOC_SE_THK_ctr INIT(0);
 EXTERN unsigned long ALLOC_THK_adm INIT(0);
 EXTERN unsigned long ALLOC_THK_gds INIT(0);
 EXTERN unsigned long ALLOC_THK_slp INIT(0);
@@ -330,11 +406,11 @@ EXTERN unsigned long ALLOC_PRIM_hst[5]
 #endif
 ;
 
-EXTERN unsigned long ALLOC_UPD_PAP_ctr INIT(0);
-EXTERN unsigned long ALLOC_UPD_PAP_adm INIT(0);
-EXTERN unsigned long ALLOC_UPD_PAP_gds INIT(0);
-EXTERN unsigned long ALLOC_UPD_PAP_slp INIT(0);
-EXTERN unsigned long ALLOC_UPD_PAP_hst[5]
+EXTERN unsigned long ALLOC_PAP_ctr INIT(0);
+EXTERN unsigned long ALLOC_PAP_adm INIT(0);
+EXTERN unsigned long ALLOC_PAP_gds INIT(0);
+EXTERN unsigned long ALLOC_PAP_slp INIT(0);
+EXTERN unsigned long ALLOC_PAP_hst[5]
 #ifdef TICKY_C
    = {0,0,0,0,0}
 #endif
@@ -380,25 +456,36 @@ EXTERN unsigned long ALLOC_BF_hst[5]
    = {0,0,0,0,0}
 #endif
 ;
-#endif
+#endif // PAR
 
 EXTERN unsigned long ENT_VIA_NODE_ctr INIT(0);
-EXTERN unsigned long ENT_THK_ctr INIT(0);
-EXTERN unsigned long ENT_FUN_STD_ctr INIT(0);
-EXTERN unsigned long ENT_FUN_DIRECT_ctr INIT(0);
-EXTERN unsigned long ENT_CON_ctr INIT(0);
-EXTERN unsigned long ENT_IND_ctr INIT(0);
+EXTERN unsigned long ENT_STATIC_THK_ctr INIT(0);
+EXTERN unsigned long ENT_DYN_THK_ctr INIT(0);
+EXTERN unsigned long ENT_STATIC_FUN_DIRECT_ctr INIT(0);
+EXTERN unsigned long ENT_DYN_FUN_DIRECT_ctr INIT(0);
+EXTERN unsigned long ENT_STATIC_CON_ctr INIT(0);
+EXTERN unsigned long ENT_DYN_CON_ctr INIT(0);
+EXTERN unsigned long ENT_STATIC_IND_ctr INIT(0);
+EXTERN unsigned long ENT_DYN_IND_ctr INIT(0);
+EXTERN unsigned long ENT_PERM_IND_ctr INIT(0);
 EXTERN unsigned long ENT_PAP_ctr INIT(0);
-EXTERN unsigned long ENT_AP_UPD_ctr INIT(0);
+EXTERN unsigned long ENT_AP_ctr INIT(0);
+EXTERN unsigned long ENT_AP_STACK_ctr INIT(0);
 EXTERN unsigned long ENT_BH_ctr INIT(0);
 
+EXTERN unsigned long SLOW_CALL_ctr INIT(0);
+EXTERN unsigned long SLOW_CALL_BUILT_PAP_ctr INIT(0);
+EXTERN unsigned long SLOW_CALL_NEW_PAP_ctr INIT(0);
+
+EXTERN unsigned long SLOW_CALL_hst[8]
+#ifdef TICKY_C
+   = {0,0,0,0,0,0,0,0}
+#endif
+;
+
 EXTERN unsigned long RET_NEW_ctr INIT(0);
 EXTERN unsigned long RET_OLD_ctr INIT(0);
 EXTERN unsigned long RET_UNBOXED_TUP_ctr INIT(0);
-EXTERN unsigned long RET_SEMI_BY_DEFAULT_ctr INIT(0);
-EXTERN unsigned long RET_SEMI_IN_HEAP_ctr INIT(0);
-EXTERN unsigned long RET_SEMI_FAILED_IND_ctr INIT(0);
-EXTERN unsigned long RET_SEMI_FAILED_UNEVAL_ctr INIT(0);
 
 EXTERN unsigned long VEC_RETURN_ctr INIT(0);
 
@@ -432,14 +519,13 @@ EXTERN unsigned long RET_SEMI_loads_avoided INIT(0);
 
 EXTERN unsigned long UPDF_OMITTED_ctr INIT(0);
 EXTERN unsigned long UPDF_PUSHED_ctr INIT(0);
-EXTERN unsigned long SEQF_PUSHED_ctr INIT(0);
 EXTERN unsigned long CATCHF_PUSHED_ctr INIT(0);
 EXTERN unsigned long UPDF_RCC_PUSHED_ctr INIT(0);
 EXTERN unsigned long UPDF_RCC_OMITTED_ctr INIT(0);
 
-EXTERN unsigned long UPD_EXISTING_ctr INIT(0);
 EXTERN unsigned long UPD_SQUEEZED_ctr INIT(0);
 EXTERN unsigned long UPD_CON_IN_NEW_ctr INIT(0);
+EXTERN unsigned long UPD_CON_IN_PLACE_ctr INIT(0);
 EXTERN unsigned long UPD_PAP_IN_NEW_ctr INIT(0);
 EXTERN unsigned long UPD_PAP_IN_PLACE_ctr INIT(0);
 
@@ -448,6 +534,11 @@ EXTERN unsigned long UPD_CON_IN_NEW_hst[9]
    = {0,0,0,0,0,0,0,0,0}
 #endif
 ;
+EXTERN unsigned long UPD_CON_IN_PLACE_hst[9]
+#ifdef TICKY_C
+   = {0,0,0,0,0,0,0,0,0}
+#endif
+;
 EXTERN unsigned long UPD_PAP_IN_NEW_hst[9]
 #ifdef TICKY_C
    = {0,0,0,0,0,0,0,0,0}
@@ -455,7 +546,14 @@ EXTERN unsigned long UPD_PAP_IN_NEW_hst[9]
 ;
 
 EXTERN unsigned long UPD_NEW_IND_ctr INIT(0);
+EXTERN unsigned long UPD_NEW_PERM_IND_ctr INIT(0);
 EXTERN unsigned long UPD_OLD_IND_ctr INIT(0);
+EXTERN unsigned long UPD_OLD_PERM_IND_ctr INIT(0);
+
+EXTERN unsigned long UPD_BH_UPDATABLE_ctr INIT(0);
+EXTERN unsigned long UPD_BH_SINGLE_ENTRY_ctr INIT(0);
+EXTERN unsigned long UPD_CAF_BH_UPDATABLE_ctr INIT(0);
+EXTERN unsigned long UPD_CAF_BH_SINGLE_ENTRY_ctr INIT(0);
 
 EXTERN unsigned long GC_SEL_ABANDONED_ctr INIT(0);
 EXTERN unsigned long GC_SEL_MINOR_ctr INIT(0);
@@ -474,14 +572,16 @@ EXTERN unsigned long GC_WORDS_COPIED_ctr INIT(0);
 
 #else /* !TICKY_TICKY */
 
-#define TICK_ALLOC_HEAP(words)
+#define TICK_ALLOC_HEAP(words, f_ct)
+#define TICK_ALLOC_HEAP_NOCTR(words)
 
 #define TICK_ALLOC_FUN(g,s)
-#define TICK_ALLOC_THK(g,s)
+#define TICK_ALLOC_UP_THK(g,s)
+#define TICK_ALLOC_SE_THK(g,s)
 #define TICK_ALLOC_CON(g,s)
 #define TICK_ALLOC_TUP(g,s)
 #define TICK_ALLOC_BH(g,s)
-#define TICK_ALLOC_UPD_PAP(g,s)
+#define TICK_ALLOC_PAP(g,s)
 #define TICK_ALLOC_TSO(g,s)
 #define TICK_ALLOC_FMBQ(a,g,s)
 #define TICK_ALLOC_FME(a,g,s)
@@ -491,16 +591,24 @@ EXTERN unsigned long GC_WORDS_COPIED_ctr INIT(0);
 
 #define TICK_ENT_VIA_NODE()    
                                
-#define TICK_ENT_THK()
-#define TICK_ENT_FUN_STD()
-#define TICK_ENT_FUN_DIRECT(n)
-                               
-#define TICK_ENT_CON(n)
-#define TICK_ENT_IND(n)
+#define TICK_ENT_STATIC_THK()
+#define TICK_ENT_DYN_THK()
+#define TICK_ENT_STATIC_FUN_DIRECT(n)
+#define TICK_ENT_DYN_FUN_DIRECT(n)
+#define TICK_ENT_STATIC_CON(n)
+#define TICK_ENT_DYN_CON(n)
+#define TICK_ENT_STATIC_IND(n)
+#define TICK_ENT_DYN_IND(n)
+#define TICK_ENT_PERM_IND(n)
 #define TICK_ENT_PAP(n)
-#define TICK_ENT_AP_UPD(n)
+#define TICK_ENT_AP(n)
+#define TICK_ENT_AP_STACK(n)
 #define TICK_ENT_BH()
 
+#define TICK_SLOW_CALL(n)
+#define TICK_SLOW_CALL_BUILT_PAP()
+#define TICK_SLOW_CALL_NEW_PAP()
+
 #define TICK_RET_NEW(n)
 #define TICK_RET_OLD(n)
 #define TICK_RET_UNBOXED_TUP(n)
@@ -510,20 +618,26 @@ EXTERN unsigned long GC_WORDS_COPIED_ctr INIT(0);
 #define TICK_VEC_RETURN(n)
 
 #define TICK_UPDF_OMITTED()
-#define TICK_UPDF_PUSHED()
-#define TICK_SEQF_PUSHED()
+#define TICK_UPDF_PUSHED(tgt,inf)
 #define TICK_CATCHF_PUSHED()
 #define TICK_UPDF_RCC_PUSHED()
 #define TICK_UPDF_RCC_OMITTED()
 
-#define TICK_UPD_EXISTING()
 #define TICK_UPD_SQUEEZED()
 #define TICK_UPD_CON_IN_NEW(n)
+#define TICK_UPD_CON_IN_PLACE(n)
 #define TICK_UPD_PAP_IN_NEW(n)
 #define TICK_UPD_PAP_IN_PLACE()
 
 #define TICK_UPD_NEW_IND()
+#define TICK_UPD_NEW_PERM_IND(tgt)
 #define TICK_UPD_OLD_IND()
+#define TICK_UPD_OLD_PERM_IND()
+
+#define TICK_UPD_BH_UPDATABLE()
+#define TICK_UPD_BH_SINGLE_ENTRY()
+#define TICK_UPD_CAF_BH_UPDATABLE()
+#define TICK_UPD_CAF_BH_SINGLE_ENTRY()
 
 #define TICK_GC_SEL_ABANDONED()
 #define TICK_GC_SEL_MINOR()