module Signal where import LogFun class (Eq a, Show{-was:Text-} a, Num a) => Signal a where showSig :: a -> String zerO, one, initial :: a tt1 :: TT1 -> a -> a tt2 :: TT2 -> a -> a -> a con10, buf, inv, con11 :: a -> a con20, and2, nimp, id21 :: a -> a -> a nimp', id22, xor, or2 :: a -> a -> a nor2, equ2, inv22, imp' :: a -> a -> a inv21, imp, nand2, con21 :: a -> a -> a and3, or3, nand3, nor3 :: a -> a -> a -> a and4, or4, nand4, nor4 :: a -> a -> a -> a -> a con10 = tt1 tt_con10 buf = tt1 tt_id inv = tt1 tt_inv con11 = tt1 tt_con11 con20 = tt2 tt_con20 and2 = tt2 tt_and2 nimp = tt2 tt_nimp id21 = tt2 tt_id21 nimp' = tt2 tt_nimp' id22 = tt2 tt_id22 xor = tt2 tt_xor or2 = tt2 tt_or2 nor2 = tt2 tt_nor2 equ2 = tt2 tt_equ2 inv22 = tt2 tt_inv22 imp' = tt2 tt_imp' inv21 = tt2 tt_inv21 imp = tt2 tt_imp nand2 = tt2 tt_nand2 con21 = tt2 tt_con21 and3 a b c = a*b*c or3 a b c = a+b+c nand3 a b c = nand2 a (nand2 b c) nor3 a b c = nor2 a (nor2 b c) and4 a b c d = (a*b)*(c*d) or4 a b c d = (a+b)+(c+d) nand4 a b c d = nand2 (nand2 a b) (nand2 c d) nor4 a b c d = nor2 (nor2 a b) (nor2 c d) class (Signal a) => Lattice a where bot, top, weakZero, weakOne :: a lub :: a -> a -> a pass :: a -> a -> a class (Signal a) => Static a where intToSig :: Int -> a sigToInt :: a -> Int showStaticSig :: a -> String class (Signal a) => Dynamic a where latch, dff :: a -> a class (Lattice a, Static a) => Log a where dumLog :: a class (Lattice a, Dynamic a) => Sig a where dumSig :: a data Stream a = Snil | Scons a (Stream a) deriving (Eq,Show{-was:Text-}) shead :: Stream a -> a shead (Scons x xs) = x stail :: Stream a -> Stream a stail (Scons x xs) = xs snull :: Stream a -> Bool snull Snil = True snull (Scons x xs) = False smap :: (a->b) -> Stream a -> Stream b smap f Snil = Snil smap f (Scons x xs) = Scons (f x) (smap f xs) stake, sdrop :: Int -> Stream a -> Stream a stake 0 xs = xs --should be: stake (i+1) (Scons x xs) = Scons x (stake i xs) stake i (Scons x xs) | i < 0 = error "Signal.stake: < 0" | otherwise = Scons x (stake (i-1) xs) sdrop 0 xs = xs --should be:sdrop (i+1) (Scons x xs) = sdrop i xs sdrop i (Scons x xs) | i < 0 = error "Signal.sdrop: < 0" | otherwise = sdrop i xs smap2 :: (a->b->c) -> Stream a -> Stream b -> Stream c smap2 f as bs = case as of Snil -> Snil Scons a as' -> case bs of Snil -> Snil Scons b bs' -> Scons (f a b) (smap2 f as' bs') srepeat :: (Static a) => a -> Stream a srepeat x = xs where xs = Scons x xs stream :: [a] -> Stream a stream [] = Snil stream (x:xs) = Scons x (stream xs) instance (Signal a, Static a) => Dynamic (Stream a) where latch xs = Scons initial xs dff xs = Scons initial xs instance (Lattice a, Static a) => Lattice (Stream a) where bot = srepeat bot top = srepeat top weakZero = srepeat weakZero weakOne = srepeat weakOne lub = smap2 lub pass = smap2 pass instance (Signal a, Static a) => Signal (Stream a) where zerO = srepeat zerO one = srepeat one tt1 = smap . tt1 tt2 = smap2 . tt2 instance (Lattice a, Static a) => Sig (Stream a) where dumSig = bot -- ??? shouldn't be necessary, check compiler instance (Static a) => Num (Stream a) where (+) = or2 (*) = and2 a - b = xor a b negate = inv abs = error "abs not defined for Signals" signum = error "signum not defined for Signals" fromInteger = error "fromInteger not defined for Signals"