[Haskell-cafe] Safe Haskell at the export symbol granularity?

Ryan Newton rrnewton at gmail.com
Mon May 14 17:18:20 CEST 2012


Separate from whether or not we actually want this -- is it feasible?

Here's my situation.  When working on parallel programming libraries in
Haskell there are very often unsafe operations one wants to do within an
otherwise pure model.  For example, Accelerate currently violates safe
haskell because it trusts the user to provide an associative function to
parallel "fold".  No associativity, no referential transparency.

The solution is to put fold in a separate namespace and mark that module as
Unsafe.  Likewise for certain monad-par operations that are unsafe.  But
this factoring can have a serious impact.  Not only are extra modules
required, but extra type classes as well.  For example, if Accelerate is
ever refactored for "Safe Haskell" then the following ParAccelerate type
class probably should be as well:

https://github.com/simonmar/monad-par/blob/5cc656bc45dc473d7a185ec99bb156192f54d520/abstract-par-accelerate/Control/Monad/Par/Accelerate.hs#L75

I.e. ParAccelerate & ParAccelerateUnsafe for the "unsafeHybrid" operation.

But this starts to be death by a thousand organizational factorings!

   - The package, abstract-par-accelerate, is already factored out from
   abstract-par just to avoid an unnecessary Accelerate dependency (which
   used to mean CUDA errors).  (And *another* factoring is possibly warranted
   for whether or not the module depends on accelerate-io.)
   - The file would be separate to mark it as Safe Haskell.
   - The type class ParAccelerateUnsafe would be separate so as to put it
   in a separate file.

What's a possible solution?  If, in addition to "Safe" and "Unsafe"
modules, there were "Partially Safe" modules, which exported a mix of safe
and unsafe identifiers, then this could all be much cleaner.

The simple rule is that any reference whatsoever to an unsafe identifier
disqualifies the client code.  For example, in the above ParAccelerate type
class we would mark the unsafeHybrid binding with something like {-# UNSAFE
unsafeHybrid #-}.  We wouldn't even have to factor it out of the type class.

Likewise, Accelerate could mark "fold" as unsafe (providing safe variants
as well) without introducing module namespace bloat and confusion.

What do you think?

   -Ryan
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://www.haskell.org/pipermail/haskell-cafe/attachments/20120514/6cc6b97c/attachment.htm>


More information about the Haskell-Cafe mailing list