MathgeomGLS
1143 строки · 45.9 Кб
1{**********************************************************************}
2{ }
3{ "The contents of this file are subject to the Mozilla Public }
4{ License Version 1.1 (the "License"); you may not use this }
5{ file except in compliance with the License. You may obtain }
6{ a copy of the License at http://www.mozilla.org/MPL/ }
7{ }
8{ Software distributed under the License is distributed on an }
9{ "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, either express }
10{ or implied. See the License for the specific language }
11{ governing rights and limitations under the License. }
12{ }
13{ Copyright Creative IT. }
14{ Current maintainer: Eric Grange }
15{ }
16{**********************************************************************}
17{
18This unit exposes MPIR dll (http://www.mpir.org)
19
20Targets MPIR 2.7.2 or above.
21
22Based on gmp_lib by wqyfavor
23}
24unit dwsMPIR;
25
26{$WARN SYMBOL_PLATFORM OFF}
27
28interface
29
30uses Winapi.Windows, System.SysUtils, dwsXPlatform;
31
32const
33MaxVarSize = MaxInt div 4;
34
35type
36mp_limb_t = Cardinal;
37mp_limb_signed_t = Integer;
38mp_bitcnt_t = Cardinal;
39
40mp_ptr = ^mp_limb_t;
41
42mp_size_t_p = ^mp_size_t;
43mp_size_t = Integer;
44mp_exp_t = Integer;
45
46// Prototype of arbitrary precision integer number
47pmpz_t = ^mpz_t;
48mpz_t = record
49mp_alloc: Integer;
50mp_size: Integer;
51mp_d: mp_ptr;
52end;
53
54mpz_array_ptr = ^mpz_array;
55mpz_array = array[0..MaxVarSize div SizeOf(mpz_t) - 1] of mpz_t;
56
57// Prototype of arbitrary precision rational number
58pmpq_t = ^mpq_t;
59mpq_t = record
60mp_num: mpz_t;
61mp_den: mpz_t;
62end;
63
64// Prototype of arbitrary precision float number
65pmpf_t = ^mpf_t;
66mpf_t = record
67mp_prec: Integer;
68mp_size: Integer;
69mp_exp: mp_exp_t;
70mp_d: mp_ptr;
71end;
72
73// Available random number generation algorithms.
74gmp_randalg_t = (GMPRandAlgLC {Linear congruential}, GMPRandAlgMT{Mersenne Twister});
75
76// Linear congruential data struct.
77gmp_randata_lc = record
78a: mpz_t; { Multiplier. }
79c: Cardinal; { Adder. }
80m: mpz_t; { Modulus (valid only if M2Exp = 0). }
81M2Exp: Cardinal; { If <> 0, modulus is 2 ^ M2Exp. }
82end;
83
84gmp_randstate_t = record
85Seed: mpz_t; { Current seed. }
86Alg: gmp_randalg_t; { Algorithm used. }
87AlgData: record { Algorithm specific data. }
88case gmp_randalg_t of
89GMPRandAlgLC: (lc: ^gmp_randata_lc) { Linear congruential. }
90end
91end;
92
93var
94{ Integer (i.e. Z) routines }
95mpz_init : procedure (var dest: mpz_t); cdecl;
96mpz_inits : procedure (p: pmpz_t {; ...}); cdecl varargs;
97mpz_init2 : procedure (var dest: mpz_t; N: mp_bitcnt_t); cdecl varargs;
98mpz_clear : procedure (var dest: mpz_t); cdecl;
99mpz_clears : procedure (p: pmpz_t {; ...}); cdecl varargs;
100mpz_realloc : function (var dest: mpz_t; Limbs: mp_size_t): Pointer; cdecl;
101mpz_realloc2 : procedure (var dest: mpz_t; Bits: mp_size_t); cdecl;
102mpz_array_init : procedure (dest: mpz_array_ptr; ArraySize, FixedNumBits: mp_size_t); cdecl;
103
104mpz_swap : procedure (var v1, v2: mpz_t); cdecl;
105mpz_set : procedure (var dest: mpz_t; const src: mpz_t); cdecl;
106mpz_set_ui : procedure (var dest: mpz_t; src: Cardinal); cdecl;
107mpz_set_si : procedure (var dest: mpz_t; src: Integer); cdecl;
108mpz_set_d : procedure (var dest: mpz_t; src: Double); cdecl;
109mpz_set_q : procedure (var dest: mpz_t; src: mpq_t); cdecl;
110mpz_set_f : procedure (var dest: mpz_t; src: mpf_t); cdecl;
111mpz_set_str : function (var dest: mpz_t; src: PAnsiChar; Base: Integer): Integer; cdecl;
112
113mpz_init_set : procedure (var dest: mpz_t; const src: mpz_t); cdecl;
114mpz_init_set_ui : procedure (var dest: mpz_t; src: Cardinal); cdecl;
115mpz_init_set_si : procedure (var dest: mpz_t; src: Integer); cdecl;
116mpz_init_set_d : procedure (var dest: mpz_t; src: Double); cdecl;
117mpz_init_set_str : function (var dest: mpz_t; src: PAnsiChar; Base: Integer): Integer; cdecl;
118
119mpz_import : procedure (var dest: mpz_t; Count: mp_size_t; Order: Integer; Size: mp_size_t; Endian: Integer; Nails: mp_size_t; op: Pointer); cdecl;
120mpz_export : function (Rop: Pointer; PCount: mp_size_t_p; Order: Integer; Size: mp_size_t; Endian: Integer; Nails: mp_size_t; const src: mpz_t): Pointer; cdecl;
121
122mpz_getlimbn : function (const src: mpz_t; n: mp_size_t): mp_limb_t; cdecl;
123mpz_size : function (const src: mpz_t): mp_size_t; cdecl;
124
125mpz_get_ui : function (const src: mpz_t): Cardinal; cdecl;
126mpz_get_si : function (const src: mpz_t): Integer; cdecl;
127mpz_get_d : function (const src: mpz_t): Double; cdecl;
128mpz_get_d_2exp : function (var Exp: Integer; src: mpz_t): Double; cdecl;
129mpz_fits_sint_p : function (const src: mpz_t): Integer; cdecl;
130mpz_fits_slong_p : function (const src: mpz_t): Integer; cdecl;
131mpz_fits_sshort_p : function (const src: mpz_t): Integer; cdecl;
132mpz_fits_uint_p : function (const src: mpz_t): Integer; cdecl;
133mpz_fits_ulong_p : function (const src: mpz_t): Integer; cdecl;
134mpz_fits_ushort_p : function (const src: mpz_t): Integer; cdecl;
135{ Pass nil for dest to let the function allocate memory for it }
136mpz_get_str : function (dest: PAnsiChar; Base: Integer; const src: mpz_t): PAnsiChar; cdecl;
137
138mpz_add : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
139mpz_add_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
140mpz_sub : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
141mpz_sub_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
142mpz_ui_sub : procedure (var dest: mpz_t; src1: Cardinal; const src2: mpz_t); cdecl;
143mpz_mul : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
144mpz_mul_si : procedure (var dest: mpz_t; const src1: mpz_t; src2: Integer); cdecl;
145mpz_mul_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
146mpz_mul_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
147mpz_addmul : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
148mpz_addmul_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
149mpz_submul : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
150mpz_submul_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
151mpz_neg : procedure (var dest: mpz_t; const src: mpz_t); cdecl;
152mpz_abs : procedure (var dest: mpz_t; const src: mpz_t); cdecl;
153
154mpz_cdiv_q : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
155mpz_cdiv_r : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
156mpz_cdiv_qr : procedure (var destQ, destR: mpz_t; const src1, src2: mpz_t); cdecl;
157mpz_cdiv_q_ui : function (var dest: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
158mpz_cdiv_r_ui : function (var dest: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
159mpz_cdiv_qr_ui : function (var destQ, destR: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
160mpz_cdiv_ui : function (const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
161mpz_cdiv_q_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
162mpz_cdiv_r_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
163
164mpz_fdiv_q : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
165mpz_fdiv_r : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
166mpz_fdiv_qr : procedure (var destQ, destR: mpz_t; const src1, src2: mpz_t); cdecl;
167mpz_fdiv_q_ui : function (var dest: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
168mpz_fdiv_r_ui : function (var dest: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
169mpz_fdiv_qr_ui : function (var destQ, destR: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
170mpz_fdiv_ui : function (const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
171mpz_fdiv_q_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
172mpz_fdiv_r_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
173
174mpz_tdiv_q : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
175mpz_tdiv_r : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
176mpz_tdiv_qr : procedure (var destQ, destR: mpz_t; const src1, src2: mpz_t); cdecl;
177mpz_tdiv_q_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
178mpz_tdiv_r_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
179mpz_tdiv_qr_ui : procedure (var destQ, destR: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
180mpz_tdiv_ui : function (const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
181mpz_tdiv_q_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
182mpz_tdiv_r_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
183
184mpz_mod : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
185mpz_mod_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
186mpz_divexact : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
187mpz_divexact_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
188
189mpz_mod_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
190mpz_div_2exp : procedure (var dest: mpz_t; const src1: mpz_t; src2: mp_bitcnt_t); cdecl;
191
192mpz_divisible_p : function (var n, d: mpz_t): Integer; cdecl;
193mpz_divisible_ui_p : function (var n: mpz_t; d: Cardinal): Integer; cdecl;
194mpz_divisible_2exp_p : function (var n: mpz_t; d: mp_bitcnt_t): Integer; cdecl;
195mpz_congruent_p : function (var n, c, d: mpz_t): Integer; cdecl;
196mpz_congruent_ui_p : function (var n: mpz_t; c, d: Cardinal): Integer; cdecl;
197mpz_congruent_2exp_p : function (var n, c: mpz_t; b: mp_bitcnt_t): Integer; cdecl;
198
199mpz_powm : procedure (var dest: mpz_t; var Base, Exponent, Modulus: mpz_t); cdecl;
200mpz_powm_ui : procedure (var dest: mpz_t; var Base: mpz_t; Exponent: Cardinal; var Modulus: mpz_t); cdecl;
201mpz_pow_ui : procedure (var dest: mpz_t; var Base: mpz_t; Exponent: Cardinal); cdecl;
202mpz_ui_pow_ui : procedure (var dest: mpz_t; Base, Exponent: Cardinal); cdecl;
203
204mpz_root : function (var dest: mpz_t; const src: mpz_t; n: Cardinal): Integer; cdecl;
205mpz_nthroot : procedure (var dest: mpz_t; const src: mpz_t; n: Cardinal); cdecl;
206mpz_rootrem : procedure (var Root: mpz_t; var Rem: mpz_t; const src: mpz_t; n: Cardinal); cdecl;
207mpz_sqrt : procedure (var dest: mpz_t; const src: mpz_t); cdecl;
208mpz_sqrtrem : procedure (var dest, destR: mpz_t; const src: mpz_t); cdecl;
209mpz_perfect_square_p : function (const src: mpz_t): Integer; cdecl;
210mpz_perfect_power_p : function (const src: mpz_t): Integer; cdecl;
211
212mpz_sizeinbase : function (const src: mpz_t; Base: Integer): Integer; cdecl;
213
214mpz_probable_prime_p : function (const src: mpz_t; var state: gmp_randstate_t; Prob: Integer; DivTested: Cardinal): Integer; cdecl;
215mpz_likely_prime_p : function (const src: mpz_t; var state: gmp_randstate_t; DivTested: Cardinal): Integer; cdecl;
216mpz_next_prime_candidate : procedure (var dest: mpz_t; const src: mpz_t; var state: gmp_randstate_t); cdecl;
217
218// Number theoretic functions
219mpz_gcd : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
220mpz_gcd_ui : function (var dest: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
221mpz_gcdext : procedure (var dest, destA, destB: mpz_t; const srcA, srcB: mpz_t); cdecl;
222mpz_lcm : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
223mpz_lcm_ui : function (var dest: mpz_t; const src1: mpz_t; src2: Cardinal): Cardinal; cdecl;
224mpz_invert : function (var dest: mpz_t; const src, Modulus: mpz_t): Integer; cdecl;
225mpz_jacobi : function (const src1, src2: mpz_t): Integer; cdecl;
226mpz_legendre : function (const src1, src2: mpz_t): Integer; cdecl;
227mpz_kronecker : function (const src1, src2: mpz_t): Integer; cdecl;
228mpz_kronecker_si : function (const src1: mpz_t; src2: Integer): Integer; cdecl;
229mpz_kronecker_ui : function (const src1: mpz_t; src2: Cardinal): Integer; cdecl;
230mpz_si_kronecker : function (src1: Integer; const src2: mpz_t): Integer; cdecl;
231mpz_ui_kronecker : function (src1: Cardinal; const src2: mpz_t): Integer; cdecl;
232mpz_remove : function (var dest: mpz_t; const src1, src2: mpz_t): Cardinal; cdecl;
233mpz_fac_ui : procedure (var dest: mpz_t; src: Cardinal); cdecl;
234mpz_primorial_ui : procedure (var dest: mpz_t; n: Cardinal); cdecl;
235mpz_fib_ui : procedure (var dest: mpz_t; src: Cardinal); cdecl;
236mpz_fib2_ui : procedure (var dest: mpz_t; var destSub: mpz_t; src: Cardinal); cdecl;
237mpz_bin_ui : procedure (var dest: mpz_t; const src1: mpz_t; src2: Cardinal); cdecl;
238mpz_bin_uiui : procedure (var dest: mpz_t; src1, src2: Cardinal); cdecl;
239mpz_lucnum_ui : procedure (var dest: mpz_t; src: Cardinal); cdecl;
240mpz_lucnum2_ui : procedure (var dest: mpz_t; var destSub: mpz_t; src: Cardinal); cdecl;
241
242mpz_cmp : function (const src1, src2: mpz_t): Integer; cdecl;
243mpz_cmp_d : function (const src1: mpz_t; src2: Double): Integer; cdecl;
244mpz_cmp_ui : function (const src1: mpz_t; src2: Cardinal): Integer; cdecl;
245mpz_cmp_si : function (const src1: mpz_t; src2: Integer): Integer; cdecl;
246mpz_cmpabs : function (const src1, src2: mpz_t): Integer; cdecl;
247mpz_cmpabs_d : function (const src1: mpz_t; src2: Double): Integer; cdecl;
248mpz_cmpabs_ui : function (const src1: mpz_t; src2: Cardinal): Integer; cdecl;
249
250mpz_and : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
251mpz_ior : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
252mpz_xor : procedure (var dest: mpz_t; const src1, src2: mpz_t); cdecl;
253mpz_com : procedure (var dest: mpz_t; const src: mpz_t); cdecl;
254mpz_popcount : function (const src: mpz_t): mp_bitcnt_t; cdecl;
255mpz_hamdist : function (const src1, src2: mpz_t): mp_bitcnt_t; cdecl;
256mpz_scan0 : function (const src: mpz_t; StartingBit: mp_bitcnt_t): mp_bitcnt_t; cdecl;
257mpz_scan1 : function (const src: mpz_t; StartingBit: mp_bitcnt_t): mp_bitcnt_t; cdecl;
258mpz_setbit : procedure (var dest: mpz_t; BitIndex: mp_bitcnt_t); cdecl;
259mpz_clrbit : procedure (var dest: mpz_t; BitIndex: mp_bitcnt_t); cdecl;
260mpz_combit : procedure (var dest: mpz_t; BitIndex: mp_bitcnt_t); cdecl;
261mpz_tstbit : function (var dest: mpz_t; BitIndex: mp_bitcnt_t): Integer; cdecl;
262
263mpz_urandomb : procedure (var ROP: mpz_t; var state: gmp_randstate_t; n: Cardinal); cdecl;
264mpz_urandomm : procedure (var ROP: mpz_t; var state: gmp_randstate_t; var n: mpz_t); cdecl;
265mpz_rrandomb : procedure (var ROP: mpz_t; var state: gmp_randstate_t; n: Cardinal); cdecl;
266
267procedure mpz_set_uint64(var dest: mpz_t; const src: UInt64);
268procedure mpz_set_int64(var dest: mpz_t; const src: Int64);
269
270function mpz_odd_p(const src: mpz_t): Boolean; inline;
271function mpz_even_p(const src: mpz_t): Boolean; inline;
272function mpz_sgn(const src: mpz_t): Integer;
273
274var
275{ Rational (i.e. Q) routines }
276mpq_canonicalize : procedure (var dest: mpq_t); cdecl;
277
278mpq_init : procedure (var dest: mpq_t); cdecl;
279mpq_inits : procedure (p: pmpq_t {; ...}); cdecl varargs;
280mpq_clear : procedure (var dest: mpq_t); cdecl;
281mpq_clears : procedure (p: pmpq_t {; ...}); cdecl varargs;
282mpq_set : procedure (var dest: mpq_t; const src: mpq_t); cdecl;
283mpq_set_z : procedure (var dest: mpq_t; const src: mpz_t); cdecl;
284mpq_set_ui : procedure (var dest: mpq_t; Nom, Den: Cardinal); cdecl;
285mpq_set_si : procedure (var dest: mpq_t; Nom: Integer; Den: Cardinal); cdecl;
286mpq_set_str : function (var dest: mpq_t; src: PAnsiChar; Base: Integer): Integer; cdecl;
287mpq_set_d : procedure (var dest: mpq_t; src: Double); cdecl;
288mpq_set_f : procedure (var dest: mpq_t; const src: mpf_t); cdecl;
289mpq_swap : procedure (var v1, v2: mpq_t); cdecl;
290
291mpq_add : procedure (var dest: mpq_t; const src1, src2: mpq_t); cdecl;
292mpq_sub : procedure (var dest: mpq_t; const src1, src2: mpq_t); cdecl;
293mpq_mul : procedure (var dest: mpq_t; const src1, src2: mpq_t); cdecl;
294mpq_div : procedure (var dest: mpq_t; const src1, src2: mpq_t); cdecl;
295mpq_neg : procedure (var dest: mpq_t; const src: mpq_t); cdecl;
296mpq_abs : procedure (var dest: mpq_t; const src: mpq_t); cdecl;
297mpq_inv : procedure (var dest: mpq_t; const src: mpq_t); cdecl;
298mpq_mul_2exp : procedure (var dest: mpq_t; const src1: mpq_t; src2: mp_bitcnt_t); cdecl;
299mpq_div_2exp : procedure (var dest: mpq_t; const src1: mpq_t; src2: mp_bitcnt_t); cdecl;
300
301mpq_cmp : function (const src1, src2: mpq_t): Integer; cdecl;
302mpq_cmp_ui : function (const src1: mpq_t; Nom2, Den2: Cardinal): Integer; cdecl;
303mpq_cmp_si : function (const src1: mpq_t; Nom2: Integer; Den2: Cardinal): Integer; cdecl;
304mpq_equal : function (const src1, src2: mpq_t): Integer; cdecl;
305
306mpq_get_d : function (const src: mpq_t): Double; cdecl;
307mpq_set_num : procedure (var dest: mpq_t; const src: mpz_t); cdecl;
308mpq_set_den : procedure (var dest: mpq_t; const src: mpz_t); cdecl;
309mpq_get_num : procedure (var dest: mpz_t; const src: mpq_t); cdecl;
310mpq_get_den : procedure (var dest: mpz_t; const src: mpq_t); cdecl;
311
312mpq_get_str : function (dest: PAnsiChar; Base: Integer; const src: mpq_t): PAnsiChar; cdecl;
313
314function mpq_sgn(const src: mpq_t): Integer; // [MACRO]
315function mpq_numref(const src: mpq_t): pmpz_t; inline; // [MACRO]
316function mpq_denref(const src: mpq_t): pmpz_t; inline; // [MACRO]
317
318var
319{ Floating point (i.e. R) routines }
320mpf_set_default_prec : procedure (Precision: mp_bitcnt_t); cdecl;
321mpf_get_default_prec: function : mp_bitcnt_t; cdecl;
322mpf_init : procedure (var dest: mpf_t); cdecl;
323mpf_init2 : procedure (var dest: mpf_t; Precision: mp_bitcnt_t); cdecl;
324mpf_inits : procedure (p: pmpf_t {; ...}); cdecl varargs;
325mpf_clear : procedure (var dest: mpf_t); cdecl;
326mpf_clears : procedure (p: pmpf_t {; ...}); cdecl varargs;
327mpf_set_prec : procedure (var dest: mpf_t; Precision: mp_bitcnt_t); cdecl;
328mpf_get_prec : function (const src: mpf_t): mp_bitcnt_t; cdecl;
329mpf_set_prec_raw : procedure (var dest: mpf_t; Precision: mp_bitcnt_t); cdecl;
330
331mpf_set : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
332mpf_set_ui : procedure (var dest: mpf_t; src: Cardinal); cdecl;
333mpf_set_si : procedure (var dest: mpf_t; src: Integer); cdecl;
334mpf_set_d : procedure (var dest: mpf_t; src: Double); cdecl;
335mpf_set_z : procedure (var dest: mpf_t; const src: mpz_t); cdecl;
336mpf_set_q : procedure (var dest: mpf_t; const src: mpq_t); cdecl;
337mpf_set_str : function (var dest: mpf_t; src: PAnsiChar; Base: Integer): Integer; cdecl;
338mpf_swap : procedure (var v1, v2: mpf_t); cdecl;
339
340mpf_init_set : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
341mpf_init_set_ui : procedure (var dest: mpf_t; src: Cardinal); cdecl;
342mpf_init_set_si : procedure (var dest: mpf_t; src: Integer); cdecl;
343mpf_init_set_d : procedure (var dest: mpf_t; src: Double); cdecl;
344mpf_init_set_str : function (var dest: mpf_t; src: PAnsiChar; Base: Integer): Integer; cdecl;
345
346mpf_get_d : function (const src: mpf_t): Double; cdecl;
347mpf_get_si : function (const src: mpf_t): Integer; cdecl;
348mpf_get_ui : function (const src: mpf_t): Cardinal; cdecl;
349mpf_get_d_2exp : function (var Exp: Integer; const src: mpf_t): Double; cdecl;
350mpf_fits_sint_p : function (const src: mpf_t): Integer; cdecl;
351mpf_fits_slong_p : function (const src: mpf_t): Integer; cdecl;
352mpf_fits_sshort_p : function (const src: mpf_t): Integer; cdecl;
353mpf_fits_uint_p : function (const src: mpf_t): Integer; cdecl;
354mpf_fits_ulong_p : function (const src: mpf_t): Integer; cdecl;
355mpf_fits_ushort_p : function (const src: mpf_t): Integer; cdecl;
356
357mpf_cmp : function (const src1, src2: mpf_t): Integer; cdecl;
358mpf_cmp_si : function (const src1: mpf_t; src2: Integer): Integer; cdecl;
359mpf_cmp_ui : function (const src1: mpf_t; src2: Cardinal): Integer; cdecl;
360mpf_cmp_d : function (const src1: mpf_t; src2: Double): Integer; cdecl;
361mpf_eq : function (const src1, src2: mpf_t; NumberOfBits: mp_bitcnt_t): Integer; cdecl;
362mpf_reldiff : procedure (var dest: mpf_t; const src1, src2: mpf_t); cdecl;
363
364mpf_get_str : function (dest: PAnsiChar; var Exponent: mp_exp_t; Base: Integer;
365NumberOfDigits: mp_size_t; const src: mpf_t): PAnsiChar; cdecl;
366
367mpf_add : procedure (var dest: mpf_t; const src1, src2: mpf_t); cdecl;
368mpf_add_ui : procedure (var dest: mpf_t; const src1: mpf_t; src2: Cardinal); cdecl;
369mpf_sub : procedure (var dest: mpf_t; const src1, src2: mpf_t); cdecl;
370mpf_ui_sub : procedure (var dest: mpf_t; src1: Cardinal; const src2: mpf_t); cdecl;
371mpf_sub_ui : procedure (var dest: mpf_t; const src1: mpf_t; src2: Cardinal); cdecl;
372mpf_mul : procedure (var dest: mpf_t; const src1, src2: mpf_t); cdecl;
373mpf_mul_ui : procedure (var dest: mpf_t; const src1: mpf_t; src2: Cardinal); cdecl;
374mpf_div : procedure (var dest: mpf_t; const src1, src2: mpf_t); cdecl;
375mpf_ui_div : procedure (var dest: mpf_t; src1: Cardinal; const src2: mpf_t); cdecl;
376mpf_div_ui : procedure (var dest: mpf_t; const src1: mpf_t; src2: Cardinal); cdecl;
377mpf_sqrt : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
378mpf_sqrt_ui : procedure (var dest: mpf_t; src: Cardinal); cdecl;
379mpf_pow_ui : procedure (var dest: mpf_t; const src1: mpf_t; src2: Cardinal); cdecl;
380mpf_neg : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
381mpf_abs : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
382mpf_mul_2exp : procedure (var dest: mpf_t; const src1: mpf_t; src2: mp_bitcnt_t); cdecl;
383mpf_div_2exp : procedure (var dest: mpf_t; const src1: mpf_t; src2: mp_bitcnt_t); cdecl;
384
385mpf_ceil : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
386mpf_floor : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
387mpf_trunc : procedure (var dest: mpf_t; const src: mpf_t); cdecl;
388mpf_integer_p : function (const src: mpf_t): Integer; cdecl;
389
390mpf_urandomb : procedure (var ROP: mpf_t; var state: gmp_randstate_t; nBits: mp_bitcnt_t); cdecl;
391mpf_rrandomb : procedure (var ROP: mpf_t; var state: gmp_randstate_t; maxSize: mp_size_t; exp: mp_exp_t); cdecl;
392
393function mpf_sgn(const src: mpf_t): Integer;
394
395var
396gmp_randinit_default : procedure (var state: gmp_randstate_t); cdecl;
397gmp_randinit_mt : procedure (var state: gmp_randstate_t); cdecl;
398gmp_randinit_lc_2exp : procedure (var state: gmp_randstate_t; var a: mpz_t; c: Cardinal; M2Exp: mp_bitcnt_t); cdecl;
399gmp_randinit_lc_2exp_size : procedure (var state: gmp_randstate_t; size: mp_bitcnt_t); cdecl;
400gmp_randinit_set : procedure (var dest: gmp_randstate_t; const src: gmp_randstate_t); cdecl;
401gmp_randclear : procedure (var state: gmp_randstate_t); cdecl;
402gmp_randseed : procedure (var state: gmp_randstate_t; Seed: mpz_t); cdecl;
403gmp_randseed_ui : procedure (var state: gmp_randstate_t; Seed: Cardinal); cdecl;
404gmp_urandomb_ui : function (var state: gmp_randstate_t; n: Cardinal): Cardinal; cdecl;
405gmp_urandomm_ui : function (var state: gmp_randstate_t; n: Cardinal): Cardinal; cdecl;
406
407{ Formatted I/O functions }
408// for "..." arguments, pointer to mpx_t and PAnsiChar should be used.
409// e.g:
410// var i: mpz_t;
411// buf: AnsiString;
412// begin
413// mpz_init_set_ui(i, 12345);
414// SetLength(buf, 100); // allocate memory
415// gmp_printf(PAnsiChar(buf), '%s is an mpz %Zd', PAnsiChar('hear'), @i);
416// mpz_clear(i);
417// end;
418
419// for rational numbers,
420gmp_printf : procedure (Buf: PAnsiChar; Fmt: PAnsiChar{; ...}); cdecl varargs;
421gmp_scanf : procedure (Buf: PAnsiChar; Fmt: PAnsiChar{; ...}); cdecl varargs;
422
423{ Extensions to the GMP library, implemented in this unit }
424
425procedure mpf_exp(var dest: mpf_t; const src: mpf_t);
426
427(*
428
429Disabled for now, as these are not thread-safe
430
431procedure mpf_ln(var dest: mpf_t; const src: mpf_t);
432procedure mpf_pow(var dest: mpf_t; const src1, src2: mpf_t);
433procedure mpf_sin(var dest: mpf_t; const src: mpf_t);
434procedure mpf_cos(var dest: mpf_t; const src: mpf_t);
435procedure mpf_arctan(var dest: mpf_t; const src: mpf_t);
436procedure mpf_pi(var dest: mpf_t);
437
438*)
439
440var
441vOnNeedMPIRDynamicDLLName : function : String;
442
443function Bind_MPIR_DLL(const dllName : String = '') : Boolean;
444
445// ------------------------------------------------------------------
446// ------------------------------------------------------------------
447// ------------------------------------------------------------------
448implementation
449// ------------------------------------------------------------------
450// ------------------------------------------------------------------
451// ------------------------------------------------------------------
452
453var
454vDLLHandle : THandle;
455vBindMRSW : TMultiReadSingleWrite;
456
457function PerformBind_MPIR_DLL(dllName : String) : Boolean;
458var
459handle : THandle;
460
461function GetProcMPZ(const name : AnsiString) : Pointer;
462begin
463Result := GetProcAddress(handle, PAnsiChar('__gmpz_'+name));
464end;
465
466function GetProcMPQ(const name : AnsiString) : Pointer;
467begin
468Result := GetProcAddress(handle, PAnsiChar('__gmpq_'+name));
469end;
470
471function GetProcMPF(const name : AnsiString) : Pointer;
472begin
473Result := GetProcAddress(handle, PAnsiChar('__gmpf_'+name));
474end;
475
476function GetProcGMP(const name : AnsiString) : Pointer;
477begin
478Result := GetProcAddress(handle, PAnsiChar('__gmp_'+name));
479end;
480
481begin
482vBindMRSW.BeginWrite;
483try
484if dllName = '' then begin
485if Assigned(vOnNeedMPIRDynamicDLLName) then
486dllName := vOnNeedMPIRDynamicDLLName();
487if dllName = '' then
488dllName := 'mpir.dll';
489end;
490
491handle := LoadLibrary(PChar(dllName));
492if handle = 0 then begin
493raise EOSError.CreateFmt('Failed to load "%s", Error %d: %s',
494[dllName, GetLastError, SysErrorMessage(GetLastError)]);
495end;
496
497mpz_init := GetProcMPZ('init');
498mpz_inits := GetProcMPZ('inits');
499mpz_init2 := GetProcMPZ('init2');
500mpz_clear := GetProcMPZ('clear');
501mpz_clears := GetProcMPZ('clears');
502mpz_realloc := GetProcMPZ('realloc');
503mpz_realloc2 := GetProcMPZ('realloc2');
504mpz_array_init := GetProcMPZ('array_init');
505mpz_swap := GetProcMPZ('swap');
506mpz_set := GetProcMPZ('set');
507mpz_set_ui := GetProcMPZ('set_ui');
508mpz_set_si := GetProcMPZ('set_si');
509mpz_set_d := GetProcMPZ('set_d');
510mpz_set_q := GetProcMPZ('set_q');
511mpz_set_f := GetProcMPZ('set_f');
512mpz_set_str := GetProcMPZ('set_str');
513mpz_init_set := GetProcMPZ('init_set');
514mpz_init_set_ui := GetProcMPZ('init_set_ui');
515mpz_init_set_si := GetProcMPZ('init_set_si');
516mpz_init_set_d := GetProcMPZ('init_set_d');
517mpz_init_set_str := GetProcMPZ('init_set_str');
518mpz_import := GetProcMPZ('import');
519mpz_export := GetProcMPZ('export');
520mpz_getlimbn := GetProcMPZ('getlimbn');
521mpz_size := GetProcMPZ('size');
522mpz_get_ui := GetProcMPZ('get_ui');
523mpz_get_si := GetProcMPZ('get_si');
524mpz_get_d := GetProcMPZ('get_d');
525mpz_get_d_2exp := GetProcMPZ('get_d_2exp');
526mpz_fits_sint_p := GetProcMPZ('fits_sint_p');
527mpz_fits_slong_p := GetProcMPZ('fits_slong_p');
528mpz_fits_sshort_p := GetProcMPZ('fits_sshort_p');
529mpz_fits_uint_p := GetProcMPZ('fits_uint_p');
530mpz_fits_ulong_p := GetProcMPZ('fits_ulong_p');
531mpz_fits_ushort_p := GetProcMPZ('fits_ushort_p');
532mpz_get_str := GetProcMPZ('get_str');
533mpz_add := GetProcMPZ('add');
534mpz_add_ui := GetProcMPZ('add_ui');
535mpz_sub := GetProcMPZ('sub');
536mpz_sub_ui := GetProcMPZ('sub_ui');
537mpz_ui_sub := GetProcMPZ('ui_sub');
538mpz_mul := GetProcMPZ('mul');
539mpz_mul_si := GetProcMPZ('mul_si');
540mpz_mul_ui := GetProcMPZ('mul_ui');
541mpz_mul_2exp := GetProcMPZ('mul_2exp');
542mpz_addmul := GetProcMPZ('addmul');
543mpz_addmul_ui := GetProcMPZ('addmul_ui');
544mpz_submul := GetProcMPZ('submul');
545mpz_submul_ui := GetProcMPZ('submul_ui');
546mpz_neg := GetProcMPZ('neg');
547mpz_abs := GetProcMPZ('abs');
548mpz_cdiv_q := GetProcMPZ('cdiv_q');
549mpz_cdiv_r := GetProcMPZ('cdiv_r');
550mpz_cdiv_qr := GetProcMPZ('cdiv_qr');
551mpz_cdiv_q_ui := GetProcMPZ('cdiv_q_ui');
552mpz_cdiv_r_ui := GetProcMPZ('cdiv_r_ui');
553mpz_cdiv_qr_ui := GetProcMPZ('cdiv_qr_ui');
554mpz_cdiv_ui := GetProcMPZ('cdiv_ui');
555mpz_cdiv_q_2exp := GetProcMPZ('cdiv_q_2exp');
556mpz_cdiv_r_2exp := GetProcMPZ('cdiv_r_2exp');
557mpz_fdiv_q := GetProcMPZ('fdiv_q');
558mpz_fdiv_r := GetProcMPZ('fdiv_r');
559mpz_fdiv_qr := GetProcMPZ('fdiv_qr');
560mpz_fdiv_q_ui := GetProcMPZ('fdiv_q_ui');
561mpz_fdiv_r_ui := GetProcMPZ('fdiv_r_ui');
562mpz_fdiv_qr_ui := GetProcMPZ('fdiv_qr_ui');
563mpz_fdiv_ui := GetProcMPZ('fdiv_ui');
564mpz_fdiv_q_2exp := GetProcMPZ('fdiv_q_2exp');
565mpz_fdiv_r_2exp := GetProcMPZ('fdiv_r_2exp');
566mpz_tdiv_q := GetProcMPZ('tdiv_q');
567mpz_tdiv_r := GetProcMPZ('tdiv_r');
568mpz_tdiv_qr := GetProcMPZ('tdiv_qr');
569mpz_tdiv_q_ui := GetProcMPZ('tdiv_q_ui');
570mpz_tdiv_r_ui := GetProcMPZ('tdiv_r_ui');
571mpz_tdiv_qr_ui := GetProcMPZ('tdiv_qr_ui');
572mpz_tdiv_ui := GetProcMPZ('tdiv_ui');
573mpz_tdiv_q_2exp := GetProcMPZ('tdiv_q_2exp');
574mpz_tdiv_r_2exp := GetProcMPZ('tdiv_r_2exp');
575mpz_mod := GetProcMPZ('mod');
576mpz_mod_ui := GetProcMPZ('mod_ui');
577mpz_divexact := GetProcMPZ('divexact');
578mpz_divexact_ui := GetProcMPZ('divexact_ui');
579mpz_mod_2exp := GetProcMPZ('mod_2exp');
580mpz_div_2exp := GetProcMPZ('div_2exp');
581mpz_divisible_p := GetProcMPZ('divisible_p');
582mpz_divisible_ui_p := GetProcMPZ('divisible_ui_p');
583mpz_divisible_2exp_p := GetProcMPZ('divisible_2exp_p');
584mpz_congruent_p := GetProcMPZ('congruent_p');
585mpz_congruent_ui_p := GetProcMPZ('congruent_ui_p');
586mpz_congruent_2exp_p := GetProcMPZ('congruent_2exp_p');
587mpz_powm := GetProcMPZ('powm');
588mpz_powm_ui := GetProcMPZ('powm_ui');
589mpz_pow_ui := GetProcMPZ('pow_ui');
590mpz_ui_pow_ui := GetProcMPZ('ui_pow_ui');
591mpz_root := GetProcMPZ('root');
592mpz_nthroot := GetProcMPZ('nthroot');
593mpz_rootrem := GetProcMPZ('rootrem');
594mpz_sqrt := GetProcMPZ('sqrt');
595mpz_sqrtrem := GetProcMPZ('sqrtrem');
596mpz_perfect_square_p := GetProcMPZ('perfect_square_p');
597mpz_perfect_power_p := GetProcMPZ('perfect_power_p');
598mpz_sizeinbase := GetProcMPZ('sizeinbase');
599mpz_probable_prime_p := GetProcMPZ('probable_prime_p');
600mpz_likely_prime_p := GetProcMPZ('likely_prime_p');
601mpz_next_prime_candidate := GetProcMPZ('next_prime_candidate');
602mpz_gcd := GetProcMPZ('gcd');
603mpz_gcd_ui := GetProcMPZ('gcd_ui');
604mpz_gcdext := GetProcMPZ('gcdext');
605mpz_lcm := GetProcMPZ('lcm');
606mpz_lcm_ui := GetProcMPZ('lcm_ui');
607mpz_invert := GetProcMPZ('invert');
608mpz_jacobi := GetProcMPZ('jacobi');
609mpz_legendre := GetProcMPZ('legendre');
610mpz_kronecker := GetProcMPZ('kronecker');
611mpz_kronecker_si := GetProcMPZ('kronecker_si');
612mpz_kronecker_ui := GetProcMPZ('kronecker_ui');
613mpz_si_kronecker := GetProcMPZ('si_kronecker');
614mpz_ui_kronecker := GetProcMPZ('ui_kronecker');
615mpz_remove := GetProcMPZ('remove');
616mpz_fac_ui := GetProcMPZ('fac_ui');
617mpz_primorial_ui := GetProcMPZ('primorial_ui');
618mpz_fib_ui := GetProcMPZ('fib_ui');
619mpz_fib2_ui := GetProcMPZ('fib2_ui');
620mpz_bin_ui := GetProcMPZ('bin_ui');
621mpz_bin_uiui := GetProcMPZ('bin_uiui');
622mpz_lucnum_ui := GetProcMPZ('lucnum_ui');
623mpz_lucnum2_ui := GetProcMPZ('lucnum2_ui');
624mpz_cmp := GetProcMPZ('cmp');
625mpz_cmp_d := GetProcMPZ('cmp_d');
626mpz_cmp_ui := GetProcMPZ('cmp_ui');
627mpz_cmp_si := GetProcMPZ('cmp_si');
628mpz_cmpabs := GetProcMPZ('cmpabs');
629mpz_cmpabs_d := GetProcMPZ('cmpabs_d');
630mpz_cmpabs_ui := GetProcMPZ('cmpabs_ui');
631mpz_and := GetProcMPZ('and');
632mpz_ior := GetProcMPZ('ior');
633mpz_xor := GetProcMPZ('xor');
634mpz_com := GetProcMPZ('com');
635mpz_popcount := GetProcMPZ('popcount');
636mpz_hamdist := GetProcMPZ('hamdist');
637mpz_scan0 := GetProcMPZ('scan0');
638mpz_scan1 := GetProcMPZ('scan1');
639mpz_setbit := GetProcMPZ('setbit');
640mpz_clrbit := GetProcMPZ('clrbit');
641mpz_combit := GetProcMPZ('combit');
642mpz_tstbit := GetProcMPZ('tstbit');
643mpz_urandomb := GetProcMPZ('urandomb');
644mpz_urandomm := GetProcMPZ('urandomm');
645mpz_rrandomb := GetProcMPZ('rrandomb');
646
647mpq_canonicalize := GetProcMPQ('canonicalize');
648mpq_init := GetProcMPQ('init');
649mpq_inits := GetProcMPQ('inits');
650mpq_clear := GetProcMPQ('clear');
651mpq_clears := GetProcMPQ('clears');
652mpq_set := GetProcMPQ('set');
653mpq_set_z := GetProcMPQ('set_z');
654mpq_set_ui := GetProcMPQ('set_ui');
655mpq_set_si := GetProcMPQ('set_si');
656mpq_set_str := GetProcMPQ('set_str');
657mpq_set_d := GetProcMPQ('set_d');
658mpq_set_f := GetProcMPQ('set_f');
659mpq_swap := GetProcMPQ('swap');
660mpq_add := GetProcMPQ('add');
661mpq_sub := GetProcMPQ('sub');
662mpq_mul := GetProcMPQ('mul');
663mpq_div := GetProcMPQ('div');
664mpq_neg := GetProcMPQ('neg');
665mpq_abs := GetProcMPQ('abs');
666mpq_inv := GetProcMPQ('inv');
667mpq_mul_2exp := GetProcMPQ('mul_2exp');
668mpq_div_2exp := GetProcMPQ('div_2exp');
669mpq_cmp := GetProcMPQ('cmp');
670mpq_cmp_ui := GetProcMPQ('cmp_ui');
671mpq_cmp_si := GetProcMPQ('cmp_si');
672mpq_equal := GetProcMPQ('equal');
673mpq_get_d := GetProcMPQ('get_d');
674mpq_set_num := GetProcMPQ('set_num');
675mpq_set_den := GetProcMPQ('set_den');
676mpq_get_num := GetProcMPQ('get_num');
677mpq_get_den := GetProcMPQ('get_den');
678mpq_get_str := GetProcMPQ('get_str');
679
680mpf_set_default_prec := GetProcMPF('set_default_prec');
681mpf_get_default_prec := GetProcMPF('get_default_prec');
682mpf_init := GetProcMPF('init');
683mpf_init2 := GetProcMPF('init2');
684mpf_inits := GetProcMPF('inits');
685mpf_clear := GetProcMPF('clear');
686mpf_clears := GetProcMPF('clears');
687mpf_set_prec := GetProcMPF('set_prec');
688mpf_get_prec := GetProcMPF('get_prec');
689mpf_set_prec_raw := GetProcMPF('set_prec_raw');
690mpf_set := GetProcMPF('set');
691mpf_set_ui := GetProcMPF('set_ui');
692mpf_set_si := GetProcMPF('set_si');
693mpf_set_d := GetProcMPF('set_d');
694mpf_set_z := GetProcMPF('set_z');
695mpf_set_q := GetProcMPF('set_q');
696mpf_set_str := GetProcMPF('set_str');
697mpf_swap := GetProcMPF('swap');
698mpf_init_set := GetProcMPF('init_set');
699mpf_init_set_ui := GetProcMPF('init_set_ui');
700mpf_init_set_si := GetProcMPF('init_set_si');
701mpf_init_set_d := GetProcMPF('init_set_d');
702mpf_init_set_str := GetProcMPF('init_set_str');
703mpf_get_d := GetProcMPF('get_d');
704mpf_get_si := GetProcMPF('get_si');
705mpf_get_ui := GetProcMPF('get_ui');
706mpf_get_d_2exp := GetProcMPF('get_d_2exp');
707mpf_fits_sint_p := GetProcMPF('fits_sint_p');
708mpf_fits_slong_p := GetProcMPF('fits_slong_p');
709mpf_fits_sshort_p := GetProcMPF('fits_sshort_p');
710mpf_fits_uint_p := GetProcMPF('fits_uint_p');
711mpf_fits_ulong_p := GetProcMPF('fits_ulong_p');
712mpf_fits_ushort_p := GetProcMPF('fits_ushort_p');
713mpf_cmp := GetProcMPF('cmp');
714mpf_cmp_si := GetProcMPF('cmp_si');
715mpf_cmp_ui := GetProcMPF('cmp_ui');
716mpf_cmp_d := GetProcMPF('cmp_d');
717mpf_eq := GetProcMPF('eq');
718mpf_reldiff := GetProcMPF('reldiff');
719mpf_get_str := GetProcMPF('get_str');
720mpf_add := GetProcMPF('add');
721mpf_add_ui := GetProcMPF('add_ui');
722mpf_sub := GetProcMPF('sub');
723mpf_ui_sub := GetProcMPF('ui_sub');
724mpf_sub_ui := GetProcMPF('sub_ui');
725mpf_mul := GetProcMPF('mul');
726mpf_mul_ui := GetProcMPF('mul_ui');
727mpf_div := GetProcMPF('div');
728mpf_ui_div := GetProcMPF('ui_div');
729mpf_div_ui := GetProcMPF('div_ui');
730mpf_sqrt := GetProcMPF('sqrt');
731mpf_sqrt_ui := GetProcMPF('sqrt_ui');
732mpf_pow_ui := GetProcMPF('pow_ui');
733mpf_neg := GetProcMPF('neg');
734mpf_abs := GetProcMPF('abs');
735mpf_mul_2exp := GetProcMPF('mul_2exp');
736mpf_div_2exp := GetProcMPF('div_2exp');
737mpf_ceil := GetProcMPF('ceil');
738mpf_floor := GetProcMPF('floor');
739mpf_trunc := GetProcMPF('trunc');
740mpf_integer_p := GetProcMPF('integer_p');
741mpf_urandomb := GetProcMPF('urandomb');
742mpf_rrandomb := GetProcMPF('rrandomb');
743
744gmp_randinit_default := GetProcGMP('randinit_default');
745gmp_randinit_mt := GetProcGMP('randinit_mt');
746gmp_randinit_lc_2exp := GetProcGMP('randinit_lc_2exp');
747gmp_randinit_lc_2exp_size := GetProcGMP('randinit_lc_2exp_size');
748gmp_randinit_set := GetProcGMP('randinit_set');
749gmp_randclear := GetProcGMP('randclear');
750gmp_randseed := GetProcGMP('randseed');
751gmp_randseed_ui := GetProcGMP('randseed_ui');
752gmp_urandomb_ui := GetProcGMP('urandomb_ui');
753gmp_urandomm_ui := GetProcGMP('urandomm_ui');
754gmp_printf := GetProcGMP('printf');
755gmp_scanf := GetProcGMP('scanf');
756
757vDLLHandle := handle;
758
759Result := True;
760finally
761vBindMRSW.EndWrite;
762end;
763end;
764
765function Bind_MPIR_DLL(const dllName : String = '') : Boolean;
766begin
767if vDLLHandle <> 0 then Exit(True);
768Result := PerformBind_MPIR_DLL(dllName);
769end;
770
771function mpz_odd_p(const src: mpz_t): Boolean;
772begin
773Result := (src.mp_size <> 0) and Odd(src.mp_d^);
774end;
775
776function mpz_even_p(const src: mpz_t): Boolean;
777begin
778Result := (src.mp_size = 0) or not Odd(src.mp_d^);
779end;
780
781function mpq_numref(const src: mpq_t): pmpz_t;
782begin
783Result := @src.mp_num;
784end;
785
786function mpq_denref(const src: mpq_t): pmpz_t;
787begin
788Result := @src.mp_den;
789end;
790
791procedure mpz_set_uint64(var dest: mpz_t; const src: UInt64); // by delphi code
792type
793_UINT64 = record
794m_lo: UInt32;
795m_hi: UInt32;
796end;
797begin
798if _UINT64(src).m_hi = 0 then begin
799mpz_set_ui(dest, _UINT64(src).m_lo);
800end else begin
801mpz_set_ui(dest, _UINT64(src).m_hi);
802mpz_mul_2exp(dest, dest, 32);
803mpz_add_ui(dest, dest, _UINT64(src).m_lo);
804end;
805end;
806
807procedure mpz_set_int64(var dest: mpz_t; const src: Int64); // by delphi code
808var
809u64: UInt64;
810begin
811if src < 0 then begin
812u64 := Abs(src);
813mpz_set_uint64(dest, u64);
814dest.mp_size := -dest.mp_size;
815end else begin
816mpz_set_uint64(dest, src);
817end;
818end;
819
820function mpz_sgn(const src: mpz_t): Integer;
821begin
822if src.mp_size < 0 then
823Result := -1
824else if src.mp_size > 0 then
825Result := 1
826else Result := 0;
827end;
828
829function mpq_sgn(const src: mpq_t): Integer;
830begin
831if src.mp_num.mp_size < 0 then
832Result := -1
833else if src.mp_num.mp_size > 0 then
834Result := 1
835else Result := 0;
836end;
837
838function mpf_sgn(const src: mpf_t): Integer;
839begin
840if src.mp_size < 0 then
841Result := -1
842else if src.mp_size > 0 then
843Result := 1
844else Result := 0;
845end;
846
847function GetExp(var x: mpf_t): Integer;
848begin
849mpf_get_d_2exp(Result, x);
850end;
851
852const
853PREC_PRO = 25; // To keep the precision of intermediate calculation.
854
855procedure mpf_exp(var dest: mpf_t; const src: mpf_t);
856var
857y, s, c0: mpf_t;
858precision, n: Cardinal;
859exp, i: mp_exp_t;
860negative: Boolean;
861begin
862precision := mpf_get_prec(dest) + PREC_PRO;
863mpf_init2(y, precision);
864mpf_set(y, src);
865mpf_set_ui(dest, 1);
866negative := mpf_sgn(y) < 0;
867if negative then
868mpf_neg(y, y);
869exp := GetExp(y);
870if exp > 0 then
871mpf_div_2exp(y, y, exp);
872mpf_init2(c0, precision);
873mpf_init2(s, precision);
874mpf_set_ui(s, 1);
875n := 1;
876repeat
877mpf_mul(s, s, y);
878mpf_div_ui(s, s, n);
879mpf_set(c0, dest);
880mpf_add(dest, dest, s);
881Inc(n)
882until mpf_eq(c0, dest, precision) <> 0;
883for i := 1 to exp do
884mpf_mul(dest, dest, dest);
885if negative then
886mpf_ui_div(dest, 1, dest);
887mpf_clear(s);
888mpf_clear(c0);
889mpf_clear(y);
890end;
891
892var
893LnHalf: mpf_t;
894LnHalfInited: Boolean = False;
895
896procedure mpf_ln(var dest: mpf_t; const src: mpf_t);
897var
898y, s, p, c0, half: mpf_t;
899n, precision: Cardinal;
900exp: mp_exp_t;
901begin
902if mpf_sgn(src) <= 0 then
903raise EMathError.Create('Invalid argument for Ln');
904precision := mpf_get_prec(dest) + PREC_PRO;
905mpf_init2(y, precision);
906mpf_set(y, src);
907mpf_set_ui(dest, 0);
908exp := GetExp(y);
909if exp <> 0 then begin
910if not LnHalfInited or (mpf_get_prec(LnHalf) < precision) then begin
911if LnHalfInited then
912mpf_clear(LnHalf);
913LnHalfInited := True;
914mpf_init2(LnHalf, precision);
915mpf_init2(half, precision);
916mpf_set_d(half, 0.5);
917mpf_ln(LnHalf, half);
918mpf_clear(half)
919end;
920mpf_set(dest, LnHalf);
921mpf_mul_ui(dest, dest, Abs(exp));
922if exp > 0 then begin
923mpf_neg(dest, dest);
924mpf_div_2exp(y, y, exp)
925end else begin
926mpf_mul_2exp(y, y, -Exp)
927end;
928end;
929mpf_ui_sub(y, 1, y);
930mpf_init2(c0, precision);
931mpf_init2(s, precision);
932mpf_init2(p, precision);
933mpf_set_si(p, -1);
934n := 1;
935repeat
936mpf_mul(p, p, y);
937mpf_div_ui(s, p, n);
938mpf_set(c0, dest);
939mpf_add(dest, dest, s);
940Inc(n)
941until mpf_eq(c0, dest, precision) <> 0;
942mpf_clear(p);
943mpf_clear(s);
944mpf_clear(c0);
945mpf_clear(y);
946end;
947
948procedure mpf_pow(var dest: mpf_t; const src1, src2: mpf_t);
949var
950temp: mpf_t;
951begin
952mpf_init2(temp, mpf_get_prec(src1) + PREC_PRO);
953mpf_ln(temp, src1);
954mpf_mul(temp, temp, src2);
955mpf_exp(dest, temp);
956mpf_clear(temp);
957end;
958(*
959var
960SqRtTwo: mpf_t;
961SqRtTwoInited: Boolean = False;
962
963procedure mpf_arctan(var dest: mpf_t; const src: mpf_t);
964var
965precision, n: Cardinal;
966xx, mx2, a, b: mpf_t;
967begin
968precision := mpf_get_prec(dest) + PREC_PRO;
969mpf_init2(xx, precision);
970mpf_init2(mx2, precision);
971mpf_init2(a, precision);
972mpf_init2(b, precision);
973mpf_abs(xx, src);
974if not SqRtTwoInited or (mpf_get_prec(SqRtTwo) < precision) then begin
975if SqRtTwoInited then
976mpf_clear(SqRtTwo);
977SqRtTwoInited := True;
978mpf_init2(SqRtTwo, precision);
979mpf_sqrt_ui(SqRtTwo, 2)
980end;
981mpf_add_ui(a, SqRtTwo, 1);
982if mpf_cmp(xx, a) > 0 then begin
983mpf_pi(dest);
984mpf_div_2exp(dest, dest, 1);
985mpf_ui_div(xx, 1, xx);
986mpf_neg(xx, xx)
987end else begin
988mpf_sub_ui(b, SqRtTwo, 1);
989if mpf_cmp(xx, b) > 0 then begin
990mpf_pi(dest);
991mpf_div_2exp(dest, dest, 2);
992mpf_sub_ui(a, xx, 1);
993mpf_add_ui(b, xx, 1);
994mpf_div(xx, a, b)
995end else begin
996mpf_set_ui(dest, 0)
997end;
998end;
999mpf_mul(mx2, xx, xx);
1000mpf_neg(mx2, mx2);
1001mpf_add(dest, dest, xx);
1002n := 1;
1003repeat
1004mpf_mul(xx, xx, mx2);
1005mpf_div_ui(a, xx, 2 * n + 1);
1006mpf_set(b, dest);
1007mpf_add(dest, dest, a);
1008Inc(n)
1009until mpf_eq(b, dest, precision) <> 0;
1010if mpf_sgn(src) < 0 then
1011mpf_neg(dest, dest);
1012mpf_clear(xx);
1013mpf_clear(mx2);
1014mpf_clear(a);
1015mpf_clear(b);
1016end;
1017
1018var
1019_Pi: mpf_t;
1020PiInited: Boolean = False;
1021
1022procedure mpf_pi(var dest: mpf_t);
1023{ 4 arctan 1/5 - arctan 1/239 = pi/4 }
1024var
1025b: mpf_t;
1026Precision: Cardinal;
1027begin
1028Precision := mpf_get_prec(dest) + PREC_PRO;
1029if not PiInited or (mpf_get_prec(_Pi) < Precision) then begin
1030if PiInited then
1031mpf_clear(_Pi);
1032PiInited := True;
1033mpf_init2(_Pi, Precision);
1034mpf_set_ui(_Pi, 1);
1035mpf_div_ui(_Pi, _Pi, 5);
1036mpf_arctan(_Pi, _Pi);
1037mpf_mul_ui(_Pi, _Pi, 4);
1038mpf_init2(b, Precision);
1039mpf_set_ui(b, 1);
1040mpf_div_ui(b, b, 239);
1041mpf_arctan(b, b);
1042mpf_sub(_Pi, _Pi, b);
1043mpf_mul_ui(_Pi, _Pi, 4);
1044mpf_clear(b)
1045end;
1046mpf_set(dest, _Pi);
1047end;
1048
1049procedure mpf_sin(var dest: mpf_t; const src: mpf_t);
1050var
1051precision, quadrant, n: Cardinal;
1052sign: Integer;
1053a, b, z, xx, c0: mpf_t;
1054begin
1055precision := mpf_get_prec(dest) + PREC_PRO;
1056mpf_init2(a, precision);
1057mpf_init2(b, precision);
1058mpf_init2(z, precision);
1059mpf_init2(xx, precision);
1060mpf_init2(c0, precision);
1061sign := mpf_sgn(src);
1062mpf_abs(xx, src);
1063mpf_pi(z);
1064mpf_div_2exp(z, z, 1);
1065mpf_div(a, xx, z);
1066mpf_floor(xx, a);
1067if mpf_cmp_ui(xx, 4) >= 0 then begin
1068mpf_div_2exp(b, xx, 2);
1069mpf_floor(b, b);
1070mpf_mul_2exp(b, b, 2);
1071mpf_sub(b, xx, b)
1072end else begin
1073mpf_set(b, xx);
1074end;
1075quadrant := mpf_get_ui(b);
1076mpf_sub(b, a, xx);
1077mpf_mul(xx, z, b);
1078if quadrant > 1 then
1079sign := -Sign;
1080if Odd(quadrant) then
1081mpf_sub(xx, z, xx);
1082mpf_mul(z, xx, xx);
1083mpf_neg(z, z);
1084n := 1;
1085mpf_set_ui(b, 1);
1086mpf_set_ui(dest, 1);
1087repeat
1088Inc(n);
1089mpf_div_ui(b, b, n);
1090Inc(n);
1091mpf_div_ui(b, b, n);
1092mpf_mul(b, b, z);
1093mpf_set(c0, dest);
1094mpf_add(dest, dest, b)
1095until mpf_eq(c0, dest, precision) <> 0;
1096mpf_mul(dest, dest, xx);
1097if sign < 0 then
1098mpf_neg(dest, dest);
1099mpf_clear(a);
1100mpf_clear(b);
1101mpf_clear(z);
1102mpf_clear(xx);
1103mpf_clear(c0);
1104end;
1105
1106procedure mpf_cos(var dest: mpf_t; const src: mpf_t);
1107var
1108temp: mpf_t;
1109begin
1110mpf_init2(temp, mpf_get_prec(dest) + PREC_PRO);
1111mpf_pi(temp);
1112mpf_div_2exp(temp, temp, 1);
1113mpf_sub(temp, temp, src);
1114mpf_sin(dest, temp);
1115mpf_clear(temp);
1116end;
1117*)
1118// ------------------------------------------------------------------
1119// ------------------------------------------------------------------
1120// ------------------------------------------------------------------
1121initialization
1122// ------------------------------------------------------------------
1123// ------------------------------------------------------------------
1124// ------------------------------------------------------------------
1125
1126vBindMRSW := TMultiReadSingleWrite.Create;
1127
1128finalization
1129
1130(*
1131if LnHalfInited then
1132mpf_clear(LnHalf);
1133
1134if SqRtTwoInited then
1135mpf_clear(SqRtTwo);
1136
1137if PiInited then
1138mpf_clear(_Pi);
1139*)
1140
1141FreeAndNil(vBindMRSW);
1142
1143end.
1144