edenskel (empty) → 1.1.0.0
raw patch · 13 files changed
+5192/−0 lines, 13 filesdep +basedep +edenmodulesdep +parallelsetup-changed
Dependencies added: base, edenmodules, parallel
Files
- Control/Parallel/Eden/EdenSkel/Auxiliary.hs +262/−0
- Control/Parallel/Eden/EdenSkel/DCSkels.hs +386/−0
- Control/Parallel/Eden/EdenSkel/IterSkels.hs +77/−0
- Control/Parallel/Eden/EdenSkel/MapRedSkels.hs +127/−0
- Control/Parallel/Eden/EdenSkel/MapSkels.hs +305/−0
- Control/Parallel/Eden/EdenSkel/TopoSkels.hs +254/−0
- Control/Parallel/Eden/EdenSkel/WPSkels.hs +727/−0
- LICENSE +10/−0
- Setup.hs +6/−0
- configure +2929/−0
- configure.ac +52/−0
- edenskel.buildinfo.in +1/−0
- edenskel.cabal +56/−0
+ Control/Parallel/Eden/EdenSkel/Auxiliary.hs view
@@ -0,0 +1,262 @@+{-# LANGUAGE CPP, ScopedTypeVariables #-}+-----------------------------------------------------------------------------+-- |+-- Module : Control.Parallel.Eden.EdenSkel.Auxiliary+-- Copyright : (c) Philipps Universitaet Marburg 2009-2012+-- License : BSD-style (see the file LICENSE)+-- +-- Maintainer : eden@mathematik.uni-marburg.de+-- Stability : beta+-- Portability : not portable+--+-- This Haskell module defines auxiliary functions for +-- programming with the parallel functional language Eden.+--+-- Depends on GHC. Using standard GHC, you will get a threaded simulation of Eden. +-- Use the forked GHC-Eden compiler from http:\/\/www.mathematik.uni-marburg.de/~eden +-- for a parallel build.+--+-- Eden Group ( http:\/\/www.mathematik.uni-marburg.de/~eden )+++#if defined(NOT_PARALLEL) +#warning !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!\+ Eden BUILD WITH CONCURRENT HASKELL SIMULATION OF PARALLEL PRIMITIVES, \+ DON'T EXPECT BIG SPEEDUPS! USE THE EDEN VERSION OF GHC FROM \+ http://www.mathematik.uni-marburg.de/~eden \+ FOR A PARALLEL BUILD \+ !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!'+#endif+module Control.Parallel.Eden.EdenSkel.Auxiliary ( + -- * Distribution and combine functions+ -- | ... of form: @ Int -> [a] -> [[a]] @ / @ [[a]] -> [a] @+ unshuffle, shuffle,+ splitIntoN, unSplit,+ chunk, unchunk,+ -- * Distribution function for workpools+ distribute,+ -- * Lazy functions+ lazy,+ lazy1ZipWith, lazy2ZipWith, + lazy1Zip, lazy2Zip,+ lazyTranspose,+ -- * other useful functions+ takeEach, transposeRt,+ -- * unLiftRDs+ unLiftRD, unLiftRD2, unLiftRD3, unLiftRD4,+ -- * More predefined Parallel Actions+ spawnPss, fetch2, fetchRDss, mergeS+ ) where++import Data.List+import Data.Maybe(maybeToList,mapMaybe)+import Control.Concurrent+import System.IO.Unsafe(unsafePerformIO,unsafeInterleaveIO)+#if defined( __PARALLEL_HASKELL__ ) || defined (NOT_PARALLEL)+import Control.Parallel.Eden+#else+import Control.Parallel.Eden.EdenConcHs+#endif++-- | Round robin distribution - inverse to shuffle+-- +unshuffle :: Int -- ^number of sublists+ -> [a] -- ^input list+ -> [[a]] -- ^distributed output+unshuffle n xs = [takeEach n (drop i xs) | i <- [0..n-1]]++takeEach :: Int -> [a] -> [a] +takeEach n [] = []+takeEach n (x:xs) = x : takeEach n (drop (n-1) xs)+++-- | Simple shuffling - inverse to round robin distribution+shuffle :: [[a]] -- ^ sublists+ -> [a] -- ^ shuffled sublists+shuffle = concat . transpose++-- | transpose for matrices of rectangular shape (rows of equal length). Top level list of the resulting matrix is defined as soon as the first row of the original matrix is closed.+transposeRt :: [[a]] -> [[a]]+transposeRt [] = []+transposeRt ([] : xss) = [] -- originally transpose xss -- keeps top level list open until all rows are done+transposeRt ((x:xs) : xss) = (x : [h | (h:_) <- xss]) : transposeRt (xs : [ t | (_:t) <- xss])++-- | Block distribution, @ splitIntoN @ distributes one list on n lists with+-- equal distribution ((+-1) without precondition on length).+splitIntoN :: Int -- ^ number of blocks+ -> [a] -- ^list to be split+ -> [[a]] -- ^list of blocks+splitIntoN n xs = chunkBalance (l `div` n) (l `mod` n) xs where+ l = length xs+-- | Inverse function to @ splitIntoN @ - alias for concat.+unSplit :: [[a]] -- ^list of blocks+ -> [a] -- ^restored list+unSplit = concat++-- | Creates a list of chunks of length @ d @. The first @ m @ chunks will+-- contain an extra element. +--+-- Result: list of chunks (blocks)+chunkBalance :: Int -- ^@ d @: chunk-length+ -> Int -- ^@ m @: number of bigger blocks + -> [a] -- ^list to be split + -> [[a]] -- ^list of chunks (blocks)+chunkBalance d = chunk' where+ chunk' _ [] = []+ chunk' 0 xs = ys : chunk' 0 zs where+ (ys,zs) = splitAt d xs+ chunk' m xs = ys : chunk' (m-1) zs where+ (ys,zs) = splitAt (d+1) xs++-- | Creates a list of chunks of length @ d@ .+--+-- Result: list of chunks (blocks)+chunk :: Int -- ^@ d @: chunk-length+ -> [a] -- ^list to be split + -> [[a]] -- ^list of chunks (blocks)+chunk l = chunkBalance l 0++-- | Inverse function to @ chunk @ - alias for concat.+unchunk :: [[a]] -- ^list of chunks+ -> [a] -- ^restored list+unchunk = concat++-- | Task distribution according to worker requests.+--+distribute :: Int -- ^number of workers+ -> [Int] -- ^ request stream (worker IDs ranging from 0 to n-1)+ -> [t] -- ^ task list+ -> [[t]] -- ^ task distribution, each inner list for one worker+distribute np reqs tasks = [taskList reqs tasks n | n<-[0..np-1]]+ where taskList (r:rs) (t:ts) pe+ | pe == r = t:(taskList rs ts pe)+ | otherwise = taskList rs ts pe+ taskList _ _ _ = []+++++----------------------------Lazy Functions----------------------------+-- | A lazy list is an infinite stream+lazy :: [a] -> [a]+lazy ~(x:xs) = x : lazy xs++-- |lazy in first argument+lazy1ZipWith :: (a->b->c) -> [a] -> [b] -> [c]+lazy1ZipWith f xs = zipWith f (lazy xs)++-- |lazy in second argument+lazy2ZipWith :: (a->b->c) -> [a] -> [b] -> [c]+lazy2ZipWith f xs ys = zipWith f xs (lazy ys)++-- |lazy in first argument+lazy1Zip :: [a] -> [b] -> [(a,b)]+lazy1Zip xs ys = zip (lazy xs) ys++-- |lazy in second argument+lazy2Zip :: [a] -> [b] -> [(a,b)]+lazy2Zip xs ys = zip xs (lazy ys)++-- |lazy in tail lists+lazyTranspose :: [[a]] -> [[a]]+lazyTranspose = foldr (lazy2ZipWith (:)) (repeat [])++---------------------------unLiftRDs------------------------------+unLiftRD :: (Trans a, Trans b) =>+ (RD a -> RD b) -- ^ Function to be unlifted+ -> a -- ^ input+ -> b -- ^ output+unLiftRD f = fetch . f . release++-- | see @liftRD@+unLiftRD2 :: (Trans a, Trans b, Trans c) + => (RD a -> RD b -> RD c) -- ^ Function to be unlifted+ -> a -- ^ First input+ -> b -- ^ Second input+ -> c -- ^ output+unLiftRD2 f x = unLiftRD (f (release x)) ++-- | see @liftRD@+unLiftRD3 :: (Trans a, Trans b, Trans c, Trans d) => (RD a -> RD b -> RD c -> RD d) -> a -> b -> c -> d+unLiftRD3 f x = unLiftRD2 (f (release x)) ++-- | see @liftRD@+unLiftRD4 :: (Trans a, Trans b, Trans c, Trans d, Trans e) => (RD a -> RD b -> RD c -> RD d -> RD e) -> a -> b -> c -> d -> e+unLiftRD4 f x = unLiftRD3 (f (release x)) ++---------------------------Parallel Actions---------------------------------+-- | Spawn a matrix of processes+spawnPss :: (Trans a, Trans b) => [[Process a b]] -> [[a]] -> [[b]]+spawnPss pss xss = runPA $ sequence $ zipWith3 (\is ps xs -> sequence (zipWith3 instantiateAt is ps xs)) iss pss xss where+ iss = (unshuffle (length (zip pss xss)) [selfPe+1..])++-- | Fetch two Remote Data values+fetch2 :: (Trans a, Trans b) => RD a -> RD b -> (a,b)+fetch2 a b = runPA $+ do a' <- fetchPA a+ b' <- fetchPA b+ return (a',b')+-- | Fetch a matrix of Remote Data+fetchRDss :: Trans a => [[RD a]] -> [[a]]+fetchRDss rda = runPA $ mapM (mapM fetchPA) rda++--------------------merge variant mergeS-----------------+-- | A variant of non-deterministic list merging, which applies a strategy to list elements prior to merging them and stops the additional merge thread (the suckIO_S thread) when only one input stream is left.+mergeS:: [[a]] -> Strategy a -> [a]+mergeS l st = unsafePerformIO (nmergeIO_S l st)+++nmergeIO_S :: [[a]] -> Strategy a -> IO [a]+nmergeIO_S lss st+ = let+ len = length lss+ in+ newEmptyMVar >>= \ tail_node ->+ newMVar tail_node >>= \ tail_list ->+ newQSem max_buff_size >>= \ e ->+ newMVar len >>= \ branches_running ->+ let+ buff = (tail_list,e)+ in+ mapIO (\ x -> forkIO (suckIO_S branches_running buff x st)) lss >>+ takeMVar tail_node >>= \ val ->+ signalQSem e >>+ return val+ where+ mapIO f xs = sequence (map f xs)+ + +suckIO_S :: MVar Int -> Buffer a -> [a] -> Strategy a -> IO ()++suckIO_S branches_running buff@(tail_list,e) vs st+ = do count <- takeMVar branches_running+ if count == 1 then+ takeMVar tail_list >>= \ node ->+ putMVar node vs >>+ putMVar tail_list node+ else putMVar branches_running count >>+ case vs of+ [] -> takeMVar branches_running >>= \ val ->+ if val == 1 then+ takeMVar tail_list >>= \ node ->+ putMVar node [] >>+ putMVar tail_list node+ else + putMVar branches_running (val-1)+ (x:xs) ->+ (st x `seq` waitQSem e) >>+ takeMVar tail_list >>= \ node ->+ newEmptyMVar >>= \ next_node ->+ unsafeInterleaveIO (+ takeMVar next_node >>= \ y ->+ signalQSem e >>+ return y) >>= \ next_node_val ->+ putMVar node (x:next_node_val) >>+ putMVar tail_list next_node >>+ suckIO_S branches_running buff xs st++type Buffer a + = (MVar (MVar [a]), QSem)++max_buff_size :: Int+max_buff_size = 1
+ Control/Parallel/Eden/EdenSkel/DCSkels.hs view
@@ -0,0 +1,386 @@+{-# LANGUAGE CPP #-}+-----------------------------------------------------------------------------+-- |+-- Module : Control.Parallel.Eden.EdenSkel.DCSkels+-- Copyright : (c) Philipps Universitaet Marburg 2009-2012+-- License : BSD-style (see the file LICENSE)+-- +-- Maintainer : eden@mathematik.uni-marburg.de+-- Stability : beta+-- Portability : not portable+--+-- This Haskell module defines divide-and-conquer skeletons for +-- the parallel functional language Eden.+--+-- All divide-and-conquer algorithms are parameterised with control functions+-- which decide if a problem is trivial, how to solve a trivial problem, +-- how to split a non-trivial problem into smaller problems and how to combine solutions +-- of subproblems into a solution of the problem.+--+-- Depends on GHC. Using standard GHC, you will get a threaded simulation of Eden. +-- Use the forked GHC-Eden compiler from http:\/\/www.mathematik.uni-marburg.de/~eden +-- for a parallel build.+--+-- Eden Group ( http:\/\/www.mathematik.uni-marburg.de/~eden )+--++module Control.Parallel.Eden.EdenSkel.DCSkels (+ -- * Divide-and-conquer scheme+ DivideConquer, DivideConquerSimple,+ -- * Sequential divide-and-conquer+ dc, + -- * Distributed expansion divide-and-conquer skeletons+ -- ** Straightforward implementation for arbitrary DC problems + parDC, + -- ** Divide-and-conquer skeleton for regular n-ary trees + disDC, offline_disDC, disDCdepth, disDCn, + -- * Flat expansion divide-and-conquer skeletons+ flatDC, ++ -- * Deprecated divide-and-conquer skeletons (legacy code)+ -- ** Deprecated sequential divide-and-conquer+ divConSeq, divConSeq_c,+ -- ** Deprecated straightforward implementations for arbitrary DC problems + divCon, divCon_c, divConD, divConD_c,+ -- ** Deprecated divide-and-conquer skeleton for regular n-ary trees + dcN, dcN_c, dcN', dcN_c', dcNTickets, dcNTickets_c,+ -- ** Deprecated flat expansion divide-and-conquer skeletons+ divConFlat, divConFlat_c + ) where+#if defined( __PARALLEL_HASKELL__ )+import Control.Parallel.Eden+#else+import Control.Parallel.Eden.EdenConcHs+#endif+import Control.Parallel.Eden.EdenSkel.MapSkels+import Control.Parallel.Eden.EdenSkel.Auxiliary++++-- Divide-and-conquer scheme+type DivideConquer a b+ = (a -> Bool) -- ^ trivial? + -> (a -> b) -- ^ solve+ -> (a -> [a]) -- ^ split+ -> (a -> [b] -> b) -- ^ combine+ -> a -- ^ input + -> b -- ^ result++-- | Sequential Version.+dc :: DivideConquer a b+dc trivial solve split combine = rec_dc+ where+ rec_dc x = if trivial x then solve x+ else combine x (map rec_dc (split x))+++-- | Simple parMap parallelisation with depth control but+-- no placement control. This variant allows to+-- give an additional depth parameter for the recursion, proceeding in a+-- sequential manner when @depth=0@. The process scheme unfolds the call +-- tree on processors chosen by the runtime environment. Round-Robin +-- distribution is unfavourable for this skeleton, better use RTS option +-- @+RTS -qrnd@ when using it.+parDC :: (Trans a, Trans b) + => Int -- ^ parallel depth+ -> DivideConquer a b+parDC lv trivial solve split combine+ = pdc lv+ where+ pdc lv x+ | lv == 0 = dc trivial solve split combine x+ | lv > 0 = if trivial x then solve x+ else combine x (parMap (pdc (lv-1)) (split x))+++-- | Distributed-expansion divide-and-conquer skeleton+-- (tutorial version, similar to dcNTickets).+disDC :: (Trans a, Trans b) + => Int -- ^ branching degree+ -> Places -- ^ tickets+ -> DivideConquer a b+disDC k tickets trivial solve split combine x+ = if null tickets then seqDC x+ else recDC tickets x+ where+ seqDC = dc trivial solve split combine+ recDC tickets x =+ if trivial x then solve x+ else childRes `pseq` -- explicit demand+ rdeepseq myRes `pseq` -- control+ combine x ( myRes:childRes ++ localRess )+ where+ -- child process generation+ childRes = spawnAt childTickets childProcs procIns+ childProcs = map (process . recDC) theirTs+ -- ticket distribution+ (childTickets, restTickets) = splitAt (k-1) tickets+ (myTs: theirTs) = unshuffle k restTickets+ -- input splitting+ (myIn:theirIn) = split x+ (procIns, localIns)+ = splitAt (length childTickets) theirIn+ -- local computations+ myRes = recDC myTs myIn+ localRess = map seqDC localIns++-- | offline distributed-expansion divide-and-conquer skeleton.+offline_disDC :: Trans b + => Int -- ^ branching degree+ -> [Int] -- ^ tickets+ -> DivideConquer a b+offline_disDC k ts triv solve split combine x+ = snd (disDC k ts newtriv newsolve newsplit newcombine 0)+ where+ seqDC = dc triv solve split combine+ newsplit = successors k+ newtriv n = length ts <= k^(length (path k n))+ newsolve n = (flag, seqDC localx)+ where (flag, localx) = select triv split x (path k n)+ newcombine n bs@((flag,bs1):_)+ = if flag then (True, combine localx (map snd bs))+ else (lab, bs1)+ where (lab, localx) = select triv split x (path k n)+++-- local selection function for offline distributed-expansion divide-and-conquer skeleton+select :: (a -> Bool) -> (a -> [a]) -- ^ trivial / split+ -> a -> [Int] -> (Bool,a)+select trivial split x ys = go x ys+ where go x [] = (True, x)+ go x (y:ys) = if trivial x then (False, x)+ else go (split x !! y) ys++-- auxiliary functions for offline distributed-expansion divide-and-conquer skeleton+successors :: Int -> Int -> [Int]+successors k n = [nk + i | let nk = n*k, i <- [1..k]]++path :: Int -> Int -> [Int]+path k n | n == 0 = []+ | otherwise = reverse (factors k n)++factors :: Int -> Int -> [Int]+factors k n+ | n <= 0 = []+ | otherwise = (n+k-1) `mod` k : factors k ((n-1) `div` k)+ +-- | DC skeleton with fixed branching degree, parallel depth control and explicit process +-- placement (tree-shaped process creation, one task in each recursive step stays local).+disDCdepth :: (Trans a, Trans b) + => Int -- ^ branching degree+ -> Int -- ^ parallel depth+ -> DivideConquer a b+disDCdepth k depth trivial solve split combine x + | depth < 1 = dc trivial solve split combine x+ | trivial x = solve x + | otherwise = childRs `seq` -- early demand on children list+ combine x (myR : childRs)+ where myself = disDCdepth k (depth - 1) trivial solve split combine+ (mine:rest) = split x+ myR = myself mine+ childRs = parMapAt places myself rest+ `using` seqList r0 -- ???+ -- placement with stride for next children, round-robin+ places = map ((+1) . (`mod` noPe) . (+(-1))) shifts+ shifts = map (selfPe +) [shift,2*shift..]+ shift = k ^ (depth -1)++-- | Like 'disDCdepth', but controls parallelism by limiting the number of processes instead of the parallel depth.+disDCn :: (Trans a, Trans b) + => Int -- ^ branching degree + -> Int -- ^ number of processes+ -> DivideConquer a b+disDCn k n = disDCdepth n depth+ where depth = logN k n++-- rounding-up log approximation+logN n 1 = 0+logN n k | k > 0 = 1 + logN n ((k + n-1) `div` n) -- round up+ | otherwise = error "logN"+ +-------------------------------Flat Expansion----------------------------------+-- | DC Skeleton with flat expansion of upper DC-tree levels, takes custom map +-- skeletons to solve expanded tasks (a sequential map skeleton leads to a +-- sequential DC-skeleton).+flatDC :: (Trans a,Trans b) => + ((a->b)->[a]->[b]) -- ^custom map implementation+ -> Int -- ^depth+ -> DivideConquer a b+flatDC myMap depth trivial solve split combine x+ = combineTopMaster combine levels results+ where (tasks,levels) = generateTasks depth trivial split x+ results = myMap(divConSeq_c trivial solve split combine) tasks++++combineTopMaster :: (NFData b) =>+ (a->[b]->b) -> (Tree a) -> [b] -> b+combineTopMaster c t bs = fst (combineTopRnf c t bs)+++combineTopRnf :: (NFData b) => + (a->[b]->b) -> (Tree a) -> [b] -> (b,[b])+combineTopRnf _ (Leaf a) (b:bs) = (b,bs)+combineTopRnf combine (Tree a ts) bs + = (rnf res `pseq` combine a res, bs')+ where (bs',res) = foldl f (bs,[]) ts+ f (olds,news) t = (remaining,news++[b]) + where (b,remaining) = combineTopRnf combine t olds+ ++generateTasks :: Int -> (a->Bool) -> (a->[a]) -> a -> ([a],Tree a)+generateTasks 0 _ _ a = ([a],Leaf a)+generateTasks n trivial split a+ | trivial a = ([a],Leaf a)+ | otherwise = (concat ass,Tree a ts)+ where assts = map (generateTasks (n-1) trivial split) (split a)+ (ass,ts) = unzip assts+++data Tree a = Tree a [Tree a] | Leaf a deriving Show+instance NFData a => NFData (Tree a)+ where rnf (Tree a ls) = rnf a `seq` rnf ls + rnf (Leaf a) = rnf a ++-----------------------------------DEPRECATED--------------------------------+-- | The simple interface (deprecated): combine function without input+type DivideConquerSimple a b+ = (a -> Bool) -- ^ trivial? + -> (a -> b) -- ^ solve+ -> (a -> [a]) -- ^ split+ -> ([b] -> b) -- ^ combine (only uses sub-results, not the input)+ -> a -- ^ input + -> b -- ^ result+++-- | Like 'dc' but uses simple DC Interface.+{-# DEPRECATED divConSeq, divConSeq_c "better use dc instead" #-}+divConSeq :: (Trans a, Trans b) => DivideConquerSimple a b+divConSeq trivial solve split combine x + = dc trivial solve split (\_ parts -> combine parts) x++-- | Same as 'dc'++divConSeq_c :: (Trans a, Trans b) => DivideConquer a b+divConSeq_c = dc+++-- | Straightforward implementation.+--+-- The straightforward method to parallelise divide-and-conquer+-- algorithms is to unfold the call tree onto different+-- processors. The process scheme unfolds the call tree on processors chosen by the+-- runtime environment. Round-Robin distribution is unfavourable for this+-- skeleton, better use runtime option @-qrnd@ when using it.+{-# DEPRECATED divCon, divCon_c, divConD, divConD_c "better use parDC instead" #-}+divCon :: (Trans a, Trans b) => DivideConquerSimple a b+divCon trivial solve split combine x + = divCon_c trivial solve split (\_ parts -> combine parts) x++-- | Like 'divCon' but with different combine signature (takes the original problem as additional input).+divCon_c :: (Trans a, Trans b) => DivideConquer a b+divCon_c trivial solve split combine x+ | trivial x = solve x+ | otherwise = combine x children+ where children = parMap (divCon_c trivial solve split combine) (split x) +++-- | Like 'parDC' but uses simple DC Interface.+divConD :: (Trans a, Trans b) + => Int -- ^parallel depth+ -> DivideConquerSimple a b+divConD depth trivial solve split combine x + = parDC depth trivial solve split (\_ parts -> combine parts) x++-- | Same as 'parDC'.+divConD_c :: (Trans a, Trans b) + => Int -- ^parallel depth+ -> DivideConquer a b+divConD_c = parDC++-- | Like 'disDCdepth' but uses simple DC Interface.+{-# DEPRECATED dcN, dcN_c "better use disDCdepth instead" #-}+dcN :: (Trans a, Trans b) + => Int -- ^ branching degree+ -> Int -- ^ parallel depth+ -> DivideConquerSimple a b+dcN n depth trivial solve split combine x + = disDCdepth n depth trivial solve split (\_ parts -> combine parts) x++-- | Same as 'disDCdepth'+dcN_c :: (Trans a, Trans b) + => Int -- ^ branching degree+ -> Int -- ^ parallel depth+ -> DivideConquer a b+dcN_c = disDCdepth++-- | Like 'disDCn' but uses simple DC Interface.+{-# DEPRECATED dcN', dcN_c' "better use disDCn instead" #-}+dcN' :: (Trans a, Trans b) + => Int -- ^ branching degree+ -> Int -- ^ number of processes+ -> DivideConquerSimple a b+dcN' n pes = dcN n depth+ where depth = logN n pes++-- | Same as 'disDCn'.+dcN_c' :: (Trans a, Trans b) + => Int -- ^ branching degree+ -> Int -- ^ number of processes+ -> DivideConquer a b+dcN_c' = disDCn++---------------------------------------------------------------+-- | Like 'disDC', but differs in demand control and uses simple DC Interface.+{-# DEPRECATED dcNTickets, dcNTickets_c "better use disDC instead" #-}+dcNTickets :: (Trans a, Trans b) => + Int -- ^ branching degree+ -> Places -- ^ tickets (places to use)+ -> DivideConquerSimple a b+dcNTickets k ts trivial solve split combine x + = dcNTickets_c k ts trivial solve split (\_ parts -> combine parts) x++-- | Like 'disDC', but differs in demand control.+dcNTickets_c :: (Trans a, Trans b) + => Int -- ^ branching degree+ -> Places -- ^ Tickets (places to use)+ -> DivideConquer a b+dcNTickets_c k [] trivial solve split combine x + = divConSeq_c trivial solve split combine x+dcNTickets_c k tickets trivial solve split combine x + = if trivial x then solve x + else childRes `pseq` -- early demand on children list+ rnf myRes `pseq` rnf localRess `pseq` + combine x (myRes:childRes ++ localRess )+ where+ -- splitting computation into processes+ (childTickets,restTickets) = splitAt (k-1) tickets --position of (children,further ancestors)+ (myTs:theirTs)= unshuffle k restTickets+ ticketF ts = dcNTickets_c k ts trivial solve split combine+ insts = length childTickets+ (procIns, localIns) = splitAt insts theirIn + childProcs = map (process . ticketF) theirTs + childRes = spawnAt childTickets childProcs procIns++ -- local computation:+ myRes = ticketF myTs myIn+ (myIn:theirIn) = split x+ localRess = map (divConSeq_c trivial solve split combine) localIns+++ +-- | Like as 'flatDC' but uses simple DC Interface.+{-# DEPRECATED divConFlat, divConFlat_c "better use flatDC instead" #-}+divConFlat :: (Trans a,Trans b) => + ((a->b)->[a]->[b]) -- ^custom map implementation+ -> Int -- ^depth+ -> DivideConquerSimple a b+divConFlat myMap depth trivial solve split combine x + = divConFlat_c myMap depth trivial solve split (\_ parts -> combine parts) x+ +-- | Tutorial version, same as 'flatDC'.+divConFlat_c :: (Trans a,Trans b) + => ((a->b)->[a]->[b]) -- ^ custom map implementation+ -> Int -- ^ parallel depth+ -> DivideConquer a b+divConFlat_c = flatDC
+ Control/Parallel/Eden/EdenSkel/IterSkels.hs view
@@ -0,0 +1,77 @@+{-# LANGUAGE CPP #-}+-----------------------------------------------------------------------------+-- |+-- Module : Control.Parallel.Eden.EdenSkel.MiscSkels+-- Copyright : (c) Philipps Universitaet Marburg 2009-2010+-- License : BSD-style (see the file LICENSE)+-- +-- Maintainer : eden@mathematik.uni-marburg.de+-- Stability : beta+-- Portability : not portable+--+-- This Haskell module defines iteration skeletons for Eden.+--+-- Depends on the Eden Compiler.+--+-- Eden Project+--+module Control.Parallel.Eden.EdenSkel.IterSkels ( + -- * Iteration Skeletons + iterUntilAt, iterUntil+ ) where+import Control.Parallel.Eden.EdenSkel.Auxiliary+import Control.Parallel.Eden.EdenSkel.MapSkels+#if defined( __PARALLEL_HASKELL__ ) || defined (NOT_PARALLEL)+import Control.Parallel.Eden+#else+import Control.Parallel.Eden.EdenConcHs+#endif++-- \cite{SkeletonBookChapter02}, code (c) Fernando Rubio+-- | The iterUntil skeleton is an iterated map skeleton. Each worker+-- function transforms one local worker state and one task per iteration.+-- The result is the next local state and the iterations+-- result, which is send back to the master. The master transforms the+-- output of all tasks of one iteration and a local master state into+-- the worker inputs of the next iteration and a new master state+-- using the combine function (output: Right tasks masterState) or+-- decides to terminate the iteration (output: Left result). The input+-- transformation function generates all initial worker states and+-- initial worker tasks and the initial master state from the skeleton.+iterUntil :: (Trans wl,Trans t, Trans sr) => + (inp -> ([wl],[t],ml)) -- ^input transformation function+ -> (wl -> t -> (sr,wl)) -- ^worker function+ -> (ml -> [sr] -> Either r ([t],ml)) -- ^combine function+ -> inp -- ^input+ -> r -- ^result+iterUntil = iterUntilAt [0]++-- | This is the basic implementation, using places for explicit process+-- | placement of the worker processes.+iterUntilAt :: (Trans wl,Trans t, Trans sr) => + Places -- ^where to instatiate+ -> (inp -> ([wl],[t],ml)) -- ^input transformation function+ -> (wl -> t -> (sr,wl)) -- ^worker function+ -> (ml -> [sr] -> Either r ([t],ml)) -- ^combine function+ -> inp -- ^input+ -> r -- ^result+iterUntilAt pids split wf comb x = result where + (result, moretaskss) = manager comb ml (lazyTranspose srss)+ srss = parMapAt pids (worker wf) (zip wlocals taskss)+ taskss = lazyTranspose (initials: moretaskss)+ (wlocals,initials,ml)= split x++-- master/manager functionality of the iterUntil skeleton+manager :: (ml -> [sr] -> Either r ([t],ml)) -> + ml -> [[sr]] -> (r,[[t]])+manager comb ml (srs:srss) = case comb ml srs of+ Left res -> (res,[]) -- Left: stop iteration+ Right (ts,ml') -> -- Right: proceed with new tasks (ts) and new state ml'+ let (res',tss) = manager comb ml' srss+ in (res', ts:tss)++--worker functionality of the iterUntil skeleton+worker :: (wl -> t -> (sr,wl)) -> (wl,[t]) -> [sr]+worker wf (local,[]) = []+worker wf (local, t:ts) = sr: worker wf (local',ts) where + (sr,local') = wf local t
+ Control/Parallel/Eden/EdenSkel/MapRedSkels.hs view
@@ -0,0 +1,127 @@+{-# LANGUAGE CPP, ScopedTypeVariables #-}+-----------------------------------------------------------------------------+-- |+-- Module : Control.Parallel.Eden.EdenSkel.MapRedSkels+-- Copyright : (c) Philipps Universitaet Marburg 2011-2012+-- License : BSD-style (see the file LICENSE)+-- +-- Maintainer : eden@mathematik.uni-marburg.de+-- Stability : beta+-- Portability : not portable+--+-- This Haskell module defines map-reduce skeletons for +-- the parallel functional language Eden.+--+-- Depends on GHC. Using standard GHC, you will get a threaded simulation of Eden. +-- Use the forked GHC-Eden compiler from http:\/\/www.mathematik.uni-marburg.de/~eden +-- for a parallel build.+--+-- Eden Group ( http:\/\/www.mathematik.uni-marburg.de/~eden )+-- Depends on the Eden Compiler.+++module Control.Parallel.Eden.EdenSkel.MapRedSkels (+ -- * Sequential map-reduce definitions+ mapRedr, mapRedl, mapRedl', + -- * Simple map-reduce skeletons + parMapRedr, parMapRedl, parMapRedl', + -- * offline map-reduce skeletons + offlineParMapRedr, offlineParMapRedl, offlineParMapRedl', + -- Google map-reduce+ ) where+#if defined( __PARALLEL_HASKELL__ ) || defined (NOT_PARALLEL)+import Control.Parallel.Eden+#else+import Control.Parallel.Eden.EdenConcHs+#endif+import Control.Parallel.Eden.EdenSkel.Auxiliary+import Control.Parallel.Eden.EdenSkel.MapSkels+import Data.List++mapRedr :: (b -> c -> c) -- ^ reduce function+ -> c -- ^ neutral for reduce function+ -> (a -> b) -- ^ map function+ -> [a] -- ^ input+ -> c -- ^ result+mapRedr g e f = (foldr g e) . (map f)++mapRedl :: (c -> b -> c) -- ^ reduce function+ -> c -- ^ neutral for reduce function+ -> (a -> b) -- ^ map function+ -> [a] -- ^ input+ -> c -- ^ result+mapRedl g e f = (foldl g e) . (map f)++mapRedl' :: (c -> b -> c) -- ^ reduce function+ -> c -- ^ neutral for reduce function+ -> (a -> b) -- ^ map function+ -> [a] -- ^ input+ -> c -- ^ result+mapRedl' g e f = (foldl' g e) . (map f)++++-- | Basic parMapRedr skeleton - as many processes as noPe. +-- local pre-folding per PE and final folding of PE-results +-- via different fold variants+parMapRedr :: (Trans a, Trans b) =>+ (b -> b -> b) -> b -> (a -> b) -> [a] -> b+parMapRedr g e f+ = if noPe == 1 then mapRedr g e f else+ (foldr g e) . (parMap (mapRedr g e f)) . (splitIntoN noPe)++-- | Basic parMapRedl skeleton - as many processes as noPe. +-- local pre-folding per PE and final folding of PE-results +-- via different fold variants+parMapRedl :: (Trans a, Trans b) =>+ (b -> b -> b) -> b -> (a -> b) -> [a] -> b+parMapRedl g e f+ = if noPe == 1 then mapRedl g e f else+ (foldl g e) . (parMap (mapRedl g e f)) . (splitIntoN noPe)++-- | Basic parMapRedl' skeleton - as many processes as noPe. +-- local pre-folding per PE and final folding of PE-results +-- via different fold variants+parMapRedl' :: (Trans a, Trans b) =>+ (b -> b -> b) -> b -> (a -> b) -> [a] -> b+parMapRedl' g e f+ = if noPe == 1 then mapRedl' g e f else+ (foldl' g e) . (parMap (mapRedl' g e f)) . (splitIntoN noPe)++++-- | Offline parMapRedr skeleton - as many processes as noPe. +-- local pre-folding per PE and final folding of PE-results +-- via different fold variants, +-- BUT local selection of input sub-list by worker processes+offlineParMapRedr :: (Trans a, Trans b) =>+ (b -> b -> b) -> b -> (a -> b) -> [a] -> b+offlineParMapRedr g e f xs+ = if noPe == 1 then mapRedr g e f xs else+ foldr g e (parMap worker [0..noPe-1])+ where worker i = mapRedr g e f ((splitIntoN noPe xs)!!i)++-- | Offline parMapRedl skeleton - as many processes as noPe. +-- local pre-folding per PE and final folding of PE-results +-- via different fold variants, +-- BUT local selection of input sub-list by worker processes+offlineParMapRedl :: (Trans a, Trans b) =>+ (b -> b -> b) -> b -> (a -> b) -> [a] -> b+offlineParMapRedl g e f xs+ = if noPe == 1 then mapRedl g e f xs else+ foldr g e (parMap worker [0..noPe-1])+ where worker i = mapRedl g e f ((splitIntoN noPe xs)!!i)++-- | Offline parMapRedl' skeleton - as many processes as noPe. +-- local pre-folding per PE and final folding of PE-results +-- via different fold variants, +-- BUT local selection of input sub-list by worker processes+offlineParMapRedl' :: (Trans a, Trans b) =>+ (b -> b -> b) -> b -> (a -> b) -> [a] -> b+offlineParMapRedl' g e f xs+ = if noPe == 1 then mapRedl' g e f xs else+ foldr g e (parMap worker [0..noPe-1])+ where worker i = mapRedl' g e f ((splitIntoN noPe xs)!!i)+++
+ Control/Parallel/Eden/EdenSkel/MapSkels.hs view
@@ -0,0 +1,305 @@+{-# LANGUAGE CPP, ScopedTypeVariables #-}+-----------------------------------------------------------------------------+-- |+-- Module : Control.Parallel.Eden.EdenSkel.MapSkels+-- Copyright : (c) Philipps Universitaet Marburg 2009-2012+-- License : BSD-style (see the file LICENSE)+-- +-- Maintainer : eden@mathematik.uni-marburg.de+-- Stability : beta+-- Portability : not portable+--+-- This Haskell module defines map-like skeletons for +-- the parallel functional language Eden.+--+-- Depends on GHC. Using standard GHC, you will get a threaded simulation of Eden. +-- Use the forked GHC-Eden compiler from http:\/\/www.mathematik.uni-marburg.de/~eden +-- for a parallel build.+--+-- Eden Group ( http:\/\/www.mathematik.uni-marburg.de/~eden )+++module Control.Parallel.Eden.EdenSkel.MapSkels (+ -- * Custom map skeletons + -- | These skeletons expose many parameters to the user and thus have varying types+ parMap, ranch, + farm, farmS, farmB, + offlineFarm, offlineFarmS, offlineFarmB,+ -- * Custom map skeletons with explicit placement+ -- | Map skeleton versions with explicit placement+ parMapAt, ranchAt, farmAt, offlineFarmAt, + -- * Simple map skeleton variants + -- | The map skeletons 'farm' and 'offlineFarm' can be used to define + -- skeletons with the simpler sequential map interface :: (a -> b) -> [a] -> [b]+ mapFarmB, mapFarmS, mapOfflineFarmS, mapOfflineFarmB,+ -- * Deprecated map skeletons+ -- | These skeletons are included to keep old code alive. Use the skeletons above.+ farmClassic, ssf, offline_farm, map_par, map_farm, map_offlineFarm, map_ssf+ ) where+#if defined( __PARALLEL_HASKELL__ )+import Control.Parallel.Eden+#else+import Control.Parallel.Eden.EdenConcHs+#endif+import Control.Parallel.Eden.EdenSkel.Auxiliary+import Data.List+++-- | Basic parMap Skeleton - one process for each list element. This version takes +-- places for instantiation on particular PEs. +parMapAt :: (Trans a, Trans b) => + Places -- ^places for instantiation + -> (a -> b) -- ^worker function+ -> [a] -- ^task list+ -> [b] -- ^result list+parMapAt pos f tasks = spawnAt pos (repeat (process f)) tasks+++-- | Basic parMap Skeleton - one process for each list element+parMap :: (Trans a, Trans b) => + (a -> b) -- ^worker function+ -> [a] -- ^task list+ -> [b] -- ^result list+parMap = parMapAt [0]+++-- | A process ranch is a generalized (or super-) farm. This version takes +-- places for instantiation. Arbitrary input is transformed into a list of inputs +-- for the worker processes (one worker for each transformed value). The worker +-- inputs are processed by the worker function.+-- The results of the worker processes are then reduced using the reduction function.+ranchAt :: (Trans b, Trans c) => + Places -- ^places for instantiation+ -> (a -> [b]) -- ^input transformation function + -> ([c] -> d) -- ^result reduction function+ -> (b -> c) -- ^worker function+ -> a -- ^input + -> d -- ^output+ranchAt pos transform reduce fs xs = + reduce $ spawnAt pos (repeat $ process fs) (transform xs)++-- | A process ranch is a generalized (or super-) farm. Arbitrary input +-- is transformed into a list of inputs for the worker processes (one worker +-- for each transformed value). The worker inputs are processed by the worker function.+-- The results of the worker processes are then reduced using the reduction function.+ranch :: (Trans b, Trans c) => + (a -> [b]) -- ^input transformation function + -> ([c] -> d) -- ^result reduction function+ -> (b -> c) -- ^worker function+ -> a -- ^input + -> d -- ^output+ranch = ranchAt [0]+++-- | A farm distributes its input to a number of worker processes.+-- This version takes places for instantiation.+-- The distribution function divides the input list into +-- sublists - each sublist is input to one worker process, the +-- number of worker processes is determined by the number of +-- sublists. The results of the worker processes are +-- then combined using the combination function.+-- +-- Use 'map_farm' if you want a simpler interface.+--+farmAt :: (Trans a, Trans b) => + Places -- ^places for instantiation+ -> ([a] -> [[a]]) -- ^input distribution function + -> ([[b]] -> [b]) -- ^result combination function+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output+farmAt pos distr combine f tasks = ranchAt pos distr combine (map f) tasks++-- | A farm distributes its input to a number of worker processes.+-- The distribution function divides the input list into +-- sublists - each sublist is input to one worker process, the +-- number of worker processes is determined by the number of +-- sublists. The results of the worker processes are +-- then combined using the combination function.+-- +-- Use 'mapFarmS' or 'mapFarmB' if you want a simpler interface.+--+farm :: (Trans a, Trans b) => + ([a] -> [[a]]) -- ^input distribution function + -> ([[b]] -> [b]) -- ^result combination function+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output+farm = farmAt [0]++-- | Like the 'farm', but uses a fixed round-robin distribution of tasks.+farmS :: (Trans a, Trans b) + => Int -- ^number of processes+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output+farmS np = farm (unshuffle np) shuffle++-- | Like the 'farm', but uses a fixed block distribution of tasks.+farmB :: (Trans a, Trans b) + => Int -- ^number of processes+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output+farmB np = farm (splitIntoN np) concat+++++-- | Offline farm with explicit placement (alias self-service farm or+-- direct mapping): Like the farm, but tasks are evaluated inside the+-- workers (less communication overhead). Tasks are mapped inside each+-- generated process abstraction, avoiding evaluating and sending+-- them. This often reduces the communication overhead because+-- unevaluated data is usually much smaller than evaluated data.+-- +-- Use 'map_offlineFarm' if you want a simpler interface.+--+-- Notice: The task lists structure has to be completely defined+-- before process instantiation takes place.+--+offlineFarmAt :: Trans b => + Places -- ^places for instantiation+ -> Int -- ^number of processes+ -> ([a] -> [[a]]) -- ^input distribution function + -> ([[b]] -> [b]) -- ^result combination function+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output++offlineFarmAt pos np distribute combine f xs + = combine $ spawnAt pos (map (rfi (map f)) [select i xs | i <- [0 .. np-1]])+ (repeat ())+ where select i xs = (distribute xs ++ repeat []) !! i++++-- | Offline farm (alias direct mapping): Like the farm, but+-- tasks are evaluated inside the workers (less communication+-- overhead). Tasks are mapped inside each generated process+-- abstraction avoiding evaluating and sending them. This often+-- reduces the communication overhead because unevaluated data is+-- usually much smaller than evaluated data.+-- +-- Use 'map_offlineFarm' if you want a simpler interface.+--+-- Notice: The offline farm receives the number of processes to be created+-- as its first parameter. +-- The task lists structure has to be completely defined+-- before process instantiation takes place.+--+offlineFarm :: Trans b => + Int -- ^number of processes + -> ([a] -> [[a]]) -- ^input distribution function + -> ([[b]] -> [b]) -- ^result combination function+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output++offlineFarm = offlineFarmAt [0]++-- | Like the 'offlineFarm', but with fixed round-robin distribution of tasks.+offlineFarmS :: (Trans a, Trans b) + => Int -- ^number of processes+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output+offlineFarmS np = offlineFarm np (unshuffle np) shuffle++-- | Like the 'offlineFarm', but with fixed block distribution of tasks.+offlineFarmB :: (Trans a, Trans b) + => Int -- ^number of processes+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output+offlineFarmB np = offlineFarm np (splitIntoN np) concat+++------------------------------------------------------------------------------------+numProc = max (noPe-1) 1++-- | Parallel map variant with map interface using (max (noPe-1) 1) worker processes. Skeletons ending on @S@ use round-robin distribution, skeletons ending on @B@ use block distribution of tasks.+mapFarmS, mapFarmB, mapOfflineFarmS, mapOfflineFarmB :: (Trans a , Trans b) => + (a -> b) -- ^worker function+ -> [a] -- ^task list+ -> [b] -- ^result list +mapFarmS = farmS numProc+mapFarmB = farmB numProc+mapOfflineFarmS = offlineFarmS numProc+mapOfflineFarmB = offlineFarmB numProc++-----------------------------DEPRECATED---------------------------------+++-- | Deprecated, use the 'farm';+-- @farmClassic@ distributes its input to a number of worker processes.+-- This is the Classic version as described in the Eden standard reference +-- "Parallel Functional Programming in Eden".+-- The distribution function is expected to divide the input list into +-- the given number of sublists. In the new farm the number of sublists is +-- determined only by the distribution function.+-- +-- Use 'map_farm' if you want a simpler interface.+{-# DEPRECATED farmClassic "better use farm instead" #-}+farmClassic :: (Trans a, Trans b) => + Int -- ^number of child processes+ -> (Int -> [a] -> [[a]]) -- ^input distribution function + -> ([[b]] -> [b]) -- ^result combination function+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output++farmClassic np distribute = farm $ distribute np+++-- | Deprecated, use 'offlineFarm'; +-- Self service farm. Like the farm, but+-- tasks are evaluated in the workers (less communication overhead).+-- This is the classic version. The distribution function is expected+-- to divide the input list into the given number of sublists. In the+-- new self service farm the number of sublists is determined only by+-- the distribution function.+-- +-- Use 'map_ssf' if you want a simpler interface.+--+-- Notice: The task lists structure has to be completely defined+-- before process instantiation takes place.+{-# DEPRECATED ssf "better use offlineFarm instead" #-}+ssf :: forall a b . Trans b => + Int -- ^number of child processes+ -> (Int -> [a] -> [[a]]) -- ^input distribution function + -> ([[b]] -> [b]) -- ^result combination function+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output++ssf np distribute = offlineFarm np (distribute np) ++-- | Deprecated: Same as 'offlineFarm'.+{-# DEPRECATED offline_farm "better use offlineFarm instead" #-}+offline_farm :: Trans b => + Int -- ^number of processes + -> ([a] -> [[a]]) -- ^input distribution function + -> ([[b]] -> [b]) -- ^result combination function+ -> (a -> b) -- ^mapped function+ -> [a] -- ^input + -> [b] -- ^output+offline_farm = offlineFarm++-- | Deprecated: Same as 'parMap'.+{-# DEPRECATED map_par "better use parMap instead" #-}+map_par :: (Trans a , Trans b) => + (a -> b) -- ^worker function+ -> [a] -- ^task list+ -> [b] -- ^result list +map_par = parMap++-- | Deprecated: Parallel map variants with map interface using noPe worker processes.+{-# DEPRECATED map_farm, map_offlineFarm, map_ssf "better use mapFarmS or mapOfflineFarmS instead" #-}+map_farm, map_offlineFarm, map_ssf :: (Trans a , Trans b) => + (a -> b) -- ^worker function+ -> [a] -- ^task list+ -> [b] -- ^result list +map_farm = farmS noPe+map_offlineFarm = offlineFarmS noPe+map_ssf = map_offlineFarm
+ Control/Parallel/Eden/EdenSkel/TopoSkels.hs view
@@ -0,0 +1,254 @@+{-# LANGUAGE CPP, ScopedTypeVariables #-}+-----------------------------------------------------------------------------+-- |+-- Module : Control.Parallel.Eden.EdenSkel.TopoSkels+-- Copyright : (c) Philipps Universitaet Marburg 2009-2012+-- License : BSD-style (see the file LICENSE)+-- +-- Maintainer : eden@mathematik.uni-marburg.de+-- Stability : beta+-- Portability : not portable+--+-- This Haskell module defines topology skeletons for the parallel functional+-- language Eden. Topology skeletons are skeletons that implement a network of+-- processes interconnected by a characteristic communication topology.+--+-- Depends on GHC. Using standard GHC, you will get a threaded simulation of Eden. +-- Use the forked GHC-Eden compiler from http:\/\/www.mathematik.uni-marburg.de/~eden +-- for a parallel build.+--+-- Eden Group ( http:\/\/www.mathematik.uni-marburg.de/~eden )+++module Control.Parallel.Eden.EdenSkel.TopoSkels (+ -- * Skeletons that are primarily characterized by their topology.+ + -- ** Pipeline skeletons+ -- |+ pipe, pipeRD+ -- ** Ring skeletons+ -- |+ ,ringSimple, ring, ringFl, ringAt, ringFlAt+ -- ** Torus skeleton+ -- | + ,torus + -- ** The Hypercube skeleton+ -- |++ -- ** The All-To-All skeleton + -- | The allToAll skeleton allows distributed data exchange and+ -- transformation including data of all processes. Input and output+ -- are provided as remote data. A typical application is the+ -- distributed transposition of a distributed matrix.+ ,allToAllRD, parTransposeRD + -- ** The All-Reduce skeleton + -- | The All-Reduce skeleton uses a butterfly topology to reduce the data of+ -- participating processes P in log(|P|) communication stages. Input+ -- and output are provided as remote data.+ --+ -- Notice: The number of processes has to be a power of 2!+ ,allReduceRD+ + ) where+#if defined( __PARALLEL_HASKELL__ ) || defined (NOT_PARALLEL)+import Control.Parallel.Eden+#else+import Control.Parallel.Eden.EdenConcHs+#endif+import Control.Parallel.Eden.EdenSkel.Auxiliary+import Control.Parallel.Eden.EdenSkel.MapSkels+import Data.List++ + +-- |Simple pipe where the parent process creates all pipe processes. The processes communicate their results via the caller process. +pipe :: forall a . Trans a => + [a -> a] -- ^functions of the pipe+ -> a -- ^input+ -> a -- ^output+pipe fs = unLiftRD (pipeRD fs)+ +-- |Process pipe where the processes communicate their Remote Data handles via the caller process but fetch the actual data from their predecessor processes+pipeRD :: forall a . Trans a => + [a -> a] -- ^functions of the pipe+ -> RD a -- ^remote input+ -> RD a -- ^remote output+pipeRD fs xs = (last outs) where + outs = spawn ps $ lazy $ xs : outs+ ps :: [Process (RD a) (RD a)]+ ps = map (process . liftRD) fs+++-- | Simple ring skeleton (tutorial version) +-- using remote data for providing direct inter-ring communication +-- without input distribution and output combination +ringSimple :: (Trans i, Trans o, Trans r) =>+ (i -> r -> (o,r)) -- ^ ring process function+ -> [i] -> [o] -- ^ input output mapping+ringSimple f is = os+ where+ (os,ringOuts) = unzip (parMap (toRD $ uncurry f)+ (zip is $ lazy ringIns))+ ringIns = rightRotate ringOuts++toRD :: (Trans i, Trans o, Trans r) =>+ ((i,r) -> (o,r)) -- ^ ring process function+ -> ((i, RD r) -> (o, RD r)) -- ^ -- with remote data+toRD f (i, ringIn) = (o, release ringOut)+ where (o, ringOut) = f (i, fetch ringIn)++rightRotate :: [a] -> [a]+rightRotate [] = []+rightRotate xs = last xs : init xs++-- | The ringFlAt establishes a ring topology, the ring process functions+-- transform the initial input of a ring process and the input stream from the ring into the +-- ring output stream and the ring processes' final result. Every ring process +-- applies its individual function which e.g. allows to route individual offline input into the +-- ring processes. This version uses explicit placement.+ringFlAt :: (Trans a,Trans b,Trans r) =>+ Places -- ^where to put workers+ -> (i -> [a]) -- ^distribute input+ -> ([b] -> o) -- ^combine output+ -> [(a -> [r] -> (b,[r]))] -- ^ring process fcts+ -> i -- ^ring input+ -> o -- ^ring output+ringFlAt places distrib combine fs i = combine os where+ (os, ringOuts) = unzip $ spawnFAt places (map (toRD . uncurry) fs) + (zip (distrib i) $ lazy ringIns)+ ringIns = rightRotate ringOuts++-- | The ringFl establishes a ring topology, the ring process functions+-- transform the initial input of a ring process and the input stream from the ring into the +-- ring output stream and the ring processes' final result. Every ring process +-- applies an individual function which e.g. allows to route individual offline input into the +-- ring processes. Use ringFlAt if explicit placement is desired.+ringFl :: (Trans a,Trans b,Trans r) =>+ (i -> [a]) -- ^distribute input+ -> ([b] -> o) -- ^combine output+ -> [(a -> [r] -> (b,[r]))] -- ^ring process fcts+ -> i -- ^ring input+ -> o -- ^ring output+ringFl = ringFlAt [0]++-- | Skeleton @ringAt@ establishes a ring topology, the ring process function+-- transforms the initial input of a ring process and the input stream from the ring into the +-- ring output stream and the ring processes' final result. The +-- same function is used by every ring process. Use ringFlAt+-- if you need different functions in the processes. This version uses explicit placement.+ringAt :: (Trans a,Trans b,Trans r) =>+ Places -- ^where to put workers+ -> (i -> [a]) -- ^distribute input+ -> ([b] -> o) -- ^combine output+ -> (a -> [r] -> (b,[r])) -- ^ring process fct+ -> i -- ^ring input+ -> o -- ^ring output +ringAt places distrib combine f i =+ ringFlAt places distrib combine [f] i ++-- | The ring establishes a ring topology, the ring process function+-- transforms the initial input of a ring process and the input stream from the ring into the +-- ring output stream and the ring processes final result. The +-- same function is used by every ring process. Use ringFl+-- if you need different functions in the processes. Use ringAt if +-- explicit placement is desired.+ring :: (Trans a,Trans b,Trans r) =>+ (i -> [a]) -- ^distribute input+ -> ([b] -> o) -- ^combine output+ -> (a -> [r] -> (b,[r])) -- ^ring process fct+ -> i -- ^ring input+ -> o -- ^ring output+ring = ringAt [0]++++-- | Parallel torus skeleton (tutorial version) with stream rotation in 2 directions: initial inputs for each torus element are given. The node function is used on each torus element to transform the initial input and a stream of inputs from each direction to a stream of outputs to each direction. Each torus input should have the same size in both dimensions, otherwise the smaller input will determine the size of the torus.+torus :: (Trans a, Trans b, Trans c, Trans d) =>+ (c -> [a] -> [b] -> (d,[a],[b])) -- ^ node function+ -> [[c]] -> [[d]] -- ^ input-output mapping+torus f inss = outss+ where+ t_outss = spawnPss (repeat (repeat (ptorus f))) t_inss -- optimised+ (outss,outssA,outssB) = unzip3 (map unzip3 t_outss)+ inssA = map rightRotate outssA+ inssB = rightRotate outssB+ t_inss = zipWith3 lazyzip3 inss (lazy inssA) (lazy inssB)+ lazyzip3 as bs cs = zip3 as (lazy bs) (lazy cs)++-- each individual process of the torus (tutorial version)+ptorus :: (Trans a, Trans b, Trans c, Trans d) =>+ (c -> [a] -> [b] -> (d,[a],[b])) ->+ Process (c,RD [a],RD [b])+ (d,RD [a],RD [b])+ptorus f + = process (\ (fromParent, inA, inB) ->+ let (toParent, outA, outB) = f fromParent inA' inB'+ (inA',inB') = fetch2 inA inB+ in (toParent, release outA, release outB))+++-- | The allToAllRD skeleton creates as many processes as elements in the input list (@np@). +-- The processes are all-to-all connected, each process' input is transformed to +-- @np@ intermediate values by the first parameter function, where the @i@-th value+-- will be sent to process @i@. The second transformation function combines the initial+-- input and the @np@ received intermediate values to the final output.+allToAllRD :: forall a b i. (Trans a, Trans b, Trans i) =>+ (Int -> a -> [i]) -- ^transform before bcast (num procs, input, sync-data out)+ -> (a -> [i] ->b) -- ^transform after bcast (input, sync-data in, output)+ -> [RD a] -- ^remote input for each process+ -> [RD b] -- ^remote output for each process+allToAllRD t1 t2 xs = res where+ n = length xs --same amount of procs as #xs+ (res,iss) = n `pseq` unzip $ parMap (uncurry p) inp+ inp = zip xs $ lazy $ transpose iss++ p :: RD a-> [RD i]-> (RD b,[RD i])+ p xRD theirIs = (resF theirIs, myIsF x) where+ x = fetch xRD+ myIsF = releaseAll . t1 n+ resF = release . t2 x . fetchAll+++-- works similar for splitIntoN and unsplit (concat)??? +-- |Parallel transposition for matrices which are row-wise round robin distributed among the machines, the transposed result matrix is also row-wise round robin distributed.+parTransposeRD :: Trans b => + [RD [[b]]] -- ^input list of remote partial matrices+ -> [RD [[b]]] -- ^output list of remote partial matrices+parTransposeRD = allToAllRD (\ n -> unshuffle n . transpose)+ (\ _ -> map shuffle . transpose)+++-- | Performs an all-reduce with the reduce function using a butterfly scheme.+-- The input list should have length 2^i, where i is an arbitrary natural number.+-- If not, the input list will be truncated to the next smaller power of two.+-- The initial transformation is applied in the processes to obtain the values+-- that will be reduced. The final combine function is used to create a processes+-- result from the initial input and the reduced value.+allReduceRD :: forall a b c. (Trans a, Trans b, Trans c) =>+ (a -> b) -- ^initial transform function+ -> (b -> b -> b) -- ^reduce function+ -> (a -> b -> c) -- ^final combine function+ -> [RD a] -- ^remote input+ -> [RD c] -- ^remote output+allReduceRD initF redF resF rdAs = rdCs where+ steps = (floor . logBase 2 . fromIntegral . length) rdAs+ rdAs' = take (2^steps) rdAs --cut input to power of 2++ -- topology, inputs and instantiation+ (rdBss,rdCs) = unzip $ parMap (uncurry p) inp --steps in rows+ bufly = zipWith bitFlipF [1..steps] $ transpose rdBss+ inp = zip rdAs' $ lazy $ transpose bufly --steps in cols++ -- process functionality and abstraction+ p :: RD a -> [RD b] -> ([RD b], RD c)+ p rdA theirReds = (reduced, release $ resF a $ head res) where+ reduced = (releaseAll . scanl1 redF) toReduce+ (toReduce,res) = splitAt steps $ initF a : fetchAll theirReds'+ theirReds' = zipWith (curry snd) [1..steps] $ lazy theirReds+ a = fetch rdA++bitFlipF :: Int -> [a] -> [a]+bitFlipF step xs = (shuffle . flipAtHalfF . unshuffle d) xs where+ d = (2 ^ step)+ flipAtHalfF xs = let (xs1, xs2) = splitAt (d `div` 2) xs+ in xs2 ++ xs1
+ Control/Parallel/Eden/EdenSkel/WPSkels.hs view
@@ -0,0 +1,727 @@+{-# LANGUAGE CPP, ScopedTypeVariables #-}+-----------------------------------------------------------------------------+-- |+-- Module : Control.Parallel.Eden.EdenSkel.WPSkels+-- Copyright : (c) Philipps Universitaet Marburg 2009-2012+-- License : BSD-style (see the file LICENSE)+-- +-- Maintainer : eden@mathematik.uni-marburg.de+-- Stability : beta+-- Portability : not portable+--+-- This Haskell module defines workpool skeletons for dynamic task+-- distribution for the parallel functional language Eden.+--+-- Depends on GHC. Using standard GHC, you will get a threaded simulation of Eden. +-- Use the forked GHC-Eden compiler from http:\/\/www.mathematik.uni-marburg.de/~eden +-- for a parallel build.+--+-- Eden Group ( http:\/\/www.mathematik.uni-marburg.de/~eden )+++module Control.Parallel.Eden.EdenSkel.WPSkels (+ -- * Workpool skeletons with a single master+ -- ** Simple workpool skeletons+ -- | The workpool skeletons use the non-deterministic merge function to achieve dynamic load balancing.+ workpool, workpoolSorted, workpoolSortedNonBlock, workpoolReduce,+ -- ** Simple workpool skeletons - versions using explicit placement+ -- | The workpool skeletons use the non-deterministic merge function to achieve dynamic load balancing.+ workpoolAt, workpoolSortedAt, workpoolSortedNonBlockAt, workpoolReduceAt,+ workpoolAuxAt,+ -- * Hierarchical workpool skeleton+ -- |These skeletons can be nested with an arbitrary number of submaster+ -- levels to unload the top master.+ wpNested, + -- ** Hierarchical workpool skeleton with dynamic task creation+ -- |The worker function is extended such that dynamic creation of+ -- new tasks is possible. New tasks are added to the end of the+ -- task list, thus tasks are traversed breath first (not strictly+ -- because of the skeletons' nondeterminism). Furthermore, these+ -- skeletons can be nested with an arbitrary number of submaster+ -- levels to unload the top master.+ wpDynNested, wpDNI,+-- * Distributed workpool skeletons with state and dynamic task creation+ distribWPAt,+-- * Deprecated skeletons+ masterWorker, mwNested, mwDynNested, mwDNI,+ ) where+#if defined( __PARALLEL_HASKELL__ ) || defined (NOT_PARALLEL)+import Control.Parallel.Eden+#else+import Control.Parallel.Eden.EdenConcHs+#endif+import Control.Parallel.Eden.EdenSkel.Auxiliary+import Control.Parallel.Eden.EdenSkel.MapSkels+import Control.Parallel.Eden.EdenSkel.TopoSkels+import Data.List+import Data.Maybe(maybeToList,mapMaybe)++import System.IO.Unsafe+import Control.Monad++import Control.Concurrent+++-- | Simple workpool (result list in non-deterministic order)+-- This version takes places for instantiation.+--+-- Notice: Result list in non-deterministic order.+workpoolAt :: forall t r . (Trans t, Trans r) =>+ Places+ -> Int -- ^number of child processes (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (t -> r) -- ^worker function (mapped to tasks) + -> [t] -> [r] -- ^what to do+workpoolAt pos np prefetch wf tasks+ = map snd fromWorkers+ where + fromWorkers :: [(Int,r)]+ fromWorkers = merge (tagWithPids (parMapAt pos worker taskss))+ taskss :: [[t]]+ taskss = distribute np (initialReqs ++ newReqs) tasks+ initialReqs, newReqs :: [Int]+ initialReqs = concat (replicate prefetch [0..np-1])+ newReqs = map fst fromWorkers+ worker = map wf+++-- | Tag each element of the inner list with the id of its inner list.+tagWithPids :: [[r]] -- ^untagged input+ -> [[(Int,r)]] -- ^tagged output+tagWithPids rss = [ zip (repeat i) rs |(i,rs) <-zip [0..] rss] +++-- | Simple workpool (result list in non-deterministic order)+--+-- Notice: Result list in non-deterministic order.+workpool :: (Trans t, Trans r) =>+ Int -- ^number of child processes (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (t -> r) -- ^worker function (mapped to tasks) + -> [t] -> [r] -- ^what to do+workpool = workpoolAt [0]++++-- | Workpool version with one result stream for each worker and meta+-- information about the task distribution.+-- This meta-skeleton can be used to define workpool-skeletons which+-- can reestablish the result list order.+--+-- Notice: Result list in non-deterministic order.+workpoolAuxAt :: (Trans t, Trans r) =>+ Places+ -> Int -- ^number of child processes+ -- (workers)+ -> Int -- ^prefetch of tasks (for+ -- workers)+ -> (t -> r) -- ^worker function (tasks to+ -- results mapping)+ -> [t] -- ^tasks+ -> ([Int],[[Int]],[[r]]) -- ^(input distribution (input i+ -- is in sub-list distribs!i),+ -- task positions (element i of+ -- result-sub-list j was in the+ -- input list at (poss!j)!i ),+ -- result streams of workers)+workpoolAuxAt pos np prefetch wf tasks+ = (reqs,poss,fromWorkers)+ where fromWorkers = parMapAt pos (map wf) taskss+ (taskss,poss) = distributeWithPos np reqs tasks+ -- generate only as many reqs as there are tasks+ reqs = map snd $ zip tasks $ initialReqs ++ newReqs+ initialReqs = concat (replicate prefetch [0..np-1])+ newReqs = merge $ [ [ i | j<-rs] + | (i,rs) <-zip [0..] fromWorkers]+++-- | Task distribution according to worker requests. Returns additionally to @ distribute @ a nested list of the positions to indicate where the tasks have been located in the original list+--+distributeWithPos :: Int -- ^number of workers+ -> [Int] -- ^ request stream (worker IDs ranging from 0 to n-1)+ -> [t] -- ^ task list+ -> ([[t]],[[Int]]) -- ^(task positions in original list, task distribution), each inner list for one worker.+distributeWithPos np reqs tasks + = unzip [unzip (taskList reqs tasks [0..] n) | n<-[0..np-1]]+ where taskList (r:rs) (t:ts) (tag:tags) pe+ | pe == r = (t,tag):(taskList rs ts tags pe)+ | otherwise = taskList rs ts tags pe+ taskList _ _ _ _ = []+++-- | Sorted workpool (results in the order of the tasks).+-- This version takes places for instantiation. +workpoolSortedAt :: (Trans t, Trans r) =>+ Places+ -> Int -- ^number of child processes+ -- (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (t -> r) -- ^worker function+ -> [t] -- ^tasks+ -> [r] -- ^results+workpoolSortedAt pos np prefetch f tasks = res+ where (_, poss, ress) = workpoolAuxAt pos np prefetch f tasks+ res = map snd $ mergeByPos ress'+ ress' = map (uncurry zip) (zip poss ress)+++-- | Join sorted lists into one sorted list.+-- This function uses a balanced binary combination scheme to merge sublists.+mergeByPos :: [[(Int,r)]] -- ^ tagged input + -> [(Int,r)] -- ^ output sorted by tags+mergeByPos [] = []+mergeByPos [wOut] = wOut+mergeByPos [w1,w2] = merge2ByTag w1 w2+mergeByPos wOuts = merge2ByTag+ (mergeHalf wOuts)+ (mergeHalf (tail wOuts))+ where mergeHalf = mergeByPos . (takeEach 2)++merge2ByTag [] w2 = w2+merge2ByTag w1 [] = w1+merge2ByTag w1@(r1@(i,_):w1s) w2@(r2@(j,_):w2s)+ | i < j = r1: merge2ByTag w1s w2+ | i > j = r2: merge2ByTag w1 w2s+ | otherwise = error "found tags i == j"++++-- | Sorted workpool: Efficient implementation using a the+-- distribution lookup list.+--+-- Notice: Results in the order of the tasks.+workpoolSorted :: (Trans t, Trans r) =>+ Int -- ^number of child processes (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (t -> r) -- ^worker function (mapped to tasks) + -> [t] -- ^tasks+ -> [r] -- ^results+workpoolSorted = workpoolSortedAt [0]++-- | Non-blocking sorted workpool. Result list is structurally defined+-- up to the position where tasks are distributed, independent of the+-- received worker results. This version needs still performance+-- testing.+--+-- Notice: Results in the order of the tasks.+workpoolSortedNonBlockAt :: (Trans t, Trans r) =>+ Places+ -> Int -- ^number of child processes (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (t -> r) -- ^worker function (mapped to tasks) + -> [t] -> [r] -- ^what to do+workpoolSortedNonBlockAt pos np prefetch f tasks+ = orderBy fromWorkers reqs+ where (reqs, _ ,fromWorkers) = workpoolAuxAt pos np prefetch f tasks+++-- | Orders a nested list (sublist are ordered) by a given distribution (non-blocking on result elements of other sub lists)+orderBy :: forall idx r . Integral idx => + [[r]] -- ^ nested input list (@inputss@)+ -> [idx] -- ^ distribution (result i is in sublist @inputss!(idxs!i)@)+ -> [r] -- ^ ordered result list+orderBy _ [] = []+orderBy [rs] is = rs+orderBy (xs:rss) is = fst $ foldl (f is) (xs,1) rss+ where f :: [idx] -> ([r],idx) -> [r] -> ([r], idx)+ f is (xs,a) ys = (m xs ys is, a+1)+ where m :: [r] -> [r] -> [idx] -> [r]+ m _ _ [] = []+ m xs ys (i:is) | i < a = head xs : m (tail xs) ys is+ | i==a = head ys : m xs (tail ys) is+ | otherwise = m xs ys is+ + +-- | orders a nested list by a given distribution (alternative code)+orderBy' :: Integral idx => + [[r]] -- ^ nested input list (@inputss@)+ -> [idx] -- ^ distribution (result i is in sublist @inputss!(idxs!i)@)+ -> [r] -- ^ ordered result list+orderBy' rss [] = []+orderBy' rss (r:reqs)+ = let (rss1,(rs2:rss2)) = splitAt (fromIntegral r) rss+ in (head rs2): orderBy' (rss1 ++ ((tail rs2):rss2)) reqs+++-- | Non-blocking sorted workpool (results in the order of the+-- tasks). Result list is structurally defined up to the position+-- where tasks are distributed, independent of the received worker+-- results. This version needs still performance testing. This+-- version takes places for instantiation.+--+-- Notice: Results in the order of the tasks.+workpoolSortedNonBlock :: (Trans t, Trans r) =>+ Int -- ^number of child processes (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (t -> r) -- ^worker function (mapped to tasks) + -> [t] -> [r] -- ^what to do+workpoolSortedNonBlock = workpoolSortedNonBlockAt [0]++++++-- | Simple workpool with additional reduce function for worker outputs.+-- This version takes places for instantiation.+--+-- Notice: Result list in non-deterministic order.+workpoolReduceAt :: forall t r r' . (Trans t, Trans r, Trans r') =>+ Places+ -> Int -- ^number of child processes (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (r' -> r -> r) -- ^reduce function+ -> r -- ^neutral for reduce function+ -> (t -> r') -- ^worker function (mapped to tasks) + -> [t] -- ^tasks + -> [r] -- ^results (one from each worker)+workpoolReduceAt pos np prefetch rf e wf tasks+ = map snd fromWorkers+ where + fromWorkers :: [([Int],r)]+ fromWorkers = spawnFAt pos (map worker [1..np]) taskss+ taskss = distribute np (initialReqs ++ newReqs) tasks+ initialReqs = concat (replicate prefetch [0..np-1])+ newReqs = merge (map fst fromWorkers)+ worker i ts = (map (\r -> rnf r `seq` i) rs, foldr rf e rs)+ where rs = map wf ts+++-- | Simple workpool with additional reduce function for worker outputs.+-- This version takes places for instantiation.+--+-- Notice: Result list in non-deterministic order.+workpoolReduce :: forall t r r' . (Trans t, Trans r, Trans r') =>+ Int -- ^number of child processes (workers)+ -> Int -- ^prefetch of tasks (for workers)+ -> (r' -> r -> r) -- ^reduce function+ -> r -- ^neutral for reduce function + -> (t -> r') -- ^worker function (mapped to tasks) + -> [t] -- ^tasks + -> [r] -- ^results (one from each worker)+workpoolReduce = workpoolReduceAt [0]++-- |Hierachical WP-Skeleton. The worker+-- function is mapped to the worker input stream (list type). A worker+-- produces a result. The workers are located on the leaves of a+-- WP-hierarchy, in the intermediate levels are submasters which unload+-- the master by streaming 'result' streams of their child+-- processes into a single result stream.+--+-- Notice: Result list in non-deterministic order.+wpNested :: forall t r . (Trans t, Trans r) => + [Int] -- ^branching degrees: the i-th+ -- element defines the branching+ -- degree of for the i-th level of+ -- the WP-hierarchy. Use a singleton+ -- list for a flat MW-Skeleton.+ -> [Int] -- ^Prefetches for the+ -- sub-master/worker levels+ -> (t -> r) -- ^worker function+ -> [t] -- ^initial tasks+ -> [r] -- ^results+wpNested ns pfs wf initTasks = wpDynNested ns pfs (\t -> (wf t,[])) initTasks+++-- |Simple interface for 'wpDynNested'. Parameters are the number of child processes, the first+-- level branching degree, the nesting depth (use 1 for a+-- single master), and the task prefetch amount for the worker level.+-- All processes that are not needed for the submasters are+-- used for the workers. If the number of submasters in the last level+-- and the number of remaining child processes are prime to each+-- other, then the next larger divisor is chosen for the number of+-- workers.+--+-- Notice: Result list in non-deterministic order.+wpDNI :: (Trans t, Trans r) =>+ Int -- ^number of processes (submasters and workers)+ -> Int -- ^nesting depth+ -> Int -- ^branching degree of the first submaster+ -- level (further submaster levels are+ -- branched binary)+ -> Int -- ^task prefetch for the workers+ -> (t -> (r,[t])) -- ^worker function - produces a tuple of+ -- result and tasks for the processed task+ -> [t] -- ^initial tasks+ -> [r] -- ^results+wpDNI np levels l_1 pf f tasks + = let nesting = mkNesting np levels l_1+ in wpDynNested nesting (mkPFs pf nesting) f tasks+ ++-- |Hierachical WP-Skeleton with dynamic task creation. The worker+-- function is mapped to the worker input stream (list type). A worker+-- produces a tuple of result and dynamicly created tasks for each+-- processed task. The workers are located on the leaves of a+-- WP-hierarchy, in the intermediate levels are submasters which unload+-- the master by streamlining 'result/newtask' streams of their child+-- processes into a single result/newtask stream. Furthermore, the+-- submasters retain locally half of the tasks which are +-- dynamically created by the workers in their subtree.+--+-- Notice: Result list in non-deterministic order.+wpDynNested :: forall t r . (Trans t, Trans r) => + [Int] -- ^branching degrees: the i-th+ -- element defines the branching+ -- degree of for the i-th level of+ -- the MW-hierarchy. Use a singleton+ -- list for a flat MW-Skeleton.+ -> [Int] -- ^Prefetches for the+ -- sub-master/worker levels+ -> (t -> (r,[t])) -- ^worker function - produces a+ -- tuple of result and new tasks for+ -- the processed task+ -> [t] -- ^initial tasks+ -> [r] -- ^results+wpDynNested ns pfs wf initTasks + = topMasterStride strideTM (head ns) (head pfs) subWF initTasks+ where subWF = foldr fld wf' (zip3 stds (tail ns) (tail pfs))+ wf' :: [Maybe t] -> [(r,[t],Int)]+ -- explicit Nothing-Request after each result+ wf' xs = map(\ (r,ts) -> (r,ts,0)) (map (wf)(inp xs))+ inp ((Just x):rest) = x:inp rest+ inp (Nothing:_) = [] -- STOP!!!+ -- placement:+ (strideTM:stds) = scanr (\x y -> ((y*x)+1)) 1 (tail ns)+ fld :: (Int, Int, Int) -> ([Maybe t] -> [(r,[t],Int)])+ -> [Maybe t] -> [(r,[t],Int)]+ fld (stride,n,pf) wf = mwDynSubStride stride n pf wf++++--------------------------mwDynNested auxiliary---------------------------------++topMasterStride :: forall t r . (Trans t, Trans r) =>+ Int -> Int -> Int -> ([Maybe t] -> [(r,[t],Int)]) -> [t] -> [r]+topMasterStride stride branch prefetch wf initTasks = finalResults+ where+ -- identical to static task pool except for the type of workers+ ress = merge (spawnAt places workers inputs)+ places = nextPes branch stride+ workers :: [Process [Maybe t] [(Int,(r,[t],Int))]]+ workers = [process (zip [i,i..] . wf) | i <- [0..branch-1]]+ inputs = distribute branch (initReqs ++ reqs) tasks+ initReqs = concat (replicate prefetch [0..branch-1])+ -- additions for task queue management and+ -- termination detection+ tasks = (map Just initTasks) ++ newTasks+ -----------------------------+ initNumTasks = length initTasks+ -- => might lead to deadlock!+ -----------------------------+ (finalResults, reqs, newTasks) + = tdetectTop ress initNumTasks+++mwDynSubStride :: forall t r . (Trans t, Trans r) =>+ Int -> Int -> Int -> ([Maybe t] -> [(r,[t],Int)])+ -> [Maybe t] -> [(r,[t],Int)]+mwDynSubStride stride branch prefetch wf initTasks = finalResults where+ fromWorkers = map flatten (spawnAt places workers inputs)+ places = nextPes branch stride+ workers :: [Process [Maybe t] [(Int,(r,[t],Int))]]+ workers = [process (zip [i,i..] . wf) | i <- [0..branch-1]]+ inputs = distribute branch (initReqs ++ reqs) tasks+ initReqs = concat (replicate prefetch [0..branch-1])+ -- task queue management+ controlInput = merge (map Right initTasks: map (map Left) fromWorkers)+ (finalResults, tasks, reqs)+ = tcontrol controlInput 0 0 (branch * (prefetch+1)) False+++-- task queue control for termination detection+tdetectTop :: [(Int,(r,[t],Int))] -> Int -> ([r], [Int], [Maybe t])+tdetectTop ((req,(r,ts,subHoldsTs)):ress) numTs+ | numTs == 1 && null ts && subHoldsTs == 0+ = ([r], [], repeat Nothing) -- final result+ | subHoldsTs == 1+ = (r:moreRes, moreReqs, (map Just ts) ++ moreTs)+ | otherwise+ = (r:moreRes, req:moreReqs, (map Just ts) ++ moreTs)+ where --localNumTaks is 0 or 1, if it's 1 -> no Request + -- -> numTs will not be decreased+ (moreRes, moreReqs, moreTs) + = tdetectTop ress (numTs-1+length ts+subHoldsTs)+++tcontrol :: [Either (Int,r,[t],Int) (Maybe t)] -> -- controlInput+ Int -> Int -> -- task / hold counter+ Int -> Bool -> -- prefetch, split mode+ ([(r,[t],Int)],[Maybe t],[Int]) -- (results,tasks,requests)+tcontrol ((Right Nothing):_) 0 _ _ _+ = ([],repeat Nothing,[]) -- Final termination+tcontrol ((Right (Just t)):ress) numTs hldTs pf even -- task from above+ = let (moreRes, moreTs, reqs) = tcontrol ress (numTs+1) hldTs pf even+ in (moreRes, (Just t):moreTs, reqs)+tcontrol ((Left (i,r,ts,subHoldsTs)):ress) numTs hldTs pf even+ = let (moreRes, moreTs, reqs)+ = tcontrol ress (numTs + differ) (hldTs') pf evenAct+ differ = length localTs + subHoldsTs - 1+ hldTs' = max (hldTs + differ) 0+ holdInf | (hldTs+differ+1 > 0) = 1+ | otherwise = 0+ (localTs,fatherTs,evenAct)+ = split numTs pf ts even -- part of tasks to parent+ newreqs | (subHoldsTs == 0) = i:reqs + | otherwise = reqs -- no tasks kept below?+ in ((r,fatherTs,holdInf):moreRes,+ (map Just localTs) ++ moreTs, newreqs)++-- error case, not shown in paper+tcontrol ((Right Nothing):_) n _ _ _+ = error "Received Stop signal, although not finished!"+ + +flatten [] = []+flatten ((i,(r,ts,n)):ps) = (i,r,ts,n) : flatten ps++split :: Int -> Int -> [t] -> Bool ->([t],[t],Bool)+split num pf ts even-- = splitAt (2*pf - num) ts+ | num >= 2*pf = ([],ts,False)+ --no tasks or odd -> keep first + | ((not even)||(num == 1)) = oddEven ts+ | otherwise = evenOdd ts+ -- | num < pf `div` 2 = (ts,[])+++oddEven :: [t] -> ([t],[t],Bool)+oddEven [] = ([],[],False)+oddEven (x:xs) = (x:localT ,fatherT, even)+ where (localT,fatherT,even) = evenOdd xs++evenOdd :: [t] -> ([t],[t],Bool)+evenOdd [] = ([],[],True)+evenOdd (x:xs) = (localT, x:fatherT, even)+ where (localT,fatherT,even) = oddEven xs++nextPes :: Int -> Int -> [Int]+nextPes n stride | start > noPe = replicate n noPe+ | otherwise = concat (replicate n ps)+ where ps = cycle (takeWhile (<= noPe) [start,start+stride..])+ start = selfPe + 1+ +mkNesting :: Int -> Int -> Int -> [Int]+mkNesting np 1 _ = [np]+mkNesting np depth level1 = level1:(replicate (depth - 2) 2) ++ [numWs]+ where -- leaves = np - #submasters+ leaves = np - level1 * ( 2^(depth-1) - 1 )+ -- num of lowest submasters+ numSubMs = level1 * 2^(depth - 2)+ -- workers per branch (rounded up)+ numWs = (leaves + numSubMs - 1) `div` numSubMs++mkPFs :: Int -> -- prefetch value for worker processes+ [Int] -> -- branching per level top-down+ [Int] -- list of prefetches+mkPFs pf nesting+ = [ factor * (pf+1) | factor <- scanr1 (*) (tail nesting) ] ++ [pf]++++---------------------------distributed workpool skeletons-------------------------------------------++-- | A distributed workpool skeleton that uses task generation and a global state (s) with a total order.+-- Split and Detatch policy must give tasks away (may not produce empty lists), unless all tasks are pruned!+distribWPAt :: (Trans onT, Trans t, Trans r, Trans s, NFData r') =>+ Places -- ^ where to put workers+ -> ((t,s) -> (Maybe (r',s),[t])) -- ^ worker function+ -> (Maybe ofT -> Maybe onT -> [t]) -- ^ input transformation (e.g. (fetch . fromJust . snd) for online input of type [RD[t]])+ -> ([Maybe (r',s)] -> s -> r) -- ^ result transformation (prior to release results in the workers)+ -> ([t]->[t]->s->[t]) -- ^ taskpool transform attach function+ -> ([t]->s->([t],Maybe (t,s))) -- ^ taskpool transform detach function (local request)+ -> ([t]->s->([t],[t])) -- ^ taskpool transform split function (remote request)+ -> (s->s->Bool) -- ^ state comparison (checks if new state is better than old state)+ -> s -- ^ initial state (offline input)+ -> [ofT] -- ^ offline input (if non empty, outer list defines the number of workers, else the shorter list does)+ -> [onT] -- ^ dynamic input (if non empty, outer list defines the number of workers, else the shorter list does)+ -> [r] -- ^ results of workers+distribWPAt places wf inputT resT ttA ttD ttSplit sUpdate st ofTasks onTasks = res where+ res = ringFlAt places id id workers onTasks'+ workers = zipWith (worker) (True:(repeat False)) ofTasks'+ -- length of ontasks and oftasks is adjusted such that the desired number of workers will be instantiated+ (ofTasks',onTasks') | null ofTasks = (repeat Nothing , map Just onTasks)+ | null onTasks = (map Just ofTasks, repeat Nothing )+ | otherwise = (map Just ofTasks, map Just onTasks)+ -- worker functionality+ worker isFirst ofTasks onTasks ringIn = (resT ress sFinal,init ringOut) where+ ts = (inputT ofTasks onTasks)+ (ress,ntssNtoMe) = unzip $ genResNReqs $ map wf ts' --seperate+ reqList = Me : mergeS [ringIn, --merge external Requests+ ntssNtoMe] rnf --and nf reduced local Requests+ -- manage Taskpool & Requests+ (ts',ringOut) = control ttA ttSplit ttD sUpdate reqList ts st isFirst+ sFinal = getState $ last ringOut+++control:: (Trans t, Trans s) =>+ ([t]->[t]->s->[t]) -> --Taskpool Transform Attach+ ([t]->s->([t],[t])) -> --Split Policy (remote Req)+ ([t]->s->([t],Maybe (t,s))) -> --tt Detach (local Req)+ (s->s->Bool)-> --Checks if newState is better than oldState+ [Req [t] s]->[t]->s->Bool-> --reqs,tasks,state,isFirstInRing+ ([(t,s)],[Req [t] s]) --localTasks,RequestsToRing+control ttA ttSplit ttD sUpdate requests initTasks st isFirst + = distribWork requests initTasks Nothing st (0,0)+ where+ --until no tasks left: react on own and Others requests & add new Tasks+ --distribWork :: Trans t => [Req [t] s] -> [t] -> $+ -- Maybe (ChanName (Req [t] s))->(Int,Int)-> ([t],[ReqS [t] s],s)+ distribWork (TasksNMe nts:rs) tS replyCh st sNr --selfmade Tasks arrive+ = distribWork (Me:rs) (ttA tS nts st) replyCh st sNr --add Tasks and MeReq + + distribWork (NewState st':rs) tS replyCh st sNr --Updated State arrives+ | sUpdate st' st = let (tS',wReqs') =distribWork rs tS replyCh st' sNr+ in (tS',(NewState st':wReqs')) --then check and send + | otherwise = distribWork rs tS replyCh st sNr --or discard+ + distribWork (req@(Others tag tCh):rs) [] replyCh st sNr --Others Request &+ | tag==None = (tS',req:wReqs') --no tasks left --> pass Request + | otherwise = (tS', Others Black tCh : wReqs') --I'm still working -> Black+ where(tS',wReqs') = distribWork rs [] replyCh st sNr + + distribWork (Me:rs) [] replyCh st sNr = --last own Task solved and no new ones+ new (\reqChan (newTS,replyChan) -> --gen new reqChan to get newTS & replyC+ let (tS',wReqs) = passWhileReceive (mergeS [rs, --wait for fst newTask+ newTS `pseq` [TasksNMe newTS]] r0) replyChan st sNr --to merge+ tag | isFirst = Black --First Worker starts Black (For Termination)+ | otherwise = None --normal Workers with None Tag+ in(case replyCh of --First own Request into Ring- others dynamic+ Nothing -> (tS', Others tag reqChan : wReqs)+ Just replyCh' -> parfill replyCh' (Others tag reqChan) + (tS',wReqs)))+ + distribWork (Me:rs) tS replyCh st sNr --local Request and Tasks present+ = let (tS',tDetatch) = ttD tS st --TaskpoolTransform Detatch+ (tsDetatch,wReqs) = case tDetatch of + Nothing -> distribWork (Me:rs) [] replyCh st sNr + Just t -> distribWork rs tS' replyCh st sNr+ in ((maybeToList tDetatch)++tsDetatch,wReqs) --add Maybe one Task to wf+ + distribWork reqs@(Others _ tCh :rs) tS replyCh st (s,r) --foreign Req & have Ts+ = let (holdTs,sendTs) = ttSplit tS st --split ts to send and ts to hold+ ((tS',wReqs'),replyReq) + = new (\replyChan replyReq' -> --gen ReplyC and send Tasks & new+ parfill tCh (sendTs,Just replyChan) --ReplyC in Chan of the Req+ ((distribWork rs holdTs replyCh st (s+1,r)),replyReq')) + in case sendTs of --ReplyReqToOutp+ [] -> distribWork reqs [] replyCh st (s,r) --No tasks left+ (_:_) -> (tS',mergeS [[replyReq],wReqs'] rnf)++-- Pass all until foreign Tasks arrive or Termination starts+-- passWhileRecive :: Trans t => [ReqS [t] s] -> Maybe(ChanName (ReqS [t] s)) +-- -> (Int,Int) -> ([t],[ReqS [t] s])+ passWhileReceive (NewState st':rs) replyCh st sNr --Updated State arrives+ | sUpdate st' st =let (tS',wReqs')=passWhileReceive rs replyCh st' sNr+ in (tS',(NewState st':wReqs')) --then check and send + | otherwise = passWhileReceive rs replyCh st sNr --or discard+ + passWhileReceive (req@(Others None tCh):rs) replyCh st sNr --Req of normal + = let (tS',wReqs) = passWhileReceive rs replyCh st sNr --Worker -> pass it+ in (tS',req:wReqs)+ + passWhileReceive (req@(Others Black tCh ):rs) replyCh st (s,r) --Black Req+ | (not isFirst) = (tS',req :wReqs) --normal Workers: pass it+ | otherwise = (tS',req':wReqs) --First Worker: new Round starts White+ where (tS',wReqs) = passWhileReceive rs replyCh st (s,r)+ req'= Others (White s r 0 0) tCh --Start with own Counters+ + passWhileReceive (Others (White s1 r1 s2 r2) tCh :rs) replyCh st (s,r) + | (not isFirst) = (tS',req':wReqs) --Normal Workers: add Counter and pass+ --4 counters equal -> pass Black as end of reqs Symbol, start Termination+ | otherwise = if terminate + then ([],Others Black tCh : (termRing rs ++ [NewState st]))+ else (tS',req'':wReqs) --no Termination+ where (tS',wReqs) = passWhileReceive rs replyCh st (s,r)+ req' = Others (White (s1+s) (r1+r) s2 r2) tCh --add Counters+ req'' = Others (White s r s1 r1) tCh --Move Counters->NewTurn + terminate = (s1==r1)&&(r1==s2)&&(s2==r2) --Check Termination++ passWhileReceive (TasksNMe newTS:rs) replyCh st (s,r) --Task List arrives+ | null newTS = ([],(termRing rs) --got empty newTs -> begin Termination+ ++ [NewState st]) --attach final State at the End+ | otherwise = (distribWork (Me:rs) newTS replyCh st (s,r+1)) --have newTs+++data Req t s = + Me | --Work Request of local Worker - Fuction+ --Request of other Workers with Tag, and Chanel to Send Tasks and+ Others { getTag :: Tag, + getReplyChan :: (ChanName (t,Maybe (ChanName(Req t s))))+ } | --Reply Chanel+ TasksNMe { getTask :: t} | -- New Tasks and additional Me Request to add+ NewState { getState :: s }++instance (NFData t, NFData s) => NFData (Req t s)+ where + rnf Me = () + rnf (Others t c) = rnf t `pseq` rnf c+ rnf (TasksNMe t) = rnf t+ rnf (NewState s) = rnf s+ +instance (Trans t,Trans s) => Trans (Req t s)++data Tag = Black | --no Termination Situation / Term Mode: Last Request in Ring+ White Int Int Int Int | --check Termination Situation:(send&recv)+ None --Request of normal Worker++instance NFData Tag + where rnf Black = ()+ rnf None = ()+ rnf (White a b c d) = rnf (a,b,c,d)++instance Eq Tag where+ Black == Black = True+ None == None = True+ White a b c d == White a' b' c' d' = (a,b,c,d)==(a',b',c',d')+ a == b = False+++---------------------auxiliary-----------------+termRing :: (Trans t,Trans s) => [Req [t] s] -> [Req [t] s]+termRing [] = [] -- Predecessors tells no more reqs+termRing (Others Black tCh : _ ) = parfill tCh ([],Nothing) [] --reply last req+termRing (Others None tCh : rs) = parfill tCh ([],Nothing) termRing rs --reply+termRing (_ : rs) = termRing rs --ignore isFirsts reply++genResNReqs :: (NFData t,NFData r',NFData s)=>+ [(Maybe (r',s),[t])] -> [(Maybe (r',s),Req [t] s)]+genResNReqs [] = [] --No more tasks+genResNReqs ((res@(Nothing,nts)):ress) --No new State -> Attach new Tasks + = rnf res `pseq` (Nothing,TasksNMe nts): genResNReqs ress+genResNReqs ((res@(Just (r,st),nts)):ress) --New State found -> Attach+ = rnf res `pseq` (Just (r,st),NewState st): genResNReqs ((Nothing,nts):ress)+++-----------------------------DEPRECATED---------------------------------+-- | Deprecated, same as 'workpoolSortedNonBlock'+{-# DEPRECATED masterWorker "better use workpoolSortedNonBlock instead" #-}+masterWorker :: (Trans a, Trans b) => + Int -> Int -> (a -> b) -> [a] -> [b]+masterWorker = workpoolSortedNonBlock++-- | Deprecated, same as 'wpNested'+{-# DEPRECATED mwNested "better use wpNested instead" #-}+mwNested :: forall t r . (Trans t, Trans r) => + [Int] -> [Int] -> (t -> r) -> [t] -> [r] +mwNested = wpNested++-- | Deprecated, same as 'wpDNI'+{-# DEPRECATED mwDNI "better use wpDNI instead" #-}+mwDNI :: (Trans t, Trans r) =>+ Int + -> Int + -> Int + -> Int + -> (t -> (r,[t]))+ -> [t] + -> [r] +mwDNI = wpDNI+ +-- | Deprecated, same as 'wpDynNested'+{-# DEPRECATED mwDynNested "better use wpDynNested instead" #-}+mwDynNested :: forall t r . (Trans t, Trans r) => + [Int] + -> [Int] + -> (t -> (r,[t]))+ -> [t] + -> [r] +mwDynNested = wpDynNested
+ LICENSE view
@@ -0,0 +1,10 @@+Copyright (c) 2005-2010, Philipps Universitaet Marburg.+All rights reserved.++Redistribution and use in source and binary forms, with or without modification, are permitted provided that the following conditions are met:+Redistributions of source code must retain the above copyright notice, this list of conditions and the following disclaimer.+Redistributions in binary form must reproduce the above copyright notice, this list of conditions and the following disclaimer in the documentation and/or other materials provided with the distribution.+Neither the name of the Philipps Universitaet Marburg nor the names of its contributors may be used to endorse or promote products derived from this software without specific prior written permission.++THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.+-----------------------------------------------------------------------------
+ Setup.hs view
@@ -0,0 +1,6 @@+module Main (main) where++import Distribution.Simple++main :: IO ()+main = defaultMainWithHooks autoconfUserHooks
+ configure view
@@ -0,0 +1,2929 @@+#! /bin/sh+# Guess values for system-dependent variables and create Makefiles.+# Generated by GNU Autoconf 2.68 for Eden skeleton library for parallel Haskell 1.1.0.0.+#+# Report bugs to <eden@informatik.uni-marburg.de>.+#+#+# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1998, 1999, 2000, 2001,+# 2002, 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010 Free Software+# Foundation, Inc.+#+#+# This configure script is free software; the Free Software Foundation+# gives unlimited permission to copy, distribute and modify it.+## -------------------- ##+## M4sh Initialization. ##+## -------------------- ##++# Be more Bourne compatible+DUALCASE=1; export DUALCASE # for MKS sh+if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then :+ emulate sh+ NULLCMD=:+ # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which+ # is contrary to our usage. Disable this feature.+ alias -g '${1+"$@"}'='"$@"'+ setopt NO_GLOB_SUBST+else+ case `(set -o) 2>/dev/null` in #(+ *posix*) :+ set -o posix ;; #(+ *) :+ ;;+esac+fi+++as_nl='+'+export as_nl+# Printing a long string crashes Solaris 7 /usr/bin/printf.+as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo+# Prefer a ksh shell builtin over an external printf program on Solaris,+# but without wasting forks for bash or zsh.+if test -z "$BASH_VERSION$ZSH_VERSION" \+ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then+ as_echo='print -r --'+ as_echo_n='print -rn --'+elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then+ as_echo='printf %s\n'+ as_echo_n='printf %s'+else+ if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then+ as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"'+ as_echo_n='/usr/ucb/echo -n'+ else+ as_echo_body='eval expr "X$1" : "X\\(.*\\)"'+ as_echo_n_body='eval+ arg=$1;+ case $arg in #(+ *"$as_nl"*)+ expr "X$arg" : "X\\(.*\\)$as_nl";+ arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;;+ esac;+ expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl"+ '+ export as_echo_n_body+ as_echo_n='sh -c $as_echo_n_body as_echo'+ fi+ export as_echo_body+ as_echo='sh -c $as_echo_body as_echo'+fi++# The user is always right.+if test "${PATH_SEPARATOR+set}" != set; then+ PATH_SEPARATOR=:+ (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {+ (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||+ PATH_SEPARATOR=';'+ }+fi+++# IFS+# We need space, tab and new line, in precisely that order. Quoting is+# there to prevent editors from complaining about space-tab.+# (If _AS_PATH_WALK were called with IFS unset, it would disable word+# splitting by setting IFS to empty value.)+IFS=" "" $as_nl"++# Find who we are. Look in the path if we contain no directory separator.+as_myself=+case $0 in #((+ *[\\/]* ) as_myself=$0 ;;+ *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR+for as_dir in $PATH+do+ IFS=$as_save_IFS+ test -z "$as_dir" && as_dir=.+ test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break+ done+IFS=$as_save_IFS++ ;;+esac+# We did not find ourselves, most probably we were run as `sh COMMAND'+# in which case we are not to be found in the path.+if test "x$as_myself" = x; then+ as_myself=$0+fi+if test ! -f "$as_myself"; then+ $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2+ exit 1+fi++# Unset variables that we do not need and which cause bugs (e.g. in+# pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1"+# suppresses any "Segmentation fault" message there. '((' could+# trigger a bug in pdksh 5.2.14.+for as_var in BASH_ENV ENV MAIL MAILPATH+do eval test x\${$as_var+set} = xset \+ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :+done+PS1='$ '+PS2='> '+PS4='+ '++# NLS nuisances.+LC_ALL=C+export LC_ALL+LANGUAGE=C+export LANGUAGE++# CDPATH.+(unset CDPATH) >/dev/null 2>&1 && unset CDPATH++if test "x$CONFIG_SHELL" = x; then+ as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then :+ emulate sh+ NULLCMD=:+ # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which+ # is contrary to our usage. Disable this feature.+ alias -g '\${1+\"\$@\"}'='\"\$@\"'+ setopt NO_GLOB_SUBST+else+ case \`(set -o) 2>/dev/null\` in #(+ *posix*) :+ set -o posix ;; #(+ *) :+ ;;+esac+fi+"+ as_required="as_fn_return () { (exit \$1); }+as_fn_success () { as_fn_return 0; }+as_fn_failure () { as_fn_return 1; }+as_fn_ret_success () { return 0; }+as_fn_ret_failure () { return 1; }++exitcode=0+as_fn_success || { exitcode=1; echo as_fn_success failed.; }+as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; }+as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; }+as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; }+if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then :++else+ exitcode=1; echo positional parameters were not saved.+fi+test x\$exitcode = x0 || exit 1"+ as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO+ as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO+ eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" &&+ test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1"+ if (eval "$as_required") 2>/dev/null; then :+ as_have_required=yes+else+ as_have_required=no+fi+ if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null; then :++else+ as_save_IFS=$IFS; IFS=$PATH_SEPARATOR+as_found=false+for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH+do+ IFS=$as_save_IFS+ test -z "$as_dir" && as_dir=.+ as_found=:+ case $as_dir in #(+ /*)+ for as_base in sh bash ksh sh5; do+ # Try only shells that exist, to save several forks.+ as_shell=$as_dir/$as_base+ if { test -f "$as_shell" || test -f "$as_shell.exe"; } &&+ { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$as_shell"; } 2>/dev/null; then :+ CONFIG_SHELL=$as_shell as_have_required=yes+ if { $as_echo "$as_bourne_compatible""$as_suggested" | as_run=a "$as_shell"; } 2>/dev/null; then :+ break 2+fi+fi+ done;;+ esac+ as_found=false+done+$as_found || { if { test -f "$SHELL" || test -f "$SHELL.exe"; } &&+ { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$SHELL"; } 2>/dev/null; then :+ CONFIG_SHELL=$SHELL as_have_required=yes+fi; }+IFS=$as_save_IFS+++ if test "x$CONFIG_SHELL" != x; then :+ # We cannot yet assume a decent shell, so we have to provide a+ # neutralization value for shells without unset; and this also+ # works around shells that cannot unset nonexistent variables.+ # Preserve -v and -x to the replacement shell.+ BASH_ENV=/dev/null+ ENV=/dev/null+ (unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV+ export CONFIG_SHELL+ case $- in # ((((+ *v*x* | *x*v* ) as_opts=-vx ;;+ *v* ) as_opts=-v ;;+ *x* ) as_opts=-x ;;+ * ) as_opts= ;;+ esac+ exec "$CONFIG_SHELL" $as_opts "$as_myself" ${1+"$@"}+fi++ if test x$as_have_required = xno; then :+ $as_echo "$0: This script requires a shell more modern than all"+ $as_echo "$0: the shells that I found on your system."+ if test x${ZSH_VERSION+set} = xset ; then+ $as_echo "$0: In particular, zsh $ZSH_VERSION has bugs and should"+ $as_echo "$0: be upgraded to zsh 4.3.4 or later."+ else+ $as_echo "$0: Please tell bug-autoconf@gnu.org and+$0: eden@informatik.uni-marburg.de about your system,+$0: including any error possibly output before this+$0: message. Then install a modern shell, or manually run+$0: the script under such a shell if you do have one."+ fi+ exit 1+fi+fi+fi+SHELL=${CONFIG_SHELL-/bin/sh}+export SHELL+# Unset more variables known to interfere with behavior of common tools.+CLICOLOR_FORCE= GREP_OPTIONS=+unset CLICOLOR_FORCE GREP_OPTIONS++## --------------------- ##+## M4sh Shell Functions. ##+## --------------------- ##+# as_fn_unset VAR+# ---------------+# Portably unset VAR.+as_fn_unset ()+{+ { eval $1=; unset $1;}+}+as_unset=as_fn_unset++# as_fn_set_status STATUS+# -----------------------+# Set $? to STATUS, without forking.+as_fn_set_status ()+{+ return $1+} # as_fn_set_status++# as_fn_exit STATUS+# -----------------+# Exit the shell with STATUS, even in a "trap 0" or "set -e" context.+as_fn_exit ()+{+ set +e+ as_fn_set_status $1+ exit $1+} # as_fn_exit++# as_fn_mkdir_p+# -------------+# Create "$as_dir" as a directory, including parents if necessary.+as_fn_mkdir_p ()+{++ case $as_dir in #(+ -*) as_dir=./$as_dir;;+ esac+ test -d "$as_dir" || eval $as_mkdir_p || {+ as_dirs=+ while :; do+ case $as_dir in #(+ *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'(+ *) as_qdir=$as_dir;;+ esac+ as_dirs="'$as_qdir' $as_dirs"+ as_dir=`$as_dirname -- "$as_dir" ||+$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \+ X"$as_dir" : 'X\(//\)[^/]' \| \+ X"$as_dir" : 'X\(//\)$' \| \+ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null ||+$as_echo X"$as_dir" |+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{+ s//\1/+ q+ }+ /^X\(\/\/\)[^/].*/{+ s//\1/+ q+ }+ /^X\(\/\/\)$/{+ s//\1/+ q+ }+ /^X\(\/\).*/{+ s//\1/+ q+ }+ s/.*/./; q'`+ test -d "$as_dir" && break+ done+ test -z "$as_dirs" || eval "mkdir $as_dirs"+ } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir"+++} # as_fn_mkdir_p+# as_fn_append VAR VALUE+# ----------------------+# Append the text in VALUE to the end of the definition contained in VAR. Take+# advantage of any shell optimizations that allow amortized linear growth over+# repeated appends, instead of the typical quadratic growth present in naive+# implementations.+if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then :+ eval 'as_fn_append ()+ {+ eval $1+=\$2+ }'+else+ as_fn_append ()+ {+ eval $1=\$$1\$2+ }+fi # as_fn_append++# as_fn_arith ARG...+# ------------------+# Perform arithmetic evaluation on the ARGs, and store the result in the+# global $as_val. Take advantage of shells that can avoid forks. The arguments+# must be portable across $(()) and expr.+if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then :+ eval 'as_fn_arith ()+ {+ as_val=$(( $* ))+ }'+else+ as_fn_arith ()+ {+ as_val=`expr "$@" || test $? -eq 1`+ }+fi # as_fn_arith+++# as_fn_error STATUS ERROR [LINENO LOG_FD]+# ----------------------------------------+# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are+# provided, also output the error to LOG_FD, referencing LINENO. Then exit the+# script with STATUS, using 1 if that was 0.+as_fn_error ()+{+ as_status=$1; test $as_status -eq 0 && as_status=1+ if test "$4"; then+ as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack+ $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4+ fi+ $as_echo "$as_me: error: $2" >&2+ as_fn_exit $as_status+} # as_fn_error++if expr a : '\(a\)' >/dev/null 2>&1 &&+ test "X`expr 00001 : '.*\(...\)'`" = X001; then+ as_expr=expr+else+ as_expr=false+fi++if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then+ as_basename=basename+else+ as_basename=false+fi++if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then+ as_dirname=dirname+else+ as_dirname=false+fi++as_me=`$as_basename -- "$0" ||+$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \+ X"$0" : 'X\(//\)$' \| \+ X"$0" : 'X\(/\)' \| . 2>/dev/null ||+$as_echo X/"$0" |+ sed '/^.*\/\([^/][^/]*\)\/*$/{+ s//\1/+ q+ }+ /^X\/\(\/\/\)$/{+ s//\1/+ q+ }+ /^X\/\(\/\).*/{+ s//\1/+ q+ }+ s/.*/./; q'`++# Avoid depending upon Character Ranges.+as_cr_letters='abcdefghijklmnopqrstuvwxyz'+as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'+as_cr_Letters=$as_cr_letters$as_cr_LETTERS+as_cr_digits='0123456789'+as_cr_alnum=$as_cr_Letters$as_cr_digits+++ as_lineno_1=$LINENO as_lineno_1a=$LINENO+ as_lineno_2=$LINENO as_lineno_2a=$LINENO+ eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" &&+ test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || {+ # Blame Lee E. McMahon (1931-1989) for sed's syntax. :-)+ sed -n '+ p+ /[$]LINENO/=+ ' <$as_myself |+ sed '+ s/[$]LINENO.*/&-/+ t lineno+ b+ :lineno+ N+ :loop+ s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/+ t loop+ s/-\n.*//+ ' >$as_me.lineno &&+ chmod +x "$as_me.lineno" ||+ { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; }++ # Don't try to exec as it changes $[0], causing all sort of problems+ # (the dirname of $[0] is not the place where we might find the+ # original and so on. Autoconf is especially sensitive to this).+ . "./$as_me.lineno"+ # Exit status is that of the last command.+ exit+}++ECHO_C= ECHO_N= ECHO_T=+case `echo -n x` in #(((((+-n*)+ case `echo 'xy\c'` in+ *c*) ECHO_T=' ';; # ECHO_T is single tab character.+ xy) ECHO_C='\c';;+ *) echo `echo ksh88 bug on AIX 6.1` > /dev/null+ ECHO_T=' ';;+ esac;;+*)+ ECHO_N='-n';;+esac++rm -f conf$$ conf$$.exe conf$$.file+if test -d conf$$.dir; then+ rm -f conf$$.dir/conf$$.file+else+ rm -f conf$$.dir+ mkdir conf$$.dir 2>/dev/null+fi+if (echo >conf$$.file) 2>/dev/null; then+ if ln -s conf$$.file conf$$ 2>/dev/null; then+ as_ln_s='ln -s'+ # ... but there are two gotchas:+ # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail.+ # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable.+ # In both cases, we have to default to `cp -p'.+ ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||+ as_ln_s='cp -p'+ elif ln conf$$.file conf$$ 2>/dev/null; then+ as_ln_s=ln+ else+ as_ln_s='cp -p'+ fi+else+ as_ln_s='cp -p'+fi+rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file+rmdir conf$$.dir 2>/dev/null++if mkdir -p . 2>/dev/null; then+ as_mkdir_p='mkdir -p "$as_dir"'+else+ test -d ./-p && rmdir ./-p+ as_mkdir_p=false+fi++if test -x / >/dev/null 2>&1; then+ as_test_x='test -x'+else+ if ls -dL / >/dev/null 2>&1; then+ as_ls_L_option=L+ else+ as_ls_L_option=+ fi+ as_test_x='+ eval sh -c '\''+ if test -d "$1"; then+ test -d "$1/.";+ else+ case $1 in #(+ -*)set "./$1";;+ esac;+ case `ls -ld'$as_ls_L_option' "$1" 2>/dev/null` in #((+ ???[sx]*):;;*)false;;esac;fi+ '\'' sh+ '+fi+as_executable_p=$as_test_x++# Sed expression to map a string onto a valid CPP name.+as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'"++# Sed expression to map a string onto a valid variable name.+as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'"+++test -n "$DJDIR" || exec 7<&0 </dev/null+exec 6>&1++# Name of the host.+# hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status,+# so uname gets run too.+ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q`++#+# Initializations.+#+ac_default_prefix=/usr/local+ac_clean_files=+ac_config_libobj_dir=.+LIBOBJS=+cross_compiling=no+subdirs=+MFLAGS=+MAKEFLAGS=++# Identity of this package.+PACKAGE_NAME='Eden skeleton library for parallel Haskell'+PACKAGE_TARNAME='edenskel'+PACKAGE_VERSION='1.1.0.0'+PACKAGE_STRING='Eden skeleton library for parallel Haskell 1.1.0.0'+PACKAGE_BUGREPORT='eden@informatik.uni-marburg.de'+PACKAGE_URL=''++ac_unique_file="edenskel.cabal"+ac_subst_vars='LTLIBOBJS+LIBOBJS+NOT_PARALLEL+WithGhc+GHC+target_alias+host_alias+build_alias+LIBS+ECHO_T+ECHO_N+ECHO_C+DEFS+mandir+localedir+libdir+psdir+pdfdir+dvidir+htmldir+infodir+docdir+oldincludedir+includedir+localstatedir+sharedstatedir+sysconfdir+datadir+datarootdir+libexecdir+sbindir+bindir+program_transform_name+prefix+exec_prefix+PACKAGE_URL+PACKAGE_BUGREPORT+PACKAGE_STRING+PACKAGE_VERSION+PACKAGE_TARNAME+PACKAGE_NAME+PATH_SEPARATOR+SHELL'+ac_subst_files=''+ac_user_opts='+enable_option_checking+with_compiler+'+ ac_precious_vars='build_alias+host_alias+target_alias'+++# Initialize some variables set by options.+ac_init_help=+ac_init_version=false+ac_unrecognized_opts=+ac_unrecognized_sep=+# The variables have the same names as the options, with+# dashes changed to underlines.+cache_file=/dev/null+exec_prefix=NONE+no_create=+no_recursion=+prefix=NONE+program_prefix=NONE+program_suffix=NONE+program_transform_name=s,x,x,+silent=+site=+srcdir=+verbose=+x_includes=NONE+x_libraries=NONE++# Installation directory options.+# These are left unexpanded so users can "make install exec_prefix=/foo"+# and all the variables that are supposed to be based on exec_prefix+# by default will actually change.+# Use braces instead of parens because sh, perl, etc. also accept them.+# (The list follows the same order as the GNU Coding Standards.)+bindir='${exec_prefix}/bin'+sbindir='${exec_prefix}/sbin'+libexecdir='${exec_prefix}/libexec'+datarootdir='${prefix}/share'+datadir='${datarootdir}'+sysconfdir='${prefix}/etc'+sharedstatedir='${prefix}/com'+localstatedir='${prefix}/var'+includedir='${prefix}/include'+oldincludedir='/usr/include'+docdir='${datarootdir}/doc/${PACKAGE_TARNAME}'+infodir='${datarootdir}/info'+htmldir='${docdir}'+dvidir='${docdir}'+pdfdir='${docdir}'+psdir='${docdir}'+libdir='${exec_prefix}/lib'+localedir='${datarootdir}/locale'+mandir='${datarootdir}/man'++ac_prev=+ac_dashdash=+for ac_option+do+ # If the previous option needs an argument, assign it.+ if test -n "$ac_prev"; then+ eval $ac_prev=\$ac_option+ ac_prev=+ continue+ fi++ case $ac_option in+ *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;;+ *=) ac_optarg= ;;+ *) ac_optarg=yes ;;+ esac++ # Accept the important Cygnus configure options, so we can diagnose typos.++ case $ac_dashdash$ac_option in+ --)+ ac_dashdash=yes ;;++ -bindir | --bindir | --bindi | --bind | --bin | --bi)+ ac_prev=bindir ;;+ -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*)+ bindir=$ac_optarg ;;++ -build | --build | --buil | --bui | --bu)+ ac_prev=build_alias ;;+ -build=* | --build=* | --buil=* | --bui=* | --bu=*)+ build_alias=$ac_optarg ;;++ -cache-file | --cache-file | --cache-fil | --cache-fi \+ | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c)+ ac_prev=cache_file ;;+ -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \+ | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*)+ cache_file=$ac_optarg ;;++ --config-cache | -C)+ cache_file=config.cache ;;++ -datadir | --datadir | --datadi | --datad)+ ac_prev=datadir ;;+ -datadir=* | --datadir=* | --datadi=* | --datad=*)+ datadir=$ac_optarg ;;++ -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \+ | --dataroo | --dataro | --datar)+ ac_prev=datarootdir ;;+ -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \+ | --dataroot=* | --dataroo=* | --dataro=* | --datar=*)+ datarootdir=$ac_optarg ;;++ -disable-* | --disable-*)+ ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'`+ # Reject names that are not valid shell variable names.+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&+ as_fn_error $? "invalid feature name: $ac_useropt"+ ac_useropt_orig=$ac_useropt+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`+ case $ac_user_opts in+ *"+"enable_$ac_useropt"+"*) ;;+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig"+ ac_unrecognized_sep=', ';;+ esac+ eval enable_$ac_useropt=no ;;++ -docdir | --docdir | --docdi | --doc | --do)+ ac_prev=docdir ;;+ -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*)+ docdir=$ac_optarg ;;++ -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv)+ ac_prev=dvidir ;;+ -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*)+ dvidir=$ac_optarg ;;++ -enable-* | --enable-*)+ ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'`+ # Reject names that are not valid shell variable names.+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&+ as_fn_error $? "invalid feature name: $ac_useropt"+ ac_useropt_orig=$ac_useropt+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`+ case $ac_user_opts in+ *"+"enable_$ac_useropt"+"*) ;;+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig"+ ac_unrecognized_sep=', ';;+ esac+ eval enable_$ac_useropt=\$ac_optarg ;;++ -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \+ | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \+ | --exec | --exe | --ex)+ ac_prev=exec_prefix ;;+ -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \+ | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \+ | --exec=* | --exe=* | --ex=*)+ exec_prefix=$ac_optarg ;;++ -gas | --gas | --ga | --g)+ # Obsolete; use --with-gas.+ with_gas=yes ;;++ -help | --help | --hel | --he | -h)+ ac_init_help=long ;;+ -help=r* | --help=r* | --hel=r* | --he=r* | -hr*)+ ac_init_help=recursive ;;+ -help=s* | --help=s* | --hel=s* | --he=s* | -hs*)+ ac_init_help=short ;;++ -host | --host | --hos | --ho)+ ac_prev=host_alias ;;+ -host=* | --host=* | --hos=* | --ho=*)+ host_alias=$ac_optarg ;;++ -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht)+ ac_prev=htmldir ;;+ -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \+ | --ht=*)+ htmldir=$ac_optarg ;;++ -includedir | --includedir | --includedi | --included | --include \+ | --includ | --inclu | --incl | --inc)+ ac_prev=includedir ;;+ -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \+ | --includ=* | --inclu=* | --incl=* | --inc=*)+ includedir=$ac_optarg ;;++ -infodir | --infodir | --infodi | --infod | --info | --inf)+ ac_prev=infodir ;;+ -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*)+ infodir=$ac_optarg ;;++ -libdir | --libdir | --libdi | --libd)+ ac_prev=libdir ;;+ -libdir=* | --libdir=* | --libdi=* | --libd=*)+ libdir=$ac_optarg ;;++ -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \+ | --libexe | --libex | --libe)+ ac_prev=libexecdir ;;+ -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \+ | --libexe=* | --libex=* | --libe=*)+ libexecdir=$ac_optarg ;;++ -localedir | --localedir | --localedi | --localed | --locale)+ ac_prev=localedir ;;+ -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*)+ localedir=$ac_optarg ;;++ -localstatedir | --localstatedir | --localstatedi | --localstated \+ | --localstate | --localstat | --localsta | --localst | --locals)+ ac_prev=localstatedir ;;+ -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \+ | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*)+ localstatedir=$ac_optarg ;;++ -mandir | --mandir | --mandi | --mand | --man | --ma | --m)+ ac_prev=mandir ;;+ -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*)+ mandir=$ac_optarg ;;++ -nfp | --nfp | --nf)+ # Obsolete; use --without-fp.+ with_fp=no ;;++ -no-create | --no-create | --no-creat | --no-crea | --no-cre \+ | --no-cr | --no-c | -n)+ no_create=yes ;;++ -no-recursion | --no-recursion | --no-recursio | --no-recursi \+ | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r)+ no_recursion=yes ;;++ -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \+ | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \+ | --oldin | --oldi | --old | --ol | --o)+ ac_prev=oldincludedir ;;+ -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \+ | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \+ | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*)+ oldincludedir=$ac_optarg ;;++ -prefix | --prefix | --prefi | --pref | --pre | --pr | --p)+ ac_prev=prefix ;;+ -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*)+ prefix=$ac_optarg ;;++ -program-prefix | --program-prefix | --program-prefi | --program-pref \+ | --program-pre | --program-pr | --program-p)+ ac_prev=program_prefix ;;+ -program-prefix=* | --program-prefix=* | --program-prefi=* \+ | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*)+ program_prefix=$ac_optarg ;;++ -program-suffix | --program-suffix | --program-suffi | --program-suff \+ | --program-suf | --program-su | --program-s)+ ac_prev=program_suffix ;;+ -program-suffix=* | --program-suffix=* | --program-suffi=* \+ | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*)+ program_suffix=$ac_optarg ;;++ -program-transform-name | --program-transform-name \+ | --program-transform-nam | --program-transform-na \+ | --program-transform-n | --program-transform- \+ | --program-transform | --program-transfor \+ | --program-transfo | --program-transf \+ | --program-trans | --program-tran \+ | --progr-tra | --program-tr | --program-t)+ ac_prev=program_transform_name ;;+ -program-transform-name=* | --program-transform-name=* \+ | --program-transform-nam=* | --program-transform-na=* \+ | --program-transform-n=* | --program-transform-=* \+ | --program-transform=* | --program-transfor=* \+ | --program-transfo=* | --program-transf=* \+ | --program-trans=* | --program-tran=* \+ | --progr-tra=* | --program-tr=* | --program-t=*)+ program_transform_name=$ac_optarg ;;++ -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd)+ ac_prev=pdfdir ;;+ -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*)+ pdfdir=$ac_optarg ;;++ -psdir | --psdir | --psdi | --psd | --ps)+ ac_prev=psdir ;;+ -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*)+ psdir=$ac_optarg ;;++ -q | -quiet | --quiet | --quie | --qui | --qu | --q \+ | -silent | --silent | --silen | --sile | --sil)+ silent=yes ;;++ -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb)+ ac_prev=sbindir ;;+ -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \+ | --sbi=* | --sb=*)+ sbindir=$ac_optarg ;;++ -sharedstatedir | --sharedstatedir | --sharedstatedi \+ | --sharedstated | --sharedstate | --sharedstat | --sharedsta \+ | --sharedst | --shareds | --shared | --share | --shar \+ | --sha | --sh)+ ac_prev=sharedstatedir ;;+ -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \+ | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \+ | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \+ | --sha=* | --sh=*)+ sharedstatedir=$ac_optarg ;;++ -site | --site | --sit)+ ac_prev=site ;;+ -site=* | --site=* | --sit=*)+ site=$ac_optarg ;;++ -srcdir | --srcdir | --srcdi | --srcd | --src | --sr)+ ac_prev=srcdir ;;+ -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*)+ srcdir=$ac_optarg ;;++ -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \+ | --syscon | --sysco | --sysc | --sys | --sy)+ ac_prev=sysconfdir ;;+ -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \+ | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*)+ sysconfdir=$ac_optarg ;;++ -target | --target | --targe | --targ | --tar | --ta | --t)+ ac_prev=target_alias ;;+ -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*)+ target_alias=$ac_optarg ;;++ -v | -verbose | --verbose | --verbos | --verbo | --verb)+ verbose=yes ;;++ -version | --version | --versio | --versi | --vers | -V)+ ac_init_version=: ;;++ -with-* | --with-*)+ ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'`+ # Reject names that are not valid shell variable names.+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&+ as_fn_error $? "invalid package name: $ac_useropt"+ ac_useropt_orig=$ac_useropt+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`+ case $ac_user_opts in+ *"+"with_$ac_useropt"+"*) ;;+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig"+ ac_unrecognized_sep=', ';;+ esac+ eval with_$ac_useropt=\$ac_optarg ;;++ -without-* | --without-*)+ ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'`+ # Reject names that are not valid shell variable names.+ expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null &&+ as_fn_error $? "invalid package name: $ac_useropt"+ ac_useropt_orig=$ac_useropt+ ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'`+ case $ac_user_opts in+ *"+"with_$ac_useropt"+"*) ;;+ *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig"+ ac_unrecognized_sep=', ';;+ esac+ eval with_$ac_useropt=no ;;++ --x)+ # Obsolete; use --with-x.+ with_x=yes ;;++ -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \+ | --x-incl | --x-inc | --x-in | --x-i)+ ac_prev=x_includes ;;+ -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \+ | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*)+ x_includes=$ac_optarg ;;++ -x-libraries | --x-libraries | --x-librarie | --x-librari \+ | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l)+ ac_prev=x_libraries ;;+ -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \+ | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*)+ x_libraries=$ac_optarg ;;++ -*) as_fn_error $? "unrecognized option: \`$ac_option'+Try \`$0 --help' for more information"+ ;;++ *=*)+ ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='`+ # Reject names that are not valid shell variable names.+ case $ac_envvar in #(+ '' | [0-9]* | *[!_$as_cr_alnum]* )+ as_fn_error $? "invalid variable name: \`$ac_envvar'" ;;+ esac+ eval $ac_envvar=\$ac_optarg+ export $ac_envvar ;;++ *)+ # FIXME: should be removed in autoconf 3.0.+ $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2+ expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null &&+ $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2+ : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}"+ ;;++ esac+done++if test -n "$ac_prev"; then+ ac_option=--`echo $ac_prev | sed 's/_/-/g'`+ as_fn_error $? "missing argument to $ac_option"+fi++if test -n "$ac_unrecognized_opts"; then+ case $enable_option_checking in+ no) ;;+ fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;;+ *) $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;;+ esac+fi++# Check all directory arguments for consistency.+for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \+ datadir sysconfdir sharedstatedir localstatedir includedir \+ oldincludedir docdir infodir htmldir dvidir pdfdir psdir \+ libdir localedir mandir+do+ eval ac_val=\$$ac_var+ # Remove trailing slashes.+ case $ac_val in+ */ )+ ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'`+ eval $ac_var=\$ac_val;;+ esac+ # Be sure to have absolute directory names.+ case $ac_val in+ [\\/$]* | ?:[\\/]* ) continue;;+ NONE | '' ) case $ac_var in *prefix ) continue;; esac;;+ esac+ as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val"+done++# There might be people who depend on the old broken behavior: `$host'+# used to hold the argument of --host etc.+# FIXME: To remove some day.+build=$build_alias+host=$host_alias+target=$target_alias++# FIXME: To remove some day.+if test "x$host_alias" != x; then+ if test "x$build_alias" = x; then+ cross_compiling=maybe+ $as_echo "$as_me: WARNING: if you wanted to set the --build type, don't use --host.+ If a cross compiler is detected then cross compile mode will be used" >&2+ elif test "x$build_alias" != "x$host_alias"; then+ cross_compiling=yes+ fi+fi++ac_tool_prefix=+test -n "$host_alias" && ac_tool_prefix=$host_alias-++test "$silent" = yes && exec 6>/dev/null+++ac_pwd=`pwd` && test -n "$ac_pwd" &&+ac_ls_di=`ls -di .` &&+ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` ||+ as_fn_error $? "working directory cannot be determined"+test "X$ac_ls_di" = "X$ac_pwd_ls_di" ||+ as_fn_error $? "pwd does not report name of working directory"+++# Find the source files, if location was not specified.+if test -z "$srcdir"; then+ ac_srcdir_defaulted=yes+ # Try the directory containing this script, then the parent directory.+ ac_confdir=`$as_dirname -- "$as_myself" ||+$as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \+ X"$as_myself" : 'X\(//\)[^/]' \| \+ X"$as_myself" : 'X\(//\)$' \| \+ X"$as_myself" : 'X\(/\)' \| . 2>/dev/null ||+$as_echo X"$as_myself" |+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{+ s//\1/+ q+ }+ /^X\(\/\/\)[^/].*/{+ s//\1/+ q+ }+ /^X\(\/\/\)$/{+ s//\1/+ q+ }+ /^X\(\/\).*/{+ s//\1/+ q+ }+ s/.*/./; q'`+ srcdir=$ac_confdir+ if test ! -r "$srcdir/$ac_unique_file"; then+ srcdir=..+ fi+else+ ac_srcdir_defaulted=no+fi+if test ! -r "$srcdir/$ac_unique_file"; then+ test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .."+ as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir"+fi+ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work"+ac_abs_confdir=`(+ cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg"+ pwd)`+# When building in place, set srcdir=.+if test "$ac_abs_confdir" = "$ac_pwd"; then+ srcdir=.+fi+# Remove unnecessary trailing slashes from srcdir.+# Double slashes in file names in object file debugging info+# mess up M-x gdb in Emacs.+case $srcdir in+*/) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;;+esac+for ac_var in $ac_precious_vars; do+ eval ac_env_${ac_var}_set=\${${ac_var}+set}+ eval ac_env_${ac_var}_value=\$${ac_var}+ eval ac_cv_env_${ac_var}_set=\${${ac_var}+set}+ eval ac_cv_env_${ac_var}_value=\$${ac_var}+done++#+# Report the --help message.+#+if test "$ac_init_help" = "long"; then+ # Omit some internal or obsolete options to make the list less imposing.+ # This message is too long to be a string in the A/UX 3.1 sh.+ cat <<_ACEOF+\`configure' configures Eden skeleton library for parallel Haskell 1.1.0.0 to adapt to many kinds of systems.++Usage: $0 [OPTION]... [VAR=VALUE]...++To assign environment variables (e.g., CC, CFLAGS...), specify them as+VAR=VALUE. See below for descriptions of some of the useful variables.++Defaults for the options are specified in brackets.++Configuration:+ -h, --help display this help and exit+ --help=short display options specific to this package+ --help=recursive display the short help of all the included packages+ -V, --version display version information and exit+ -q, --quiet, --silent do not print \`checking ...' messages+ --cache-file=FILE cache test results in FILE [disabled]+ -C, --config-cache alias for \`--cache-file=config.cache'+ -n, --no-create do not create output files+ --srcdir=DIR find the sources in DIR [configure dir or \`..']++Installation directories:+ --prefix=PREFIX install architecture-independent files in PREFIX+ [$ac_default_prefix]+ --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX+ [PREFIX]++By default, \`make install' will install all the files in+\`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify+an installation prefix other than \`$ac_default_prefix' using \`--prefix',+for instance \`--prefix=\$HOME'.++For better control, use the options below.++Fine tuning of the installation directories:+ --bindir=DIR user executables [EPREFIX/bin]+ --sbindir=DIR system admin executables [EPREFIX/sbin]+ --libexecdir=DIR program executables [EPREFIX/libexec]+ --sysconfdir=DIR read-only single-machine data [PREFIX/etc]+ --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com]+ --localstatedir=DIR modifiable single-machine data [PREFIX/var]+ --libdir=DIR object code libraries [EPREFIX/lib]+ --includedir=DIR C header files [PREFIX/include]+ --oldincludedir=DIR C header files for non-gcc [/usr/include]+ --datarootdir=DIR read-only arch.-independent data root [PREFIX/share]+ --datadir=DIR read-only architecture-independent data [DATAROOTDIR]+ --infodir=DIR info documentation [DATAROOTDIR/info]+ --localedir=DIR locale-dependent data [DATAROOTDIR/locale]+ --mandir=DIR man documentation [DATAROOTDIR/man]+ --docdir=DIR documentation root [DATAROOTDIR/doc/edenskel]+ --htmldir=DIR html documentation [DOCDIR]+ --dvidir=DIR dvi documentation [DOCDIR]+ --pdfdir=DIR pdf documentation [DOCDIR]+ --psdir=DIR ps documentation [DOCDIR]+_ACEOF++ cat <<\_ACEOF+_ACEOF+fi++if test -n "$ac_init_help"; then+ case $ac_init_help in+ short | recursive ) echo "Configuration of Eden skeleton library for parallel Haskell 1.1.0.0:";;+ esac+ cat <<\_ACEOF++Optional Packages:+ --with-PACKAGE[=ARG] use PACKAGE [ARG=yes]+ --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no)+ --with-compiler=ARG Use path ARG for GHC (we only support GHC!)++Report bugs to <eden@informatik.uni-marburg.de>.+_ACEOF+ac_status=$?+fi++if test "$ac_init_help" = "recursive"; then+ # If there are subdirs, report their specific --help.+ for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue+ test -d "$ac_dir" ||+ { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } ||+ continue+ ac_builddir=.++case "$ac_dir" in+.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;+*)+ ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'`+ # A ".." for each directory in $ac_dir_suffix.+ ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'`+ case $ac_top_builddir_sub in+ "") ac_top_builddir_sub=. ac_top_build_prefix= ;;+ *) ac_top_build_prefix=$ac_top_builddir_sub/ ;;+ esac ;;+esac+ac_abs_top_builddir=$ac_pwd+ac_abs_builddir=$ac_pwd$ac_dir_suffix+# for backward compatibility:+ac_top_builddir=$ac_top_build_prefix++case $srcdir in+ .) # We are building in place.+ ac_srcdir=.+ ac_top_srcdir=$ac_top_builddir_sub+ ac_abs_top_srcdir=$ac_pwd ;;+ [\\/]* | ?:[\\/]* ) # Absolute name.+ ac_srcdir=$srcdir$ac_dir_suffix;+ ac_top_srcdir=$srcdir+ ac_abs_top_srcdir=$srcdir ;;+ *) # Relative name.+ ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix+ ac_top_srcdir=$ac_top_build_prefix$srcdir+ ac_abs_top_srcdir=$ac_pwd/$srcdir ;;+esac+ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix++ cd "$ac_dir" || { ac_status=$?; continue; }+ # Check for guested configure.+ if test -f "$ac_srcdir/configure.gnu"; then+ echo &&+ $SHELL "$ac_srcdir/configure.gnu" --help=recursive+ elif test -f "$ac_srcdir/configure"; then+ echo &&+ $SHELL "$ac_srcdir/configure" --help=recursive+ else+ $as_echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2+ fi || ac_status=$?+ cd "$ac_pwd" || { ac_status=$?; break; }+ done+fi++test -n "$ac_init_help" && exit $ac_status+if $ac_init_version; then+ cat <<\_ACEOF+Eden skeleton library for parallel Haskell configure 1.1.0.0+generated by GNU Autoconf 2.68++Copyright (C) 2010 Free Software Foundation, Inc.+This configure script is free software; the Free Software Foundation+gives unlimited permission to copy, distribute and modify it.+_ACEOF+ exit+fi++## ------------------------ ##+## Autoconf initialization. ##+## ------------------------ ##+cat >config.log <<_ACEOF+This file contains any messages produced by compilers while+running configure, to aid debugging if configure makes a mistake.++It was created by Eden skeleton library for parallel Haskell $as_me 1.1.0.0, which was+generated by GNU Autoconf 2.68. Invocation command line was++ $ $0 $@++_ACEOF+exec 5>>config.log+{+cat <<_ASUNAME+## --------- ##+## Platform. ##+## --------- ##++hostname = `(hostname || uname -n) 2>/dev/null | sed 1q`+uname -m = `(uname -m) 2>/dev/null || echo unknown`+uname -r = `(uname -r) 2>/dev/null || echo unknown`+uname -s = `(uname -s) 2>/dev/null || echo unknown`+uname -v = `(uname -v) 2>/dev/null || echo unknown`++/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown`+/bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown`++/bin/arch = `(/bin/arch) 2>/dev/null || echo unknown`+/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown`+/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown`+/usr/bin/hostinfo = `(/usr/bin/hostinfo) 2>/dev/null || echo unknown`+/bin/machine = `(/bin/machine) 2>/dev/null || echo unknown`+/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown`+/bin/universe = `(/bin/universe) 2>/dev/null || echo unknown`++_ASUNAME++as_save_IFS=$IFS; IFS=$PATH_SEPARATOR+for as_dir in $PATH+do+ IFS=$as_save_IFS+ test -z "$as_dir" && as_dir=.+ $as_echo "PATH: $as_dir"+ done+IFS=$as_save_IFS++} >&5++cat >&5 <<_ACEOF+++## ----------- ##+## Core tests. ##+## ----------- ##++_ACEOF+++# Keep a trace of the command line.+# Strip out --no-create and --no-recursion so they do not pile up.+# Strip out --silent because we don't want to record it for future runs.+# Also quote any args containing shell meta-characters.+# Make two passes to allow for proper duplicate-argument suppression.+ac_configure_args=+ac_configure_args0=+ac_configure_args1=+ac_must_keep_next=false+for ac_pass in 1 2+do+ for ac_arg+ do+ case $ac_arg in+ -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;;+ -q | -quiet | --quiet | --quie | --qui | --qu | --q \+ | -silent | --silent | --silen | --sile | --sil)+ continue ;;+ *\'*)+ ac_arg=`$as_echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;;+ esac+ case $ac_pass in+ 1) as_fn_append ac_configure_args0 " '$ac_arg'" ;;+ 2)+ as_fn_append ac_configure_args1 " '$ac_arg'"+ if test $ac_must_keep_next = true; then+ ac_must_keep_next=false # Got value, back to normal.+ else+ case $ac_arg in+ *=* | --config-cache | -C | -disable-* | --disable-* \+ | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \+ | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \+ | -with-* | --with-* | -without-* | --without-* | --x)+ case "$ac_configure_args0 " in+ "$ac_configure_args1"*" '$ac_arg' "* ) continue ;;+ esac+ ;;+ -* ) ac_must_keep_next=true ;;+ esac+ fi+ as_fn_append ac_configure_args " '$ac_arg'"+ ;;+ esac+ done+done+{ ac_configure_args0=; unset ac_configure_args0;}+{ ac_configure_args1=; unset ac_configure_args1;}++# When interrupted or exit'd, cleanup temporary files, and complete+# config.log. We remove comments because anyway the quotes in there+# would cause problems or look ugly.+# WARNING: Use '\'' to represent an apostrophe within the trap.+# WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug.+trap 'exit_status=$?+ # Save into config.log some information that might help in debugging.+ {+ echo++ $as_echo "## ---------------- ##+## Cache variables. ##+## ---------------- ##"+ echo+ # The following way of writing the cache mishandles newlines in values,+(+ for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do+ eval ac_val=\$$ac_var+ case $ac_val in #(+ *${as_nl}*)+ case $ac_var in #(+ *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5+$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;;+ esac+ case $ac_var in #(+ _ | IFS | as_nl) ;; #(+ BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(+ *) { eval $ac_var=; unset $ac_var;} ;;+ esac ;;+ esac+ done+ (set) 2>&1 |+ case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #(+ *${as_nl}ac_space=\ *)+ sed -n \+ "s/'\''/'\''\\\\'\'''\''/g;+ s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p"+ ;; #(+ *)+ sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p"+ ;;+ esac |+ sort+)+ echo++ $as_echo "## ----------------- ##+## Output variables. ##+## ----------------- ##"+ echo+ for ac_var in $ac_subst_vars+ do+ eval ac_val=\$$ac_var+ case $ac_val in+ *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;;+ esac+ $as_echo "$ac_var='\''$ac_val'\''"+ done | sort+ echo++ if test -n "$ac_subst_files"; then+ $as_echo "## ------------------- ##+## File substitutions. ##+## ------------------- ##"+ echo+ for ac_var in $ac_subst_files+ do+ eval ac_val=\$$ac_var+ case $ac_val in+ *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;;+ esac+ $as_echo "$ac_var='\''$ac_val'\''"+ done | sort+ echo+ fi++ if test -s confdefs.h; then+ $as_echo "## ----------- ##+## confdefs.h. ##+## ----------- ##"+ echo+ cat confdefs.h+ echo+ fi+ test "$ac_signal" != 0 &&+ $as_echo "$as_me: caught signal $ac_signal"+ $as_echo "$as_me: exit $exit_status"+ } >&5+ rm -f core *.core core.conftest.* &&+ rm -f -r conftest* confdefs* conf$$* $ac_clean_files &&+ exit $exit_status+' 0+for ac_signal in 1 2 13 15; do+ trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal+done+ac_signal=0++# confdefs.h avoids OS command line length limits that DEFS can exceed.+rm -f -r conftest* confdefs.h++$as_echo "/* confdefs.h */" > confdefs.h++# Predefined preprocessor variables.++cat >>confdefs.h <<_ACEOF+#define PACKAGE_NAME "$PACKAGE_NAME"+_ACEOF++cat >>confdefs.h <<_ACEOF+#define PACKAGE_TARNAME "$PACKAGE_TARNAME"+_ACEOF++cat >>confdefs.h <<_ACEOF+#define PACKAGE_VERSION "$PACKAGE_VERSION"+_ACEOF++cat >>confdefs.h <<_ACEOF+#define PACKAGE_STRING "$PACKAGE_STRING"+_ACEOF++cat >>confdefs.h <<_ACEOF+#define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT"+_ACEOF++cat >>confdefs.h <<_ACEOF+#define PACKAGE_URL "$PACKAGE_URL"+_ACEOF+++# Let the site file select an alternate cache file if it wants to.+# Prefer an explicitly selected file to automatically selected ones.+ac_site_file1=NONE+ac_site_file2=NONE+if test -n "$CONFIG_SITE"; then+ # We do not want a PATH search for config.site.+ case $CONFIG_SITE in #((+ -*) ac_site_file1=./$CONFIG_SITE;;+ */*) ac_site_file1=$CONFIG_SITE;;+ *) ac_site_file1=./$CONFIG_SITE;;+ esac+elif test "x$prefix" != xNONE; then+ ac_site_file1=$prefix/share/config.site+ ac_site_file2=$prefix/etc/config.site+else+ ac_site_file1=$ac_default_prefix/share/config.site+ ac_site_file2=$ac_default_prefix/etc/config.site+fi+for ac_site_file in "$ac_site_file1" "$ac_site_file2"+do+ test "x$ac_site_file" = xNONE && continue+ if test /dev/null != "$ac_site_file" && test -r "$ac_site_file"; then+ { $as_echo "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5+$as_echo "$as_me: loading site script $ac_site_file" >&6;}+ sed 's/^/| /' "$ac_site_file" >&5+ . "$ac_site_file" \+ || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}+as_fn_error $? "failed to load site script $ac_site_file+See \`config.log' for more details" "$LINENO" 5; }+ fi+done++if test -r "$cache_file"; then+ # Some versions of bash will fail to source /dev/null (special files+ # actually), so we avoid doing that. DJGPP emulates it as a regular file.+ if test /dev/null != "$cache_file" && test -f "$cache_file"; then+ { $as_echo "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5+$as_echo "$as_me: loading cache $cache_file" >&6;}+ case $cache_file in+ [\\/]* | ?:[\\/]* ) . "$cache_file";;+ *) . "./$cache_file";;+ esac+ fi+else+ { $as_echo "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5+$as_echo "$as_me: creating cache $cache_file" >&6;}+ >$cache_file+fi++# Check that the precious variables saved in the cache have kept the same+# value.+ac_cache_corrupted=false+for ac_var in $ac_precious_vars; do+ eval ac_old_set=\$ac_cv_env_${ac_var}_set+ eval ac_new_set=\$ac_env_${ac_var}_set+ eval ac_old_val=\$ac_cv_env_${ac_var}_value+ eval ac_new_val=\$ac_env_${ac_var}_value+ case $ac_old_set,$ac_new_set in+ set,)+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5+$as_echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;}+ ac_cache_corrupted=: ;;+ ,set)+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5+$as_echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;}+ ac_cache_corrupted=: ;;+ ,);;+ *)+ if test "x$ac_old_val" != "x$ac_new_val"; then+ # differences in whitespace do not lead to failure.+ ac_old_val_w=`echo x $ac_old_val`+ ac_new_val_w=`echo x $ac_new_val`+ if test "$ac_old_val_w" != "$ac_new_val_w"; then+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5+$as_echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;}+ ac_cache_corrupted=:+ else+ { $as_echo "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5+$as_echo "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;}+ eval $ac_var=\$ac_old_val+ fi+ { $as_echo "$as_me:${as_lineno-$LINENO}: former value: \`$ac_old_val'" >&5+$as_echo "$as_me: former value: \`$ac_old_val'" >&2;}+ { $as_echo "$as_me:${as_lineno-$LINENO}: current value: \`$ac_new_val'" >&5+$as_echo "$as_me: current value: \`$ac_new_val'" >&2;}+ fi;;+ esac+ # Pass precious variables to config.status.+ if test "$ac_new_set" = set; then+ case $ac_new_val in+ *\'*) ac_arg=$ac_var=`$as_echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;;+ *) ac_arg=$ac_var=$ac_new_val ;;+ esac+ case " $ac_configure_args " in+ *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy.+ *) as_fn_append ac_configure_args " '$ac_arg'" ;;+ esac+ fi+done+if $ac_cache_corrupted; then+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5+$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}+ { $as_echo "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5+$as_echo "$as_me: error: changes in the environment can compromise the build" >&2;}+ as_fn_error $? "run \`make distclean' and/or \`rm $cache_file' and start over" "$LINENO" 5+fi+## -------------------- ##+## Main body of script. ##+## -------------------- ##++ac_ext=c+ac_cpp='$CPP $CPPFLAGS'+ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'+ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'+ac_compiler_gnu=$ac_cv_c_compiler_gnu++++# Safety check: Ensure that we are in the correct source directory.+++# figure out GHC to use++# Check whether --with-compiler was given.+if test "${with_compiler+set}" = set; then :+ withval=$with_compiler; WithGhc="$withval"+else+ if test "$HC" = ""; then+ # Extract the first word of "ghc", so it can be a program name with args.+set dummy ghc; ac_word=$2+{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5+$as_echo_n "checking for $ac_word... " >&6; }+if ${ac_cv_path_GHC+:} false; then :+ $as_echo_n "(cached) " >&6+else+ case $GHC in+ [\\/]* | ?:[\\/]*)+ ac_cv_path_GHC="$GHC" # Let the user override the test with a path.+ ;;+ *)+ as_save_IFS=$IFS; IFS=$PATH_SEPARATOR+for as_dir in $PATH+do+ IFS=$as_save_IFS+ test -z "$as_dir" && as_dir=.+ for ac_exec_ext in '' $ac_executable_extensions; do+ if { test -f "$as_dir/$ac_word$ac_exec_ext" && $as_test_x "$as_dir/$ac_word$ac_exec_ext"; }; then+ ac_cv_path_GHC="$as_dir/$ac_word$ac_exec_ext"+ $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5+ break 2+ fi+done+ done+IFS=$as_save_IFS++ ;;+esac+fi+GHC=$ac_cv_path_GHC+if test -n "$GHC"; then+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: $GHC" >&5+$as_echo "$GHC" >&6; }+else+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5+$as_echo "no" >&6; }+fi+++ fi+ WithGhc="$GHC"+fi+++++# we require it to be really GHC+if test "$WithGhc" == ""; then :+ as_fn_error $? "GHC is required for this library." "$LINENO" 5+fi++# GHC should be callable+if $WithGhc --version; then :++else+ as_fn_error $? "Your GHC does not work!" "$LINENO" 5+fi++{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for Eden extensions to the GHC runtime system" >&5+$as_echo_n "checking for Eden extensions to the GHC runtime system... " >&6; }+# create Haskell which imports primitives+rm -f conftest.*;+cat > conftest.hs << EOF+{-# OPTIONS_GHC -XMagicHash #-}+module Edentest where+import GHC.Base(expectData#, connectToPort#, sendData# )+test s = expectData# s+EOF+#try to compile this, using WithGhc:+if $WithGhc -c conftest.hs 2>&5 ; then :+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: found" >&5+$as_echo "found" >&6; }; eden=YES+else+ { $as_echo "$as_me:${as_lineno-$LINENO}: result: not found" >&5+$as_echo "not found" >&6; }; eden=NO++fi++# Build the package as a simulation if the runtime does not support Eden+if test "$eden" = YES+ then { $as_echo "$as_me:${as_lineno-$LINENO}: result: Parallel build enabled" >&5+$as_echo "Parallel build enabled" >&6; }+ NOT_PARALLEL=+ else { $as_echo "$as_me:${as_lineno-$LINENO}: result: Parallel build disabled-using simulation" >&5+$as_echo "Parallel build disabled-using simulation" >&6; }+ NOT_PARALLEL=-DNOT_PARALLEL+fi+++# this creates the buildinfo file from buildinfo.in+ac_config_files="$ac_config_files edenskel.buildinfo"++cat >confcache <<\_ACEOF+# This file is a shell script that caches the results of configure+# tests run on this system so they can be shared between configure+# scripts and configure runs, see configure's option --config-cache.+# It is not useful on other systems. If it contains results you don't+# want to keep, you may remove or edit it.+#+# config.status only pays attention to the cache file if you give it+# the --recheck option to rerun configure.+#+# `ac_cv_env_foo' variables (set or unset) will be overridden when+# loading this file, other *unset* `ac_cv_foo' will be assigned the+# following values.++_ACEOF++# The following way of writing the cache mishandles newlines in values,+# but we know of no workaround that is simple, portable, and efficient.+# So, we kill variables containing newlines.+# Ultrix sh set writes to stderr and can't be redirected directly,+# and sets the high bit in the cache file unless we assign to the vars.+(+ for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do+ eval ac_val=\$$ac_var+ case $ac_val in #(+ *${as_nl}*)+ case $ac_var in #(+ *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5+$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;;+ esac+ case $ac_var in #(+ _ | IFS | as_nl) ;; #(+ BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(+ *) { eval $ac_var=; unset $ac_var;} ;;+ esac ;;+ esac+ done++ (set) 2>&1 |+ case $as_nl`(ac_space=' '; set) 2>&1` in #(+ *${as_nl}ac_space=\ *)+ # `set' does not quote correctly, so add quotes: double-quote+ # substitution turns \\\\ into \\, and sed turns \\ into \.+ sed -n \+ "s/'/'\\\\''/g;+ s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p"+ ;; #(+ *)+ # `set' quotes correctly as required by POSIX, so do not add quotes.+ sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p"+ ;;+ esac |+ sort+) |+ sed '+ /^ac_cv_env_/b end+ t clear+ :clear+ s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/+ t end+ s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/+ :end' >>confcache+if diff "$cache_file" confcache >/dev/null 2>&1; then :; else+ if test -w "$cache_file"; then+ if test "x$cache_file" != "x/dev/null"; then+ { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5+$as_echo "$as_me: updating cache $cache_file" >&6;}+ if test ! -f "$cache_file" || test -h "$cache_file"; then+ cat confcache >"$cache_file"+ else+ case $cache_file in #(+ */* | ?:*)+ mv -f confcache "$cache_file"$$ &&+ mv -f "$cache_file"$$ "$cache_file" ;; #(+ *)+ mv -f confcache "$cache_file" ;;+ esac+ fi+ fi+ else+ { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5+$as_echo "$as_me: not updating unwritable cache $cache_file" >&6;}+ fi+fi+rm -f confcache++test "x$prefix" = xNONE && prefix=$ac_default_prefix+# Let make expand exec_prefix.+test "x$exec_prefix" = xNONE && exec_prefix='${prefix}'++# Transform confdefs.h into DEFS.+# Protect against shell expansion while executing Makefile rules.+# Protect against Makefile macro expansion.+#+# If the first sed substitution is executed (which looks for macros that+# take arguments), then branch to the quote section. Otherwise,+# look for a macro that doesn't take arguments.+ac_script='+:mline+/\\$/{+ N+ s,\\\n,,+ b mline+}+t clear+:clear+s/^[ ]*#[ ]*define[ ][ ]*\([^ (][^ (]*([^)]*)\)[ ]*\(.*\)/-D\1=\2/g+t quote+s/^[ ]*#[ ]*define[ ][ ]*\([^ ][^ ]*\)[ ]*\(.*\)/-D\1=\2/g+t quote+b any+:quote+s/[ `~#$^&*(){}\\|;'\''"<>?]/\\&/g+s/\[/\\&/g+s/\]/\\&/g+s/\$/$$/g+H+:any+${+ g+ s/^\n//+ s/\n/ /g+ p+}+'+DEFS=`sed -n "$ac_script" confdefs.h`+++ac_libobjs=+ac_ltlibobjs=+U=+for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue+ # 1. Remove the extension, and $U if already installed.+ ac_script='s/\$U\././;s/\.o$//;s/\.obj$//'+ ac_i=`$as_echo "$ac_i" | sed "$ac_script"`+ # 2. Prepend LIBOBJDIR. When used with automake>=1.10 LIBOBJDIR+ # will be set to the directory where LIBOBJS objects are built.+ as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext"+ as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo'+done+LIBOBJS=$ac_libobjs++LTLIBOBJS=$ac_ltlibobjs++++: "${CONFIG_STATUS=./config.status}"+ac_write_fail=0+ac_clean_files_save=$ac_clean_files+ac_clean_files="$ac_clean_files $CONFIG_STATUS"+{ $as_echo "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5+$as_echo "$as_me: creating $CONFIG_STATUS" >&6;}+as_write_fail=0+cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1+#! $SHELL+# Generated by $as_me.+# Run this file to recreate the current configuration.+# Compiler output produced by configure, useful for debugging+# configure, is in config.log if it exists.++debug=false+ac_cs_recheck=false+ac_cs_silent=false++SHELL=\${CONFIG_SHELL-$SHELL}+export SHELL+_ASEOF+cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1+## -------------------- ##+## M4sh Initialization. ##+## -------------------- ##++# Be more Bourne compatible+DUALCASE=1; export DUALCASE # for MKS sh+if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then :+ emulate sh+ NULLCMD=:+ # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which+ # is contrary to our usage. Disable this feature.+ alias -g '${1+"$@"}'='"$@"'+ setopt NO_GLOB_SUBST+else+ case `(set -o) 2>/dev/null` in #(+ *posix*) :+ set -o posix ;; #(+ *) :+ ;;+esac+fi+++as_nl='+'+export as_nl+# Printing a long string crashes Solaris 7 /usr/bin/printf.+as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo+as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo+# Prefer a ksh shell builtin over an external printf program on Solaris,+# but without wasting forks for bash or zsh.+if test -z "$BASH_VERSION$ZSH_VERSION" \+ && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then+ as_echo='print -r --'+ as_echo_n='print -rn --'+elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then+ as_echo='printf %s\n'+ as_echo_n='printf %s'+else+ if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then+ as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"'+ as_echo_n='/usr/ucb/echo -n'+ else+ as_echo_body='eval expr "X$1" : "X\\(.*\\)"'+ as_echo_n_body='eval+ arg=$1;+ case $arg in #(+ *"$as_nl"*)+ expr "X$arg" : "X\\(.*\\)$as_nl";+ arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;;+ esac;+ expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl"+ '+ export as_echo_n_body+ as_echo_n='sh -c $as_echo_n_body as_echo'+ fi+ export as_echo_body+ as_echo='sh -c $as_echo_body as_echo'+fi++# The user is always right.+if test "${PATH_SEPARATOR+set}" != set; then+ PATH_SEPARATOR=:+ (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {+ (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||+ PATH_SEPARATOR=';'+ }+fi+++# IFS+# We need space, tab and new line, in precisely that order. Quoting is+# there to prevent editors from complaining about space-tab.+# (If _AS_PATH_WALK were called with IFS unset, it would disable word+# splitting by setting IFS to empty value.)+IFS=" "" $as_nl"++# Find who we are. Look in the path if we contain no directory separator.+as_myself=+case $0 in #((+ *[\\/]* ) as_myself=$0 ;;+ *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR+for as_dir in $PATH+do+ IFS=$as_save_IFS+ test -z "$as_dir" && as_dir=.+ test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break+ done+IFS=$as_save_IFS++ ;;+esac+# We did not find ourselves, most probably we were run as `sh COMMAND'+# in which case we are not to be found in the path.+if test "x$as_myself" = x; then+ as_myself=$0+fi+if test ! -f "$as_myself"; then+ $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2+ exit 1+fi++# Unset variables that we do not need and which cause bugs (e.g. in+# pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1"+# suppresses any "Segmentation fault" message there. '((' could+# trigger a bug in pdksh 5.2.14.+for as_var in BASH_ENV ENV MAIL MAILPATH+do eval test x\${$as_var+set} = xset \+ && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :+done+PS1='$ '+PS2='> '+PS4='+ '++# NLS nuisances.+LC_ALL=C+export LC_ALL+LANGUAGE=C+export LANGUAGE++# CDPATH.+(unset CDPATH) >/dev/null 2>&1 && unset CDPATH+++# as_fn_error STATUS ERROR [LINENO LOG_FD]+# ----------------------------------------+# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are+# provided, also output the error to LOG_FD, referencing LINENO. Then exit the+# script with STATUS, using 1 if that was 0.+as_fn_error ()+{+ as_status=$1; test $as_status -eq 0 && as_status=1+ if test "$4"; then+ as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack+ $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4+ fi+ $as_echo "$as_me: error: $2" >&2+ as_fn_exit $as_status+} # as_fn_error+++# as_fn_set_status STATUS+# -----------------------+# Set $? to STATUS, without forking.+as_fn_set_status ()+{+ return $1+} # as_fn_set_status++# as_fn_exit STATUS+# -----------------+# Exit the shell with STATUS, even in a "trap 0" or "set -e" context.+as_fn_exit ()+{+ set +e+ as_fn_set_status $1+ exit $1+} # as_fn_exit++# as_fn_unset VAR+# ---------------+# Portably unset VAR.+as_fn_unset ()+{+ { eval $1=; unset $1;}+}+as_unset=as_fn_unset+# as_fn_append VAR VALUE+# ----------------------+# Append the text in VALUE to the end of the definition contained in VAR. Take+# advantage of any shell optimizations that allow amortized linear growth over+# repeated appends, instead of the typical quadratic growth present in naive+# implementations.+if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then :+ eval 'as_fn_append ()+ {+ eval $1+=\$2+ }'+else+ as_fn_append ()+ {+ eval $1=\$$1\$2+ }+fi # as_fn_append++# as_fn_arith ARG...+# ------------------+# Perform arithmetic evaluation on the ARGs, and store the result in the+# global $as_val. Take advantage of shells that can avoid forks. The arguments+# must be portable across $(()) and expr.+if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then :+ eval 'as_fn_arith ()+ {+ as_val=$(( $* ))+ }'+else+ as_fn_arith ()+ {+ as_val=`expr "$@" || test $? -eq 1`+ }+fi # as_fn_arith+++if expr a : '\(a\)' >/dev/null 2>&1 &&+ test "X`expr 00001 : '.*\(...\)'`" = X001; then+ as_expr=expr+else+ as_expr=false+fi++if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then+ as_basename=basename+else+ as_basename=false+fi++if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then+ as_dirname=dirname+else+ as_dirname=false+fi++as_me=`$as_basename -- "$0" ||+$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \+ X"$0" : 'X\(//\)$' \| \+ X"$0" : 'X\(/\)' \| . 2>/dev/null ||+$as_echo X/"$0" |+ sed '/^.*\/\([^/][^/]*\)\/*$/{+ s//\1/+ q+ }+ /^X\/\(\/\/\)$/{+ s//\1/+ q+ }+ /^X\/\(\/\).*/{+ s//\1/+ q+ }+ s/.*/./; q'`++# Avoid depending upon Character Ranges.+as_cr_letters='abcdefghijklmnopqrstuvwxyz'+as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'+as_cr_Letters=$as_cr_letters$as_cr_LETTERS+as_cr_digits='0123456789'+as_cr_alnum=$as_cr_Letters$as_cr_digits++ECHO_C= ECHO_N= ECHO_T=+case `echo -n x` in #(((((+-n*)+ case `echo 'xy\c'` in+ *c*) ECHO_T=' ';; # ECHO_T is single tab character.+ xy) ECHO_C='\c';;+ *) echo `echo ksh88 bug on AIX 6.1` > /dev/null+ ECHO_T=' ';;+ esac;;+*)+ ECHO_N='-n';;+esac++rm -f conf$$ conf$$.exe conf$$.file+if test -d conf$$.dir; then+ rm -f conf$$.dir/conf$$.file+else+ rm -f conf$$.dir+ mkdir conf$$.dir 2>/dev/null+fi+if (echo >conf$$.file) 2>/dev/null; then+ if ln -s conf$$.file conf$$ 2>/dev/null; then+ as_ln_s='ln -s'+ # ... but there are two gotchas:+ # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail.+ # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable.+ # In both cases, we have to default to `cp -p'.+ ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||+ as_ln_s='cp -p'+ elif ln conf$$.file conf$$ 2>/dev/null; then+ as_ln_s=ln+ else+ as_ln_s='cp -p'+ fi+else+ as_ln_s='cp -p'+fi+rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file+rmdir conf$$.dir 2>/dev/null+++# as_fn_mkdir_p+# -------------+# Create "$as_dir" as a directory, including parents if necessary.+as_fn_mkdir_p ()+{++ case $as_dir in #(+ -*) as_dir=./$as_dir;;+ esac+ test -d "$as_dir" || eval $as_mkdir_p || {+ as_dirs=+ while :; do+ case $as_dir in #(+ *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'(+ *) as_qdir=$as_dir;;+ esac+ as_dirs="'$as_qdir' $as_dirs"+ as_dir=`$as_dirname -- "$as_dir" ||+$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \+ X"$as_dir" : 'X\(//\)[^/]' \| \+ X"$as_dir" : 'X\(//\)$' \| \+ X"$as_dir" : 'X\(/\)' \| . 2>/dev/null ||+$as_echo X"$as_dir" |+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{+ s//\1/+ q+ }+ /^X\(\/\/\)[^/].*/{+ s//\1/+ q+ }+ /^X\(\/\/\)$/{+ s//\1/+ q+ }+ /^X\(\/\).*/{+ s//\1/+ q+ }+ s/.*/./; q'`+ test -d "$as_dir" && break+ done+ test -z "$as_dirs" || eval "mkdir $as_dirs"+ } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir"+++} # as_fn_mkdir_p+if mkdir -p . 2>/dev/null; then+ as_mkdir_p='mkdir -p "$as_dir"'+else+ test -d ./-p && rmdir ./-p+ as_mkdir_p=false+fi++if test -x / >/dev/null 2>&1; then+ as_test_x='test -x'+else+ if ls -dL / >/dev/null 2>&1; then+ as_ls_L_option=L+ else+ as_ls_L_option=+ fi+ as_test_x='+ eval sh -c '\''+ if test -d "$1"; then+ test -d "$1/.";+ else+ case $1 in #(+ -*)set "./$1";;+ esac;+ case `ls -ld'$as_ls_L_option' "$1" 2>/dev/null` in #((+ ???[sx]*):;;*)false;;esac;fi+ '\'' sh+ '+fi+as_executable_p=$as_test_x++# Sed expression to map a string onto a valid CPP name.+as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'"++# Sed expression to map a string onto a valid variable name.+as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'"+++exec 6>&1+## ----------------------------------- ##+## Main body of $CONFIG_STATUS script. ##+## ----------------------------------- ##+_ASEOF+test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1++cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+# Save the log message, to keep $0 and so on meaningful, and to+# report actual input values of CONFIG_FILES etc. instead of their+# values after options handling.+ac_log="+This file was extended by Eden skeleton library for parallel Haskell $as_me 1.1.0.0, which was+generated by GNU Autoconf 2.68. Invocation command line was++ CONFIG_FILES = $CONFIG_FILES+ CONFIG_HEADERS = $CONFIG_HEADERS+ CONFIG_LINKS = $CONFIG_LINKS+ CONFIG_COMMANDS = $CONFIG_COMMANDS+ $ $0 $@++on `(hostname || uname -n) 2>/dev/null | sed 1q`+"++_ACEOF++case $ac_config_files in *"+"*) set x $ac_config_files; shift; ac_config_files=$*;;+esac++++cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+# Files that config.status was made for.+config_files="$ac_config_files"++_ACEOF++cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+ac_cs_usage="\+\`$as_me' instantiates files and other configuration actions+from templates according to the current configuration. Unless the files+and actions are specified as TAGs, all are instantiated by default.++Usage: $0 [OPTION]... [TAG]...++ -h, --help print this help, then exit+ -V, --version print version number and configuration settings, then exit+ --config print configuration, then exit+ -q, --quiet, --silent+ do not print progress messages+ -d, --debug don't remove temporary files+ --recheck update $as_me by reconfiguring in the same conditions+ --file=FILE[:TEMPLATE]+ instantiate the configuration file FILE++Configuration files:+$config_files++Report bugs to <eden@informatik.uni-marburg.de>."++_ACEOF+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`"+ac_cs_version="\\+Eden skeleton library for parallel Haskell config.status 1.1.0.0+configured by $0, generated by GNU Autoconf 2.68,+ with options \\"\$ac_cs_config\\"++Copyright (C) 2010 Free Software Foundation, Inc.+This config.status script is free software; the Free Software Foundation+gives unlimited permission to copy, distribute and modify it."++ac_pwd='$ac_pwd'+srcdir='$srcdir'+test -n "\$AWK" || AWK=awk+_ACEOF++cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+# The default lists apply if the user does not specify any file.+ac_need_defaults=:+while test $# != 0+do+ case $1 in+ --*=?*)+ ac_option=`expr "X$1" : 'X\([^=]*\)='`+ ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'`+ ac_shift=:+ ;;+ --*=)+ ac_option=`expr "X$1" : 'X\([^=]*\)='`+ ac_optarg=+ ac_shift=:+ ;;+ *)+ ac_option=$1+ ac_optarg=$2+ ac_shift=shift+ ;;+ esac++ case $ac_option in+ # Handling of the options.+ -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r)+ ac_cs_recheck=: ;;+ --version | --versio | --versi | --vers | --ver | --ve | --v | -V )+ $as_echo "$ac_cs_version"; exit ;;+ --config | --confi | --conf | --con | --co | --c )+ $as_echo "$ac_cs_config"; exit ;;+ --debug | --debu | --deb | --de | --d | -d )+ debug=: ;;+ --file | --fil | --fi | --f )+ $ac_shift+ case $ac_optarg in+ *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;;+ '') as_fn_error $? "missing file argument" ;;+ esac+ as_fn_append CONFIG_FILES " '$ac_optarg'"+ ac_need_defaults=false;;+ --he | --h | --help | --hel | -h )+ $as_echo "$ac_cs_usage"; exit ;;+ -q | -quiet | --quiet | --quie | --qui | --qu | --q \+ | -silent | --silent | --silen | --sile | --sil | --si | --s)+ ac_cs_silent=: ;;++ # This is an error.+ -*) as_fn_error $? "unrecognized option: \`$1'+Try \`$0 --help' for more information." ;;++ *) as_fn_append ac_config_targets " $1"+ ac_need_defaults=false ;;++ esac+ shift+done++ac_configure_extra_args=++if $ac_cs_silent; then+ exec 6>/dev/null+ ac_configure_extra_args="$ac_configure_extra_args --silent"+fi++_ACEOF+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+if \$ac_cs_recheck; then+ set X '$SHELL' '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion+ shift+ \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6+ CONFIG_SHELL='$SHELL'+ export CONFIG_SHELL+ exec "\$@"+fi++_ACEOF+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+exec 5>>config.log+{+ echo+ sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX+## Running $as_me. ##+_ASBOX+ $as_echo "$ac_log"+} >&5++_ACEOF+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+_ACEOF++cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1++# Handling of arguments.+for ac_config_target in $ac_config_targets+do+ case $ac_config_target in+ "edenskel.buildinfo") CONFIG_FILES="$CONFIG_FILES edenskel.buildinfo" ;;++ *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;;+ esac+done+++# If the user did not use the arguments to specify the items to instantiate,+# then the envvar interface is used. Set only those that are not.+# We use the long form for the default assignment because of an extremely+# bizarre bug on SunOS 4.1.3.+if $ac_need_defaults; then+ test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files+fi++# Have a temporary directory for convenience. Make it in the build tree+# simply because there is no reason against having it here, and in addition,+# creating and moving files from /tmp can sometimes cause problems.+# Hook for its removal unless debugging.+# Note that there is a small window in which the directory will not be cleaned:+# after its creation but before its name has been assigned to `$tmp'.+$debug ||+{+ tmp= ac_tmp=+ trap 'exit_status=$?+ : "${ac_tmp:=$tmp}"+ { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status+' 0+ trap 'as_fn_exit 1' 1 2 13 15+}+# Create a (secure) tmp directory for tmp files.++{+ tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` &&+ test -d "$tmp"+} ||+{+ tmp=./conf$$-$RANDOM+ (umask 077 && mkdir "$tmp")+} || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5+ac_tmp=$tmp++# Set up the scripts for CONFIG_FILES section.+# No need to generate them if there are no CONFIG_FILES.+# This happens for instance with `./config.status config.h'.+if test -n "$CONFIG_FILES"; then+++ac_cr=`echo X | tr X '\015'`+# On cygwin, bash can eat \r inside `` if the user requested igncr.+# But we know of no other shell where ac_cr would be empty at this+# point, so we can use a bashism as a fallback.+if test "x$ac_cr" = x; then+ eval ac_cr=\$\'\\r\'+fi+ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' </dev/null 2>/dev/null`+if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then+ ac_cs_awk_cr='\\r'+else+ ac_cs_awk_cr=$ac_cr+fi++echo 'BEGIN {' >"$ac_tmp/subs1.awk" &&+_ACEOF+++{+ echo "cat >conf$$subs.awk <<_ACEOF" &&+ echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' &&+ echo "_ACEOF"+} >conf$$subs.sh ||+ as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5+ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'`+ac_delim='%!_!# '+for ac_last_try in false false false false false :; do+ . ./conf$$subs.sh ||+ as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5++ ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X`+ if test $ac_delim_n = $ac_delim_num; then+ break+ elif $ac_last_try; then+ as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5+ else+ ac_delim="$ac_delim!$ac_delim _$ac_delim!! "+ fi+done+rm -f conf$$subs.sh++cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK &&+_ACEOF+sed -n '+h+s/^/S["/; s/!.*/"]=/+p+g+s/^[^!]*!//+:repl+t repl+s/'"$ac_delim"'$//+t delim+:nl+h+s/\(.\{148\}\)..*/\1/+t more1+s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/+p+n+b repl+:more1+s/["\\]/\\&/g; s/^/"/; s/$/"\\/+p+g+s/.\{148\}//+t nl+:delim+h+s/\(.\{148\}\)..*/\1/+t more2+s/["\\]/\\&/g; s/^/"/; s/$/"/+p+b+:more2+s/["\\]/\\&/g; s/^/"/; s/$/"\\/+p+g+s/.\{148\}//+t delim+' <conf$$subs.awk | sed '+/^[^""]/{+ N+ s/\n//+}+' >>$CONFIG_STATUS || ac_write_fail=1+rm -f conf$$subs.awk+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+_ACAWK+cat >>"\$ac_tmp/subs1.awk" <<_ACAWK &&+ for (key in S) S_is_set[key] = 1+ FS = ""++}+{+ line = $ 0+ nfields = split(line, field, "@")+ substed = 0+ len = length(field[1])+ for (i = 2; i < nfields; i++) {+ key = field[i]+ keylen = length(key)+ if (S_is_set[key]) {+ value = S[key]+ line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3)+ len += length(value) + length(field[++i])+ substed = 1+ } else+ len += 1 + keylen+ }++ print line+}++_ACAWK+_ACEOF+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then+ sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g"+else+ cat+fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \+ || as_fn_error $? "could not setup config files machinery" "$LINENO" 5+_ACEOF++# VPATH may cause trouble with some makes, so we remove sole $(srcdir),+# ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and+# trailing colons and then remove the whole line if VPATH becomes empty+# (actually we leave an empty line to preserve line numbers).+if test "x$srcdir" = x.; then+ ac_vpsub='/^[ ]*VPATH[ ]*=[ ]*/{+h+s///+s/^/:/+s/[ ]*$/:/+s/:\$(srcdir):/:/g+s/:\${srcdir}:/:/g+s/:@srcdir@:/:/g+s/^:*//+s/:*$//+x+s/\(=[ ]*\).*/\1/+G+s/\n//+s/^[^=]*=[ ]*$//+}'+fi++cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+fi # test -n "$CONFIG_FILES"+++eval set X " :F $CONFIG_FILES "+shift+for ac_tag+do+ case $ac_tag in+ :[FHLC]) ac_mode=$ac_tag; continue;;+ esac+ case $ac_mode$ac_tag in+ :[FHL]*:*);;+ :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;;+ :[FH]-) ac_tag=-:-;;+ :[FH]*) ac_tag=$ac_tag:$ac_tag.in;;+ esac+ ac_save_IFS=$IFS+ IFS=:+ set x $ac_tag+ IFS=$ac_save_IFS+ shift+ ac_file=$1+ shift++ case $ac_mode in+ :L) ac_source=$1;;+ :[FH])+ ac_file_inputs=+ for ac_f+ do+ case $ac_f in+ -) ac_f="$ac_tmp/stdin";;+ *) # Look for the file first in the build tree, then in the source tree+ # (if the path is not absolute). The absolute path cannot be DOS-style,+ # because $ac_f cannot contain `:'.+ test -f "$ac_f" ||+ case $ac_f in+ [\\/$]*) false;;+ *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";;+ esac ||+ as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;;+ esac+ case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac+ as_fn_append ac_file_inputs " '$ac_f'"+ done++ # Let's still pretend it is `configure' which instantiates (i.e., don't+ # use $as_me), people would be surprised to read:+ # /* config.h. Generated by config.status. */+ configure_input='Generated from '`+ $as_echo "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g'+ `' by configure.'+ if test x"$ac_file" != x-; then+ configure_input="$ac_file. $configure_input"+ { $as_echo "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5+$as_echo "$as_me: creating $ac_file" >&6;}+ fi+ # Neutralize special characters interpreted by sed in replacement strings.+ case $configure_input in #(+ *\&* | *\|* | *\\* )+ ac_sed_conf_input=`$as_echo "$configure_input" |+ sed 's/[\\\\&|]/\\\\&/g'`;; #(+ *) ac_sed_conf_input=$configure_input;;+ esac++ case $ac_tag in+ *:-:* | *:-) cat >"$ac_tmp/stdin" \+ || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;;+ esac+ ;;+ esac++ ac_dir=`$as_dirname -- "$ac_file" ||+$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \+ X"$ac_file" : 'X\(//\)[^/]' \| \+ X"$ac_file" : 'X\(//\)$' \| \+ X"$ac_file" : 'X\(/\)' \| . 2>/dev/null ||+$as_echo X"$ac_file" |+ sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{+ s//\1/+ q+ }+ /^X\(\/\/\)[^/].*/{+ s//\1/+ q+ }+ /^X\(\/\/\)$/{+ s//\1/+ q+ }+ /^X\(\/\).*/{+ s//\1/+ q+ }+ s/.*/./; q'`+ as_dir="$ac_dir"; as_fn_mkdir_p+ ac_builddir=.++case "$ac_dir" in+.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;+*)+ ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'`+ # A ".." for each directory in $ac_dir_suffix.+ ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'`+ case $ac_top_builddir_sub in+ "") ac_top_builddir_sub=. ac_top_build_prefix= ;;+ *) ac_top_build_prefix=$ac_top_builddir_sub/ ;;+ esac ;;+esac+ac_abs_top_builddir=$ac_pwd+ac_abs_builddir=$ac_pwd$ac_dir_suffix+# for backward compatibility:+ac_top_builddir=$ac_top_build_prefix++case $srcdir in+ .) # We are building in place.+ ac_srcdir=.+ ac_top_srcdir=$ac_top_builddir_sub+ ac_abs_top_srcdir=$ac_pwd ;;+ [\\/]* | ?:[\\/]* ) # Absolute name.+ ac_srcdir=$srcdir$ac_dir_suffix;+ ac_top_srcdir=$srcdir+ ac_abs_top_srcdir=$srcdir ;;+ *) # Relative name.+ ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix+ ac_top_srcdir=$ac_top_build_prefix$srcdir+ ac_abs_top_srcdir=$ac_pwd/$srcdir ;;+esac+ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix+++ case $ac_mode in+ :F)+ #+ # CONFIG_FILE+ #++_ACEOF++cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+# If the template does not know about datarootdir, expand it.+# FIXME: This hack should be removed a few years after 2.60.+ac_datarootdir_hack=; ac_datarootdir_seen=+ac_sed_dataroot='+/datarootdir/ {+ p+ q+}+/@datadir@/p+/@docdir@/p+/@infodir@/p+/@localedir@/p+/@mandir@/p'+case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in+*datarootdir*) ac_datarootdir_seen=yes;;+*@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*)+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5+$as_echo "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;}+_ACEOF+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+ ac_datarootdir_hack='+ s&@datadir@&$datadir&g+ s&@docdir@&$docdir&g+ s&@infodir@&$infodir&g+ s&@localedir@&$localedir&g+ s&@mandir@&$mandir&g+ s&\\\${datarootdir}&$datarootdir&g' ;;+esac+_ACEOF++# Neutralize VPATH when `$srcdir' = `.'.+# Shell code in configure.ac might set extrasub.+# FIXME: do we really want to maintain this feature?+cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1+ac_sed_extra="$ac_vpsub+$extrasub+_ACEOF+cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1+:t+/@[a-zA-Z_][a-zA-Z_0-9]*@/!b+s|@configure_input@|$ac_sed_conf_input|;t t+s&@top_builddir@&$ac_top_builddir_sub&;t t+s&@top_build_prefix@&$ac_top_build_prefix&;t t+s&@srcdir@&$ac_srcdir&;t t+s&@abs_srcdir@&$ac_abs_srcdir&;t t+s&@top_srcdir@&$ac_top_srcdir&;t t+s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t+s&@builddir@&$ac_builddir&;t t+s&@abs_builddir@&$ac_abs_builddir&;t t+s&@abs_top_builddir@&$ac_abs_top_builddir&;t t+$ac_datarootdir_hack+"+eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \+ >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5++test -z "$ac_datarootdir_hack$ac_datarootdir_seen" &&+ { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } &&+ { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \+ "$ac_tmp/out"`; test -z "$ac_out"; } &&+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir'+which seems to be undefined. Please make sure it is defined" >&5+$as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir'+which seems to be undefined. Please make sure it is defined" >&2;}++ rm -f "$ac_tmp/stdin"+ case $ac_file in+ -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";;+ *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";;+ esac \+ || as_fn_error $? "could not create $ac_file" "$LINENO" 5+ ;;++++ esac++done # for ac_tag+++as_fn_exit 0+_ACEOF+ac_clean_files=$ac_clean_files_save++test $ac_write_fail = 0 ||+ as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5+++# configure is writing to config.log, and then calls config.status.+# config.status does its own redirection, appending to config.log.+# Unfortunately, on DOS this fails, as config.log is still kept open+# by configure, so config.status won't be able to write to it; its+# output is simply discarded. So we exec the FD to /dev/null,+# effectively closing config.log, so it can be properly (re)opened and+# appended to by config.status. When coming back to configure, we+# need to make the FD available again.+if test "$no_create" != yes; then+ ac_cs_success=:+ ac_config_status_args=+ test "$silent" = yes &&+ ac_config_status_args="$ac_config_status_args --quiet"+ exec 5>/dev/null+ $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false+ exec 5>>config.log+ # Use ||, not &&, to avoid exiting from the if with $? = 1, which+ # would make configure fail if this is the last instruction.+ $ac_cs_success || as_fn_exit 1+fi+if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then+ { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5+$as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;}+fi+
+ configure.ac view
@@ -0,0 +1,52 @@+AC_INIT([Eden skeleton library for parallel Haskell], [1.1.0.0], [eden@informatik.uni-marburg.de], [edenskel])++# Safety check: Ensure that we are in the correct source directory.+AC_CONFIG_SRCDIR([edenskel.cabal])++# figure out GHC to use+AC_ARG_WITH([compiler],+ [AC_HELP_STRING([--with-compiler=ARG],+ [Use path ARG for GHC (we only support GHC!)])],+ [WithGhc="$withval"],+ [if test "$HC" = ""; then+ AC_PATH_PROG([GHC], [ghc])+ fi+ WithGhc="$GHC"])++AC_SUBST([WithGhc])++# we require it to be really GHC+AS_IF([test "$WithGhc" == ""],+ AC_MSG_ERROR([GHC is required for this library.]))++# GHC should be callable+AS_IF([$WithGhc --version],[],+ AC_MSG_ERROR([Your GHC does not work!]))++AC_MSG_CHECKING([for Eden extensions to the GHC runtime system])+# create Haskell which imports primitives+rm -f conftest.*; +cat > conftest.hs << EOF+{-# OPTIONS_GHC -XMagicHash #-}+module Edentest where+import GHC.Base(expectData#, connectToPort#, sendData# )+test s = expectData# s+EOF+#try to compile this, using WithGhc:+AS_IF( $WithGhc -c conftest.hs 2>&AS_MESSAGE_LOG_FD ,+ [AC_MSG_RESULT([found]); eden=YES],+ [AC_MSG_RESULT([not found]); eden=NO ]+)++# Build the package as a simulation if the runtime does not support Eden+if test "$eden" = YES+ then AC_MSG_RESULT([Parallel build enabled])+ NOT_PARALLEL=+ else AC_MSG_RESULT([Parallel build disabled-using simulation])+ NOT_PARALLEL=-DNOT_PARALLEL+fi+AC_SUBST([NOT_PARALLEL])++# this creates the buildinfo file from buildinfo.in+AC_CONFIG_FILES([edenskel.buildinfo])+AC_OUTPUT
+ edenskel.buildinfo.in view
@@ -0,0 +1,1 @@+cpp-options: @NOT_PARALLEL@
+ edenskel.cabal view
@@ -0,0 +1,56 @@+name: edenskel+version: 1.1.0.0+license: BSD3+license-file: LICENSE+maintainer: eden@mathematik.uni-marburg.de+homepage: http://www.mathematik.uni-marburg.de/~eden+synopsis: Semi-explicit parallel programming skeleton library+description:+ This package provides a skeleton library for semi-explicit parallel programming with Eden.++ Eden and the skeleton library depend on GHC, and should normally use a GHC extension to support parallel execution using message passing.+ This modified GHC-Eden compiler is available from+ <http://www.mathematik.uni-marburg.de/~eden>.+ When built using a standard GHC, this package will use a + threaded simulation of Eden. ++ The Eden homepage <http://www.mathematik.uni-marburg.de/~eden>+ provides more documentation and a tutorial.+category: Control, Distributed Computing, Eden, Parallelism+build-type: Configure+cabal-version: >=1.6++extra-source-files: + edenskel.buildinfo.in,+ configure,+ configure.ac+extra-tmp-files:config.status,+ config.log,+ edenskel.buildinfo++source-repository head+ type: git+ location: git://james.mathematik.uni-marburg.de/edenskel.git++Flag par+ Description: Enable parallel support+ Default: True++library {+ exposed-modules:+ Control.Parallel.Eden.EdenSkel.Auxiliary+ Control.Parallel.Eden.EdenSkel.IterSkels+ Control.Parallel.Eden.EdenSkel.MapSkels+ Control.Parallel.Eden.EdenSkel.MapRedSkels+ Control.Parallel.Eden.EdenSkel.DCSkels+ Control.Parallel.Eden.EdenSkel.WPSkels+ Control.Parallel.Eden.EdenSkel.TopoSkels+ extensions: CPP++ if flag(par)+ CPP-Options: -D__PARALLEL_HASKELL__++ build-depends: base >= 4 && < 5,+ edenmodules >= 1.1.0.1 && < 2,+ parallel >= 3.1 && <4+ }