Brandon Simmons | 15 Dec 22:21 2014
Picon

Behavior of touch#

The `primitive` package exports a lifted version of the undocumented `touch#`

    http://hackage.haskell.org/package/ghc-prim-0.3.1.0/docs/GHC-Prim.html

which has type:

    touch :: PrimMonad m => a -> m ()

I'd like to know if this works correctly in general, or will it suffer
from the same gotches w/r/t unboxing as with addFinalizer and Weak
references? i.e. must it only be passed an unboxed type?

Brandon
Evan Laforge | 4 Dec 19:50 2014
Picon

confusing type error

I recently got a confusing error msg, and reduced it to a small case:

f1 :: Monad m => m Bool
f1 = f2 0 0 'a'

f2 :: Monad m => Int -> Float -> m Bool
f2 = undefined

From this, it's clear that f2 is being given an extra Char argument it
didn't ask for.  However, the error msg (ghc 7.8.3) is:

    Couldn't match type ‘m Bool’ with ‘Bool’
    Expected type: Char -> m Bool
      Actual type: Char -> Bool
    Relevant bindings include f1 :: m Bool (bound at Bug.hs:4:1)
    The function ‘f2’ is applied to three arguments,
    but its type ‘Int -> Float -> Char -> Bool’ has only three
    In the expression: f2 0 0 'a'
    In an equation for ‘f1’: f1 = f2 0 0 'a'

The confusing part is that 'f2' was applied to three arguments, but
it's type has only three.  It includes the Char in expected and actual
types, and implies that the type of 'f2' includes the Char.  So I took
quite a while to realize that the type of 'f2' in fact *didn't* expect
a Char (and had an 'm'), so that the "but its type" is *not* in fact
its declared type.

I suppose it infers a type for 'f2' based on its use, and that then
becomes the "actual" type, but it seems less confusing if it picked
the declared type of 'f2' as its actual type.  Perhaps this is working
(Continue reading)

Brandon Simmons | 25 Nov 21:24 2014
Picon

Defining a custom newByteArray primop that uses calloc?

In my tests, using calloc from:

    https://hackage.haskell.org/package/missing-foreign-0.1.1/docs/Foreign-Marshal-MissingAlloc.html

was about twice as fast as allocating and zeroing the same amount of
memory with `newByteArray` + any of `copy/set/fillMutableByteArray`
(all three were nearly identical). Is there a way I can reasonably
define my own `newByteArray` that uses calloc?

FWIW here are a couple of the benchmarks I'm working with in criterion:

    arrTestSet :: Int -> IO ()
    arrTestSet len = do
        let eBytes = (P.sizeOf (undefined::Int))*len
        a <- P.newAlignedPinnedByteArray
                    eBytes
                    (P.alignment (undefined :: Int))
        void $ P.setByteArray a 0 len (1::Int)

    arrTestCallocAndWrite :: Int -> IO ()
    arrTestCallocAndWrite len = do
        ptr <- callocBytes (len*(P.sizeOf(undefined::Int))) :: IO (Ptr Int)
        pokeElemOff ptr 0 1
        free ptr

Thanks,
Brandon
Austin Seipp | 25 Nov 20:46 2014

ANNOUNCE: GHC 7.8.4 Release Candidate 1

We are pleased to announce the first release candidate for GHC 7.8.4:

    https://downloads.haskell.org/~ghc/7.8.4-rc1/

This includes the source tarball and bindists for 64bit Linux. Binary
builds for other platforms will be available shortly. These binaries
and tarballs have an accompanying SHA256SUMS file signed by my GPG key
id (0x3B58D86F).

We plan to make the 7.8.4 release sometime in the next few weeks.

Please test as much as possible; bugs are much cheaper if we find them
before the release!

--

-- 
Regards,

Austin Seipp, Haskell Consultant
Well-Typed LLP, http://www.well-typed.com/
Lars Hupel | 25 Nov 10:36 2014

Discovery of source dependencies without --make

(cross-posted from [haskell-cafe])

Hi,

I've got a problem in our – admittedly complex – build process. We're
running an automated grading system for student-submitted homework
exercises. The compilation proceeds in stages:

1) Compile a library file, marked as trustworthy
2) Compile student submissions using Safe Haskell, able to access a
whitelisted set of packages and the previously compiled library files
3) Compile the test suite
4) Link everything together into an executable

The invocation is similar to this:

ghc -c -outputdir "$OUT"          -XTrustworthy Library.hs
ghc -c -outputdir "$OUT" -i"$OUT" -XSafe "$SUBMISSION"
ghc -c -outputdir "$OUT" -i"$OUT" Test_Suite.hs
ghc    -outputdir "$OUT" -i"$OUT" -o "$OUT/runner"

The second stage works well under the assumption that there's just one
single submitted file. If there's more than one, I need to specify them
in topological order wrt their module dependencies. Consider two simple
modules:

A.hs
> module A where
>
> import B
(Continue reading)

Bas van Dijk | 25 Nov 08:51 2014
Picon

Proving properties of type-level natural numbers obtained from user input

Hi,

I have another type-level programming related question:

> {-# LANGUAGE GADTs #-}
> {-# LANGUAGE TypeOperators #-}
> {-# LANGUAGE ScopedTypeVariables #-}
> {-# LANGUAGE KindSignatures #-}
>
> import GHC.TypeLits

Say I have a Proxy p of some type-level natural number:

> p :: forall (n :: Nat). Proxy n
> p = Proxy

Imagine I get p from user input like this:

> main :: IO ()
> main = do
>     [arg] <- getArgs
>     let n = read arg :: Integer
>
>     case someNatVal n of
>       Nothing -> error "Input is not a natural number!"
>       Just (SomeNat (p :: Proxy n)) -> ...

I also have a function f which takes a proxy of a natural number but
it has the additional constraint that the number should be lesser than
or equal to 255:
(Continue reading)

Dr. ÉRDI Gergő | 21 Nov 09:21 2014
Picon

Re: Type-level Replicate function

I've replaced the definition of Replicate with a closed type family, and now isNull typechecks on 7.8.2:

type family Replicate (n :: Nat) t : [*] where
  Replicate 0 t = '[]
  Replicate n t = t ': Replicate (n-1) t

On Nov 21, 2014 3:52 PM, "Bas van Dijk" <v.dijk.bas <at> gmail.com> wrote:
Hi,

tl;dr
How do I implement a type-level Replicate function that takes a (n ::
Nat) and a type e and produces a type-level list of n e elements.

The rest of my email gives some background on why I need this, how
it's supposed to be used and my current erroneous implementation. I'm
presenting it as a Haskell program:

{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE DataKinds #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE UndecidableInstances #-}
{-# LANGUAGE GADTs #-}

import GHC.TypeLits
import Data.Type.Equality
import Data.Type.Bool

-- For work I'm implementing a binary protocol for
-- communicating with some device. I need to be able to send
-- a packet of orders to a device.
--
-- An order is a list of addresses and command to send to
-- these addresses.
--
-- After sending the packets of orders the device should
-- send back a packet of replies. The packet of replies
-- should have a reply for each command send to each
-- address.
--
-- I would like to make the latter requirement apparent in
-- the types so that when I send a packet of orders the type
-- will tell me what packet of replies to expect.
--
-- So I introduce the OrderPacket type which is
-- parameterised with a type-level lists of commands:
data OrderPacket (cmds :: [*]) where

    -- The empty packet:
    NoOrders :: OrderPacket '[]

    -- Extending an existing packet with an order.
    --
    -- The (n :: Nat) in Order denotes the number of
    -- addresses to send the command to. Note that because I
    -- expect n command replies back I need to create a
    -- type-level list of n commands and prepend that to the
    -- existing commands:
    (:>) :: !(Order n command)
         -> !(OrderPacket commands)
         -> OrderPacket (Replicate n command :++: commands)

-- As explained, an Order is a vector of addresses of length
-- n paired with a command:
data Order (n :: Nat) command where
    Order :: (Command command)
          => !(Addresses n)
          -> !command
          -> Order n command

-- In my real implementation this class describes how to
-- encode / decode commands:
class Command command

-- This is the typical Vector of length n type specialised
-- to Address:
data Addresses (n :: Nat) where
    Nil   :: Addresses 0
    (:*:) :: !Address -> !(Addresses n) -> Addresses (n+1)

infixr 5 :*:

type Address = Int

-- Append two type-level lists.
type family (rs1 :: [*]) :++: (rs2 :: [*]) :: [*]

type instance '[]        :++: rs2 = rs2
type instance (r ': rs1) :++: rs2 = r ': (rs1 :++: rs2)


-- I'm currently using the following Replicate type-level
-- function:
type family Replicate (n :: Nat) r :: [*]

type instance Replicate (n :: Nat) r =
    If (n == 0) '[] (r ': Replicate (n-1) r)

-- However when I write some code like the following:
isNull :: OrderPacket cmds -> Bool
isNull NoOrders                = True
isNull (orderMsg :> orderMsgs) = False

-- I get the following error:

src/TypeLevelReplicate.hs:49:9:
    Type function application stack overflow; size = 201
    Use -ftype-function-depth=N to increase stack size to N
      GHC.TypeLits.EqNat
        (((n-1)-1)-1)...) 0
      ~ (((n-1)-1)-1)...) == 0)
    In the pattern: orderMsg :> orderMsgs
    In an equation for ‘isNull’:
      isNull (orderMsg :> orderMsgs) = True
Failed, modules loaded: none.

-- Note that when I adapt my code to use my own type-level
-- inductive implementation of natural numbers like:

data N = Z | S N

type family Replicate (n :: N) r :: [*]

type instance Replicate Z     r = '[]
type instance Replicate (S n) r = r ': Replicate n r

-- I don't get the type function application stack overflow.

Any hints on how to make this work with Nats from GHC.TypeLits?

Thanks,

Bas
_______________________________________________
Glasgow-haskell-users mailing list
Glasgow-haskell-users <at> haskell.org
http://www.haskell.org/mailman/listinfo/glasgow-haskell-users
_______________________________________________
Glasgow-haskell-users mailing list
Glasgow-haskell-users <at> haskell.org
http://www.haskell.org/mailman/listinfo/glasgow-haskell-users
Bas van Dijk | 21 Nov 08:51 2014
Picon

Type-level Replicate function

Hi,

tl;dr
How do I implement a type-level Replicate function that takes a (n ::
Nat) and a type e and produces a type-level list of n e elements.

The rest of my email gives some background on why I need this, how
it's supposed to be used and my current erroneous implementation. I'm
presenting it as a Haskell program:

{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE DataKinds #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE UndecidableInstances #-}
{-# LANGUAGE GADTs #-}

import GHC.TypeLits
import Data.Type.Equality
import Data.Type.Bool

-- For work I'm implementing a binary protocol for
-- communicating with some device. I need to be able to send
-- a packet of orders to a device.
--
-- An order is a list of addresses and command to send to
-- these addresses.
--
-- After sending the packets of orders the device should
-- send back a packet of replies. The packet of replies
-- should have a reply for each command send to each
-- address.
--
-- I would like to make the latter requirement apparent in
-- the types so that when I send a packet of orders the type
-- will tell me what packet of replies to expect.
--
-- So I introduce the OrderPacket type which is
-- parameterised with a type-level lists of commands:
data OrderPacket (cmds :: [*]) where

    -- The empty packet:
    NoOrders :: OrderPacket '[]

    -- Extending an existing packet with an order.
    --
    -- The (n :: Nat) in Order denotes the number of
    -- addresses to send the command to. Note that because I
    -- expect n command replies back I need to create a
    -- type-level list of n commands and prepend that to the
    -- existing commands:
    (:>) :: !(Order n command)
         -> !(OrderPacket commands)
         -> OrderPacket (Replicate n command :++: commands)

-- As explained, an Order is a vector of addresses of length
-- n paired with a command:
data Order (n :: Nat) command where
    Order :: (Command command)
          => !(Addresses n)
          -> !command
          -> Order n command

-- In my real implementation this class describes how to
-- encode / decode commands:
class Command command

-- This is the typical Vector of length n type specialised
-- to Address:
data Addresses (n :: Nat) where
    Nil   :: Addresses 0
    (:*:) :: !Address -> !(Addresses n) -> Addresses (n+1)

infixr 5 :*:

type Address = Int

-- Append two type-level lists.
type family (rs1 :: [*]) :++: (rs2 :: [*]) :: [*]

type instance '[]        :++: rs2 = rs2
type instance (r ': rs1) :++: rs2 = r ': (rs1 :++: rs2)

-- I'm currently using the following Replicate type-level
-- function:
type family Replicate (n :: Nat) r :: [*]

type instance Replicate (n :: Nat) r =
    If (n == 0) '[] (r ': Replicate (n-1) r)

-- However when I write some code like the following:
isNull :: OrderPacket cmds -> Bool
isNull NoOrders                = True
isNull (orderMsg :> orderMsgs) = False

-- I get the following error:

src/TypeLevelReplicate.hs:49:9:
    Type function application stack overflow; size = 201
    Use -ftype-function-depth=N to increase stack size to N
      GHC.TypeLits.EqNat
        (((n-1)-1)-1)...) 0
      ~ (((n-1)-1)-1)...) == 0)
    In the pattern: orderMsg :> orderMsgs
    In an equation for ‘isNull’:
      isNull (orderMsg :> orderMsgs) = True
Failed, modules loaded: none.

-- Note that when I adapt my code to use my own type-level
-- inductive implementation of natural numbers like:

data N = Z | S N

type family Replicate (n :: N) r :: [*]

type instance Replicate Z     r = '[]
type instance Replicate (S n) r = r ': Replicate n r

-- I don't get the type function application stack overflow.

Any hints on how to make this work with Nats from GHC.TypeLits?

Thanks,

Bas
_______________________________________________
Glasgow-haskell-users mailing list
Glasgow-haskell-users <at> haskell.org
http://www.haskell.org/mailman/listinfo/glasgow-haskell-users
Austin Seipp | 18 Nov 17:07 2014

RE: The future of the Haskell98 and Haskell2010 packages

Hello all,

A few weeks ago, I opened up a discussion about a particular GHC bug, #9590.

This bug is concerned with the future of the Haskell98 and Haskell2010
packages, which try to embody their two respective Haskell standards.
They do this by shipping the 'exact library specification' that the
standards have.

In our discussion this past week between me, SimonM, SPJ, Herbert and
Mikolaj, we came to this discussion again since the 7.10 STABLE freeze
is almost here, and it seems to have puttered out.

In this discussion, we came to the conclusion we think these packages
should be removed from GHC for the 7.10 release. To be clear, this was
not a 100% unanimous decision or formal vote; SimonM and I supported
removal, while everyone else seemed to be rather undecided or
ambivalent.

Most of the proposed alternative solutions seemed somewhat one-off.
Furthermore, we didn't find a solution that wouldn't either A) require
some amount of GHC modifications (possibly indefinitely into the
future) to support these packages, or B) changing the definitions in
these packages to deviate from the standard.

Instead, we proposed that we instead overhaul part of the GHC users
manual, and clearly outline our deviations from the Haskell 2010
standard library.

To be clear: GHC can still typecheck, compile, and efficiently execute
Haskell 2010 code. It is merely the distribution of compatible
packages that has put us in something of a bind.

Furthermore, we aren't aware of any other compilers/platforms like
ours that try to maintain such stringent separation of these packages,
and furthermore, both of the haskell{98,2010} packages have a fairly
small number of reverse dependencies.

I'd like to hear what people think about this. It seems likely I will
move forward on this by the end of the week unless we face very strong
opposition to this idea, or someone is willing to fix #9590 somehow
for us.

--

-- 
Regards,

Austin Seipp, Haskell Consultant
Well-Typed LLP, http://www.well-typed.com/
Merijn Verstraaten | 14 Nov 05:22 2014
Picon

More flexible literate Haskell extensions (Trac #9789), summary on wiki

As requested on my ticket I summarised the entire proposal on the wiki here: https://ghc.haskell.org/trac/ghc/wiki/FlexibleLiterateExtension

I don't expect a lot of disagreement on discussion, aside from minor bike shedding on the flavour of the
extension. I've started implementing this already. I'm open to bikesheds on exact extension, as it
shouldn't affect the implementation.

Unless there's any vehement objections, I'll produce a diff on fabricator asap.

Cheers,
Merijn
Wolfgang Jeltsch | 13 Nov 20:02 2014

Under what conditions are finalizers not run?

Hi,

the documentation of System.Mem.Weak under

    <http://hackage.haskell.org/package/base-4.7.0.1/docs/System-Mem-Weak.html>

says the following:

> It is not guaranteed that a finalizer will eventually run, and no
> attempt is made to run outstanding finalizers when the program exits.

In which situations are finalizers not run? I see that they might not be
run when the program ends while the weak pointer is still alive, but are
there also other situations? The above quote seems to say that even an
implementation that ignores any finalizers would conform to the API
specification.

I think it is actually quite bad if you do not have any guarantees about
when finalizers are run. In the memo table example, for instance, this
would mean that the memo table could grow very large, which would not
just result in bad space complexity, but also bad time complexity for
lookups.

I am actually particularly interested in adding finalizers to IORefs.
Are there any stronger guarantees for finalizers attached to IORefs and
MVars?

All the best,
Wolfgang

Gmane