
#13611: Segfault due to levity polymorphism of mkWeak# -------------------------------------+------------------------------------- Reporter: nomeata | Owner: (none) Type: bug | Status: new Priority: normal | Milestone: 8.2.1 Component: Compiler | Version: 8.1 Resolution: | Keywords: Operating System: Unknown/Multiple | Architecture: | Unknown/Multiple Type of failure: None/Unknown | Test Case: Blocked By: | Blocking: Related Tickets: | Differential Rev(s): Wiki Page: | -------------------------------------+------------------------------------- Changes (by simonpj): * cc: simonmar (added) Comment:
Though what guarantees do we provide when a user writes the IO constructor explicitly? This is tantamount to unsafePerformIO, is it not?
You might get sequencing or concurrency errors, but not seg-faults.
But there is one use of mkWeak# in the libraries that seems to use a different TypeRep
Actually ''all'' the uses in `base` are on `UnliftedRep` except the single use in `GHC.Weak.mkWeak`.
Or, the easy way out, is to have two copies of the mkWeak# primop, one for LiftedRep and one for UnliftedRep.
Yes, let's do that. In principle we could further structure `RuntimeRep` to have {{{ data RuntimeRep = IntRep | WordRep | PtrRep Liftedness data Liftedness = Lifted | Unlifted }}} and now we could have polymorphism over liftedness, but I just don't think it's worth it. BTW I think that (like `dataToTag#`) `mkWeak#` probably requires its argument to be evaluated. (I don't think it does and eval itself, though perhaps it should.) Reason: `mkWeak#` should not make a weak pointer to a thunk. I think. So I am pretty suspicious of this `GHC.Weak.mkWeak`: {{{ mkWeak key val (Just (IO finalizer)) = IO $ \s -> case mkWeak# key val finalizer s of { (# s1, w #) -> (# s1, Weak w #) } }}} Looks wrong to me; e.g. `mkWeak# (head xs)`? Copying Simon M. -- Ticket URL: http://ghc.haskell.org/trac/ghc/ticket/13611#comment:6 GHC http://www.haskell.org/ghc/ The Glasgow Haskell Compiler