Safe Haskell | Unsafe |
---|---|

Language | Haskell2010 |

## Synopsis

- unsafeCoerce :: a -> b
- unsafeCoerceUnlifted :: forall (a :: UnliftedType) (b :: UnliftedType). a -> b
- unsafeCoerceAddr :: forall (a :: TYPE 'AddrRep) (b :: TYPE 'AddrRep). a -> b
- unsafeEqualityProof :: forall {k} (a :: k) (b :: k). UnsafeEquality a b
- data UnsafeEquality (a :: k) (b :: k) where
- UnsafeRefl :: forall {k} (a :: k). UnsafeEquality a a

- unsafeCoerce# :: a -> b

# Documentation

unsafeCoerce :: a -> b Source #

`unsafeCoerce`

coerces a value from one type to another, bypassing the type-checker.

There are several legitimate ways to use `unsafeCoerce`

:

- To coerce a lifted type such as
`Int`

to`Any`

, put it in a list of`Any`

, and then later coerce it back to`Int`

before using it. - To produce e.g.
`(a+b) :~: (b+a)`

from`unsafeCoerce Refl`

. Here the two sides really are the same type -- so nothing unsafe is happening -- but GHC is not clever enough to see it. - In
`Data.Typeable`

we have

eqTypeRep :: forall k1 k2 (a :: k1) (b :: k2). TypeRep a -> TypeRep b -> Maybe (a :~~: b) eqTypeRep a b | sameTypeRep a b = Just (unsafeCoerce HRefl) | otherwise = Nothing

Here again, the `unsafeCoerce HRefl`

is safe, because the two types really
are the same -- but the proof of that relies on the complex, trusted
implementation of `Typeable`

.

- (superseded) The "reflection trick", which takes advantage of the fact that in
`class C a where { op :: ty }`

, we can safely coerce between`C a`

and`ty`

(which have different kinds!) because it's really just a newtype. Note: there is*no guarantee, at all*that this behavior will be supported into perpetuity. It is now preferred to use`withDict`

in`GHC.Magic.Dict`

, which is type-safe. See Note [withDict] in GHC.Tc.Instance.Class for details. - (superseded) Casting between two types which have exactly the same structure:
between a newtype of T and T, or between types which differ only
in "phantom" type parameters.
It is now preferred to use
`coerce`

from`Data.Coerce`

, which is type-safe.

Other uses of `unsafeCoerce`

are undefined. In particular, you should not use
`unsafeCoerce`

to cast a T to an algebraic data type D, unless T is also
an algebraic data type. For example, do not cast

to `Int`

->`Int`

`Bool`

, even if
you later cast that `Bool`

back to

before applying it. The reasons
have to do with GHC's internal representation details (for the cognoscenti, data values
can be entered but function closures cannot). If you want a safe type to cast things
to, use `Int`

->`Int`

`Any`

, which is not an algebraic data type.

unsafeCoerceUnlifted :: forall (a :: UnliftedType) (b :: UnliftedType). a -> b Source #

unsafeEqualityProof :: forall {k} (a :: k) (b :: k). UnsafeEquality a b Source #

data UnsafeEquality (a :: k) (b :: k) where Source #

This type is treated magically within GHC. Any pattern match of the
form `case unsafeEqualityProof of UnsafeRefl -> body`

gets transformed just into `body`

.
This is ill-typed, but the transformation takes place after type-checking is
complete. It is used to implement `unsafeCoerce`

. You probably don't want to
use `UnsafeRefl`

in an expression, but you might conceivably want to pattern-match
on it. Use `unsafeEqualityProof`

to create one of these.

UnsafeRefl :: forall {k} (a :: k). UnsafeEquality a a |

unsafeCoerce# :: a -> b Source #

Highly, terribly dangerous coercion from one representation type to another. Misuse of this function can invite the garbage collector to trounce upon your data and then laugh in your face. You don't want this function. Really.

This becomes more obvious when looking at its actual type:
`forall (r1 :: RuntimeRep) (r2 :: RuntimeRep) (a :: TYPE r1) (b :: TYPE r2). a -> b`

Which often get's rendered as `a -> b`

in haddock for technical reasons.