[commit: ghc] master: prof: Fix heap census for large ARR_WORDS (#11627) (ba95f22)
git at git.haskell.org
git at git.haskell.org
Sun Mar 20 21:11:54 UTC 2016
Repository : ssh://git@git.haskell.org/ghc
On branch : master
Link : http://ghc.haskell.org/trac/ghc/changeset/ba95f22eb98cc2ee2d8d76e56df80769c379413d/ghc
>---------------------------------------------------------------
commit ba95f22eb98cc2ee2d8d76e56df80769c379413d
Author: Jason Eisenberg <jasoneisenberg at gmail.com>
Date: Sun Mar 20 17:49:24 2016 +0100
prof: Fix heap census for large ARR_WORDS (#11627)
The heap census now handles large ARR_WORDS objects which have
been shrunk by shrinkMutableByteArray# or resizeMutableByteArray#.
Test Plan: ./validate && make test WAY=profasm
Reviewers: hvr, bgamari, austin, thomie
Reviewed By: thomie
Subscribers: thomie
Differential Revision: https://phabricator.haskell.org/D2005
GHC Trac Issues: #11627
>---------------------------------------------------------------
ba95f22eb98cc2ee2d8d76e56df80769c379413d
rts/ProfHeap.c | 14 ++++++++
.../should_run/T11627a.hs} | 1 +
.../should_run/T11627a.stdout} | 0
testsuite/tests/profiling/should_run/T11627b.hs | 42 ++++++++++++++++++++++
testsuite/tests/profiling/should_run/all.T | 8 +++++
5 files changed, 65 insertions(+)
diff --git a/rts/ProfHeap.c b/rts/ProfHeap.c
index a7ea3eb..819faeb 100644
--- a/rts/ProfHeap.c
+++ b/rts/ProfHeap.c
@@ -937,6 +937,20 @@ heapCensusChain( Census *census, bdescr *bd )
}
p = bd->start;
+
+ // When we shrink a large ARR_WORDS, we do not adjust the free pointer
+ // of the associated block descriptor, thus introducing slop at the end
+ // of the object. This slop remains after GC, violating the assumption
+ // of the loop below that all slop has been eliminated (#11627).
+ // Consequently, we handle large ARR_WORDS objects as a special case.
+ if (bd->flags & BF_LARGE
+ && get_itbl((StgClosure *)p)->type == ARR_WORDS) {
+ size = arr_words_sizeW((StgArrBytes *)p);
+ prim = rtsTrue;
+ heapProfObject(census, (StgClosure *)p, size, prim);
+ continue;
+ }
+
while (p < bd->free) {
info = get_itbl((StgClosure *)p);
prim = rtsFalse;
diff --git a/testsuite/tests/perf/space_leaks/space_leak_001.hs b/testsuite/tests/profiling/should_run/T11627a.hs
similarity index 65%
copy from testsuite/tests/perf/space_leaks/space_leak_001.hs
copy to testsuite/tests/profiling/should_run/T11627a.hs
index cabde0a..3e1ce3c 100644
--- a/testsuite/tests/perf/space_leaks/space_leak_001.hs
+++ b/testsuite/tests/profiling/should_run/T11627a.hs
@@ -1,3 +1,4 @@
+-- Original test case for #11627 (space_leak_001.hs)
import Data.List
diff --git a/testsuite/tests/perf/space_leaks/space_leak_001.stdout b/testsuite/tests/profiling/should_run/T11627a.stdout
similarity index 100%
copy from testsuite/tests/perf/space_leaks/space_leak_001.stdout
copy to testsuite/tests/profiling/should_run/T11627a.stdout
diff --git a/testsuite/tests/profiling/should_run/T11627b.hs b/testsuite/tests/profiling/should_run/T11627b.hs
new file mode 100644
index 0000000..5e5545a
--- /dev/null
+++ b/testsuite/tests/profiling/should_run/T11627b.hs
@@ -0,0 +1,42 @@
+{-# LANGUAGE MagicHash #-}
+{-# LANGUAGE UnboxedTuples #-}
+
+
+-- A reduced test case for #11627
+
+
+import GHC.Prim
+import GHC.Types (Int(..),IO(..))
+import System.Mem
+
+
+main :: IO ()
+main = do
+ -- Allocate a large object (size >= 8/10 of one block = 8/10 * 4096 B)
+ let nBytes = 123 * 4096
+ b <- newBlob nBytes
+
+ -- Shrink it by at least one word
+ let delta = 100
+ shrinkBlob b $ nBytes - delta
+
+ -- Perform a heap census (assumes we are running with -i0, so a census is
+ -- run after every GC)
+ performGC
+
+ -- Hold on to b so it is not GCed before the census
+ shrinkBlob b $ nBytes - delta
+
+------------------------------------------------------------------------------
+
+data Blob = Blob# !(MutableByteArray# RealWorld)
+
+newBlob :: Int -> IO Blob
+newBlob (I# n#) =
+ IO $ \s -> case newByteArray# n# s of
+ (# s', mba# #) -> (# s', Blob# mba# #)
+
+shrinkBlob :: Blob -> Int -> IO ()
+shrinkBlob (Blob# mba#) (I# n#) =
+ IO $ \s -> case shrinkMutableByteArray# mba# n# s of
+ s' -> (# s', () #)
diff --git a/testsuite/tests/profiling/should_run/all.T b/testsuite/tests/profiling/should_run/all.T
index 41597a4..c6ce6d4 100644
--- a/testsuite/tests/profiling/should_run/all.T
+++ b/testsuite/tests/profiling/should_run/all.T
@@ -98,3 +98,11 @@ test('callstack002', [], compile_and_run,
test('T5363', [], compile_and_run, [''])
test('profinline001', [], compile_and_run, [''])
+
+test('T11627a', [extra_ways(extra_prof_ways)], compile_and_run, [''])
+
+test('T11627b', [ extra_run_opts('+RTS -i0 -RTS') # census after each GC
+ , extra_ways(extra_prof_ways)
+ ]
+ , compile_and_run
+ , [''])
More information about the ghc-commits
mailing list