Skip to content

Implement recompilation checking for pre-build rules#11731

Open
sheaf wants to merge 2 commits intohaskell:masterfrom
sheaf:hooks-recomp
Open

Implement recompilation checking for pre-build rules#11731
sheaf wants to merge 2 commits intohaskell:masterfrom
sheaf:hooks-recomp

Conversation

@sheaf
Copy link
Copy Markdown
Collaborator

@sheaf sheaf commented Apr 10, 2026

Template Α: This PR modifies behaviour or interface


This PR adds recompilation logic for SetupHooks pre-build rules, implementing the behaviour described in the SetupHooks API. That is, a rule is considered stale if:

  • The rule is new, or
  • A dependency of the rule is stale. That is, either we have re-run another rule that this rule depends on, or one of the file inputs to the rule is newer than the oldest output of the rule (or the rule output doesn't exist at all), or
  • The rule itself has changed, e.g. the parameters stored in RuleData have changed.

Tested in cabal-testsuite/PackageTests/SetupHooks/SetupHooksRecompRules/setup.test.hs.

@sheaf sheaf changed the title Hooks recomp Implement recompilation checking for pre-build rules Apr 10, 2026
This commit adds 'Structured' instances for the 'RuleCommands' and
'RuleData' datatypes. This allows us to serialise and deserialise them,
which allows us to compute which rules have changed across builds.
This is necessary for recompilation checking for pre-build rules.
This commit adds recompilation logic for SetupHooks pre-build rules.
This implements the behaviour described in the SetupHooks API. That is,
a rule is considered stale if:

  [N] The rule is new, or
  [S1] A dependency of the rule is stale. That is, either we have
       re-run another rule that this rule depends on, or one of the
       file inputs to the rule is newer than the oldest output of the
       rule (or the rule output doesn't exist at all), or
  [S2] The rule itself has changed, e.g. the parameters stored in
       RuleData have changed.

Fixes haskell#11730
-- Load the rule cache from the previous build.
-- Used to detect when rule definitions have changed.
oldRules <- do
cacheExists <- doesFileExist rulesCacheFile
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Does this have a TOCTOU issue?


mtimeIfExists :: FilePath -> IO (Maybe UTCTime)
mtimeIfExists fp = do
ex <- doesFileExist fp
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Granting that it's brief, but this looks like a TOCTOU as well.

have changed.

In particular, Cabal will now write per-component caches of pre-build rules
in order to compute which rules have changed across run, with file name
Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
in order to compute which rules have changed across run, with file name
in order to compute which rules have changed between runs, with file name

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants