module OrdinaryDiffEqExtrapolation

import OrdinaryDiffEqCore: alg_maximum_order, get_current_adaptive_order,
    get_current_alg_order,
    accept_step_controller,
    beta2_default, beta1_default, gamma_default,
    perform_step!, @cache, unwrap_alg,
    isthreaded, PIController,
    OrdinaryDiffEqMutableCache, OrdinaryDiffEqConstantCache,
    reset_alg_dependent_opts!, AbstractController,
    step_accept_controller!, step_reject_controller!,
    OrdinaryDiffEqAdaptiveAlgorithm,
    OrdinaryDiffEqAdaptiveImplicitAlgorithm,
    alg_cache, CompiledFloats, stepsize_controller!,
    qmin_default,
    constvalue, PolyesterThreads,
    _fixup_ad,
    get_fsalfirstlast
import OrdinaryDiffEqCore: default_controller, AbstractControllerCache, setup_controller_cache,
    get_qmin, get_qmax
import OrdinaryDiffEqCore

# Owned by SciMLBase / DiffEqBase, re-exported through OrdinaryDiffEqCore /
# OrdinaryDiffEqDifferentiation.
import SciMLBase: alg_order, LinearAliasSpecifier,
    TimeDerivativeWrapper, UDerivativeWrapper,
    TimeGradientWrapper, UJacobianWrapper
import DiffEqBase: initialize!, calculate_residuals, calculate_residuals!, timedepentdtmin

using FastBroadcast: FastBroadcast, @..
using MuladdMacro: MuladdMacro, @muladd
using RecursiveArrayTools: RecursiveArrayTools, recursivefill!
using LinearSolve: LinearSolve, RFLUFactorization
using FastPower: fastpower
using SciMLOperators: SciMLOperators, WOperator
import SciMLLogging: @SciMLMessage
import OrdinaryDiffEqDifferentiation: calc_J,
    build_grad_config,
    build_jac_config, calc_J!, jacobian2W!, dolinsolve
import ADTypes: AutoForwardDiff

using CommonSolve: init
using SciMLBase: SciMLBase, LinearProblem

include("utils.jl")
include("algorithms.jl")
include("alg_utils.jl")
include("controllers.jl")
include("extrapolation_caches.jl")
include("extrapolation_perform_step.jl")

@inline function SciMLBase.get_tmp_cache(
        integrator,
        alg::OrdinaryDiffEqImplicitExtrapolationAlgorithm,
        cache::OrdinaryDiffEqMutableCache
    )
    return (cache.tmp, cache.utilde)
end

export AitkenNeville, ExtrapolationMidpointDeuflhard, ExtrapolationMidpointHairerWanner,
    ImplicitEulerExtrapolation,
    ImplicitDeuflhardExtrapolation, ImplicitHairerWannerExtrapolation,
    ImplicitEulerBarycentricExtrapolation

end
