box-tuples (empty) → 0.1.0.0
raw patch · 4 files changed
+235/−0 lines, 4 filesdep +basedep +ghc-primsetup-changed
Dependencies added: base, ghc-prim
Files
- LICENSE +20/−0
- Setup.hs +2/−0
- box-tuples.cabal +27/−0
- src/Data/Tuple/Unboxed.hs +186/−0
+ LICENSE view
@@ -0,0 +1,20 @@+Copyright (c) 2016 mniip++Permission is hereby granted, free of charge, to any person obtaining+a copy of this software and associated documentation files (the+"Software"), to deal in the Software without restriction, including+without limitation the rights to use, copy, modify, merge, publish,+distribute, sublicense, and/or sell copies of the Software, and to+permit persons to whom the Software is furnished to do so, subject to+the following conditions:++The above copyright notice and this permission notice shall be included+in all copies or substantial portions of the Software.++THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,+EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF+MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.+IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY+CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,+TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE+SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
+ Setup.hs view
@@ -0,0 +1,2 @@+import Distribution.Simple+main = defaultMain
+ box-tuples.cabal view
@@ -0,0 +1,27 @@+-- Initial box-tuples.cabal generated by cabal init. For further +-- documentation, see http://haskell.org/cabal/users-guide/++name: box-tuples+version: 0.1.0.0+synopsis: A hack to use GHC.Prim primitives in GHCi+description: As of now, the GHCi interactive runtime is incapable of working on unboxed+ tuples. In particular, it is unable to fully apply any function returning an+ unboxed tuple, create a function that takes a non-nullary unboxed tuple as+ argument, or pass a non-nullary tuple to some other function. The usual+ solution is to enable object code generation with @-fobject-code@. This+ package serves as a workaround for the cases where @-fobject-code@ is+ undesiable.++license: MIT+license-file: LICENSE+author: mniip+maintainer: mniip@mniip.com+category: GHC, Debug+build-type: Simple+cabal-version: >=1.10++library+ exposed-modules: Data.Tuple.Unboxed+ build-depends: base == 4.*, ghc-prim+ hs-source-dirs: src+ default-language: Haskell2010
+ src/Data/Tuple/Unboxed.hs view
@@ -0,0 +1,186 @@+{-# LANGUAGE UnboxedTuples, MagicHash #-}+-------------------------------------------------------------------------------+-- |+-- Module : Data.Tuple.Unboxed+-- Copyright : (C) 2016 mniip+-- License : MIT+-- Maintainer : mniip <mniip@mniip.com>+-- Stability : experimental+-- Portability : non-portable+--+-- As of now, the GHCi interactive runtime is incapable of working on unboxed+-- tuples. In particular, it is unable to fully apply any function returning an+-- unboxed tuple, create a function that takes a non-nullary unboxed tuple as+-- argument, or pass a non-nullary tuple to some other function. The usual+-- solution is to enable object code generation with @-fobject-code@. This+-- module serves as a workaround for the cases where @-fobject-code@ is+-- undesiable.+--+-- Due to the aforementioned restrictions on operations on unboxed tuples, we+-- can't simply expose operations of type @(\# a, b \#) -> (a, b)@. We have to+-- provide operations for working on functions of type @a -> (\# b, c \#)@.+--+-- More often than not, the types in unboxed tuples are themselves unboxed.+-- There are two major issues with this: 1) we cannot use @(,)@ and 2) we have to+-- provide different functions for different combinations of types. It is also+-- worth mentioning that the 'a' above can also be unboxed and therefore cannot+-- be quantified either.+--+-- This module provides a class of @compose@ functions of type+--+-- > composeA#BC :: (a -> (# b, c, ... #)) -> a -> (b -> c -> ... -> r) -> r+--+-- Where @A@ is the function argument type 'a', @#@ is number of fields in the+-- tuple, and @BC@ are the tupled types 'b', 'c', ...+-- +-- The key for type names is as follows:+--+-- * _ = @forall (a :: *). a@ (regular lifted type)+-- * a = 'Array#'+-- * Aa = 'ArrayArray#'+-- * b = 'ByteArray#'+-- * c = 'Char#'+-- * d = 'Double#'+-- * f = 'Float#'+-- * i = 'Int#'+-- * Ma = 'MutableArray#'+-- * MAa = 'MutableArrayArray#'+-- * Mb = 'MutableByteArray#'+-- * Mv = 'MVar#'+-- * o = 'BCO#'+-- * p = 'Addr#'+-- * s = 'State#'+-- * Sa = 'SmallArray#'+-- * SMa = 'SmallMutableArray#'+-- * Sn = 'StableName#'+-- * Sp = 'StablePtr#'+-- * t = 'ThreadId#'+-- * Tv = 'TVar#'+-- * v = 'MutVar#'+-- * w = 'Word#'+-- * Wp = 'Weak#'+--+-- This module contains functions for all combinations of types that come up in+-- "GHC.Prim" but in principle other cases could be added too.+-------------------------------------------------------------------------------+module Data.Tuple.Unboxed+ (+ composea1_,+ composei1_,+ composeo1_,+ composed2ii,+ composef2ii,+ composei2i_,+ composei2ii,+ composes2s_,+ composes2sa,+ composes2sAa,+ composes2sb,+ composes2sc,+ composes2sd,+ composes2sf,+ composes2si,+ composes2sSa,+ composes2sSMa,+ composes2sSn,+ composes2sSp,+ composes2sMa,+ composes2sMAa,+ composes2sMb,+ composes2sMv,+ composes2so,+ composes2sp,+ composes2st,+ composes2sTv,+ composes2sv,+ composes2sw,+ composes2sWp,+ composew2ww,+ compose_3pab,+ composes3si_,+ composed4iwwi,+ composes4siii,+ decomposes2s_+ )+ where++import GHC.Prim++composea1_ :: (Addr# -> (# a #)) -> Addr# -> (a -> r) -> r+composei1_ :: (Int# -> (# a #)) -> Int# -> (a -> r) -> r+composeo1_ :: (BCO# -> (# a #)) -> BCO# -> (a -> r) -> r+composed2ii :: (Double# -> (# Int#, Int# #)) -> Double# -> (Int# -> Int# -> r) -> r+composef2ii :: (Float# -> (# Int#, Int# #)) -> Float# -> (Int# -> Int# -> r) -> r+composei2i_ :: (Int# -> (# Int#, a #)) -> Int# -> (Int# -> a -> r) -> r+composei2ii :: (Int# -> (# Int#, Int# #)) -> Int# -> (Int# -> Int# -> r) -> r+composes2s_ :: (State# s -> (# State# t, a #)) -> State# s -> (State# t -> a -> r) -> r+composes2sa :: (State# s -> (# State# t, Array# a #)) -> State# s -> (State# t -> Array# a -> r) -> r+composes2sAa :: (State# s -> (# State# t, ArrayArray# #)) -> State# s -> (State# t -> ArrayArray# -> r) -> r+composes2sb :: (State# s -> (# State# t, ByteArray# #)) -> State# s -> (State# t -> ByteArray# -> r) -> r+composes2sc :: (State# s -> (# State# t, Char# #)) -> State# s -> (State# t -> Char# -> r) -> r+composes2sd :: (State# s -> (# State# t, Double# #)) -> State# s -> (State# t -> Double# -> r) -> r+composes2sf :: (State# s -> (# State# t, Float# #)) -> State# s -> (State# t -> Float# -> r) -> r+composes2si :: (State# s -> (# State# t, Int# #)) -> State# s -> (State# t -> Int# -> r) -> r+composes2sSa :: (State# s -> (# State# t, SmallArray# a #)) -> State# s -> (State# t -> SmallArray# a -> r) -> r+composes2sSMa :: (State# s -> (# State# t, SmallMutableArray# u a #)) -> State# s -> (State# t -> SmallMutableArray# u a -> r) -> r+composes2sSn :: (State# s -> (# State# t, StableName# a #)) -> State# s -> (State# t -> StableName# a -> r) -> r+composes2sSp :: (State# s -> (# State# t, StablePtr# a #)) -> State# s -> (State# t -> StablePtr# a -> r) -> r+composes2sMa :: (State# s -> (# State# t, MutableArray# u a #)) -> State# s -> (State# t -> MutableArray# u a -> r) -> r+composes2sMAa :: (State# s -> (# State# t, MutableArrayArray# u #)) -> State# s -> (State# t -> MutableArrayArray# u -> r) -> r+composes2sMb :: (State# s -> (# State# t, MutableByteArray# u #)) -> State# s -> (State# t -> MutableByteArray# u -> r) -> r+composes2sMv :: (State# s -> (# State# t, MVar# u a #)) -> State# s -> (State# t -> MVar# u a -> r) -> r+composes2so :: (State# s -> (# State# t, BCO# #)) -> State# s -> (State# t -> BCO# -> r) -> r+composes2sp :: (State# s -> (# State# t, Addr# #)) -> State# s -> (State# t -> Addr# -> r) -> r+composes2st :: (State# s -> (# State# t, ThreadId# #)) -> State# s -> (State# t -> ThreadId# -> r) -> r+composes2sTv :: (State# s -> (# State# t, TVar# u a #)) -> State# s -> (State# t -> TVar# u a -> r) -> r+composes2sv :: (State# s -> (# State# t, MutVar# u a #)) -> State# s -> (State# t -> MutVar# u a -> r) -> r+composes2sw :: (State# s -> (# State# t, Word# #)) -> State# s -> (State# t -> Word# -> r) -> r+composes2sWp :: (State# s -> (# State# t, Weak# a #)) -> State# s -> (State# t -> Weak# a -> r) -> r+composew2ww :: (Word# -> (# Word#, Word# #)) -> Word# -> (Word# -> Word# -> r) -> r+compose_3pab :: (a -> (# Addr#, Array# b, ByteArray# #)) -> a -> (Addr# -> Array# b -> ByteArray# -> r) -> r+composes3si_ :: (State# s -> (# State# t, Int#, a #)) -> State# s -> (State# t -> Int# -> a -> r) -> r+composed4iwwi :: (Double# -> (# Int#, Word#, Word#, Int# #)) -> Double# -> (Int# -> Word# -> Word# -> Int# -> r) -> r+composes4siii :: (State# s -> (# State# t, Int#, Int#, Int# #)) -> State# s -> (State# t -> Int# -> Int# -> Int# -> r) -> r+composea1_ p x f = case p x of (# a #) -> f a+composei1_ p x f = case p x of (# a #) -> f a+composeo1_ p x f = case p x of (# a #) -> f a+composed2ii p x f = case p x of (# a, b #) -> f a b+composef2ii p x f = case p x of (# a, b #) -> f a b+composei2i_ p x f = case p x of (# a, b #) -> f a b+composei2ii p x f = case p x of (# a, b #) -> f a b+composes2s_ p x f = case p x of (# a, b #) -> f a b+composes2sa p x f = case p x of (# a, b #) -> f a b+composes2sAa p x f = case p x of (# a, b #) -> f a b+composes2sb p x f = case p x of (# a, b #) -> f a b+composes2sc p x f = case p x of (# a, b #) -> f a b+composes2sd p x f = case p x of (# a, b #) -> f a b+composes2sf p x f = case p x of (# a, b #) -> f a b+composes2si p x f = case p x of (# a, b #) -> f a b+composes2sSa p x f = case p x of (# a, b #) -> f a b+composes2sSMa p x f = case p x of (# a, b #) -> f a b+composes2sSn p x f = case p x of (# a, b #) -> f a b+composes2sSp p x f = case p x of (# a, b #) -> f a b+composes2sMa p x f = case p x of (# a, b #) -> f a b+composes2sMAa p x f = case p x of (# a, b #) -> f a b+composes2sMb p x f = case p x of (# a, b #) -> f a b+composes2sMv p x f = case p x of (# a, b #) -> f a b+composes2so p x f = case p x of (# a, b #) -> f a b+composes2sp p x f = case p x of (# a, b #) -> f a b+composes2st p x f = case p x of (# a, b #) -> f a b+composes2sTv p x f = case p x of (# a, b #) -> f a b+composes2sv p x f = case p x of (# a, b #) -> f a b+composes2sw p x f = case p x of (# a, b #) -> f a b+composes2sWp p x f = case p x of (# a, b #) -> f a b+composew2ww p x f = case p x of (# a, b #) -> f a b+compose_3pab p x f = case p x of (# a, b, c #) -> f a b c+composes3si_ p x f = case p x of (# a, b, c #) -> f a b c+composed4iwwi p x f = case p x of (# a, b, c, d #) -> f a b c d+composes4siii p x f = case p x of (# a, b, c, d #) -> f a b c d++-- | This is an \"inverse\" of 'composes2s_' because sometimes it might be+-- useful to produce a @'State#' s a -> (\# 'State#' s, a \#)@ of your own.+-- Example:+-- +-- @returnIO x = 'IO' ('decomposes2s_' (\s r -> r s x))@+decomposes2s_ :: (State# s -> (State# s -> a -> (# State# s, a #)) -> (# State# s, a #)) -> State# s -> (# State# s, a #)+decomposes2s_ f x = f x (\a b -> (# a, b #))