@@ -60,6 +60,7 @@ import Clash.Core.HasType
6060import Clash.Core.Name (Name (.. ), NameSort (.. ))
6161import Clash.Core.Pretty (PrettyOptions (.. ), showPpr , showPpr' )
6262import Clash.Core.Subst
63+ import qualified Clash.Core.Term as Term
6364import Clash.Core.Term
6465 ( CoreContext (.. ), Pat (.. ), PrimInfo (.. ), Term (.. ), WorkInfo (.. ), collectArgs
6566 , collectArgsTicks , mkApps , mkTicks , stripTicks )
@@ -397,13 +398,20 @@ simply a variable reference. See issue #779 -}
397398-- synthesis boundaries (NOINLINE/OPAQUE functions) to avoid running too early
398399-- on functions that might be inlined later. See #3036.
399400collapseRHSNoops :: HasCallStack => NormRewrite
400- collapseRHSNoops _ letrec@ (Letrec binds body) = do
401+ collapseRHSNoops _ letrec@ (Let letBind body) = do
401402 (curFunId, _) <- Lens. use curFun
402403 curBinding <- lookupVarEnv curFunId <$> Lens. use bindings
403404 case curBinding of
404405 Just binding | isNoInline (bindingSpec binding) -> do
405- binds1 <- mapM runCollapseNoop binds
406- pure (Letrec binds1 body)
406+ -- Explicitly match on Let instead of using LetRec, because we need to
407+ -- preserve the structure. See https://github.com/clash-lang/clash-compiler/issues/3044.
408+ case letBind of
409+ Term. Rec binds -> do
410+ binds1 <- mapM runCollapseNoop binds
411+ pure (Let (Term. Rec binds1) body)
412+ Term. NonRec b0 e0 -> do
413+ (b1, e1) <- runCollapseNoop (b0, e0)
414+ pure (Let (Term. NonRec b1 e1) body)
407415 _ -> pure letrec
408416 where
409417 runCollapseNoop orig =
0 commit comments