Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion Project.toml
Original file line number Diff line number Diff line change
Expand Up @@ -77,6 +77,7 @@ ChainRulesCore = "1.22"
ConcreteStructs = "0.2.3"
DocStringExtensions = "0.9.3"
EnumX = "1.0.4"
ExplicitImports = "1"
EnzymeCore = "0.8.1"
FastAlmostBandedMatrices = "0.1"
FastLapackInterface = "2"
Expand Down Expand Up @@ -122,6 +123,7 @@ julia = "1.10"
[extras]
AllocCheck = "9b6a8646-10ed-4001-bbdc-1d2f46dfbb1a"
Aqua = "4c88cf16-eb10-579e-8560-4a9242c79595"
ExplicitImports = "7d51a73a-1435-4ff3-83d9-f097790105c7"
BandedMatrices = "aae01518-5342-5314-be14-df237901396f"
BlockDiagonals = "0a1fb500-61f7-11e9-3c65-f5ef3456f9f0"
FastAlmostBandedMatrices = "9d29842c-ecb8-4973-b1e9-a27b1157504e"
Expand Down Expand Up @@ -150,4 +152,4 @@ Test = "8dfed614-e22c-5e08-85e1-65c5234f0b40"
Zygote = "e88e6eb3-aa80-5325-afca-941959d7151f"

[targets]
test = ["Aqua", "Test", "IterativeSolvers", "InteractiveUtils", "KrylovKit", "KrylovPreconditioners", "Pkg", "Random", "SafeTestsets", "MultiFloats", "ForwardDiff", "HYPRE", "MPI", "BlockDiagonals", "FiniteDiff", "BandedMatrices", "FastAlmostBandedMatrices", "StaticArrays", "AllocCheck", "StableRNGs", "Zygote", "RecursiveFactorization", "Sparspak", "FastLapackInterface", "SparseArrays"]
test = ["Aqua", "Test", "IterativeSolvers", "InteractiveUtils", "KrylovKit", "KrylovPreconditioners", "Pkg", "Random", "SafeTestsets", "MultiFloats", "ForwardDiff", "HYPRE", "MPI", "BlockDiagonals", "FiniteDiff", "BandedMatrices", "FastAlmostBandedMatrices", "StaticArrays", "AllocCheck", "StableRNGs", "Zygote", "RecursiveFactorization", "Sparspak", "FastLapackInterface", "SparseArrays", "ExplicitImports"]
4 changes: 3 additions & 1 deletion ext/LinearSolveCUDAExt.jl
Original file line number Diff line number Diff line change
@@ -1,7 +1,9 @@
module LinearSolveCUDAExt

using CUDA
using LinearSolve
using LinearSolve: LinearSolve, is_cusparse, defaultalg, cudss_loaded, DefaultLinearSolver,
DefaultAlgorithmChoice, ALREADY_WARNED_CUDSS, LinearCache, needs_concrete_A,
Comment on lines +4 to +5
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
using LinearSolve: LinearSolve, is_cusparse, defaultalg, cudss_loaded, DefaultLinearSolver,
DefaultAlgorithmChoice, ALREADY_WARNED_CUDSS, LinearCache, needs_concrete_A,
using LinearSolve: LinearSolve, is_cusparse, defaultalg, cudss_loaded, DefaultLinearSolver,
DefaultAlgorithmChoice, ALREADY_WARNED_CUDSS, LinearCache,
needs_concrete_A,

error_no_cudss_lu, CUDSS_LOADED, init_cacheval
using LinearSolve.LinearAlgebra, LinearSolve.SciMLBase, LinearSolve.ArrayInterface
using SciMLBase: AbstractSciMLOperator

Expand Down
2 changes: 1 addition & 1 deletion ext/LinearSolveCUDSSExt.jl
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
module LinearSolveCUDSSExt

using LinearSolve
using LinearSolve: LinearSolve, cudss_loaded
using CUDSS

LinearSolve.cudss_loaded(A::CUDSS.CUDA.CUSPARSE.CuSparseMatrixCSR) = true
Expand Down
4 changes: 3 additions & 1 deletion ext/LinearSolveEnzymeExt.jl
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
module LinearSolveEnzymeExt

using LinearSolve
using LinearSolve: LinearSolve, SciMLLinearSolveAlgorithm, init, solve!, LinearProblem,
LinearCache, AbstractKrylovSubspaceMethod, DefaultLinearSolver,
Comment on lines +3 to +4
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
using LinearSolve: LinearSolve, SciMLLinearSolveAlgorithm, init, solve!, LinearProblem,
LinearCache, AbstractKrylovSubspaceMethod, DefaultLinearSolver,
using LinearSolve: LinearSolve, SciMLLinearSolveAlgorithm, init, solve!, LinearProblem,
LinearCache, AbstractKrylovSubspaceMethod, DefaultLinearSolver,

defaultalg_adjoint_eval, solve
using LinearSolve.LinearAlgebra
using EnzymeCore
using EnzymeCore: EnzymeRules
Expand Down
3 changes: 1 addition & 2 deletions ext/LinearSolvePardisoExt.jl
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,9 @@ module LinearSolvePardisoExt
using Pardiso, LinearSolve
using SparseArrays
using SparseArrays: nonzeros, rowvals, getcolptr
using LinearSolve: PardisoJL
using LinearSolve: PardisoJL, @unpack

using LinearSolve.SciMLBase
using LinearSolve.UnPack

LinearSolve.needs_concrete_A(alg::PardisoJL) = true

Expand Down
3 changes: 2 additions & 1 deletion ext/LinearSolveRecursiveFactorizationExt.jl
Original file line number Diff line number Diff line change
@@ -1,7 +1,8 @@
module LinearSolveRecursiveFactorizationExt

using LinearSolve
using LinearSolve: LinearSolve, userecursivefactorization, LinearCache, @get_cacheval, RFLUFactorization
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
using LinearSolve: LinearSolve, userecursivefactorization, LinearCache, @get_cacheval, RFLUFactorization
using LinearSolve: LinearSolve, userecursivefactorization, LinearCache, @get_cacheval,
RFLUFactorization

using LinearSolve.LinearAlgebra, LinearSolve.ArrayInterface, RecursiveFactorization
using SciMLBase: SciMLBase, ReturnCode

LinearSolve.userecursivefactorization(A::Union{Nothing, AbstractMatrix}) = true

Expand Down
32 changes: 20 additions & 12 deletions ext/LinearSolveSparseArraysExt.jl
Original file line number Diff line number Diff line change
@@ -1,9 +1,17 @@
module LinearSolveSparseArraysExt

using LinearSolve, LinearAlgebra
using SparseArrays
using SparseArrays: AbstractSparseMatrixCSC, nonzeros, rowvals, getcolptr
using LinearSolve: BLASELTYPES, pattern_changed, ArrayInterface
using LinearSolve: LinearSolve, BLASELTYPES, pattern_changed, ArrayInterface,
@get_cacheval, CHOLMODFactorization, GenericFactorization, GenericLUFactorization,
KLUFactorization, LUFactorization, NormalCholeskyFactorization, OperatorAssumptions,
QRFactorization, RFLUFactorization, UMFPACKFactorization, solve
Comment on lines +4 to +6
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
@get_cacheval, CHOLMODFactorization, GenericFactorization, GenericLUFactorization,
KLUFactorization, LUFactorization, NormalCholeskyFactorization, OperatorAssumptions,
QRFactorization, RFLUFactorization, UMFPACKFactorization, solve
@get_cacheval, CHOLMODFactorization, GenericFactorization,
GenericLUFactorization,
KLUFactorization, LUFactorization, NormalCholeskyFactorization,
OperatorAssumptions,
QRFactorization, RFLUFactorization, UMFPACKFactorization, solve

using ArrayInterface: ArrayInterface
using LinearAlgebra: LinearAlgebra, I, Hermitian, Symmetric, cholesky, ldiv!, lu, lu!, QR
using SparseArrays: SparseArrays, AbstractSparseArray, AbstractSparseMatrixCSC, SparseMatrixCSC,
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
using SparseArrays: SparseArrays, AbstractSparseArray, AbstractSparseMatrixCSC, SparseMatrixCSC,
using SparseArrays: SparseArrays, AbstractSparseArray, AbstractSparseMatrixCSC,
SparseMatrixCSC,

nonzeros, rowvals, getcolptr, sparse, sprand
using SparseArrays.UMFPACK: UMFPACK_OK
using Base: /, \, convert
using SciMLBase: SciMLBase, LinearProblem, ReturnCode
import StaticArraysCore: SVector

# Can't `using KLU` because cannot have a dependency in there without
# requiring the user does `using KLU`
Expand Down Expand Up @@ -187,7 +195,7 @@ function SciMLBase.solve!(
end

F = LinearSolve.@get_cacheval(cache, :UMFPACKFactorization)
if F.status == SparseArrays.UMFPACK.UMFPACK_OK
if F.status == UMFPACK_OK
y = ldiv!(cache.u, F, cache.b)
SciMLBase.build_linear_solution(alg, y, nothing, cache; retcode = ReturnCode.Success)
else
Expand Down Expand Up @@ -298,36 +306,36 @@ function LinearSolve.init_cacheval(alg::NormalCholeskyFactorization,
Symmetric{T, <:AbstractSparseArray{T}}}, b, u, Pl, Pr,
maxiters::Int, abstol, reltol, verbose::Bool,
assumptions::OperatorAssumptions) where {T <: BLASELTYPES}
LinearSolve.ArrayInterface.cholesky_instance(convert(AbstractMatrix, A))
ArrayInterface.cholesky_instance(convert(AbstractMatrix, A))
end

# Specialize QR for the non-square case
# Missing ldiv! definitions: https://github.com/JuliaSparse/SparseArrays.jl/issues/242
function LinearSolve._ldiv!(x::Vector,
A::Union{SparseArrays.QR, LinearAlgebra.QRCompactWY,
A::Union{QR, LinearAlgebra.QRCompactWY,
SparseArrays.SPQR.QRSparse,
SparseArrays.CHOLMOD.Factor}, b::Vector)
x .= A \ b
end

function LinearSolve._ldiv!(x::AbstractVector,
A::Union{SparseArrays.QR, LinearAlgebra.QRCompactWY,
A::Union{QR, LinearAlgebra.QRCompactWY,
SparseArrays.SPQR.QRSparse,
SparseArrays.CHOLMOD.Factor}, b::AbstractVector)
x .= A \ b
end

# Ambiguity removal
function LinearSolve._ldiv!(::LinearSolve.SVector,
function LinearSolve._ldiv!(::SVector,
A::Union{SparseArrays.CHOLMOD.Factor, LinearAlgebra.QR,
LinearAlgebra.QRCompactWY, SparseArrays.SPQR.QRSparse},
b::AbstractVector)
(A \ b)
end
function LinearSolve._ldiv!(::LinearSolve.SVector,
function LinearSolve._ldiv!(::SVector,
A::Union{SparseArrays.CHOLMOD.Factor, LinearAlgebra.QR,
LinearAlgebra.QRCompactWY, SparseArrays.SPQR.QRSparse},
b::LinearSolve.SVector)
b::SVector)
(A \ b)
end

Expand Down Expand Up @@ -363,7 +371,7 @@ end
function LinearSolve.init_cacheval(alg::QRFactorization, A::SparseMatrixCSC{Float64, <:Integer}, b, u, Pl, Pr,
maxiters::Int, abstol, reltol, verbose::Bool,
assumptions::OperatorAssumptions)
LinearSolve.ArrayInterface.qr_instance(convert(AbstractMatrix, A), alg.pivot)
ArrayInterface.qr_instance(convert(AbstractMatrix, A), alg.pivot)
end

function LinearSolve.init_cacheval(
Expand Down
14 changes: 10 additions & 4 deletions src/KLU/klu.jl
Original file line number Diff line number Diff line change
@@ -1,15 +1,20 @@
module KLU

using SparseArrays
using SparseArrays: SparseMatrixCSC
using SparseArrays: SparseArrays, SparseMatrixCSC
import SparseArrays: nnz

export klu, klu!

const libklu = :libklu
const libsuitesparseconfig = :libsuitesparseconfig
using Base: Ptr, Cvoid, Cint, Cdouble, Cchar, Csize_t
include("wrappers.jl")

import Base: (\), size, getproperty, setproperty!, propertynames, show
import Base: (\), size, getproperty, setproperty!, propertynames, show,
copy, eachindex, view, sortperm, unsafe_load, zeros, convert, eltype,
length, parent, stride, finalizer, Complex, complex, imag, real, map!,
summary, println, oneunit, sizeof, isdefined, setfield!, getfield,
OutOfMemoryError, ArgumentError, OverflowError, ErrorException, DimensionMismatch

# Convert from 1-based to 0-based indices
function decrement!(A::AbstractArray{T}) where {T <: Integer}
Expand All @@ -29,7 +34,8 @@ function increment!(A::AbstractArray{T}) where {T <: Integer}
end
increment(A::AbstractArray{<:Integer}) = increment!(copy(A))

using LinearAlgebra
using LinearAlgebra: LinearAlgebra, ldiv!, Adjoint, Transpose, Factorization
import LinearAlgebra: issuccess

const AdjointFact = isdefined(LinearAlgebra, :AdjointFactorization) ?
LinearAlgebra.AdjointFactorization : Adjoint
Expand Down
47 changes: 27 additions & 20 deletions src/LinearSolve.jl
Original file line number Diff line number Diff line change
Expand Up @@ -5,27 +5,33 @@ if isdefined(Base, :Experimental) &&
end

import PrecompileTools
using ArrayInterface
using Base: cache_dependencies, Bool
using LinearAlgebra
using ArrayInterface: ArrayInterface
using Base: Bool, convert, copyto!, adjoint, transpose, /, \, require_one_based_indexing
using LinearAlgebra: LinearAlgebra, BlasInt, LU, Adjoint, BLAS, Bidiagonal, BunchKaufman,
ColumnNorm, Diagonal, Factorization, Hermitian, I, LAPACK, NoPivot,
RowMaximum, RowNonZero, SymTridiagonal, Symmetric, Transpose,
Tridiagonal, UniformScaling, axpby!, axpy!, bunchkaufman, bunchkaufman!,
cholesky, cholesky!, diagind, dot, inv, ldiv!, ldlt!, lu, lu!, mul!, norm,
qr, qr!, svd, svd!
Comment on lines +10 to +15
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
using LinearAlgebra: LinearAlgebra, BlasInt, LU, Adjoint, BLAS, Bidiagonal, BunchKaufman,
ColumnNorm, Diagonal, Factorization, Hermitian, I, LAPACK, NoPivot,
RowMaximum, RowNonZero, SymTridiagonal, Symmetric, Transpose,
Tridiagonal, UniformScaling, axpby!, axpy!, bunchkaufman, bunchkaufman!,
cholesky, cholesky!, diagind, dot, inv, ldiv!, ldlt!, lu, lu!, mul!, norm,
qr, qr!, svd, svd!
using LinearAlgebra: LinearAlgebra, BlasInt, LU, Adjoint, BLAS, Bidiagonal, BunchKaufman,
ColumnNorm, Diagonal, Factorization, Hermitian, I, LAPACK, NoPivot,
RowMaximum, RowNonZero, SymTridiagonal, Symmetric, Transpose,
Tridiagonal, UniformScaling, axpby!, axpy!, bunchkaufman,
bunchkaufman!,
cholesky, cholesky!, diagind, dot, inv, ldiv!, ldlt!, lu, lu!, mul!,
norm,
qr, qr!, svd, svd!

using LazyArrays: @~, BroadcastArray
using SciMLBase: AbstractLinearAlgorithm, LinearAliasSpecifier
using SciMLOperators
using SciMLOperators: AbstractSciMLOperator, IdentityOperator
using Setfield
using UnPack
using DocStringExtensions
using EnumX
using Markdown
using ChainRulesCore
using SciMLBase: SciMLBase, LinearAliasSpecifier, AbstractSciMLOperator,
init, solve!, reinit!, solve, ReturnCode, LinearProblem
using SciMLOperators: SciMLOperators, AbstractSciMLOperator, IdentityOperator, MatrixOperator,
has_ldiv!, issquare
Comment on lines +19 to +20
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
using SciMLOperators: SciMLOperators, AbstractSciMLOperator, IdentityOperator, MatrixOperator,
has_ldiv!, issquare
using SciMLOperators: SciMLOperators, AbstractSciMLOperator, IdentityOperator,
MatrixOperator,
has_ldiv!, issquare

using Setfield: @set, @set!
using UnPack: @unpack
using DocStringExtensions: DocStringExtensions
using EnumX: EnumX, @enumx
using Markdown: Markdown, @doc_str
using ChainRulesCore: ChainRulesCore, NoTangent
using Reexport: Reexport, @reexport
using Libdl: Libdl, dlsym_e
import InteractiveUtils
import RecursiveArrayTools

import StaticArraysCore: StaticArray, SVector, MVector, SMatrix, MMatrix
import StaticArraysCore: StaticArray, SVector, SMatrix

using LinearAlgebra: BlasInt, LU
using LinearAlgebra.LAPACK: require_one_based_indexing,
chkfinite, chkstride1,
using LinearAlgebra.LAPACK: chkfinite, chkstride1,
@blasfunc, chkargsok

import GPUArraysCore
Expand All @@ -34,8 +40,6 @@ import ConcreteStructs: @concrete

# wrap
import Krylov
using SciMLBase
import Preferences

const CRC = ChainRulesCore

Expand All @@ -51,9 +55,7 @@ else
const usemkl = false
end

using Reexport
@reexport using SciMLBase
using SciMLBase: _unwrap_val

abstract type SciMLLinearSolveAlgorithm <: SciMLBase.AbstractLinearAlgorithm end
abstract type AbstractFactorization <: SciMLLinearSolveAlgorithm end
Expand Down Expand Up @@ -95,6 +97,11 @@ issparsematrix(A) = false
make_SparseMatrixCSC(A) = nothing
makeempty_SparseMatrixCSC(A) = nothing

# Stub functions for SparseArrays - overridden in extension
getcolptr(A) = error("SparseArrays extension not loaded")
rowvals(A) = error("SparseArrays extension not loaded")
nonzeros(A) = error("SparseArrays extension not loaded")

EnumX.@enumx DefaultAlgorithmChoice begin
LUFactorization
QRFactorization
Expand Down
2 changes: 1 addition & 1 deletion src/appleaccelerate.jl
Original file line number Diff line number Diff line change
Expand Up @@ -252,7 +252,7 @@ function SciMLBase.solve!(cache::LinearCache, alg::AppleAccelerateLUFactorizatio
end

A, info = @get_cacheval(cache, :AppleAccelerateLUFactorization)
LinearAlgebra.require_one_based_indexing(cache.u, cache.b)
require_one_based_indexing(cache.u, cache.b)
m, n = size(A, 1), size(A, 2)
if m > n
Bc = copy(cache.b)
Expand Down
3 changes: 2 additions & 1 deletion src/common.jl
Original file line number Diff line number Diff line change
Expand Up @@ -207,7 +207,8 @@ function SciMLBase.init(prob::LinearProblem, alg::SciMLLinearSolveAlgorithm,
elseif b isa Array
copy(b)
elseif issparsematrixcsc(b)
SparseMatrixCSC(size(b)..., getcolptr(b), rowvals(b), nonzeros(b))
# Extension must be loaded if issparsematrixcsc returns true
make_SparseMatrixCSC(b)
else
deepcopy(b)
end
Expand Down
4 changes: 2 additions & 2 deletions src/default.jl
Original file line number Diff line number Diff line change
Expand Up @@ -125,7 +125,7 @@ function defaultalg(A::GPUArraysCore.AnyGPUArray, b::GPUArraysCore.AnyGPUArray,
end
end

function defaultalg(A::SciMLBase.AbstractSciMLOperator, b,
function defaultalg(A::SciMLOperators.AbstractSciMLOperator, b,
assump::OperatorAssumptions{Bool})
if has_ldiv!(A)
return DefaultLinearSolver(DefaultAlgorithmChoice.DirectLdiv!)
Expand All @@ -142,7 +142,7 @@ function defaultalg(A::SciMLBase.AbstractSciMLOperator, b,
end

# Fix ambiguity
function defaultalg(A::SciMLBase.AbstractSciMLOperator, b::GPUArraysCore.AnyGPUArray,
function defaultalg(A::SciMLOperators.AbstractSciMLOperator, b::GPUArraysCore.AnyGPUArray,
assump::OperatorAssumptions{Bool})
if has_ldiv!(A)
return DefaultLinearSolver(DefaultAlgorithmChoice.DirectLdiv!)
Expand Down
20 changes: 20 additions & 0 deletions test/qa.jl
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
using LinearSolve, Aqua
using ExplicitImports

@testset "Aqua" begin
Aqua.find_persistent_tasks_deps(LinearSolve)
Aqua.test_ambiguities(LinearSolve, recursive = false, broken = true)
Expand All @@ -10,3 +12,21 @@ using LinearSolve, Aqua
Aqua.test_unbound_args(LinearSolve)
Aqua.test_undefined_exports(LinearSolve)
end

@testset "Explicit Imports" begin
# Get extension modules that might be unanalyzable
klu_mod = try
Base.get_extension(LinearSolve, :LinearSolveSparseArraysExt).KLU
catch
nothing
end
unanalyzable_mods = (LinearSolve.OperatorCondition, LinearSolve.DefaultAlgorithmChoice)
if klu_mod !== nothing
unanalyzable_mods = (unanalyzable_mods..., klu_mod)
end

@test check_no_implicit_imports(LinearSolve; skip = (Base, Core),
Comment on lines +27 to +28
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
@test check_no_implicit_imports(LinearSolve; skip = (Base, Core),
@test check_no_implicit_imports(LinearSolve; skip = (Base, Core),

allow_unanalyzable = unanalyzable_mods) === nothing
@test check_no_stale_explicit_imports(LinearSolve; allow_unanalyzable = unanalyzable_mods) === nothing
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

[JuliaFormatter] reported by reviewdog 🐶

Suggested change
@test check_no_stale_explicit_imports(LinearSolve; allow_unanalyzable = unanalyzable_mods) === nothing
@test check_no_stale_explicit_imports(
LinearSolve; allow_unanalyzable = unanalyzable_mods) === nothing

@test check_all_qualified_accesses_via_owners(LinearSolve) === nothing
end
Loading