Browse Source

runic -i .

pull/32/head
Fredrik Ekre 11 months ago
parent
commit
85af5be132
No known key found for this signature in database
GPG Key ID: DE82E6D5E364C0A2
  1. 33
      examples/ex5.jl
  2. 10
      ext/HYPREPartitionedArrays.jl
  3. 2
      ext/HYPRESparseArrays.jl
  4. 7
      gen/generator.jl
  5. 6
      gen/prologue.jl
  6. 1
      gen/solver_options.jl
  7. 1752
      lib/LibHYPRE.jl
  8. 13
      src/HYPRE.jl
  9. 1
      src/LibHYPRE.jl
  10. 8
      src/solver_options.jl
  11. 1
      src/solvers.jl
  12. 39
      test/runtests.jl
  13. 2
      test/test_assembler.jl

33
examples/ex5.jl

@ -85,7 +85,9 @@ function main(argc, argv) @@ -85,7 +85,9 @@ function main(argc, argv)
end
# Preliminaries: want at least one processor per row
if n * n < num_procs; n = trunc(Int, sqrt(n)) + 1; end
if n * n < num_procs
n = trunc(Int, sqrt(n)) + 1
end
N = n * n # global number of rows
h = 1.0 / (n + 1) # mesh size
h2 = h * h
@ -257,8 +259,7 @@ function main(argc, argv) @@ -257,8 +259,7 @@ function main(argc, argv)
num_iterations = Ref{Cint}()
final_res_norm = Ref{Cdouble}()
# AMG
if solver_id == 0
if solver_id == 0 # AMG
# Create solver
HYPRE_BoomerAMGCreate(solver_ref)
solver = solver_ref[]
@ -270,7 +271,7 @@ function main(argc, argv) @@ -270,7 +271,7 @@ function main(argc, argv)
HYPRE_BoomerAMGSetRelaxOrder(solver, 1) # uses C/F relaxation
HYPRE_BoomerAMGSetNumSweeps(solver, 1) # Sweeeps on each level
HYPRE_BoomerAMGSetMaxLevels(solver, 20) # maximum number of levels
HYPRE_BoomerAMGSetTol(solver, 1e-7) # conv. tolerance
HYPRE_BoomerAMGSetTol(solver, 1.0e-7) # conv. tolerance
# Now setup and solve!
HYPRE_BoomerAMGSetup(solver, parcsr_A, par_b, par_x)
@ -289,15 +290,14 @@ function main(argc, argv) @@ -289,15 +290,14 @@ function main(argc, argv)
# Destroy solver
HYPRE_BoomerAMGDestroy(solver)
# PCG
elseif solver_id == 50
elseif solver_id == 50 # PCG
# Create solver
HYPRE_ParCSRPCGCreate(MPI_COMM_WORLD, solver_ref)
solver = solver_ref[]
# Set some parameters (See Reference Manual for more parameters)
HYPRE_PCGSetMaxIter(solver, 1000) # max iterations
HYPRE_PCGSetTol(solver, 1e-7) # conv. tolerance
HYPRE_PCGSetTol(solver, 1.0e-7) # conv. tolerance
HYPRE_PCGSetTwoNorm(solver, 1) # use the two norm as the stopping criteria
HYPRE_PCGSetPrintLevel(solver, 2) # prints out the iteration info
HYPRE_PCGSetLogging(solver, 1) # needed to get run info later
@ -319,15 +319,14 @@ function main(argc, argv) @@ -319,15 +319,14 @@ function main(argc, argv)
# Destroy solver
HYPRE_ParCSRPCGDestroy(solver)
# PCG with AMG preconditioner
elseif solver_id == 1
elseif solver_id == 1 # PCG with AMG preconditioner
# Create solver
HYPRE_ParCSRPCGCreate(MPI_COMM_WORLD, solver_ref)
solver = solver_ref[]
# Set some parameters (See Reference Manual for more parameters)
HYPRE_PCGSetMaxIter(solver, 1000) # max iterations
HYPRE_PCGSetTol(solver, 1e-7) # conv. tolerance
HYPRE_PCGSetTol(solver, 1.0e-7) # conv. tolerance
HYPRE_PCGSetTwoNorm(solver, 1) # use the two norm as the stopping criteria
HYPRE_PCGSetPrintLevel(solver, 2) # print solve info
HYPRE_PCGSetLogging(solver, 1) # needed to get run info later
@ -364,15 +363,14 @@ function main(argc, argv) @@ -364,15 +363,14 @@ function main(argc, argv)
HYPRE_ParCSRPCGDestroy(solver)
HYPRE_BoomerAMGDestroy(precond)
# PCG with Parasails Preconditioner
elseif solver_id == 8
elseif solver_id == 8 # PCG with Parasails Preconditioner
# Create solver
HYPRE_ParCSRPCGCreate(MPI_COMM_WORLD, solver_ref)
solver = solver_ref[]
# Set some parameters (See Reference Manual for more parameters)
HYPRE_PCGSetMaxIter(solver, 1000) # max iterations
HYPRE_PCGSetTol(solver, 1e-7) # conv. tolerance
HYPRE_PCGSetTol(solver, 1.0e-7) # conv. tolerance
HYPRE_PCGSetTwoNorm(solver, 1) # use the two norm as the stopping criteria
HYPRE_PCGSetPrintLevel(solver, 2) # print solve info
HYPRE_PCGSetLogging(solver, 1) # needed to get run info later
@ -412,8 +410,7 @@ function main(argc, argv) @@ -412,8 +410,7 @@ function main(argc, argv)
HYPRE_ParCSRPCGDestroy(solver)
HYPRE_ParaSailsDestroy(precond)
# Flexible GMRES with AMG Preconditioner
elseif solver_id == 61
elseif solver_id == 61 # Flexible GMRES with AMG Preconditioner
# Create solver
HYPRE_ParCSRFlexGMRESCreate(MPI_COMM_WORLD, solver_ref)
@ -422,7 +419,7 @@ function main(argc, argv) @@ -422,7 +419,7 @@ function main(argc, argv)
# Set some parameters (See Reference Manual for more parameters)
HYPRE_FlexGMRESSetKDim(solver, 30) # restart
HYPRE_FlexGMRESSetMaxIter(solver, 1000) # max iterations
HYPRE_FlexGMRESSetTol(solver, 1e-7) # conv. tolerance
HYPRE_FlexGMRESSetTol(solver, 1.0e-7) # conv. tolerance
HYPRE_FlexGMRESSetPrintLevel(solver, 2) # print solve info
HYPRE_FlexGMRESSetLogging(solver, 1) # needed to get run info later
@ -459,7 +456,9 @@ function main(argc, argv) @@ -459,7 +456,9 @@ function main(argc, argv)
HYPRE_BoomerAMGDestroy(precond)
else
if myid == 0; println("Invalid solver id specified."); end
if myid == 0
println("Invalid solver id specified.")
end
end
# Clean up

10
ext/HYPREPartitionedArrays.jl

@ -66,7 +66,7 @@ function Internals.to_hypre_data( @@ -66,7 +66,7 @@ function Internals.to_hypre_data(
# Keep track of the last index used for every row
lastinds = zeros(Int, nrows)
cumsum!((@view lastinds[2:end]), (@view ncols[1:end-1]))
cumsum!((@view lastinds[2:end]), (@view ncols[1:(end - 1)]))
# Second pass to populate the output. Here we need to map column
# indices from own/ghost to global
@ -149,7 +149,7 @@ function Internals.to_hypre_data( @@ -149,7 +149,7 @@ function Internals.to_hypre_data(
return nrows, ncols, rows, cols, values
end
function Internals.get_comm(A::Union{PSparseMatrix{<:Any,<:M}, PVector{<:Any,<:M}}) where M <: MPIArray
function Internals.get_comm(A::Union{PSparseMatrix{<:Any, <:M}, PVector{<:Any, <:M}}) where {M <: MPIArray}
return partition(A).comm
end
@ -238,10 +238,10 @@ function copy_check(dst::HYPREVector, src::PVector) @@ -238,10 +238,10 @@ function copy_check(dst::HYPREVector, src::PVector)
il_src, iu_src = Internals.get_proc_rows(src)
if il_dst != il_src && iu_dst != iu_src
# TODO: Why require this?
throw(ArgumentError(
"row owner mismatch between dst ($(il_dst:iu_dst)) and src ($(il_src:iu_src))"
))
msg = "row owner mismatch between dst ($(il_dst:iu_dst)) and src ($(il_src:iu_src))"
throw(ArgumentError(msg))
end
return
end
# TODO: Other eltypes could be support by using a intermediate buffer

2
ext/HYPRESparseArrays.jl

@ -33,7 +33,7 @@ function Internals.to_hypre_data(A::SparseMatrixCSC, ilower, iupper) @@ -33,7 +33,7 @@ function Internals.to_hypre_data(A::SparseMatrixCSC, ilower, iupper)
# Keep track of the last index used for every row
lastinds = zeros(Int, nrows)
cumsum!((@view lastinds[2:end]), (@view ncols[1:end-1]))
cumsum!((@view lastinds[2:end]), (@view ncols[1:(end - 1)]))
# Second pass to populate the output
@inbounds for j in 1:size(A, 2)

7
gen/generator.jl

@ -21,12 +21,15 @@ push!(args, "-DHYPRE_ENABLE_CUDA_STREAMS=OFF") @@ -21,12 +21,15 @@ push!(args, "-DHYPRE_ENABLE_CUDA_STREAMS=OFF")
push!(args, "-DHYPRE_ENABLE_CUSPARSE=OFF")
push!(args, "-DHYPRE_ENABLE_CURAND=OFF")
headers = joinpath.(hypre_include_dir, [
headers = joinpath.(
hypre_include_dir,
[
"HYPRE.h",
"HYPRE_IJ_mv.h",
"HYPRE_parcsr_mv.h",
"HYPRE_parcsr_ls.h",
])
]
)
ctx = create_context(headers, args, options)

6
gen/prologue.jl

@ -1,6 +1,8 @@ @@ -1,6 +1,8 @@
using MPI: MPI, MPI_Comm
if isdefined(MPI, :API) # MPI >= 0.20.0
if isdefined(MPI, :API)
# MPI >= 0.20.0
using MPI.API: MPI_INT, MPI_DOUBLE
else # MPI < 0.20.0
else
# MPI < 0.20.0
using MPI: MPI_INT, MPI_DOUBLE
end

1
gen/solver_options.jl

@ -43,6 +43,7 @@ function generate_options(io, structname, prefixes...) @@ -43,6 +43,7 @@ function generate_options(io, structname, prefixes...)
println(io, " end")
println(io, " end")
println(io, "end")
return
end
open(joinpath(@__DIR__, "..", "src", "solver_options.jl"), "w") do io

1752
lib/LibHYPRE.jl

File diff suppressed because it is too large Load Diff

13
src/HYPRE.jl

@ -65,8 +65,11 @@ end @@ -65,8 +65,11 @@ end
Base.unsafe_convert(::Type{HYPRE_IJMatrix}, A::HYPREMatrix) = A.ijmatrix
Base.unsafe_convert(::Type{HYPRE_ParCSRMatrix}, A::HYPREMatrix) = A.parmatrix
function HYPREMatrix(comm::MPI.Comm, ilower::Integer, iupper::Integer,
jlower::Integer=ilower, jupper::Integer=iupper)
function HYPREMatrix(
comm::MPI.Comm,
ilower::Integer, iupper::Integer,
jlower::Integer = ilower, jupper::Integer = iupper
)
# Create the IJ matrix
A = HYPREMatrix(comm, ilower, iupper, jlower, jupper, C_NULL, C_NULL)
ijmatrix_ref = Ref{HYPRE_IJMatrix}(C_NULL)
@ -191,6 +194,7 @@ function Internals.check_n_rows(A, ilower, iupper) @@ -191,6 +194,7 @@ function Internals.check_n_rows(A, ilower, iupper)
if size(A, 1) != (iupper - ilower + 1)
throw(ArgumentError("number of rows in matrix does not match global start/end rows ilower and iupper"))
end
return
end
function Internals.to_hypre_data(x::Vector, ilower, iupper)
@ -209,8 +213,9 @@ function HYPREVector(comm::MPI.Comm, x::Vector, ilower, iupper) @@ -209,8 +213,9 @@ function HYPREVector(comm::MPI.Comm, x::Vector, ilower, iupper)
return b
end
HYPREVector(x::Vector, ilower=1, iupper=length(x)) =
HYPREVector(MPI.COMM_SELF, x, ilower, iupper)
function HYPREVector(x::Vector, ilower = 1, iupper = length(x))
return HYPREVector(MPI.COMM_SELF, x, ilower, iupper)
end
# TODO: Other eltypes could be support by using a intermediate buffer
function Base.copy!(dst::Vector{HYPRE_Complex}, src::HYPREVector)

1
src/LibHYPRE.jl

@ -92,6 +92,7 @@ function __init__() @@ -92,6 +92,7 @@ function __init__()
patch_ref = Ref{HYPRE_Int}(-1)
@check HYPRE_VersionNumber(major_ref, minor_ref, patch_ref, C_NULL)
global VERSION = VersionNumber(major_ref[], minor_ref[], patch_ref[])
return
end
end

8
src/solver_options.jl

@ -29,6 +29,7 @@ function Internals.set_options(solver::BiCGSTAB, kwargs) @@ -29,6 +29,7 @@ function Internals.set_options(solver::BiCGSTAB, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.BiCGSTAB"))
end
end
return
end
function Internals.set_options(solver::BoomerAMG, kwargs)
@ -285,6 +286,7 @@ function Internals.set_options(solver::BoomerAMG, kwargs) @@ -285,6 +286,7 @@ function Internals.set_options(solver::BoomerAMG, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.BoomerAMG"))
end
end
return
end
function Internals.set_options(solver::FlexGMRES, kwargs)
@ -314,6 +316,7 @@ function Internals.set_options(solver::FlexGMRES, kwargs) @@ -314,6 +316,7 @@ function Internals.set_options(solver::FlexGMRES, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.FlexGMRES"))
end
end
return
end
function Internals.set_options(solver::GMRES, kwargs)
@ -347,6 +350,7 @@ function Internals.set_options(solver::GMRES, kwargs) @@ -347,6 +350,7 @@ function Internals.set_options(solver::GMRES, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.GMRES"))
end
end
return
end
function Internals.set_options(solver::Hybrid, kwargs)
@ -456,6 +460,7 @@ function Internals.set_options(solver::Hybrid, kwargs) @@ -456,6 +460,7 @@ function Internals.set_options(solver::Hybrid, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.Hybrid"))
end
end
return
end
function Internals.set_options(solver::ILU, kwargs)
@ -490,6 +495,7 @@ function Internals.set_options(solver::ILU, kwargs) @@ -490,6 +495,7 @@ function Internals.set_options(solver::ILU, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.ILU"))
end
end
return
end
function Internals.set_options(solver::ParaSails, kwargs)
@ -510,6 +516,7 @@ function Internals.set_options(solver::ParaSails, kwargs) @@ -510,6 +516,7 @@ function Internals.set_options(solver::ParaSails, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.ParaSails"))
end
end
return
end
function Internals.set_options(solver::PCG, kwargs)
@ -547,4 +554,5 @@ function Internals.set_options(solver::PCG, kwargs) @@ -547,4 +554,5 @@ function Internals.set_options(solver::PCG, kwargs)
throw(ArgumentError("unknown option $k for HYPRE.PCG"))
end
end
return
end

1
src/solvers.jl

@ -17,6 +17,7 @@ function Internals.safe_finalizer(Destroy, solver) @@ -17,6 +17,7 @@ function Internals.safe_finalizer(Destroy, solver)
s.solver = C_NULL
end
end
return
end
# Defining unsafe_convert enables ccall to automatically convert solver::HYPRESolver to

39
test/runtests.jl

@ -31,11 +31,10 @@ end @@ -31,11 +31,10 @@ end
@testset "HYPREMatrix(::SparseMatrixCS(C|R))" begin
ilower, iupper = 4, 6
CSC = convert(SparseMatrixCSC{HYPRE_Complex, HYPRE_Int}, sparse([
1 2 0 0 3
0 4 0 5 0
0 6 7 0 8
]))
CSC = convert(
SparseMatrixCSC{HYPRE_Complex, HYPRE_Int},
sparse([1 2 0 0 3; 0 4 0 5 0; 0 6 7 0 8])
)
CSR = sparsecsr(findnz(CSC)..., size(CSC)...)
@test CSC == CSR
csc = Internals.to_hypre_data(CSC, ilower, iupper)
@ -183,7 +182,6 @@ end @@ -183,7 +182,6 @@ end
end
@testset "HYPREVector" begin
h = HYPREVector(MPI.COMM_WORLD, 1, 5)
@test h.ijvector != HYPRE_IJVector(C_NULL)
@ -360,7 +358,7 @@ end @@ -360,7 +358,7 @@ end
b_h = HYPREVector(b)
x_h = HYPREVector(x)
# Solve
tol = 1e-9
tol = 1.0e-9
bicg = HYPRE.BiCGSTAB(; Tol = tol)
HYPRE.solve!(bicg, x_h, A_h, b_h)
copy!(x, x_h)
@ -411,7 +409,7 @@ end @@ -411,7 +409,7 @@ end
append!(J, [i, i, i + 1, i + 1]) # cols
end
A = sparse(I, J, V)
A[:, 1] .= 0; A[1, :] .= 0; A[:, end] .= 0; A[end, :] .= 0;
A[:, 1] .= 0; A[1, :] .= 0; A[:, end] .= 0; A[end, :] .= 0
A[1, 1] = 2; A[end, end] = 2
@test isposdef(A)
b = rand(100)
@ -421,7 +419,7 @@ end @@ -421,7 +419,7 @@ end
b_h = HYPREVector(b, ilower, iupper)
x_h = HYPREVector(b, ilower, iupper)
# Solve
tol = 1e-9
tol = 1.0e-9
amg = HYPRE.BoomerAMG(; Tol = tol)
HYPRE.solve!(amg, x_h, A_h, b_h)
copy!(x, x_h)
@ -451,7 +449,7 @@ end @@ -451,7 +449,7 @@ end
b_h = HYPREVector(b)
x_h = HYPREVector(x)
# Solve
tol = 1e-9
tol = 1.0e-9
gmres = HYPRE.FlexGMRES(; Tol = tol)
HYPRE.solve!(gmres, x_h, A_h, b_h)
copy!(x, x_h)
@ -494,7 +492,7 @@ end @@ -494,7 +492,7 @@ end
b_h = HYPREVector(b)
x_h = HYPREVector(x)
# Solve
tol = 1e-9
tol = 1.0e-9
gmres = HYPRE.GMRES(; Tol = tol)
HYPRE.solve!(gmres, x_h, A_h, b_h)
copy!(x, x_h)
@ -536,7 +534,7 @@ end @@ -536,7 +534,7 @@ end
b_h = HYPREVector(b)
x_h = HYPREVector(x)
# Solve
tol = 1e-9
tol = 1.0e-9
hybrid = HYPRE.Hybrid(; Tol = tol)
HYPRE.solve!(hybrid, x_h, A_h, b_h)
copy!(x, x_h)
@ -579,7 +577,7 @@ end @@ -579,7 +577,7 @@ end
b_h = HYPREVector(b)
x_h = HYPREVector(x)
# Solve
tol = 1e-9
tol = 1.0e-9
ilu = HYPRE.ILU(; Tol = tol)
HYPRE.solve!(ilu, x_h, A_h, b_h)
copy!(x, x_h)
@ -623,7 +621,7 @@ end @@ -623,7 +621,7 @@ end
b_h = HYPREVector(b, ilower, iupper)
x_h = HYPREVector(b, ilower, iupper)
# Solve with ParaSails as preconditioner
tol = 1e-9
tol = 1.0e-9
parasails = HYPRE.ParaSails()
pcg = HYPRE.PCG(; Tol = tol, Precond = parasails)
HYPRE.solve!(pcg, x_h, A_h, b_h)
@ -650,7 +648,7 @@ end @@ -650,7 +648,7 @@ end
b_h = HYPREVector(b, ilower, iupper)
x_h = HYPREVector(b, ilower, iupper)
# Solve
tol = 1e-9
tol = 1.0e-9
pcg = HYPRE.PCG(; Tol = tol)
HYPRE.solve!(pcg, x_h, A_h, b_h)
copy!(x, x_h)
@ -713,7 +711,7 @@ end @@ -713,7 +711,7 @@ end
end
# Solve
tol = 1e-9
tol = 1.0e-9
pcg = HYPRE.PCG(; Tol = tol)
## solve!
HYPRE.solve!(pcg, x_p, A_p, b_p)
@ -737,7 +735,7 @@ end @@ -737,7 +735,7 @@ end
xcsc = zeros(100)
xcsr = zeros(100)
# Solve
tol = 1e-9
tol = 1.0e-9
pcg = HYPRE.PCG(; Tol = tol)
## solve!
HYPRE.solve!(pcg, xcsc, CSC, b)
@ -752,9 +750,12 @@ end @@ -752,9 +750,12 @@ end
end
@testset "MPI execution" begin
testfiles = joinpath.(@__DIR__, [
testfiles = joinpath.(
@__DIR__,
[
"test_assembler.jl",
])
]
)
for file in testfiles
r = run(ignorestatus(`$(mpiexec()) -n 2 $(Base.julia_cmd()) $(file)`))
@test r.exitcode == 0

2
test/test_assembler.jl

@ -30,9 +30,11 @@ end @@ -30,9 +30,11 @@ end
function values_and_indices(n)
idx = [n - 1, n, n + 1]
a = Float64[
# runic: off
n -2n -n
-2n n -2n
-n -2n n
# runic: on
]
b = Float64[n, n / 2, n / 3]
return idx, a, b

Loading…
Cancel
Save