Skip to content

Fix: avoid pruning Const arguments needed by a custom derivative rule - #3224

Closed
Tuna2222 wants to merge 4 commits into
EnzymeAD:mainfrom
Tuna2222:fix-3570-const-arg-lost-across-noinline
Closed

Tuna2222 wants to merge 4 commits into
EnzymeAD:mainfrom
Tuna2222:fix-3570-const-arg-lost-across-noinline

Conversation

@Tuna2222

Copy link
Copy Markdown

Summary

A Const argument that a custom EnzymeRules derivative rule reads or writes, but that the primal never touches, was being dropped from a differentiated function's signature and replaced with jl_nothing whenever the call crossed a non-inlined function. Reported in EnzymeAD/Enzyme.jl#3570.

shouldDisableNoWrite (Utils.h) trusted write-only/no-capture attribute inference for any call to a resolved callee, as long as neither the call nor the callee carried an explicit custom-rule marker. That inference is computed from the callee's own primal semantics but a custom derivative rule actually needs the argument. shouldDisableNoWrite now also disables the no-write shortcut for any resolved callee with a body Enzyme will still analyze. Since a Const argument is potentially be read/written, readnone/readonly/writeonly attributes are also dropped wherever they get copied onto a Const argument. But only where the argument is actually passed to a call shouldDisableNoWrite disables trust for.

Tests

  • ForwardMode/callee_const_arg.ll — a Const pointer argument of a resolved, non-custom-rule callee must not be pruned to
    undef by shouldDisableNoWrite's strategy.
  • ReverseMode/custom_const_state.ll — a Const pointer argument read and written by a combined
    !enzyme_augment/!enzyme_gradient custom rule must reach the generated call as a real pointer, and the generated derivative's definition and call site must not keep a stale readnone/readonly/writeonly claim. Covers all three attributes as separate variants, with the attribute asserted directly as a parameter attribute (not inferred from a whole-call attribute) so each variant exercises both copy sites independent of pass ordering.

See EnzymeAD/Enzyme.jl#3570.

Tuna2222 and others added 4 commits September 13, 2026 12:45
A Const argument that a custom EnzymeRules derivative rule reads (or
writes) but the primal never touches was being dropped from a
differentiated function's signature and replaced with jl_nothing,
causing a segfault, whenever the call crossed a real (non-inlined)
function boundary. The write-only/no-capture attributes trusted by
shouldDisableNoWrite are inferred from the callee's primal semantics
alone and cannot see that a custom rule reachable from within an
otherwise-resolved callee may need the argument's real value.

shouldDisableNoWrite (Utils.h) now also disables the no-write shortcut
for any resolved callee with a body Enzyme will still analyze (not
just truly opaque external declarations), covering
DifferentialUseAnalysis.cpp, EnzymeLogic.cpp, and AdjointGenerator.h,
which all share this predicate.

Since the argument is now known to potentially be read/written despite
carrying stale readnone/readonly/writeonly attributes copied from the
primal, also drop those specific attributes (not enzyme_inactive or
nocapture) wherever they get copied onto a Const argument: in
FunctionUtils.cpp's CloneFunctionWithReturns, and in the two call-site
attribute-copy loops in AdjointGenerator.h.

Reported in EnzymeAD/Enzyme.jl#3570.
@vchuravy

Copy link
Copy Markdown
Member

Alternative EnzymeAD/Enzyme.jl#3610

@Tuna2222

Tuna2222 commented Oct 3, 2026

Copy link
Copy Markdown
Author

Superseded by #3352 and #3353, which stop writeonly/readnone from being inferred on the parameters of a custom-rule function. That fixes this at the source instead of stripping the attributes afterwards. Verified with Enzyme.jl v0.13.209. Closing.

@Tuna2222 Tuna2222 closed this Oct 3, 2026
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