packages feed

clash-shake 0.3.2 → 0.4.0

raw patch · 6 files changed

+145/−92 lines, 6 filesdep ~aesondep ~bytestringdep ~directoryPVP ok

version bump matches the API change (PVP)

Dependency ranges changed: aeson, bytestring, directory, shake, split, stache, text, unordered-containers

API changes (from Hackage documentation)

+ Clash.Shake: findFiles :: [FilePath] -> [FilePattern] -> [FilePath]
+ Clash.Shake: staticFiles :: FilePath -> Action [FilePath]
+ Clash.Shake: type SynthRules = ClashKit -> FilePath -> String -> Action [FilePath] -> Rules SynthKit
+ Clash.Shake.ECP5: ecp5 :: String -> SynthRules
+ Clash.Shake.ECP5: fujprog :: [String] -> FilePath -> Action ()
- Clash.Shake.F4PGA: xilinx7 :: Board -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit
+ Clash.Shake.F4PGA: xilinx7 :: Board -> SynthRules
- Clash.Shake.Intel: quartus :: Target -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit
+ Clash.Shake.Intel: quartus :: Target -> SynthRules
- Clash.Shake.Xilinx: ise :: Target -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit
+ Clash.Shake.Xilinx: ise :: Target -> SynthRules
- Clash.Shake.Xilinx: vivado :: Board -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit
+ Clash.Shake.Xilinx: vivado :: Board -> SynthRules

Files

clash-shake.cabal view
@@ -1,15 +1,15 @@ cabal-version: 1.12 --- This file has been generated from package.yaml by hpack version 0.35.0.+-- This file has been generated from package.yaml by hpack version 0.37.0. -- -- see: https://github.com/sol/hpack  name:           clash-shake-version:        0.3.2+version:        0.4.0 synopsis:       Shake rules for building Clash programs description:    Shake rules for building Clash programs and synthesizing FPGA                 configuration. Contains build rules for Xilinx ISE, Xilinx Vivado,-                Intel Quartus and the open-source SymbiFlow toolchains.  See+                Intel Quartus, F4PGA for Xilinx, and Yosys for ECP-5 and toolchains.  See                 <https://github.com/gergoerdi/clash-pong/> for an example project. category:       Hardware, Shake homepage:       https://github.com/gergoerdi/clash-shake#readme@@ -38,21 +38,22 @@       Clash.Shake.Intel       Clash.Shake.F4PGA       Clash.Shake.SymbiFlow+      Clash.Shake.ECP5   other-modules:       Paths_clash_shake   hs-source-dirs:       src   build-depends:-      aeson+      aeson <3     , base >=4.14 && <5-    , bytestring-    , clash-ghc >=1.4.2 && <1.5 || >=1.6.1 && <1.7-    , clash-lib >=1.4.2 && <1.5 || >=1.6.1 && <1.7-    , clash-prelude >=1.4.2 && <1.5 || >=1.6.1 && <1.7-    , directory-    , shake-    , split-    , stache-    , text-    , unordered-containers+    , bytestring <0.13+    , clash-ghc >=1.4.2 && <2.0+    , clash-lib >=1.4.2 && <2.0+    , clash-prelude >=1.4.2 && <2.0+    , directory <2+    , shake <0.20+    , split <0.3+    , stache <=3+    , text <3+    , unordered-containers <=1   default-language: Haskell2010
src/Clash/Shake.hs view
@@ -8,6 +8,9 @@     , RunClash(..), ClashKit(..)     , clashRules     , SynthKit(..)+    , findFiles+    , staticFiles+    , SynthRules      , binImage @@ -140,6 +143,11 @@     , phonies :: [(String, Action ())]     } +type SynthRules = ClashKit -> FilePath -> String -> Action [FilePath] -> Rules SynthKit++findFiles :: [FilePath] -> [FilePattern] -> [FilePath]+findFiles universe pats = filter (\fn -> (?== fn) `any` pats) universe+ nestedPhony :: String -> String -> Action () -> Rules () nestedPhony target name = phony (target <> ":" <> name) @@ -195,3 +203,9 @@ withTargets targets rules   | null targets = rules   | otherwise = want targets >> withoutActions rules++staticFiles :: FilePath -> Action [FilePath]+staticFiles dir = do+    files <- map (dir </>) <$> getDirectoryFiles dir ["//*"]+    need files+    return files
+ src/Clash/Shake/ECP5.hs view
@@ -0,0 +1,69 @@+{-# LANGUAGE OverloadedStrings, RecordWildCards, TemplateHaskell #-}+module Clash.Shake.ECP5+    ( ecp5+    , fujprog+    ) where++import Clash.Shake++import Development.Shake+import Development.Shake.Command+import Development.Shake.FilePath+import Development.Shake.Config+import Text.Printf++ecp5 :: String -> SynthRules+ecp5 device kit@ClashKit{..} outDir topName extraGenerated = do+    let yosys :: String -> [String] -> Action ()+        yosys tool args = cmd_ (EchoStdout False) =<< toolchain "YOSYS" tool args++    let json = outDir </> topName <.> "json"++    outDir </> topName <.> "ys" %> \out -> do+        extraFiles <- findFiles <$> extraGenerated+        srcs <- manifestSrcs+        let verilogs = extraFiles ["//*.v"]+        need $ srcs <> verilogs+        writeFileChanged out $ unlines+            [ printf "read_verilog %s" $ unwords (srcs <> verilogs)+            , printf "hierarchy -top %s" topName+            , printf "synth_ecp5 -json %s" json+            ]++    outDir <//> "*.json" %> \out -> do+        extraFiles <- findFiles <$> extraGenerated+        srcs <- manifestSrcs+        let verilogs = extraFiles ["//*.v"]+        need $ srcs <> verilogs++        let ys = out -<.> "ys"+        need [ys]+        yosys "yosys" ["-q", ys]++    outDir <//> "*.config" %> \out -> do+        extraFiles <- findFiles <$> extraGenerated+        let [lpf] = extraFiles ["//*.lpf"]+        let json = out -<.> "json"++        need [lpf, json]+        yosys "nextpnr-ecp5" ["--json", json, "--textcfg", out, "--" <> device, "--lpf", lpf]++    outDir <//> "*.bit" %> \out -> do+        let config = out -<.> "config"+        need [config]++        yosys "ecppack" ["--input", config, "--bit", out]++    let bitfile = outDir </> topName <.> "bit"++    pure SynthKit+        { bitfile = bitfile+        , phonies =+            [ "upload" |> fujprog [] bitfile+            ]+        }++fujprog :: [String] -> FilePath -> Action ()+fujprog args bitfile = do+    need [bitfile]+    cmd_ =<< toolchain "FUJPROG" "fujprog" (args ++ [bitfile])
src/Clash/Shake/F4PGA.hs view
@@ -12,23 +12,20 @@ import Development.Shake.FilePath import Development.Shake.Config -xilinx7 :: Xilinx.Board -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit-xilinx7 Xilinx.Board{ boardTarget = target@Xilinx.Target{..} } kit@ClashKit{..} outDir srcDir topName = do+xilinx7 :: Xilinx.Board -> SynthRules+xilinx7 Xilinx.Board{ boardTarget = target@Xilinx.Target{..} } kit@ClashKit{..} outDir topName extraGenerated = do     let rootDir = joinPath . map (const "..") . splitPath $ outDir      let symbiflow' :: String -> [String] -> Action ()-        symbiflow' tool args = cmd_ (EchoStdout False) (Cwd outDir) =<< toolchain "SYMBIFLOW" tool args+        symbiflow' tool args = cmd_ (EchoStdout False) (Cwd outDir) =<< toolchain "F4PGA" tool args         symbiflow :: String -> [String] -> Action ()-        symbiflow tool args = cmd_ (EchoStdout False) =<< toolchain "SYMBIFLOW" tool args--    let getFiles dir pats = map (srcDir </>) <$> getDirectoryFiles srcDir [ dir </> pat | pat <- pats ]-        verilogSrcs = getFiles "src-hdl" ["*.v"]-        xdcSrcs = getFiles "src-hdl" ["*.xdc" ]+        symbiflow tool args = cmd_ (EchoStdout False) =<< toolchain "F4PGA" tool args      outDir </> topName <.> "eblif" %> \out -> do+        extraFiles <- findFiles <$> extraGenerated         srcs <- manifestSrcs-        verilogs <- verilogSrcs-        xdcs <- xdcSrcs+        let verilogs = extraFiles ["//*.v"]+            xdcs = extraFiles ["//*.xdc"]         need $ srcs <> verilogs <> xdcs          symbiflow' "symbiflow_synth" $
src/Clash/Shake/Intel.hs view
@@ -39,58 +39,38 @@ arrowDeca :: Target arrowDeca = Target "MAX 10" "10M50DAF484C6GES" -quartus :: Target -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit-quartus fpga kit@ClashKit{..} outDir srcDir topName = do+quartus :: Target -> SynthRules+quartus fpga kit@ClashKit{..} outDir topName extraGenerated = do     let projectName = topName         rootDir = joinPath . map (const "..") . splitPath $ outDir      let quartus tool args = cmd_ (Cwd outDir) =<< toolchain "QUARTUS" tool args -    let getFiles dir pats = getDirectoryFiles srcDir [ dir </> pat | pat <- pats ]-        hdlSrcs = getFiles "src-hdl" ["*.vhdl", "*.v", "*.sv"]-        tclSrcs = getFiles "src-hdl" ["*.tcl"]-        constrSrcs = getFiles "src-hdl" ["*.sdc"]-        ipCores = getFiles "ip" ["//*.qip"]-     outDir <//> "*.tcl" %> \out -> do         srcs1 <- manifestSrcs-        srcs2 <- hdlSrcs-        tcls <- tclSrcs-        constrs <- constrSrcs-        cores <- ipCores+        extraFiles <- findFiles <$> extraGenerated+        let srcs2 = extraFiles ["//*.vhdl", "//*.v", "//*.sv"]+            tcls = extraFiles ["//*.tcl"]+            constrs = extraFiles ["//*.sdc"]+            cores = extraFiles ["//*.qip"]          let template = $(TH.compileMustacheFile "template/intel-quartus/project.tcl.mustache")         let values = object . mconcat $                 [ [ "project" .= T.pack projectName ]                   , [ "top" .= T.pack topName ]                   , targetMustache fpga-                  , [ "srcs" .= mconcat-                             [ [ object [ "fileName" .= (rootDir </> src) ] | src <- srcs1 ]-                               , [ object [ "fileName" .= (rootDir </> srcDir </> src) ] | src <- srcs2 ]-                             ]+                  , [ "srcs" .= [ object [ "fileName" .= (rootDir </> src) ] | src <- srcs1 <> srcs2 ]                     ]-                  , [ "tclSrcs" .= [ object [ "fileName" .= (rootDir </> srcDir </> src) ] | src <- tcls ] ]-                  , [ "ipcores" .= [ object [ "fileName" .= (rootDir </> srcDir </> core) ] | core <- cores ] ]-                  , [ "constraintSrcs" .= [ object [ "fileName" .= (rootDir </> srcDir </> src) ] | src <- constrs ] ]+                  , [ "tclSrcs" .= [ object [ "fileName" .= (rootDir </> src) ] | src <- tcls ] ]+                  , [ "ipcores" .= [ object [ "fileName" .= (rootDir </> core) ] | core <- cores ] ]+                  , [ "constraintSrcs" .= [ object [ "fileName" .= (rootDir </> src) ] | src <- constrs ] ]                 ]         writeFileChanged out . TL.unpack $ renderMustache template values -    outDir </> "ip" <//> "*" %> \out -> do-            let src = srcDir </> makeRelative outDir out-            copyFileChanged src out-     let bitfile = outDir </> topName <.> "sof"      bitfile %> \_out -> do-        srcs1 <- manifestSrcs-        srcs2 <- hdlSrcs-        cores <- ipCores-        need $ mconcat-            [ [ outDir </> projectName <.> "tcl" ]-              , [ src | src <- srcs1 ]-              , [ srcDir </> src | src <- srcs2 ]-              , [ outDir </> core | core <- cores ]-            ]+        need $ [ outDir </> projectName <.> "tcl" ]         quartus "quartus_sh" ["-t", projectName <.> "tcl"]      outDir </> topName <.> "rbf" %> \out -> do
src/Clash/Shake/Xilinx.hs view
@@ -82,21 +82,18 @@ pynqZ2 = Board "tul.com.tw:pynq-z2:part0:1.0" 1 $     Target "zynq7000" "xc7z020" "clg400" 1 -ise :: Target -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit-ise fpga kit@ClashKit{..} outDir srcDir topName = do+ise :: Target -> SynthRules+ise fpga kit@ClashKit{..} outDir topName extraGenerated = do     let projectName = topName         rootDir = joinPath . map (const "..") . splitPath $ outDir      let ise tool args = cmd_ (Cwd outDir) =<< toolchain "ISE" tool args -    let getFiles dir pats = getDirectoryFiles srcDir [ dir </> pat | pat <- pats ]-        hdlSrcs = getFiles "src-hdl" ["*.vhdl", "*.v", "*.ucf" ]-        ipCores = getFiles "ipcore_dir" ["*.xco", "*.xaw"]-     outDir <//> "*.tcl" %> \out -> do         srcs1 <- manifestSrcs-        srcs2 <- hdlSrcs-        cores <- ipCores+        extraFiles <- findFiles <$> extraGenerated+        let srcs2 = extraFiles ["//*.vhdl", "//*.v", "//*.ucf"]+            cores = extraFiles ["//*.xco", "//*.xaw"]          let template = $(TH.compileMustacheFile "template/xilinx-ise/project.tcl.mustache")         let values = object . mconcat $@@ -104,9 +101,8 @@                      , [ "top" .= T.pack topName ]                      , targetMustache fpga                      , [ "srcs" .= mconcat-                         [ [ object [ "fileName" .= (rootDir </> src) ] | src <- srcs1 ]-                         , [ object [ "fileName" .= (rootDir </> srcDir </> src) ] | src <- srcs2 ]-                         , [ object [ "fileName" .= core ] | core <- cores ]+                         [ [ object [ "fileName" .= (rootDir </> src) ] | src <- srcs1 <> srcs2 ]+                         , [ object [ "fileName" .= ("ipcore_dir" </> takeFileName core) ] | core <- cores ]                          ]                        ]                      , [ "ipcores" .= [ object [ "name" .= takeBaseName core ] | core <- cores ] ]@@ -114,19 +110,20 @@         writeFileChanged out . TL.unpack $ renderMustache template values      outDir </> "ipcore_dir" <//> "*" %> \out -> do-        let src = srcDir </> makeRelative outDir out-        copyFileChanged src out+        let src = makeRelative (outDir </> "ipcore_dir") out+        extraFiles <- findFiles <$> extraGenerated+        case extraFiles ["//" <> src] of+          [oneFile] -> copyFileChanged oneFile out+          [] -> error $ unwords ["Cannot find IP core file", src]+          multiple ->  error $ unwords ["Multiple candidates for IP core file", src, show multiple]      outDir </> topName <.> "bit" %> \_out -> do-        srcs1 <- manifestSrcs-        srcs2 <- hdlSrcs-        cores <- ipCores+        extraFiles <- findFiles <$> extraGenerated+        let cores = extraFiles ["//*.xco", "//*.xaw"]         need $ mconcat-            [ [ outDir </> projectName <.> "tcl" ]-            , [ src | src <- srcs1 ]-            , [ srcDir </> src | src <- srcs2 ]-            , [ outDir </> core | core <- cores ]-            ]+          [ [ outDir </> projectName <.> "tcl" ]+          , [ outDir </> "ipcore_dir" </> takeFileName core | core <- cores ]+          ]         ise "xtclsh" [projectName <.> "tcl", "rebuild_project"]      return $ SynthKit@@ -138,8 +135,8 @@             ]         } -vivado :: Board -> ClashKit -> FilePath -> FilePath -> String -> Rules SynthKit-vivado board kit@ClashKit{..} outDir srcDir topName = do+vivado :: Board -> SynthRules+vivado board kit@ClashKit{..} outDir topName extraGenerated = do     let projectName = topName         projectDir = outDir </> projectName         xpr = projectDir </> projectName <.> "xpr"@@ -155,18 +152,14 @@               , "-source", tcl               ] -    let getFiles dir pats = getDirectoryFiles srcDir [ dir </> pat | pat <- pats ]-        hdlSrcs = getFiles "src-hdl" ["*.vhdl", "*.v" ]-        constrSrcs = getFiles "src-hdl" ["*.xdc" ]-        ipCores = getFiles "ip" ["*.xci"]-     xpr %> \out -> vivadoBatch "project.tcl"      outDir </> "project.tcl" %> \out -> do         srcs1 <- manifestSrcs-        srcs2 <- hdlSrcs-        cores <- ipCores-        constrs <- constrSrcs+        extraFiles <- findFiles <$> extraGenerated+        let srcs2 = extraFiles ["//*.vhdl", "//*.v" ]+            cores = extraFiles ["//*.xci"]+            constrs = extraFiles ["//*.xdc"]          let template = $(TH.compileMustacheFile "template/xilinx-vivado/project.tcl.mustache")         let values = object . mconcat $@@ -175,17 +168,16 @@                      , [ "top" .= T.pack topName ]                      , boardMustache board                      , [ "srcs" .= mconcat-                         [ [ object [ "fileName" .= src ] | src <- srcs1 ]-                         , [ object [ "fileName" .= (srcDir </> src) ] | src <- srcs2 ]+                         [ [ object [ "fileName" .= src ] | src <- srcs1 <> srcs2 ]                          ]                        ]                      , [ "coreSrcs" .= object                          [ "nonempty" .= not (null cores)-                         , "items" .= [ object [ "fileName" .= (srcDir </> core) ] | core <- cores ]+                         , "items" .= [ object [ "fileName" .= core ] | core <- cores ]                          ]                        ]                      , [ "ipcores" .= [ object [ "name" .= takeBaseName core ] | core <- cores ] ]-                     , [ "constraintSrcs" .= [ object [ "fileName" .= (srcDir </> src) ] | src <- constrs ] ]+                     , [ "constraintSrcs" .= [ object [ "fileName" .= src ] | src <- constrs ] ]                      ]         writeFileChanged out . TL.unpack $ renderMustache template values @@ -215,7 +207,7 @@         , phonies =             [ "vivado" |> do                    need [xpr]-                   vivado "vivado" [xpr]+                   vivado "vivado" [makeRelative outDir xpr]             , "upload" |> do                    need [projectDir </> projectName <.> "runs" </> "impl_1" </> topName <.> "bit"]                    vivadoBatch "upload.tcl"