diff --git a/Project.toml b/Project.toml index 78120df1..7673c672 100644 --- a/Project.toml +++ b/Project.toml @@ -1,6 +1,6 @@ name = "StaticArrays" uuid = "90137ffa-7385-5640-81b9-e52037218182" -version = "1.0.0" +version = "1.0.1" [deps] LinearAlgebra = "37e2e46d-f89d-539d-b4ee-838fcccc9c8e" diff --git a/src/matrix_multiply_add.jl b/src/matrix_multiply_add.jl index 5d25483b..d04af8a1 100644 --- a/src/matrix_multiply_add.jl +++ b/src/matrix_multiply_add.jl @@ -218,13 +218,33 @@ const StaticVecOrMatLikeForFiveArgMulDest{T} = Union{ α::Number, β::Number) = _mul!(TSize(dest), mul_parent(dest), Size(A), Size(B), A, B, AlphaBeta(α,β)) -@inline function LinearAlgebra.mul!(dest::StaticVecOrMatLike{TDest}, A::StaticVecOrMatLike{TA}, - B::StaticVecOrMatLike{TB}) where {TDest,TA,TB} +# See https://github.com/JuliaArrays/StaticArrays.jl/issues/857. +# `StaticVecOrMatLike` is a very large union, and this caused Julia 1.0.x to +# use a large amount of memory when compiling StaticArrays in the presence +# of other packages that also extend `LinearAlgebra.mul!` in a similar +# fashion. As an example, this led to JuMP using more than 4 GB of RAM when +# running `using JuMP`, causing its CI to crash. +# +# Computing the eltypes within the function, rather than specifying them in +# the type arguments greatly improves the issue, with `using JuMP` going +# from: +# julia> @time using JuMP +# [ Info: Precompiling JuMP [4076af6c-e467-56ae-b986-b466b2749572] +# Killed +# to: +# julia> @time using JuMP +# [ Info: Precompiling JuMP [4076af6c-e467-56ae-b986-b466b2749572] +# 101.723598 seconds (12.85 M allocations: 812.902 MiB, 0.31% gc time) +@inline function LinearAlgebra.mul!( + dest::StaticVecOrMatLike, + A::StaticVecOrMatLike, + B::StaticVecOrMatLike, +) + TDest, TA, TB = eltype(dest), eltype(A), eltype(B) TMul = promote_op(matprod, TA, TB) return _mul!(TSize(dest), mul_parent(dest), Size(A), Size(B), A, B, NoMulAdd{TMul, TDest}()) end - "Calculate the product of the dimensions being multiplied. Useful as a heuristic for unrolling." @inline multiplied_dimension(A::Type{<:StaticVecOrMatLike}, B::Type{<:StaticVecOrMatLike}) = prod(size(A)) * size(B,2) @@ -310,7 +330,7 @@ function uplo_access(sa, asym, k, j, uplo) elseif uplo == :unit_lower_triangular if k > j return :($asym[$(LinearIndices(sa)[k, j])]) - elseif k == j + elseif k == j return :(oneunit($TAsym)) else return :(zero($TAsym)) @@ -439,7 +459,7 @@ end else ab = [:(a[$i] * transpose(b[$j])) for i = 1:sa[1], j = 1:sb[2]] end - + exprs = _muladd_expr(lhs, ab, _add) return quote @@ -558,7 +578,7 @@ end @inbounds $(Expr(:block, exprs...)) end end - + return quote @_inline_meta α = alpha(_add)