Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Conform Nemo to new FLINT random struct #1750

Merged
merged 1 commit into from
May 14, 2024
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
35 changes: 28 additions & 7 deletions src/Nemo.jl
Original file line number Diff line number Diff line change
Expand Up @@ -214,6 +214,14 @@
error("Problem in the Flint-Subsystem")
end

_ptr = Libdl.dlopen(libflint)
if Libdl.dlsym(_ptr, :flint_rand_init; throw_error = false) !== nothing
const NEW_FLINT = true
else
const NEW_FLINT = false
end
Libdl.dlclose(_ptr)

################################################################################
#
# Debugging tools for allocation tracking
Expand Down Expand Up @@ -525,14 +533,27 @@

Random.seed!(a::rand_ctx, s::Nothing=nothing) = Random.seed!(a, rand(UInt128))

flint_randseed!(a::rand_ctx, seed1::UInt, seed2::UInt) =
ccall((:flint_randseed, libflint), Cvoid, (Ptr{Cvoid}, UInt, UInt), a.ptr, seed1, seed2)
if NEW_FLINT
flint_randseed!(a::rand_ctx, seed1::UInt, seed2::UInt) =

Check warning on line 537 in src/Nemo.jl

View check run for this annotation

Codecov / codecov/patch

src/Nemo.jl#L537

Added line #L537 was not covered by tests
ccall((:flint_rand_set_seed, libflint), Cvoid, (Ref{rand_ctx}, UInt, UInt), a, seed1, seed2)

function flint_gmp_randseed!(a::rand_ctx, seed::BigInt)
ccall((:_flint_rand_init_gmp, libflint), Cvoid, (Ptr{Cvoid},), a.ptr)
ccall((:__gmp_randseed, :libgmp), Cvoid, (Ptr{Cvoid}, Ref{BigInt}),
a.ptr, # gmp_state is the first field of a.ptr (cf. flint.h)
seed)
function flint_gmp_randseed!(a::rand_ctx, seed::BigInt)
if a.gmp_state == C_NULL

Check warning on line 541 in src/Nemo.jl

View check run for this annotation

Codecov / codecov/patch

src/Nemo.jl#L540-L541

Added lines #L540 - L541 were not covered by tests
# gmp_state needs to be initialised
ccall((:_flint_rand_init_gmp_state, libflint), Cvoid, (Ref{rand_ctx},), a)

Check warning on line 543 in src/Nemo.jl

View check run for this annotation

Codecov / codecov/patch

src/Nemo.jl#L543

Added line #L543 was not covered by tests
end
ccall((:__gmp_randseed, :libgmp), Cvoid, (Ptr{Cvoid}, Ref{BigInt}), a.gmp_state, seed)

Check warning on line 545 in src/Nemo.jl

View check run for this annotation

Codecov / codecov/patch

src/Nemo.jl#L545

Added line #L545 was not covered by tests
end
else
flint_randseed!(a::rand_ctx, seed1::UInt, seed2::UInt) =
ccall((:flint_randseed, libflint), Cvoid, (Ref{rand_ctx}, UInt, UInt), a, seed1, seed2)

function flint_gmp_randseed!(a::rand_ctx, seed::BigInt)
ccall((:_flint_rand_init_gmp, libflint), Cvoid, (Ref{rand_ctx},), a)
ccall((:__gmp_randseed, :libgmp), Cvoid, (Ref{rand_ctx}, Ref{BigInt}),
a, # gmp_state is the first field of flint_rand_s
seed)
end
end

################################################################################
Expand Down
12 changes: 6 additions & 6 deletions src/arb/Real.jl
Original file line number Diff line number Diff line change
Expand Up @@ -2108,22 +2108,22 @@ function rand(r::RealField, prec::Int = precision(Balls); randtype::Symbol=:uran

if randtype == :urandom
ccall((:arb_urandom, libflint), Nothing,
(Ref{RealFieldElem}, Ptr{Cvoid}, Int), x, state.ptr, prec)
(Ref{RealFieldElem}, Ref{rand_ctx}, Int), x, state, prec)
elseif randtype == :randtest
ccall((:arb_randtest, libflint), Nothing,
(Ref{RealFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, prec, 30)
(Ref{RealFieldElem}, Ref{rand_ctx}, Int, Int), x, state, prec, 30)
elseif randtype == :randtest_exact
ccall((:arb_randtest_exact, libflint), Nothing,
(Ref{RealFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, prec, 30)
(Ref{RealFieldElem}, Ref{rand_ctx}, Int, Int), x, state, prec, 30)
elseif randtype == :randtest_precise
ccall((:arb_randtest_precise, libflint), Nothing,
(Ref{RealFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, prec, 30)
(Ref{RealFieldElem}, Ref{rand_ctx}, Int, Int), x, state, prec, 30)
elseif randtype == :randtest_wide
ccall((:arb_randtest_wide, libflint), Nothing,
(Ref{RealFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, prec, 30)
(Ref{RealFieldElem}, Ref{rand_ctx}, Int, Int), x, state, prec, 30)
elseif randtype == :randtest_special
ccall((:arb_randtest_special, libflint), Nothing,
(Ref{RealFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, prec, 30)
(Ref{RealFieldElem}, Ref{rand_ctx}, Int, Int), x, state, prec, 30)
else
error("Arb random generation `" * String(randtype) * "` is not defined")
end
Expand Down
12 changes: 6 additions & 6 deletions src/arb/arb.jl
Original file line number Diff line number Diff line change
Expand Up @@ -2123,22 +2123,22 @@ function rand(r::ArbField; randtype::Symbol=:urandom)

if randtype == :urandom
ccall((:arb_urandom, libflint), Nothing,
(Ref{ArbFieldElem}, Ptr{Cvoid}, Int), x, state.ptr, r.prec)
(Ref{ArbFieldElem}, Ref{rand_ctx}, Int), x, state, r.prec)
elseif randtype == :randtest
ccall((:arb_randtest, libflint), Nothing,
(Ref{ArbFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, r.prec, 30)
(Ref{ArbFieldElem}, Ref{rand_ctx}, Int, Int), x, state, r.prec, 30)
elseif randtype == :randtest_exact
ccall((:arb_randtest_exact, libflint), Nothing,
(Ref{ArbFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, r.prec, 30)
(Ref{ArbFieldElem}, Ref{rand_ctx}, Int, Int), x, state, r.prec, 30)
elseif randtype == :randtest_precise
ccall((:arb_randtest_precise, libflint), Nothing,
(Ref{ArbFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, r.prec, 30)
(Ref{ArbFieldElem}, Ref{rand_ctx}, Int, Int), x, state, r.prec, 30)
elseif randtype == :randtest_wide
ccall((:arb_randtest_wide, libflint), Nothing,
(Ref{ArbFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, r.prec, 30)
(Ref{ArbFieldElem}, Ref{rand_ctx}, Int, Int), x, state, r.prec, 30)
elseif randtype == :randtest_special
ccall((:arb_randtest_special, libflint), Nothing,
(Ref{ArbFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, r.prec, 30)
(Ref{ArbFieldElem}, Ref{rand_ctx}, Int, Int), x, state, r.prec, 30)
else
error("Arb random generation `" * String(randtype) * "` is not defined")
end
Expand Down
12 changes: 6 additions & 6 deletions src/calcium/ca.jl
Original file line number Diff line number Diff line change
Expand Up @@ -139,16 +139,16 @@ function rand(C::CalciumField; depth::Int, bits::Int,

if randtype == :null
ccall((:ca_randtest, libflint), Nothing,
(Ref{CalciumFieldElem}, Ptr{Cvoid}, Int, Int, Ref{CalciumField}),
x, state.ptr, depth, bits, C)
(Ref{CalciumFieldElem}, Ref{rand_ctx}, Int, Int, Ref{CalciumField}),
x, state, depth, bits, C)
elseif randtype == :rational
ccall((:ca_randtest_rational, libflint), Nothing,
(Ref{CalciumFieldElem}, Ptr{Cvoid}, Int, Ref{CalciumField}),
x, state.ptr, bits, C)
(Ref{CalciumFieldElem}, Ref{rand_ctx}, Int, Ref{CalciumField}),
x, state, bits, C)
elseif randtype == :special
ccall((:ca_randtest_special, libflint), Nothing,
(Ref{CalciumFieldElem}, Ptr{Cvoid}, Int, Int, Ref{CalciumField}),
x, state.ptr, depth, bits, C)
(Ref{CalciumFieldElem}, Ref{rand_ctx}, Int, Int, Ref{CalciumField}),
x, state, depth, bits, C)
else
error("randtype not defined")
end
Expand Down
6 changes: 3 additions & 3 deletions src/calcium/qqbar.jl
Original file line number Diff line number Diff line change
Expand Up @@ -341,14 +341,14 @@ function rand(R::QQBarField; degree::Int, bits::Int,

if randtype == :null
ccall((:qqbar_randtest, libflint), Nothing,
(Ref{QQBarFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, degree, bits)
(Ref{QQBarFieldElem}, Ref{rand_ctx}, Int, Int), x, state, degree, bits)
elseif randtype == :real
ccall((:qqbar_randtest_real, libflint), Nothing,
(Ref{QQBarFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, degree, bits)
(Ref{QQBarFieldElem}, Ref{rand_ctx}, Int, Int), x, state, degree, bits)
elseif randtype == :nonreal
degree < 2 && error("nonreal requires degree >= 2")
ccall((:qqbar_randtest_nonreal, libflint), Nothing,
(Ref{QQBarFieldElem}, Ptr{Cvoid}, Int, Int), x, state.ptr, degree, bits)
(Ref{QQBarFieldElem}, Ref{rand_ctx}, Int, Int), x, state, degree, bits)
else
error("randtype not defined")
end
Expand Down
46 changes: 32 additions & 14 deletions src/flint/FlintTypes.jl
Original file line number Diff line number Diff line change
Expand Up @@ -6657,22 +6657,40 @@
#
################################################################################

mutable struct rand_ctx
ptr::Ptr{Cvoid}
if NEW_FLINT
mutable struct rand_ctx
gmp_state::Ptr{Cvoid}
randval::UInt
randval2::UInt

function rand_ctx()
a = new()
ccall((:flint_rand_init, libflint), Cvoid, (Ref{rand_ctx},), a)
finalizer(_rand_ctx_clear_fn, a)
return a

Check warning on line 6670 in src/flint/FlintTypes.jl

View check run for this annotation

Codecov / codecov/patch

src/flint/FlintTypes.jl#L6666-L6670

Added lines #L6666 - L6670 were not covered by tests
end
end

function rand_ctx()
z = new()
z.ptr = ccall((:flint_rand_alloc, libflint), Ptr{Cvoid}, ( ))
ccall((:flint_randinit, libflint), Cvoid, (Ptr{Cvoid}, ), z.ptr)
finalizer(_rand_ctx_clear_fn, z)
return z
end
end
function _rand_ctx_clear_fn(a::rand_ctx)
ccall((:flint_rand_clear, libflint), Cvoid, (Ref{rand_ctx},), a)
nothing

Check warning on line 6676 in src/flint/FlintTypes.jl

View check run for this annotation

Codecov / codecov/patch

src/flint/FlintTypes.jl#L6674-L6676

Added lines #L6674 - L6676 were not covered by tests
end
else
mutable struct rand_ctx
data::NTuple{56, Int8}

function rand_ctx()
a = new()
ccall((:flint_randinit, libflint), Cvoid, (Ref{rand_ctx},), a)
finalizer(_rand_ctx_clear_fn, a)
return a
end
end

function _rand_ctx_clear_fn(a::rand_ctx)
ccall((:flint_randclear, libflint), Cvoid, (Ptr{Cvoid}, ), a.ptr)
ccall((:flint_rand_free, libflint), Cvoid, (Ptr{Cvoid}, ), a.ptr)
nothing
function _rand_ctx_clear_fn(a::rand_ctx)
ccall((:flint_randclear, libflint), Cvoid, (Ref{rand_ctx},), a)
nothing

Check warning on line 6692 in src/flint/FlintTypes.jl

View check run for this annotation

Codecov / codecov/patch

src/flint/FlintTypes.jl#L6690-L6692

Added lines #L6690 - L6692 were not covered by tests
end
end

################################################################################
Expand Down
4 changes: 2 additions & 2 deletions src/flint/fmpq.jl
Original file line number Diff line number Diff line change
Expand Up @@ -1155,8 +1155,8 @@ denominator can be smaller than $b$ bits.
function rand_bits(::QQField, b::Int)
b > 0 || throw(DomainError(b, "Bit count must be positive"))
z = QQFieldElem()
ccall((:fmpq_randbits, libflint), Nothing, (Ref{QQFieldElem}, Ptr{Cvoid}, Int),
z, _flint_rand_states[Threads.threadid()].ptr, b)
ccall((:fmpq_randbits, libflint), Nothing, (Ref{QQFieldElem}, Ref{rand_ctx}, Int),
z, _flint_rand_states[Threads.threadid()], b)
return z
end

Expand Down
12 changes: 6 additions & 6 deletions src/flint/fmpz.jl
Original file line number Diff line number Diff line change
Expand Up @@ -1499,8 +1499,8 @@ function _ecm(a::ZZRingElem, B1::UInt, B2::UInt, ncrv::UInt,
rnd = _flint_rand_states[Threads.threadid()])
f = ZZRingElem()
r = ccall((:fmpz_factor_ecm, libflint), Int32,
(Ref{ZZRingElem}, UInt, UInt, UInt, Ptr{Cvoid}, Ref{ZZRingElem}),
f, ncrv, B1, B2, rnd.ptr, a)
(Ref{ZZRingElem}, UInt, UInt, UInt, Ref{rand_ctx}, Ref{ZZRingElem}),
f, ncrv, B1, B2, rnd, a)
return r, f
end

Expand Down Expand Up @@ -2741,8 +2741,8 @@ Return a random signed integer whose absolute value has $b$ bits.
function rand_bits(::ZZRing, b::Int)
b >= 0 || throw(DomainError(b, "Bit count must be non-negative"))
z = ZZRingElem()
ccall((:fmpz_randbits, libflint), Nothing,(Ref{ZZRingElem}, Ptr{Cvoid}, Int),
z, _flint_rand_states[Threads.threadid()].ptr, b)
ccall((:fmpz_randbits, libflint), Nothing,(Ref{ZZRingElem}, Ref{rand_ctx}, Int),
z, _flint_rand_states[Threads.threadid()], b)
return z
end

Expand All @@ -2756,8 +2756,8 @@ function rand_bits_prime(::ZZRing, n::Int, proved::Bool = true)
n < 2 && throw(DomainError(n, "No primes with that many bits"))
z = ZZRingElem()
ccall((:fmpz_randprime, libflint), Nothing,
(Ref{ZZRingElem}, Ptr{Cvoid}, Int, Cint),
z, _flint_rand_states[Threads.threadid()].ptr, n, Cint(proved))
(Ref{ZZRingElem}, Ref{rand_ctx}, Int, Cint),
z, _flint_rand_states[Threads.threadid()], n, Cint(proved))
return z
end

Expand Down
Loading