X-Git-Url: https://ginac.de/CLN/cln.git//cln.git?a=blobdiff_plain;ds=sidebyside;f=src%2Finteger%2Fcl_I.h;h=5afeb4183b7c51101c97657718a3d686e62c4768;hb=5370ad8054201cf23d4f94a52f4d3f7f9f3cd511;hp=44df5eb838440c0da3c24540c764b2f0051fa5dc;hpb=9c6ab3380367e013def4fb2a41da0eac4798ba08;p=cln.git diff --git a/src/integer/cl_I.h b/src/integer/cl_I.h index 44df5eb..5afeb41 100644 --- a/src/integer/cl_I.h +++ b/src/integer/cl_I.h @@ -3,14 +3,15 @@ #ifndef _CL_I_H #define _CL_I_H -#include "cl_number.h" -#include "cl_integer.h" +#include "cln/number.h" +#include "cln/integer.h" #include "cl_macros.h" -#include "cl_malloc.h" -#include "cl_abort.h" +#include "cln/malloc.h" +#include "cln/exception.h" #include "cl_offsetof.h" #include "cl_DS.h" +namespace cln { // maximal needed length of a digit sequence for a fixnum #define FN_maxlength ceiling(cl_value_len,intDsize) @@ -41,7 +42,7 @@ inline cl_uint cl_FN_word (const cl_I& x) // Bignums. struct cl_heap_bignum : cl_heap { - unsigned int length; // length (in digits) + uintC length; // length (in digits) uintD data[1]; // number in two's complement representation }; @@ -50,9 +51,9 @@ inline cl_heap_bignum* TheBignum (cl_heap_bignum* p) inline cl_heap_bignum* TheBignum (const cl_number& obj) { return (cl_heap_bignum*)(obj.pointer); } -inline cl_heap_bignum* allocate_bignum (unsigned int length) +inline cl_heap_bignum* allocate_bignum (uintC length) { - cl_heap_bignum* p = (cl_heap_bignum*) cl_malloc_hook(offsetofa(cl_heap_bignum,data)+sizeof(uintD)*length); + cl_heap_bignum* p = (cl_heap_bignum*) malloc_hook(offsetofa(cl_heap_bignum,data)+sizeof(uintD)*length); p->refcount = 1; p->type = &cl_class_bignum; p->length = length; @@ -76,67 +77,67 @@ inline cl_I::cl_I (cl_heap_bignum* ptr) // Integers in general. // Type tests. -inline cl_boolean integerp (const cl_I& x) - { unused x; return cl_true; } -inline cl_boolean fixnump (const cl_I& x) - { return (cl_boolean) !x.pointer_p(); } -inline cl_boolean bignump (const cl_I& x) +inline bool integerp (const cl_I& x) + { unused x; return true; } +inline bool fixnump (const cl_I& x) + { return !x.pointer_p(); } +inline bool bignump (const cl_I& x) { return x.pointer_p(); } // Sign test: // (MINUSP x) == (< x 0) -inline cl_boolean minusp (const cl_I& x) +inline bool minusp (const cl_I& x) { if (fixnump(x)) // This assumes cl_value_shift + cl_value_len == cl_pointer_size. - return (cl_boolean)((cl_sint) x.word < 0); + return (cl_sint) x.word < 0; else - return (cl_boolean)((sintD)mspref(arrayMSDptr(TheBignum(x)->data,TheBignum(x)->length),0) < 0); + return (sintD)mspref(arrayMSDptr(TheBignum(x)->data,TheBignum(x)->length),0) < 0; } // (ZEROP x) == (= x 0) -inline cl_boolean zerop (const cl_I& x) +inline bool zerop (const cl_I& x) { - return (cl_boolean)(x.word == cl_combine(cl_FN_tag,0)); + return x.word == cl_combine(cl_FN_tag,0); } // (EQ x y) == (= x y), assuming y a fixnum -inline cl_boolean eq (const cl_I& x, sint32 y) +inline bool eq (const cl_I& x, sint32 y) { - return (cl_boolean)(x.word == cl_combine(cl_FN_tag,y)); + return x.word == cl_combine(cl_FN_tag,y); } // Umwandlungsroutinen Integer <--> Longword: // Wandelt Fixnum >=0 in Unsigned Longword um. -// FN_to_UL(obj) +// FN_to_UV(obj) // > obj: ein Fixnum >=0 -// < ergebnis: der Wert des Fixnum als 32-Bit-Zahl. -inline uint32 FN_to_UL (const cl_I& x) +// < ergebnis: der Wert des Fixnum als intVsize-Bit-Zahl. +inline uintV FN_to_UV (const cl_I& x) { // This assumes cl_value_shift + cl_value_len == cl_pointer_size. return (cl_uint)(x.word) >> cl_value_shift; } // Wandelt Fixnum in Longword um. -// FN_to_L(obj) +// FN_to_V(obj) // > obj: ein Fixnum -// < ergebnis: der Wert des Fixnum als 32-Bit-Zahl. -inline sint32 FN_to_L (const cl_I& x) +// < ergebnis: der Wert des Fixnum als intVsize-Bit-Zahl. +inline sintV FN_to_V (const cl_I& x) { // This assumes cl_value_shift + cl_value_len == cl_pointer_size. return (cl_sint)(x.word) >> cl_value_shift; } -// FN_L_zerop(x,x_) stellt fest, ob x = 0 ist. -// Dabei ist x ein Fixnum und x_ = FN_to_L(x). - #define FN_L_zerop(x,x_) (x_==0) +// FN_V_zerop(x,x_) stellt fest, ob x = 0 ist. +// Dabei ist x ein Fixnum und x_ = FN_to_V(x). + #define FN_V_zerop(x,x_) (x_==0) -// FN_L_minusp(x,x_) stellt fest, ob x < 0 ist. -// Dabei ist x ein Fixnum und x_ = FN_to_L(x). - #define FN_L_minusp(x,x_) (x_<0) +// FN_V_minusp(x,x_) stellt fest, ob x < 0 ist. +// Dabei ist x ein Fixnum und x_ = FN_to_V(x). + #define FN_V_minusp(x,x_) (x_<0) #ifdef intQsize @@ -211,11 +212,47 @@ inline sint64 FN_to_Q (const cl_I& x) } #endif +#ifdef intQsize + +// Wandelt Quadword in Integer um. +// Q_to_I(wert) +// > wert: Wert des Integers, ein signed 64-Bit-Integer. +// < ergebnis: Integer mit diesem Wert. + extern cl_private_thing cl_I_constructor_from_Q (sint64 wert); + inline const cl_I Q_to_I (sint64 wert) + { + return cl_I(cl_I_constructor_from_Q(wert)); + } + +// Wandelt Unsigned Quadword in Integer >=0 um. +// UQ_to_I(wert) +// > wert: Wert des Integers, ein unsigned 64-Bit-Integer. +// < ergebnis: Integer mit diesem Wert. + extern cl_private_thing cl_I_constructor_from_UQ (uint64 wert); + inline const cl_I UQ_to_I (uint64 wert) + { + return cl_I(cl_I_constructor_from_UQ(wert)); + } + + extern cl_private_thing cl_I_constructor_from_Q2 (sint64 wert_hi, uint64 wert_lo ); + inline const cl_I Q2_to_I( sint64 wert_hi, uint64 wert_lo) + { + return cl_I(cl_I_constructor_from_Q2(wert_hi, wert_lo)); + } +#endif + // Wandelt Doppel-Longword in Integer um. // L2_to_I(wert_hi,wert_lo) // > wert_hi|wert_lo: Wert des Integers, ein signed 64-Bit-Integer. // < ergebnis: Integer mit diesem Wert. +#if (cl_word_size==64) + inline cl_private_thing cl_I_constructor_from_L2 (sint32 wert_hi, uint32 wert_lo) + { + return cl_I_constructor_from_Q(((sint64)wert_hi<<32) | (sint64)wert_lo); + } +#else extern cl_private_thing cl_I_constructor_from_L2 (sint32 wert_hi, uint32 wert_lo); +#endif inline const cl_I L2_to_I (sint32 wert_hi, uint32 wert_lo) { return cl_I(cl_I_constructor_from_L2(wert_hi,wert_lo)); @@ -225,34 +262,57 @@ inline sint64 FN_to_Q (const cl_I& x) // UL2_to_I(wert_hi,wert_lo) // > wert_hi|wert_lo: Wert des Integers, ein unsigned 64-Bit-Integer. // < ergebnis: Integer mit diesem Wert. +#if (cl_word_size==64) + inline cl_private_thing cl_I_constructor_from_UL2 (uint32 wert_hi, uint32 wert_lo) + { + return cl_I_constructor_from_UQ(((uint64)wert_hi<<32) | (uint64)wert_lo); + } +#else extern cl_private_thing cl_I_constructor_from_UL2 (uint32 wert_hi, uint32 wert_lo); +#endif inline const cl_I UL2_to_I (uint32 wert_hi, uint32 wert_lo) { return cl_I(cl_I_constructor_from_UL2(wert_hi,wert_lo)); } -#ifdef intQsize +// Wandelt sintV in Integer um. +// V_to_I(wert) +// > wert: Wert des Integers, ein sintV. +// < ergebnis: Integer mit diesem Wert. +#if (intVsize<=32) + #define V_to_I(wert) L_to_I(wert) +#else + #define V_to_I(wert) Q_to_I(wert) +#endif -// Wandelt Quadword in Integer um. -// Q_to_I(wert) -// > wert: Wert des Integers, ein signed 64-Bit-Integer. +// Wandelt uintV in Integer >=0 um. +// UV_to_I(wert) +// > wert: Wert des Integers, ein uintV. // < ergebnis: Integer mit diesem Wert. - extern cl_private_thing cl_I_constructor_from_Q (sint64 wert); - inline const cl_I Q_to_I (sint64 wert) - { - return cl_I(cl_I_constructor_from_Q(wert)); - } +#if (intVsize<=32) + #define UV_to_I(wert) UL_to_I(wert) +#else + #define UV_to_I(wert) UQ_to_I(wert) +#endif -// Wandelt Unsigned Quadword in Integer >=0 um. -// UQ_to_I(wert) -// > wert: Wert des Integers, ein unsigned 64-Bit-Integer. +// Wandelt sintE in Integer um. +// E_to_I(wert) +// > wert: Wert des Integers, ein sintE. // < ergebnis: Integer mit diesem Wert. - extern cl_private_thing cl_I_constructor_from_UQ (uint64 wert); - inline const cl_I UQ_to_I (uint64 wert) - { - return cl_I(cl_I_constructor_from_UQ(wert)); - } +#if (intEsize<=32) + #define E_to_I(wert) L_to_I(wert) +#else + #define E_to_I(wert) Q_to_I(wert) +#endif +// Wandelt uintE in Integer >=0 um. +// UE_to_I(wert) +// > wert: Wert des Integers, ein uintE. +// < ergebnis: Integer mit diesem Wert. +#if (intEsize<=32) + #define UE_to_I(wert) UL_to_I(wert) +#else + #define UE_to_I(wert) UQ_to_I(wert) #endif // Wandelt uintD in Integer >=0 um. @@ -278,27 +338,43 @@ inline const cl_I minus (uintL x, uintL y) #endif } +#ifdef intQsize + +inline const cl_I minus (uintQ x, uintQ y) +{ + return Q2_to_I( (x Longword: #if (intDsize<=32) -// Holt die nächsten pFN_maxlength Digits in ein uint32. -inline uint32 pFN_maxlength_digits_at (const uintD* ptr) +// Holt die nächsten pFN_maxlength Digits in ein uintV. +inline uintV pFN_maxlength_digits_at (const uintD* ptr) { #if (pFN_maxlength==1) - return (uint32)lspref(ptr,0); + return (uintV)lspref(ptr,0); #elif (pFN_maxlength==2) - return ((uint32)lspref(ptr,1)<>(2*intDsize)); lspref(ptr,1) = (uintD)(wert>>intDsize); lspref(ptr,0) = (uintD)(wert); +#elif (pFN_maxlength==5) + lspref(ptr,4) = (uintD)(wert>>(4*intDsize)); + lspref(ptr,3) = (uintD)(wert>>(3*intDsize)); + lspref(ptr,2) = (uintD)(wert>>(2*intDsize)); + lspref(ptr,1) = (uintD)(wert>>intDsize); + lspref(ptr,0) = (uintD)(wert); +#elif (pFN_maxlength==6) + lspref(ptr,5) = (uintD)(wert>>(5*intDsize)); + lspref(ptr,4) = (uintD)(wert>>(4*intDsize)); + lspref(ptr,3) = (uintD)(wert>>(3*intDsize)); + lspref(ptr,2) = (uintD)(wert>>(2*intDsize)); + lspref(ptr,1) = (uintD)(wert>>intDsize); + lspref(ptr,0) = (uintD)(wert); +#elif (pFN_maxlength==7) + lspref(ptr,6) = (uintD)(wert>>(6*intDsize)); + lspref(ptr,5) = (uintD)(wert>>(5*intDsize)); + lspref(ptr,4) = (uintD)(wert>>(4*intDsize)); + lspref(ptr,3) = (uintD)(wert>>(3*intDsize)); + lspref(ptr,2) = (uintD)(wert>>(2*intDsize)); + lspref(ptr,1) = (uintD)(wert>>intDsize); + lspref(ptr,0) = (uintD)(wert); +#elif (pFN_maxlength==8) + lspref(ptr,7) = (uintD)(wert>>(7*intDsize)); + lspref(ptr,6) = (uintD)(wert>>(6*intDsize)); + lspref(ptr,5) = (uintD)(wert>>(5*intDsize)); + lspref(ptr,4) = (uintD)(wert>>(4*intDsize)); + lspref(ptr,3) = (uintD)(wert>>(3*intDsize)); + lspref(ptr,2) = (uintD)(wert>>(2*intDsize)); + lspref(ptr,1) = (uintD)(wert>>intDsize); + lspref(ptr,0) = (uintD)(wert); #endif } @@ -368,9 +474,9 @@ inline sintD FN_MSD (cl_uint word) #if (FN_maxlength==1) #define FN_LSD0(word) FN_MSD(word) - #define FN_LSD1(word) (cl_abort(), (uintD)0) // never used - #define FN_LSD2(word) (cl_abort(), (uintD)0) // never used - #define FN_LSD3(word) (cl_abort(), (uintD)0) // never used + #define FN_LSD1(word) (throw runtime_exception(), (uintD)0) // never used + #define FN_LSD2(word) (throw runtime_exception(), (uintD)0) // never used + #define FN_LSD3(word) (throw runtime_exception(), (uintD)0) // never used #endif #if (FN_maxlength==2) inline uintD FN_LSD0 (cl_uint word) @@ -378,8 +484,8 @@ inline sintD FN_MSD (cl_uint word) return (uintD)(word >> cl_value_shift); } #define FN_LSD1(word) FN_MSD(word) - #define FN_LSD2(word) (cl_abort(), (uintD)0) // never used - #define FN_LSD3(word) (cl_abort(), (uintD)0) // never used + #define FN_LSD2(word) (throw runtime_exception(), (uintD)0) // never used + #define FN_LSD3(word) (throw runtime_exception(), (uintD)0) // never used #endif #if (FN_maxlength==4) inline uintD FN_LSD0 (cl_uint word) @@ -520,7 +626,7 @@ inline sintD FN_MSD (cl_uint word) var uintD CONCAT(FN_store_,__LINE__) [FN_maxlength]; \ { var const cl_I& obj_from_I_to_NDS = (obj); \ if (fixnump(obj_from_I_to_NDS)) \ - { FN_to_NDS(arrayLSDptr(CONCAT(FN_store_,__LINE__),FN_maxlength), cl_FN_word(obj_from_I_to_NDS), MSDptr_zuweisung,len_zuweisung,LSDptr_zuweisung, cl_true,); } \ + { FN_to_NDS(arrayLSDptr(CONCAT(FN_store_,__LINE__),FN_maxlength), cl_FN_word(obj_from_I_to_NDS), MSDptr_zuweisung,len_zuweisung,LSDptr_zuweisung, true,); } \ else \ { BN_to_NDS(obj_from_I_to_NDS,MSDptr_zuweisung,len_zuweisung, LSDptr_zuweisung); } \ } @@ -535,7 +641,7 @@ inline sintD FN_MSD (cl_uint word) var uintD CONCAT(FN_store_,__LINE__) [1+FN_maxlength]; \ { var const cl_I& obj_from_I_to_NDS = (obj); \ if (fixnump(obj_from_I_to_NDS)) \ - { FN_to_NDS(arrayLSDptr(CONCAT(FN_store_,__LINE__),1+FN_maxlength), cl_FN_word(obj_from_I_to_NDS), MSDptr_zuweisung,len_zuweisung,LSDptr_zuweisung, cl_true,); } \ + { FN_to_NDS(arrayLSDptr(CONCAT(FN_store_,__LINE__),1+FN_maxlength), cl_FN_word(obj_from_I_to_NDS), MSDptr_zuweisung,len_zuweisung,LSDptr_zuweisung, true,); } \ else \ { BN_to_NDS_1(obj_from_I_to_NDS,MSDptr_zuweisung,len_zuweisung, LSDptr_zuweisung); } \ } @@ -550,9 +656,6 @@ inline sintD FN_MSD (cl_uint word) // < q,r: Quotient q, Rest r extern const cl_I_div_t cl_divide (const cl_I& x, const cl_I& y); -// Fehler, wenn Quotient keine ganze Zahl ist - nonreturning_function(extern, cl_error_exquo, (const cl_I& x, const cl_I& y)); - // ggT und kgV von Integers @@ -577,8 +680,8 @@ inline sintD FN_MSD (cl_uint word) // > n: ein Integer >0 // > Annahme: x > 1 und n < (integer-length x). // < w: Integer (expt x (/ n)) falls x eine n-te Potenz -// < ergebnis: cl_true ........................, cl_false sonst - extern cl_boolean cl_rootp_aux (cl_I x, uintL n, cl_I* w); +// < ergebnis: true ........................, false sonst + extern bool cl_rootp_aux (cl_I x, uintL n, cl_I* w); // Hilfsfunktion zur Eingabe von Integers @@ -589,14 +692,14 @@ inline sintD FN_MSD (cl_uint word) // > MSBptr/len/..: Ziffernfolge, bestehend aus Punkten (werden überlesen) // und Ziffern/Buchstaben mit Wert < base. // < ergebnis: der dargestellte Integer >=0 - extern const cl_I digits_to_I (const char * MSBptr, uintL len, uintD base); + extern const cl_I digits_to_I (const char * MSBptr, uintC len, uintD base); // Hilfsfunktion zur Ausgabe von Integers // cl_digits_need(len,base) liefert eine obere Abschätzung für die Anzahl der // Ziffern im Stellenwertsystem der Basis base, die x >= 0 braucht. - extern uintL cl_digits_need (const cl_I& x, uintL base); + extern uintC cl_digits_need (const cl_I& x, uintL base); // Wandelt ein Integer in ein Stellensystem um. // I_to_digits(x,base, &ergebnis); @@ -604,7 +707,7 @@ inline sintD FN_MSD (cl_uint word) // > base: Stellensystem-Basis, 2 <= base <= 36. // > ergebnis.LSBptr: darunter ist mindestens digits_need(len) Bytes Platz // < ergebnis: fertige Folge MSBptr/len/LSBptr von Ziffern - typedef struct { uintB* MSBptr; uintL len; uintB* LSBptr; } cl_digits; + typedef struct { uintB* MSBptr; uintC len; uintB* LSBptr; } cl_digits; extern void I_to_digits (const cl_I& x, uintD base, cl_digits* erg); @@ -618,19 +721,19 @@ inline sintD FN_MSD (cl_uint word) class cl_FN : public cl_I { public: // Optimization of method pointer_p(). - cl_boolean pointer_p() const - { return cl_false; } + bool pointer_p() const + { return false; } }; -inline cl_boolean fixnump (const cl_FN& x) - { unused x; return cl_true; } -inline cl_boolean bignump (const cl_FN& x) - { unused x; return cl_false; } +inline bool fixnump (const cl_FN& x) + { unused x; return true; } +inline bool bignump (const cl_FN& x) + { unused x; return false; } -inline cl_boolean minusp (const cl_FN& x) +inline bool minusp (const cl_FN& x) { // This assumes cl_value_shift + cl_value_len == cl_pointer_size. - return (cl_boolean)((cl_sint) x.word < 0); + return (cl_sint) x.word < 0; } @@ -640,20 +743,22 @@ inline cl_boolean minusp (const cl_FN& x) class cl_BN : public cl_I { public: // Optimization of method pointer_p(). - cl_boolean pointer_p() const - { return cl_true; } + bool pointer_p() const + { return true; } }; -inline cl_boolean fixnump (const cl_BN& x) - { unused x; return cl_false; } -inline cl_boolean bignump (const cl_BN& x) - { unused x; return cl_true; } +inline bool fixnump (const cl_BN& x) + { unused x; return false; } +inline bool bignump (const cl_BN& x) + { unused x; return true; } -inline cl_boolean minusp (const cl_BN& x) +inline bool minusp (const cl_BN& x) { - return (cl_boolean)((sintD)mspref(arrayMSDptr(TheBignum(x)->data,TheBignum(x)->length),0) < 0); + return (sintD)mspref(arrayMSDptr(TheBignum(x)->data,TheBignum(x)->length),0) < 0; } -inline cl_boolean zerop (const cl_BN& x) - { unused x; return cl_false; } +inline bool zerop (const cl_BN& x) + { unused x; return false; } + +} // namespace cln #endif /* _CL_I_H */