
#14361: GHC HEAD miscompiles `text-containers` -------------------------------------+------------------------------------- Reporter: hvr | Owner: (none) Type: bug | Status: new Priority: high | Milestone: 8.4.1 Component: Compiler | Version: 8.3 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: Type of failure: Incorrect result | Unknown/Multiple at runtime | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Comment (by bgamari): I could have sworn I had left a comment here when I looked at this last but alas it seems to be gone. Anyways, I've done a fair amount of digging on this one. I started by looking at differences in the call patterns of `Internal.$wcompareByteArray` in two compilations of the repro: one compiled with `{-# OPTIONS_GHC -fno-strictness #-}` in the `Internal2.hs` (which I'll call the "good" configuration) and one without (the "bad" configuration). Specifically I setup GDB to instrument calls to this function, logging each. This revealed that the bad configuration sometimes enters `$wcompareByteArray` with the `ofs2` and `n2` arguments being zero, where in good configuration they are non-zero. For instance, {{{#!patch --- gdb.good.log 2017-11-03 16:53:05.956764525 -0400 +++ gdb.bad.log 2017-11-03 16:53:27.481174930 -0400 @@ -186,8 +186,7 @@ done fffffffc memcmp a.len=1 a[0]=44 ofs1=0 n1=1 b.len=50 ofs2=4c n2=1 done ffffffff -memcmp a.len=1 a[0]=44 ofs1=0 n1=1 b.len=50 ofs2=4a n2=1 -done 1 +memcmp a.len=1 a[0]=44 ofs1=0 n1=1 b.len=50 ofs2=0 n2=0 memcmp a.len=1 a[0]=44 ofs1=0 n1=1 b.len=50 ofs2=4b n2=1 done 0 memcmp a.len=1 a[0]=45 ofs1=0 n1=1 b.len=50 ofs2=48 n2=1 }}} The (perhaps slightly poorly-named) `memcmp` message is emitted on entering `$wcompareByteArray`. The `done` message is emitted after the `memcmp` call returns. The fact that there is no `done` message in the bad case is the consequence of the implementation of `compareByteArray`, which skips the `memcmp` if `min n1 n2 == 0`. Another thing I have noticed is that the occurrence probability of the bug changes with GC patterns. Interestingly, it doesn't change monotonically with GC frequency; for a given value of `+RTS -A` I reproducibly get the same set of numbers on stdout. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/14361#comment:6 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler