-
-
Notifications
You must be signed in to change notification settings - Fork 611
Open
Labels
Description
Following the Enzyme.jl example:
using Flux: Flux
using Enzyme: Enzyme
function reproducer()
model = Flux.Chain(Flux.Dense(28^2 => 32, Flux.sigmoid), Flux.Dense(32 => 10), Flux.softmax)
# this allocates space for the gradient
model_shadow = Enzyme.Duplicated(model)
input = randn(28^2, 1)
label = [i == 3 for i in 1:10]
grad_model = Flux.gradient(
(m, x, y) -> sum(abs2, m(x) .- y),
model_shadow,
# input and label are const because we differentiate w.r.t. to the model parameters, not input or output.
Enzyme.Const(input),
Enzyme.Const(label),
)
end
reproducer()
I run into the following error both on Julia 1.10.7 and Julia 1.11.2
ERROR: Constant memory is stored (or returned) to a differentiable variable.
As a result, Enzyme cannot provably ensure correctness and throws this error.
This might be due to the use of a constant variable as temporary storage for active memory (https://enzyme.mit.edu/julia/stable/faq/#Runtime-Activity).
If Enzyme should be able to prove this use non-differentable, open an issue!
To work around this issue, either:
a) rewrite this variable to not be conditionally active (fastest, but requires a code change), or
b) set the Enzyme mode to turn on runtime activity (e.g. autodiff(set_runtime_activity(Reverse), ...) ). This will maintain correctness, but may slightly reduce performance.
Mismatched activity for: store {} addrspace(10)* %68, {} addrspace(10)* addrspace(10)* %.repack65, align 8, !dbg !331, !tbaa !333, !alias.scope !268, !noalias !335 const val: %68 = call fastcc nonnull {} addrspace(10)* @julia_summary_3629({} addrspace(10)* nocapture nofree noundef nonnull readonly align 16 dereferenceable(40) %1) #308, !dbg !323
Type tree: {[-1]:Pointer}
llvalue= %68 = call fastcc nonnull {} addrspace(10)* @julia_summary_3629({} addrspace(10)* nocapture nofree noundef nonnull readonly align 16 dereferenceable(40) %1) #308, !dbg !323
Stacktrace:
[1] #invokelatest#2
@ ./essentials.jl:894
[2] invokelatest
@ ./essentials.jl:889
[3] macro expansion
@ ./logging.jl:377
[4] _match_eltype
@ ~/.julia/packages/Flux/fteq2/src/layers/stateless.jl:60
Interestingly, each of the following changes resolves the issue:
- Calling the gradient computation as
Enzyme.gradient(Enzyme.set_runtime_activity(Enzyme.Reverse), ...)
as suggested by the error messages works. - Explicitly converting
input
toFloat32
before passing it toFlux.gradient
also resolves the issue
However, it seems that the conversion to Float32
alone is not the culprit. The following works as expected:
function sum_converted(x)
sum(convert(AbstractArray{Float32}, x))
end
function reproducer_reduced()
input = randn(10)
Enzyme.gradient(Enzyme.Reverse, sum_converted, input)
end
# returns `([1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0, 1.0],)`
ivanightingale