From e361a8b3782943c073529e4bad66212dc873fa11 Mon Sep 17 00:00:00 2001 From: Christiaan Baaij Date: Thu, 7 Oct 2021 16:58:33 +0200 Subject: [PATCH] Verify blackbox context when rendering includes Fixes #1945 --- changelog/2021-10-07T16_55_54+02_00_fix1945 | 1 + clash-lib/src/Clash/Netlist/BlackBox/Util.hs | 8 ++++ tests/Main.hs | 4 ++ tests/shouldfail/BlackBox/T1945.hs | 39 ++++++++++++++++++++ 4 files changed, 52 insertions(+) create mode 100644 changelog/2021-10-07T16_55_54+02_00_fix1945 create mode 100644 tests/shouldfail/BlackBox/T1945.hs diff --git a/changelog/2021-10-07T16_55_54+02_00_fix1945 b/changelog/2021-10-07T16_55_54+02_00_fix1945 new file mode 100644 index 0000000000..daa461e89b --- /dev/null +++ b/changelog/2021-10-07T16_55_54+02_00_fix1945 @@ -0,0 +1 @@ +FIXED: valid field of TemplateFunction isn't checked for includes [#1945](https://github.com/clash-lang/clash-compiler/issues/1945) diff --git a/clash-lib/src/Clash/Netlist/BlackBox/Util.hs b/clash-lib/src/Clash/Netlist/BlackBox/Util.hs index c3be82dba3..9a5d90adca 100644 --- a/clash-lib/src/Clash/Netlist/BlackBox/Util.hs +++ b/clash-lib/src/Clash/Netlist/BlackBox/Util.hs @@ -279,6 +279,14 @@ renderBlackBox libs imps includes bb bbCtx = do layout = LayoutOptions (AvailablePerLine 120 0.4) nms <- forM includes $ \((nm,_),inc) -> do + case verifyBlackBoxContext bbCtx inc of + Nothing -> return () + Just err0 -> do + sp <- getSrcSpan + let err1 = concat [ "Couldn't instantiate blackbox for " + , Data.Text.unpack (bbName bbCtx), ". Verification " + , "procedure reported:\n\n" ++ err0 ] + throw (ClashException sp ($(curLoc) ++ err1) Nothing) let bbCtx' = bbCtx {bbQsysIncName = map Text.toStrict nms'} incForHash <- onBlackBox (renderTemplate bbCtx') (\_name _hash (N.TemplateFunction _ _ f) -> do diff --git a/tests/Main.hs b/tests/Main.hs index a16c402039..968c8dafe5 100755 --- a/tests/Main.hs +++ b/tests/Main.hs @@ -162,6 +162,10 @@ runClashTest = defaultMain $ clashTestRoot primitive for WrongReference.myMultiplyX. These names should be the same. |]) } + , runTest "T1945" def{ + hdlTargets=[VHDL] + , expectClashFail=Just (def, "Template function for returned False") + } ] , clashTestGroup "InvalidPrimitive" [ runTest "InvalidPrimitive" def{ diff --git a/tests/shouldfail/BlackBox/T1945.hs b/tests/shouldfail/BlackBox/T1945.hs new file mode 100644 index 0000000000..d8309636c1 --- /dev/null +++ b/tests/shouldfail/BlackBox/T1945.hs @@ -0,0 +1,39 @@ +{-# LANGUAGE OverloadedStrings #-} +module T1945 where + +import Clash.Annotations.Primitive (Primitive(..), HDL(..), hasBlackBox) +import Clash.Netlist.Types (TemplateFunction (..)) +import Clash.Prelude + +import Data.String.Interpolate (i) +import Data.String.Interpolate.Util (unindent) + +bb :: a -> a +bb x = x +{-# NOINLINE bb #-} +{-# ANN bb hasBlackBox #-} +{-# ANN bb (InlinePrimitive [VHDL,Verilog,SystemVerilog] $ unindent [i| + [ { "BlackBox" : + { "name" : "T1945.bb", + "kind" : "Expression", + "template": "~ARG[0]", + "includes" : + [ { "extension" : "bin" + , "name" : "mem" + , "format" : "Haskell" + , "templateFunction" : "T1945.tf"} + + ] + } + } + ] + |]) #-} + +tf :: TemplateFunction +tf = TemplateFunction used valid (const (pure "QQ")) + where + used = [0] + valid = const False + +topEntity :: Bool -> Bool +topEntity = bb