summaryrefslogtreecommitdiff
path: root/rts/StgStdThunks.cmm
diff options
context:
space:
mode:
authorSimon Marlow <marlowsd@gmail.com>2009-03-17 14:49:39 +0000
committerSimon Marlow <marlowsd@gmail.com>2009-03-17 14:49:39 +0000
commitf8f4cb3f3a46e0495917a927cefe906531b7b38e (patch)
treed73d7f883bda109e68dca56cc9ab6e5258aa8e6d /rts/StgStdThunks.cmm
parent0ee0be109fd00ec629f7a2ad6a597885a0c9d5b4 (diff)
downloadhaskell-f8f4cb3f3a46e0495917a927cefe906531b7b38e.tar.gz
FIX biographical profiling (#3039, probably #2297)
Since we introduced pointer tagging, we no longer always enter a closure to evaluate it. However, the biographical profiler relies on closures being entered in order to mark them as "used", so we were getting spurious amounts of data attributed to VOID. It turns out there are various places that need to be fixed, and I think at least one of them was also wrong before pointer tagging (CgCon.cgReturnDataCon).
Diffstat (limited to 'rts/StgStdThunks.cmm')
-rw-r--r--rts/StgStdThunks.cmm22
1 files changed, 17 insertions, 5 deletions
diff --git a/rts/StgStdThunks.cmm b/rts/StgStdThunks.cmm
index fecbb4c3c0..be85999598 100644
--- a/rts/StgStdThunks.cmm
+++ b/rts/StgStdThunks.cmm
@@ -52,7 +52,22 @@
* so we untag it before accessing the field.
*
*/
-#define SELECTOR_CODE_UPD(offset) \
+#ifdef PROFILING
+// When profiling, we cannot shortcut by checking the tag,
+// because LDV profiling relies on entering closures to mark them as
+// "used".
+#define SEL_ENTER(offset) \
+ R1 = UNTAG(R1); \
+ jump %GET_ENTRY(R1);
+#else
+#define SEL_ENTER(offset) \
+ if (GETTAG(R1) != 0) { \
+ jump RET_LBL(stg_sel_ret_##offset##_upd); \
+ } \
+ jump %GET_ENTRY(R1);
+#endif
+
+#define SELECTOR_CODE_UPD(offset) \
INFO_TABLE_RET(stg_sel_ret_##offset##_upd, RET_SMALL, RET_PARAMS) \
{ \
R1 = StgClosure_payload(UNTAG(R1),offset); \
@@ -73,10 +88,7 @@
W_[Sp-WITHUPD_FRAME_SIZE] = stg_sel_ret_##offset##_upd_info; \
Sp = Sp - WITHUPD_FRAME_SIZE; \
R1 = StgThunk_payload(R1,0); \
- if (GETTAG(R1) != 0) { \
- jump RET_LBL(stg_sel_ret_##offset##_upd); \
- } \
- jump %GET_ENTRY(R1); \
+ SEL_ENTER(offset); \
}
/* NOTE: no need to ENTER() here, we know the closure cannot evaluate to a function,
because we're going to do a field selection on the result. */