Skip to content

Commit c31262e

Browse files
Possible solution to repeated callbacks at dt=0
Possible solution to SciML/ModelingToolkit.jl#3327 . I don't like this solution though because the way it works is that it allows it to catch a dt=0 case by eliminating the bottom_t from matching t, and then checking if the nonlinear solver did not converge, and then setting error_occured on that. I think it's possible to construct a bug where in the interval (t0,t1) you have an event `t2` and an "event" found at t0, this will search for the first event so it will narrow the intervals to `t3 < t2` and then do the search on (t0,t3), then fail, and so it would say there is no event.
1 parent a665e64 commit c31262e

File tree

1 file changed

+10
-7
lines changed

1 file changed

+10
-7
lines changed

src/callbacks.jl

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -363,13 +363,16 @@ function bisection(
363363
f, tup, t_forward::Bool, rootfind::SciMLBase.RootfindOpt, abstol, reltol;
364364
maxiters = 1000)
365365
if rootfind == SciMLBase.LeftRootFind
366-
solve(IntervalNonlinearProblem{false}(f, tup),
366+
sol = solve(IntervalNonlinearProblem{false}(f, tup),
367367
InternalITP(), abstol = abstol,
368-
reltol = reltol).left
368+
reltol = reltol)
369+
SciMLBase.successful_retcode(sol), sol.left
369370
else
370-
solve(IntervalNonlinearProblem{false}(f, tup),
371+
sol = solve(IntervalNonlinearProblem{false}(f, tup),
371372
InternalITP(), abstol = abstol,
372-
reltol = reltol).right
373+
reltol = reltol)
374+
@assert SciMLBase.successful_retcode(sol)
375+
SciMLBase.successful_retcode(sol), sol.right
373376
end
374377
end
375378

@@ -430,7 +433,7 @@ function find_callback_time(integrator, callback::ContinuousCallback, counter)
430433
sign(zero_func(bottom_t)) * sign_top >= zero(sign_top) &&
431434
error("Double callback crossing floating pointer reducer errored. Report this issue.")
432435
end
433-
Θ = bisection(zero_func, (bottom_t, top_t), isone(integrator.tdir),
436+
event_occurred, Θ = bisection(zero_func, (nextfloat(bottom_t), top_t), isone(integrator.tdir),
434437
callback.rootfind, callback.abstol, callback.reltol)
435438
integrator.last_event_error = DiffEqBase.value(ODE_DEFAULT_NORM(
436439
zero_func(Θ), Θ))
@@ -503,8 +506,7 @@ function find_callback_time(integrator, callback::VectorContinuousCallback, coun
503506
sign(zero_func(bottom_t)) * sign_top >= zero(sign_top) &&
504507
error("Double callback crossing floating pointer reducer errored. Report this issue.")
505508
end
506-
507-
Θ = bisection(zero_func, (bottom_t, top_t),
509+
event_occurred, Θ = bisection(zero_func, (nextfloat(bottom_t), top_t),
508510
isone(integrator.tdir), callback.rootfind,
509511
callback.abstol, callback.reltol)
510512
if integrator.tdir * Θ < integrator.tdir * min_t
@@ -598,6 +600,7 @@ function apply_callback!(integrator,
598600
end
599601
return true, saved_in_cb
600602
end
603+
601604
false, saved_in_cb
602605
end
603606

0 commit comments

Comments
 (0)