Skip to content

Commit

Permalink
first pass at preBuild SetupHooks
Browse files Browse the repository at this point in the history
  • Loading branch information
sheaf committed Sep 28, 2023
1 parent 8a5c4d3 commit 49e6f31
Show file tree
Hide file tree
Showing 4 changed files with 81 additions and 34 deletions.
35 changes: 24 additions & 11 deletions Cabal/src/Distribution/Simple.hs
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ import Distribution.Simple.Haddock
import Distribution.Simple.Install
import Distribution.Simple.LocalBuildInfo
import Distribution.Simple.SetupHooks
( SetupHooks(..), simpleSetupHooks
( SetupHooks, simpleSetupHooks
, applyPackagePreConfDiff
)
import qualified Distribution.Simple.SetupHooks as SetupHooks
Expand Down Expand Up @@ -156,15 +156,29 @@ defaultMainWithSetupHooks setup_hooks =

defaultMainWithSetupHooksArgs :: SetupHooks -> [String] -> IO ()
defaultMainWithSetupHooksArgs setup_hooks =
defaultMainHelper setup_hooks (simpleUserHooks { confHook = setup_confHook })
defaultMainHelper setup_hooks $
simpleUserHooks
{ confHook = setup_confHook
, buildHook = setup_buildHook
}

where
setup_confHook
:: (GenericPackageDescription, HookedBuildInfo)
-> ConfigFlags
-> IO LocalBuildInfo
setup_confHook =
configure_maybeSetupHooks (preConfComponent setup_hooks)
setup_confHook
:: (GenericPackageDescription, HookedBuildInfo)
-> ConfigFlags
-> IO LocalBuildInfo
setup_confHook =
configure_mbSetupHooks (SetupHooks.preConfComponent setup_hooks)

setup_buildHook
:: PackageDescription
-> LocalBuildInfo
-> UserHooks
-> BuildFlags
-> IO ()
setup_buildHook pkg_descr lbi hooks flags =
build_mbSetupHooks (SetupHooks.preBuild setup_hooks)
pkg_descr lbi flags (allSuffixHandlers hooks)

-- | A customizable version of 'defaultMain'.
defaultMainWithHooks :: UserHooks -> IO ()
Expand Down Expand Up @@ -270,8 +284,7 @@ configureAction setup_hooks hooks flags args = do
verbosity
(flagToMaybe (configCabalFilePath flags))

mb_lbi_diff <- for (preConfPackage setup_hooks) $ \ pre_conf_package ->
pre_conf_package args
mb_lbi_diff <- for (SetupHooks.preConfPackage setup_hooks) ($ args)


let epkg_descr = (pkg_descr0, pbi)
Expand Down Expand Up @@ -828,7 +841,7 @@ simpleUserHooks =
verbosity = fromFlag (configVerbosity flags)

autoconfSetupHooks :: SetupHooks
autoconfSetupHooks = simpleSetupHooks { preConfComponent = Just $ pre_conf }
autoconfSetupHooks = simpleSetupHooks { SetupHooks.preConfComponent = Just $ pre_conf }
where
pre_conf
:: SetupHooks.ConfigEnv
Expand Down
22 changes: 18 additions & 4 deletions Cabal/src/Distribution/Simple/Build.hs
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
-- compiler-specific actions. It does do some non-compiler specific bits like
-- running pre-processors.
module Distribution.Simple.Build
( build
( build, build_mbSetupHooks
, repl
, startInterpreter
, initialBuildSteps
Expand Down Expand Up @@ -77,6 +77,7 @@ import Distribution.Simple.Program.Builtin (haskellSuiteProgram)
import qualified Distribution.Simple.Program.GHC as GHC
import Distribution.Simple.Program.Types
import Distribution.Simple.Register
import Distribution.Simple.SetupHooks ( PreBuildHook )
import Distribution.Simple.Setup.Build
import Distribution.Simple.Setup.Config
import Distribution.Simple.Setup.Repl
Expand Down Expand Up @@ -111,7 +112,20 @@ build
-> [PPSuffixHandler]
-- ^ preprocessors to run before compiling
-> IO ()
build pkg_descr lbi flags suffixes = do
build = build_mbSetupHooks Nothing

build_mbSetupHooks
:: Maybe PreBuildHook
-> PackageDescription
-- ^ Mostly information from the .cabal file
-> LocalBuildInfo
-- ^ Configuration information
-> BuildFlags
-- ^ Flags that the user passed to build
-> [PPSuffixHandler]
-- ^ preprocessors to run before compiling
-> IO ()
build_mbSetupHooks mb_preBuildHook pkg_descr lbi flags suffixes = do
-- Currently here
checkSemaphoreSupport verbosity (compiler lbi) flags
targets <- readTargetInfos verbosity pkg_descr lbi (buildArgs flags)
Expand All @@ -136,11 +150,11 @@ build pkg_descr lbi flags suffixes = do
-- dumped.
dumpBuildInfo verbosity distPref (configDumpBuildInfo (configFlags lbi)) pkg_descr lbi flags

-- Now do the actual building
(\f -> foldM_ f (installedPkgs lbi) componentsToBuild) $ \index target -> do
-- SetupHooks TODO: hook here for preBuild
let comp = targetComponent target
clbi = targetCLBI target
for_ mb_preBuildHook $ \ preBuild_hook ->
preBuild_hook lbi comp
componentInitialBuildSteps distPref pkg_descr lbi clbi verbosity
let bi = componentBuildInfo comp
progs' = addInternalBuildTools pkg_descr lbi bi (withPrograms lbi)
Expand Down
8 changes: 4 additions & 4 deletions Cabal/src/Distribution/Simple/Configure.hs
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@
-- the user, the amount of information displayed depending on the verbosity
-- level.
module Distribution.Simple.Configure
( configure, configure_maybeSetupHooks
( configure, configure_mbSetupHooks
, writePersistBuildConfig
, getConfigStateFile
, getPersistBuildConfig
Expand Down Expand Up @@ -411,14 +411,14 @@ configure
:: (GenericPackageDescription, HookedBuildInfo)
-> ConfigFlags
-> IO LocalBuildInfo
configure = configure_maybeSetupHooks Nothing
configure = configure_mbSetupHooks Nothing

configure_maybeSetupHooks
configure_mbSetupHooks
:: Maybe PreConfComponentHook
-> (GenericPackageDescription, HookedBuildInfo)
-> ConfigFlags
-> IO LocalBuildInfo
configure_maybeSetupHooks mb_preConfComponentHook (pkg_descr0, pbi) cfg = do
configure_mbSetupHooks mb_preConfComponentHook (pkg_descr0, pbi) cfg = do
-- Determine the component we are configuring, if a user specified
-- one on the command line. We use a fake, flattened version of
-- the package since at this point, we're not really sure what
Expand Down
50 changes: 35 additions & 15 deletions Cabal/src/Distribution/Simple/SetupHooks.hs
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,11 @@ module Distribution.Simple.SetupHooks
, TestSuiteDiff, BenchmarkDiff
, BuildInfoDiff
, applyComponentDiffs

-- *** HookedBuildInfo compatibility code
, hookedBuildInfoComponents, hookedBuildInfoComponentDiff_maybe

-- * Build setup hooks
, PreBuildHook
)
where

Expand Down Expand Up @@ -51,19 +53,14 @@ import System.FilePath (takeDirectory, (</>))
-- SetupHooks

type Args2 = [String] -- SetupHooks TODO
type PreConfPackageHook = Args2 -> IO LocalBuildConfig
type PreConfComponentHook = ConfigEnv -> IO ( Set ComponentName
, Component -> IO ComponentDiff)

-- SetupHooks TODO: document this datatype and its fields.
data SetupHooks = SetupHooks
{ preConfPackage :: Maybe PreConfPackageHook

, preConfComponent :: Maybe PreConfComponentHook

--, preBuild
-- For pre-build: hook can declare list of dependencies
-- to know when it needs to re-run the pre-build hook.
-- SetupHooks TODO: see how cabal handles recompilation logic.
, preBuild :: Maybe PreBuildHook

--, hookedPrograms
-- SetupHooks TODO: hooked programs (see nix-paths?).
Expand All @@ -73,17 +70,34 @@ simpleSetupHooks :: SetupHooks
simpleSetupHooks = SetupHooks
{ preConfPackage = Nothing
, preConfComponent = Nothing
, preBuild = Nothing
}

--------------------------------------------------------------------------------
-- Per-package configure hook.

type PreConfPackageHook = Args2 -> IO LocalBuildConfig

applyPackagePreConfDiff :: LocalBuildConfig -> LocalBuildInfo -> IO LocalBuildInfo
applyPackagePreConfDiff cfg_diff lbi@(NewLocalBuildInfo { localBuildConfig = cfg0 })
= return $ lbi { localBuildConfig = cfg0 <> cfg_diff }

--------------------------------------------------------------------------------
-- Per-component configure hook.

type PreConfComponentHook = ConfigEnv -> IO ( Set ComponentName
, Component -> IO ComponentDiff )

data ConfigEnv
= ConfigEnv
{ configFlags :: ConfigFlags
, programDb :: ProgramDb
, flagAssignment :: FlagAssignment
, hostPlatform :: Platform
}
-- SetupHooks TODO: these are the fields needed to implement the Configure
-- build-type using SetupHooks. We might want to pass more information
-- to the per-component configure hook.

configEnvBuildDir :: ConfigEnv -> FilePath
configEnvBuildDir (ConfigEnv { configFlags = cfg })
Expand All @@ -103,13 +117,6 @@ configEnvBaseDir cfg_env =
""
(takeDirectory <$> configEnvCabalFilePath cfg_env)

applyPackagePreConfDiff :: LocalBuildConfig -> LocalBuildInfo -> IO LocalBuildInfo
applyPackagePreConfDiff cfg_diff lbi@(NewLocalBuildInfo { localBuildConfig = cfg0 })
= return $ lbi { localBuildConfig = cfg0 <> cfg_diff }

--------------------------------------------------------------------------------
-- Per-component configure hook.

type LibraryDiff = Library
type ForeignLibDiff = ForeignLib
type ExecutableDiff = Executable
Expand Down Expand Up @@ -385,3 +392,16 @@ buildInfoLibraryDiff bi = emptyLibrary { libBuildInfo = bi }

buildInfoExecutableDiff :: BuildInfo -> ExecutableDiff
buildInfoExecutableDiff bi = emptyExecutable { buildInfo = bi }

--------------------------------------------------------------------------------
-- Build setup hooks.

type PreBuildHook = LocalBuildInfo -> Component -> IO ()

-- SetupHooks TODO: introduce some kind of recompilation logic
-- that allows the hook to declare a list of dependencies which is then
-- used in Cabal to decide when it needs to re-run the build hooks.
--
-- To do this, we should look at how cabal handles recompilation logic.

--------------------------------------------------------------------------------

0 comments on commit 49e6f31

Please sign in to comment.