# Callbacks

Each Krylov method is able to call a callback function as `callback(solver)`

at each iteration. The callback should return `true`

if the main loop should terminate, and `false`

otherwise. If the method terminated because of the callback, the output status will be `"user-requested exit"`

. For example, if the user defines `minres_callback(solver::MinresSolver)`

, it can be passed to the solver using

`(x, stats) = minres(A, b, callback = minres_callback)`

If you need to write a callback that uses variables that are not in a `KrylovSolver`

, use a closure:

```
function custom_stopping_condition(solver::KrylovSolver, A, b, r, tol)
mul!(r, A, solver.x)
r .-= b # r := b - Ax
bool = norm(r) ≤ tol # tolerance based on the 2-norm of the residual
return bool
end
cg_callback(solver) = custom_stopping_condition(solver, A, b, r, tol)
(x, stats) = cg(A, b, callback = cg_callback)
```

Alternatively, use a structure and make it callable:

```
mutable struct CallbackWorkspace{T}
A::Matrix{T}
b::Vector{T}
r::Vector{T}
tol::T
end
function (workspace::CallbackWorkspace)(solver::KrylovSolver)
mul!(workspace.r, workspace.A, solver.x)
workspace.r .-= workspace.b
bool = norm(workspace.r) ≤ workspace.tol
return bool
end
bicgstab_callback = CallbackWorkspace(A, b, r, tol)
(x, stats) = bicgstab(A, b, callback = bicgstab_callback)
```

Although the main goal of a callback is to add new stopping conditions, it can also retrieve information from the workspace of a Krylov method along the iterations. We now illustrate how to store all iterates $x_k$ of the GMRES method.

```
S = Krylov.ktypeof(b)
global X = S[] # Storage for GMRES iterates
function gmres_callback(solver)
z = solver.z
k = solver.inner_iter
nr = sum(1:k)
V = solver.V
R = solver.R
y = copy(z)
# Solve Rk * yk = zk
for i = k : -1 : 1
pos = nr + i - k
for j = k : -1 : i+1
y[i] = y[i] - R[pos] * y[j]
pos = pos - j + 1
end
y[i] = y[i] / R[pos]
end
# xk = Vk * yk
xk = sum(V[i] * y[i] for i = 1:k)
push!(X, xk)
return false # We don't want to add new stopping conditions
end
(x, stats) = gmres(A, b, callback = gmres_callback)
```