2019-02-18 07:38:16 +01:00
|
|
|
{- sv2v
|
|
|
|
|
- Author: Zachary Snow <zach@zachjs.com>
|
|
|
|
|
-
|
|
|
|
|
- Conversion for `logic`
|
|
|
|
|
-}
|
|
|
|
|
|
|
|
|
|
-- Regarding `logic` conversion: The SystemVerilog grammar has the concept of a
|
|
|
|
|
-- `data_declaration`, which seems to cover things much more generally. While
|
|
|
|
|
-- obviously `logic` can appear as module items or ports, they can also be
|
|
|
|
|
-- function arguments, for example.
|
|
|
|
|
|
|
|
|
|
-- It seems like logic only becomes reg if it is assigned to in an always block.
|
|
|
|
|
|
|
|
|
|
module Convert.Logic (convert) where
|
|
|
|
|
|
2019-02-25 22:19:55 +01:00
|
|
|
import Control.Monad.Writer
|
2019-02-18 07:38:16 +01:00
|
|
|
import qualified Data.Set as Set
|
|
|
|
|
|
2019-02-25 22:19:55 +01:00
|
|
|
import Convert.Traverse
|
2019-02-18 07:38:16 +01:00
|
|
|
import Language.SystemVerilog.AST
|
|
|
|
|
|
|
|
|
|
type RegIdents = Set.Set String
|
|
|
|
|
|
2019-02-18 09:59:17 +01:00
|
|
|
convert :: AST -> AST
|
2019-02-25 22:19:55 +01:00
|
|
|
convert = traverseDescriptions convertDescription
|
2019-02-18 07:38:16 +01:00
|
|
|
|
2019-02-18 09:59:17 +01:00
|
|
|
convertDescription :: Description -> Description
|
2019-02-25 22:19:55 +01:00
|
|
|
convertDescription orig =
|
|
|
|
|
traverseModuleItems convertModuleItem orig
|
2019-02-18 07:38:16 +01:00
|
|
|
where
|
2019-02-25 22:19:55 +01:00
|
|
|
idents = execWriter (collectModuleItemsM regIdents orig)
|
|
|
|
|
convertModuleItem :: ModuleItem -> ModuleItem
|
|
|
|
|
convertModuleItem (MIDecl (Variable dir (Logic mr) ident a me)) =
|
|
|
|
|
MIDecl $ Variable dir (t mr) ident a me
|
|
|
|
|
where t = if Set.member ident idents then Reg else Wire
|
|
|
|
|
convertModuleItem other = other
|
|
|
|
|
|
|
|
|
|
regIdents :: ModuleItem -> Writer RegIdents ()
|
|
|
|
|
regIdents (AlwaysC _ stmt) = collectStmtLHSsM idents stmt
|
2019-02-22 02:12:34 +01:00
|
|
|
where
|
2019-02-25 22:19:55 +01:00
|
|
|
idents :: LHS -> Writer RegIdents ()
|
|
|
|
|
idents (LHS vx ) = tell $ Set.singleton vx
|
|
|
|
|
idents (LHSBit vx _) = tell $ Set.singleton vx
|
|
|
|
|
idents (LHSRange vx _) = tell $ Set.singleton vx
|
|
|
|
|
idents (LHSConcat lhss) = mapM idents lhss >>= \_ -> return ()
|
|
|
|
|
regIdents _ = return ()
|