00001
00002 #ifndef arithmetique_header_included
00003 #define arithmetique_header_included
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031 #include <stdio.h>
00032 #include <limits.h>
00033
00034 #ifdef GNUMP
00035 #include <gmp.h>
00036 #include <stdlib.h>
00037 #include <string.h>
00038 #ifndef mp_get_memory_functions
00039 #if defined(__cplusplus)
00040 extern "C" {
00041 #endif
00042 void mp_get_memory_functions(
00043 void *(**alloc_func_ptr) (size_t),
00044 void *(**realloc_func_ptr) (void *, size_t, size_t),
00045 void (**free_func_ptr) (void *, size_t));
00046 #if defined(__cplusplus)
00047 }
00048 #endif
00049 #endif
00050 #endif
00051
00052 #ifdef CLN
00053 #include <sstream>
00054 #define WANT_OBFUSCATING_OPERATORS
00055 #include <cln/cln.h>
00056 #endif
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073 #ifndef LONG_LONG_MAX
00074
00075
00076
00077
00078
00079
00080 #ifndef __LONG_LONG_MAX__
00081 #define __LONG_LONG_MAX__ 9223372036854775807LL
00082 #endif
00083 #undef LONG_LONG_MAX
00084 #define LONG_LONG_MAX __LONG_LONG_MAX__
00085 #undef LONG_LONG_MIN
00086 #define LONG_LONG_MIN (-LONG_LONG_MAX-1)
00087 #undef ULONG_LONG_MAX
00088 #define ULONG_LONG_MAX (LONG_LONG_MAX * 2ULL + 1)
00089 #endif
00090
00091 #if defined(LINEAR_VALUE_IS_LONGLONG)
00092
00093 #define LINEAR_VALUE_STRING "long long int"
00094 typedef long long int Value;
00095 #if defined(WIN32) && !defined(unix)
00096
00097 # define VALUE_FMT "%I64d"
00098 #else
00099 # define VALUE_FMT "%lld"
00100 #endif
00101 #define VALUE_CONST(val) (val##LL)
00102
00103
00104
00105
00106
00107
00108 #define VALUE_NAN LONG_LONG_MIN
00109 #define VALUE_MIN (LONG_LONG_MIN+1LL)
00110 #define VALUE_MAX LONG_LONG_MAX
00111 #define VALUE_SQRT_MIN long_to_value(LONG_MIN)
00112 #define VALUE_SQRT_MAX long_to_value(LONG_MAX)
00113 #define VALUE_ZERO (0LL)
00114 #define VALUE_ONE (1LL)
00115 #define VALUE_MONE (-1LL)
00116
00117 #define VALUE_TO_LONG(val) \
00118 ((long)((val)>(Value)LONG_MIN&&(val)<=(Value)LONG_MAX)?\
00119 (val):(THROW(overflow_error), LONG_MIN))
00120
00121 #define VALUE_TO_INT(val) \
00122 ((int)((val)>(Value)INT_MIN&&(val)<=(Value)INT_MAX)?\
00123 (val):(THROW(overflow_error), INT_MIN))
00124
00125 #define VALUE_TO_DOUBLE(val) ((double)(val))
00126
00127
00128 #define VALUE_TO_FLOAT(val) ((float)((int)(val)))
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143 #elif defined(LINEAR_VALUE_IS_LONG)
00144
00145 #define LINEAR_VALUE_STRING "long int"
00146 typedef long Value;
00147 #define VALUE_FMT "%ld"
00148 #define VALUE_CONST(val) (val##L)
00149 #define VALUE_NAN LONG_MIN
00150 #define VALUE_MIN (LONG_MIN+1L)
00151 #define VALUE_MAX LONG_MAX
00152 #define VALUE_SQRT_MIN int_to_value(INT_MIN)
00153 #define VALUE_SQRT_MAX int_to_value(INT_MAX)
00154 #define VALUE_ZERO 0L
00155 #define VALUE_ONE 1L
00156 #define VALUE_MONE -1L
00157 #define VALUE_TO_LONG(val) (val)
00158 #define VALUE_TO_INT(val) ((int)(val))
00159 #define VALUE_TO_FLOAT(val) ((float)(val))
00160 #define VALUE_TO_DOUBLE(val) ((double)(val))
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207 #elif defined(LINEAR_VALUE_IS_CHARS)
00208
00209 #define LINEAR_VALUE_STRING "char"
00210 typedef union { char *s; long l; int i; float f; double d;} Value;
00211 #define VALUE_FMT "%s"
00212 #define VALUE_CONST(val) ((Value)(val))
00213 #define VALUE_NAN ((Value)(long)0xdadeebee)
00214 #define VALUE_MIN ((Value)(long)0xdeadbeef)
00215 #define VALUE_MAX ((Value)(long)0xfeedabee)
00216 #define VALUE_ZERO ((Value)0)
00217 #define VALUE_ONE ((Value)1)
00218 #define VALUE_MONE ((Value)-1)
00219 #define VALUE_TO_LONG(val) (val.l)
00220 #define VALUE_TO_INT(val) (val.i)
00221 #define VALUE_TO_FLOAT(val) (val.f)
00222 #define VALUE_TO_DOUBLE(val) (val.d)
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233
00234
00235
00236 #elif defined(LINEAR_VALUE_IS_INT)
00237
00238 #define LINEAR_VALUE_STRING "int"
00239 typedef int Value;
00240 #define VALUE_FMT "%d"
00241 #define VALUE_CONST(val) (val)
00242 #define VALUE_NAN INT_MIN
00243 #define VALUE_MIN (INT_MIN+1)
00244 #define VALUE_MAX INT_MAX
00245 #define VALUE_ZERO 0
00246 #define VALUE_ONE 1
00247 #define VALUE_MONE -1
00248 #define VALUE_TO_LONG(val) ((long)(val))
00249 #define VALUE_TO_INT(val) ((int)(val))
00250 #define VALUE_TO_FLOAT(val) ((float)(val))
00251 #define VALUE_TO_DOUBLE(val) ((double)(val))
00252
00253
00254
00255 #elif defined(GNUMP)
00256
00257 #define LINEAR_VALUE_STRING "gmp"
00258 typedef mpz_t Value;
00259 #define VALUE_FMT "%s"
00260
00261
00262 #undef VALUE_ZERO
00263 #undef VALUE_ONE
00264 #undef VALUE_MONE
00265 #define VALUE_TO_LONG(val) (mpz_get_si(val))
00266 #define VALUE_TO_INT(val) ((int)mpz_get_si(val))
00267 #define VALUE_TO_FLOAT(val) ((float)((int)mpz_get_si(val)))
00268 #define VALUE_TO_DOUBLE(val) (mpz_get_d(val))
00269
00270 #elif defined(CLN)
00271
00272 #define LINEAR_VALUE_STRING "cln"
00273 typedef cln::cl_I Value;
00274 #define VALUE_FMT "%s"
00275
00276 #define VALUE_TO_INT(val) (cln::cl_I_to_int(val))
00277 #define VALUE_TO_DOUBLE(val) (cln::double_approx(val))
00278
00279 #endif
00280
00281
00282
00283 #if defined(CLN)
00284
00285 #define value_init(val) ((val).word = ((cln::cl_uint)cl_FN_tag) << cl_tag_shift)
00286 #define value_assign(v1,v2) ((v1) = (v2))
00287 #define value_set_si(val,i) ((val) = (i))
00288 #define value_set_double(val,d) ((val) = cln::truncate1(cln::cl_R(d)))
00289 #define value_clear(val) ((val) = 0)
00290 #define value_read(val,str) ((val) = (str))
00291 #define value_print(Dst,fmt,val) {std::ostringstream strm; strm << val; \
00292 fprintf((Dst),(fmt),strm.str().c_str()); \
00293 }
00294 #define value_swap(v1,v2) {Value tmp; tmp = v2; \
00295 v2 = v1; v1 = tmp; \
00296 }
00297
00298
00299
00300 #define value_eq(v1,v2) ((v1)==(v2))
00301 #define value_ne(v1,v2) ((v1)!=(v2))
00302 #define value_gt(v1,v2) ((v1)>(v2))
00303 #define value_ge(v1,v2) ((v1)>=(v2))
00304 #define value_lt(v1,v2) ((v1)<(v2))
00305 #define value_le(v1,v2) ((v1)<=(v2))
00306
00307 #define value_abs_eq(v1,v2) (cln::abs(v1)==cln::abs(v2))
00308 #define value_abs_ne(v1,v2) (cln::abs(v1)!=cln::abs(v2))
00309 #define value_abs_gt(v1,v2) (cln::abs(v1)>cln::abs(v2))
00310 #define value_abs_ge(v1,v2) (cln::abs(v1)>=cln::abs(v2))
00311 #define value_abs_lt(v1,v2) (cln::abs(v1)<cln::abs(v2))
00312 #define value_abs_le(v1,v2) (cln::abs(v1)<=cln::abs(v2))
00313
00314 #define value_sign(val) (cln::signum(val))
00315 #define value_compare(v1,v2) (cln::compare((v1),(v2)))
00316
00317 #define value_addto(ref,val1,val2) ((ref) = (val1)+(val2))
00318 #define value_add_int(ref,val,vint) ((ref) = (val)+(vint))
00319 #define value_addmul(ref, val1, val2) ((ref) += (val1)*(val2))
00320 #define value_increment(ref,val) ((ref) = (val)+1)
00321 #define value_multiply(ref,val1,val2) ((ref) = (val1)*(val2))
00322 #define value_subtract(ref,val1,val2) ((ref) = (val1)-(val2))
00323 #define value_sub_int(ref,val1,val2) ((ref) = (val1)-(val2))
00324 #define value_decrement(ref,val) ((ref) = (val)-1)
00325 #define value_division(ref,val1,val2) ((ref) = cln::truncate1(val1,val2))
00326 #define value_divexact(ref,val1,val2) ((ref) = cln::exquo(val1,val2))
00327 #define value_modulus(ref,val1,val2) ((ref) = cln::truncate2(val1,val2).remainder)
00328 #define value_pdivision(ref,val1,val2) ((ref) = cln::floor1(val1,val2))
00329 #define value_pmodulus(ref,val1,val2) ((ref) = cln::floor2(val1,val2).remainder)
00330 #define value_oppose(ref,val) ((ref) = -(val))
00331 #define value_absolute(ref,val) ((ref) = cln::abs(val))
00332 #define value_minimum(ref,val1,val2) ((ref) = cln::min((val1),(val2)))
00333 #define value_maximum(ref,val1,val2) ((ref) = cln::max((val1),(val2)))
00334 #define value_gcd(ref,val1,val2) ((ref) = cln::gcd((val1),(val2)))
00335 #define value_lcm(ref,val1,val2) ((ref) = cln::lcm((val1),(val2)))
00336 #define value_orto(ref,val1,val2) ((ref) = (val1)|(val2))
00337 #define value_andto(ref,val1,val2) ((ref) = (val1)&(val2))
00338
00339
00340
00341 #define value_pos_p(val) ((val) > 0)
00342 #define value_neg_p(val) ((val) < 0)
00343 #define value_posz_p(val) ((val) >= 0)
00344 #define value_negz_p(val) ((val) <= 0)
00345 #define value_zero_p(val) ((val) == 0)
00346 #define value_notzero_p(val) ((val) != 0)
00347 #define value_one_p(val) ((val) == 1)
00348 #define value_notone_p(val) ((val) != 1)
00349 #define value_mone_p(val) ((val) == -1)
00350 #define value_notmone_p(val) ((val) != -1)
00351 #define value_cmp_si(val, n) (cln::compare(val,n))
00352
00353 #elif defined(GNUMP)
00354
00355
00356
00357 #define value_init(val) (mpz_init((val)))
00358 #define value_assign(v1,v2) (mpz_set((v1),(v2)))
00359 #define value_set_si(val,i) (mpz_set_si((val),(i)))
00360 #define value_set_double(val,d)(mpz_set_d((val),(d)))
00361 #define value_clear(val) (mpz_clear((val)))
00362 #define value_read(val,str) (mpz_set_str((val),(str),10))
00363 typedef void (*value_print_gmp_free_t)(void *, size_t);
00364 #define value_print(Dst,fmt,val) {char *str; \
00365 value_print_gmp_free_t gmp_free; \
00366 str = mpz_get_str(0,10,(val)); \
00367 fprintf((Dst),(fmt),str); \
00368 mp_get_memory_functions(NULL, NULL, &gmp_free); \
00369 (*gmp_free) (str, strlen(str)+1); \
00370 }
00371 #define value_swap(val1,val2) (mpz_swap(val1, val2))
00372
00373
00374
00375 #define value_eq(v1,v2) (mpz_cmp((v1),(v2)) == 0)
00376 #define value_ne(v1,v2) (mpz_cmp((v1),(v2)) != 0)
00377 #define value_gt(v1,v2) (mpz_cmp((v1),(v2)) > 0)
00378 #define value_ge(v1,v2) (mpz_cmp((v1),(v2)) >= 0)
00379 #define value_lt(v1,v2) (mpz_cmp((v1),(v2)) < 0)
00380 #define value_le(v1,v2) (mpz_cmp((v1),(v2)) <= 0)
00381
00382 #define value_abs_eq(v1,v2) (mpz_cmpabs((v1),(v2)) == 0)
00383 #define value_abs_ne(v1,v2) (mpz_cmpabs((v1),(v2)) != 0)
00384 #define value_abs_gt(v1,v2) (mpz_cmpabs((v1),(v2)) > 0)
00385 #define value_abs_ge(v1,v2) (mpz_cmpabs((v1),(v2)) >= 0)
00386 #define value_abs_lt(v1,v2) (mpz_cmpabs((v1),(v2)) < 0)
00387 #define value_abs_le(v1,v2) (mpz_cmpabs((v1),(v2)) <= 0)
00388
00389
00390
00391 #define value_sign(val) (mpz_sgn(val))
00392 #define value_compare(v1,v2) (mpz_cmp((v1),(v2)))
00393
00394
00395
00396 #define value_addto(ref,val1,val2) (mpz_add((ref),(val1),(val2)))
00397 #define value_add_int(ref,val,vint) (mpz_add_ui((ref),(val),(long)(vint)))
00398 #define value_addmul(ref, val1, val2) (mpz_addmul((ref), (val1), (val2)))
00399 #define value_increment(ref,val) (mpz_add_ui((ref),(val),1))
00400 #define value_multiply(ref,val1,val2) (mpz_mul((ref),(val1),(val2)))
00401 #define value_subtract(ref,val1,val2) (mpz_sub((ref),(val1),(val2)))
00402 #define value_sub_int(ref,val,vint) (mpz_sub_ui((ref),(val),(long)(vint)))
00403 #define value_decrement(ref,val) (mpz_sub_ui((ref),(val),1))
00404 #define value_division(ref,val1,val2) (mpz_tdiv_q((ref),(val1),(val2)))
00405 #define value_divexact(ref,val1,val2) (mpz_divexact((ref),(val1),(val2)))
00406 #define value_modulus(ref,val1,val2) (mpz_tdiv_r((ref),(val1),(val2)))
00407 #define value_pdivision(ref,val1,val2) (mpz_fdiv_q((ref),(val1),(val2)))
00408 #define value_pmodulus(ref,val1,val2) (mpz_fdiv_r((ref),(val1),(val2)))
00409 #define value_oppose(ref,val) (mpz_neg((ref),(val)))
00410 #define value_absolute(ref,val) (mpz_abs((ref),(val)))
00411 #define value_minimum(ref,val1,val2) (value_le((val1),(val2)) ? \
00412 mpz_set((ref),(val1)) : \
00413 mpz_set((ref),(val2)))
00414 #define value_maximum(ref,val1,val2) (value_ge((val1),(val2)) ? \
00415 mpz_set((ref),(val1)) : \
00416 mpz_set((ref),(val2)))
00417 #define value_gcd(ref,val1,val2) (mpz_gcd(ref,val1,val2))
00418 #define value_lcm(ref,val1,val2) (mpz_lcm(ref,val1,val2))
00419 #define value_orto(ref,val1,val2) (mpz_ior((ref),(val1),(val2)))
00420 #define value_andto(ref,val1,val2) (mpz_and((ref),(val1),(val2)))
00421
00422
00423
00424 #define value_pos_p(val) (mpz_sgn(val) > 0)
00425 #define value_neg_p(val) (mpz_sgn(val) < 0)
00426 #define value_posz_p(val) (mpz_sgn(val) >= 0)
00427 #define value_negz_p(val) (mpz_sgn(val) <= 0)
00428 #define value_zero_p(val) (mpz_sgn(val) == 0)
00429 #define value_notzero_p(val) (mpz_sgn(val) != 0)
00430 #define value_one_p(val) (mpz_cmp_si(val,1) == 0)
00431 #define value_notone_p(val) (mpz_cmp_si(val,1) != 0)
00432 #define value_mone_p(val) (mpz_cmp_si(val,-1) ==0)
00433 #define value_notmone_p(val) (mpz_cmp_si(val,-1) !=0)
00434 #define value_cmp_si(val, n) (mpz_cmp_si(val,n))
00435
00436
00437
00438 #else
00439
00440
00441 #define value_init(val) ((val) = 0)
00442 #define value_assign(v1,v2) ((v1) = (v2))
00443 #define value_set_si(val,i) ((val) = (Value)(i))
00444 #define value_set_double(val,d) ((val) = (Value)(d))
00445 #define value_clear(val) ((val) = 0)
00446 #define value_read(val,str) (sscanf((str),VALUE_FMT,&(val)))
00447 #define value_print(Dst,fmt,val) (fprintf((Dst),(fmt),(val)))
00448 #define value_swap(v1,v2) {Value tmp; tmp = v2; \
00449 v2 = v1; v1 = tmp; \
00450 }
00451
00452
00453 #define int_to_value(i) ((Value)(i))
00454 #define long_to_value(l) ((Value)(l))
00455 #define float_to_value(f) ((Value)(f))
00456 #define double_to_value(d) ((Value)(d))
00457
00458
00459
00460 #define value_eq(v1,v2) ((v1)==(v2))
00461 #define value_ne(v1,v2) ((v1)!=(v2))
00462 #define value_gt(v1,v2) ((v1)>(v2))
00463 #define value_ge(v1,v2) ((v1)>=(v2))
00464 #define value_lt(v1,v2) ((v1)<(v2))
00465 #define value_le(v1,v2) ((v1)<=(v2))
00466
00467 #define value_abs_eq(v1,v2) (value_abs(v1)==value_abs(v2))
00468 #define value_abs_ne(v1,v2) (value_abs(v1)!=value_abs(v2))
00469 #define value_abs_gt(v1,v2) (value_abs(v1)>value_abs(v2))
00470 #define value_abs_ge(v1,v2) (value_abs(v1)>=value_abs(v2))
00471 #define value_abs_lt(v1,v2) (value_abs(v1)<value_abs(v2))
00472 #define value_abs_le(v1,v2) (value_abs(v1)<=value_abs(v2))
00473
00474
00475
00476 #define value_sign(v) (value_eq(v,VALUE_ZERO)?0:value_lt(v,VALUE_ZERO)?-1:1)
00477 #define value_compare(v1,v2) (value_eq(v1,v2)?0:value_lt(v1,v2)?-1:1)
00478
00479
00480
00481 #define value_plus(v1,v2) ((v1)+(v2))
00482 #define value_div(v1,v2) ((v1)/(v2))
00483 #define value_mod(v1,v2) ((v1)%(v2))
00484 #define value_direct_multiply(v1,v2) ((v1)*(v2))
00485 #define value_minus(v1,v2) ((v1)-(v2))
00486 #define value_pdiv(v1,v2) (DIVIDE((v1),(v2)))
00487 #define value_pmod(v1,v2) (MODULO((v1),(v2)))
00488 #define value_min(v1,v2) (value_le((v1),(v2))? (v1): (v2))
00489 #define value_max(v1,v2) (value_ge((v1),(v2))? (v1): (v2))
00490 #define value_or(v1,v2) ((v1)|(v2))
00491 #define value_and(v1,v2) ((v1)&(v2))
00492 #define value_lshift(v1,v2) ((v1)<<(v2))
00493 #define value_rshift(v1,v2) ((v1)>>(v2))
00494
00495
00496
00497 #define value_addto(ref,val1,val2) ((ref) = (val1)+(val2))
00498 #define value_add_int(ref,val,vint) ((ref) = (val)+(Value)(vint))
00499 #define value_addmul(ref, val1, val2) ((ref) += (val1)*(val2))
00500 #define value_increment(ref,val) ((ref) = (val)+VALUE_ONE)
00501 #define value_direct_product(ref,val1,val2) ((ref) = (val1)*(val2))
00502 #define value_multiply(ref,val1,val2) ((ref) = value_mult((val1),(val2)))
00503 #define value_subtract(ref,val1,val2) ((ref) = (val1)-(val2))
00504 #define value_sub_int(ref,val,vint) ((ref) = (val)-(Value)(vint))
00505 #define value_decrement(ref,val) ((ref) = (val)-VALUE_ONE)
00506 #define value_division(ref,val1,val2) ((ref) = (val1)/(val2))
00507 #define value_divexact(ref,val1,val2) ((ref) = (val1)/(val2))
00508 #define value_modulus(ref,val1,val2) ((ref) = (val1)%(val2))
00509 #define value_pdivision(ref,val1,val2) ((ref) = value_pdiv((val1),(val2)))
00510 #define value_pmodulus(ref,val1,val2) ((ref) = value_pmod((val1),(val2)))
00511 #define value_oppose(ref,val) ((ref) = value_uminus((val)))
00512 #define value_absolute(ref,val) ((ref) = value_abs((val)))
00513 #define value_minimum(ref,val1,val2) ((ref) = value_min((val1),(val2)))
00514 #define value_maximum(ref,val1,val2) ((ref) = value_max((val1),(val2)))
00515 #define value_gcd(ref,val1,val2) Gcd((val1),(val2),&(ref))
00516 #define value_lcm(ref,val1,val2) Lcm3((val1),(val2),&(ref))
00517 #define value_orto(ref,val1,val2) ((ref) = (val1)|(val2))
00518 #define value_andto(ref,val1,val2) ((ref) = (val1)&(val2))
00519
00520
00521
00522 #define value_uminus(val) (-(val))
00523 #define value_not(val) (~(val))
00524 #define value_abs(val) (value_posz_p(val)? \
00525 (val) : \
00526 (value_ne((val), VALUE_NAN) ? \
00527 value_uminus(val) : \
00528 (THROW (overflow_error), VALUE_NAN )))
00529
00530
00531
00532 #define value_pos_p(val) value_gt(val,VALUE_ZERO)
00533 #define value_neg_p(val) value_lt(val,VALUE_ZERO)
00534 #define value_posz_p(val) value_ge(val,VALUE_ZERO)
00535 #define value_negz_p(val) value_le(val,VALUE_ZERO)
00536 #define value_zero_p(val) value_eq(val,VALUE_ZERO)
00537 #define value_notzero_p(val) value_ne(val,VALUE_ZERO)
00538 #define value_one_p(val) value_eq(val,VALUE_ONE)
00539 #define value_notone_p(val) value_ne(val,VALUE_ONE)
00540 #define value_mone_p(val) value_eq(val,VALUE_MONE)
00541 #define value_notmone_p(val) value_ne(val,VALUE_MONE)
00542 #define value_cmp_si(val, n) (val - (n))
00543 #define value_min_p(val) value_eq(val,VALUE_MIN)
00544 #define value_max_p(val) value_eq(val,VALUE_MAX)
00545 #define value_notmin_p(val) value_ne(val,VALUE_MIN)
00546 #define value_notmax_p(val) value_ne(val,VALUE_MAX)
00547
00548 #endif
00549
00550
00551
00552
00553 #include "arithmetic_errors.h"
00554
00555
00556
00557
00558 #define value_protected_hard_idiv_multiply(v,w,throw) \
00559 ((value_zero_p(w) || value_zero_p(v))? VALUE_ZERO: \
00560 value_lt(value_abs(v),value_div(VALUE_MAX,value_abs(w)))? \
00561 value_direct_multiply(v,w): (throw, VALUE_NAN))
00562
00563
00564
00565 #if defined(LINEAR_VALUE_ASSUME_SOFTWARE_IDIV)
00566 #define value_protected_multiply(v,w,throw) \
00567 ((value_le(v,VALUE_SQRT_MAX) && value_le(w,VALUE_SQRT_MAX) && \
00568 value_ge(v,VALUE_SQRT_MIN) && value_ge(w,VALUE_SQRT_MIN))? \
00569 value_direct_multiply(v,w): value_protected_hard_idiv_multiply(v,w,throw))
00570 #else
00571 #define value_protected_multiply(v,w,throw) \
00572 value_protected_hard_idiv_multiply(v,w,throw)
00573 #endif
00574
00575
00576
00577 #define value_protected_mult(v,w) \
00578 value_protected_multiply(v,w,THROW(overflow_error))
00579 #define value_protected_product(v,w) \
00580 v=value_protected_mult(v,w)
00581
00582
00583
00584
00585 #if defined(LINEAR_VALUE_PROTECT_MULTIPLY)
00586 #define value_mult(v,w) value_protected_mult(v,w)
00587 #define value_product(v,w) value_protected_product(v,w)
00588 #else
00589
00590
00591
00592
00593
00594 #define value_mult(v,w) \
00595 value_protected_multiply(v,w, \
00596 (fprintf(stderr,"[value_mult] value overflow!\n"),THROW(overflow_error)))
00597 #define value_product(v,w) v=value_mult(v,w)
00598
00599
00600
00601
00602
00603
00604 #endif
00605
00606
00607
00608
00609
00610
00611
00612 #if defined(LINEAR_VALUE_IS_CHARS)
00613 #define value_fake_binary(v1,v2) ((Value)((v1).i+(v2).i))
00614 #define value_bool_binary(v1,v2) ((int)((v1).i+(v2).i))
00615 #undef float_to_value
00616 #define float_to_value(f) ((Value)f)
00617 #undef double_to_value
00618 #define double_to_value(f) ((Value)f)
00619 #undef value_uminus
00620 #define value_uminus(v) (v)
00621 #undef value_mult
00622 #define value_mult(v1,v2) value_fake_binary(v1,v2)
00623 #undef value_mod
00624 #define value_mod(v1,v2) value_fake_binary(v1,v2)
00625 #undef value_ge
00626 #define value_ge(v1,v2) value_bool_binary(v1,v2)
00627 #undef value_gt
00628 #define value_gt(v1,v2) value_bool_binary(v1,v2)
00629 #undef value_le
00630 #define value_le(v1,v2) value_bool_binary(v1,v2)
00631 #undef value_lt
00632 #define value_lt(v1,v2) value_bool_binary(v1,v2)
00633 #undef value_ne
00634 #define value_ne(v1,v2) value_bool_binary(v1,v2)
00635 #undef value_eq
00636 #define value_eq(v1,v2) value_bool_binary(v1,v2)
00637 #undef value_plus
00638 #define value_plus(v1,v2) value_fake_binary(v1,v2)
00639 #undef value_minus
00640 #define value_minus(v1,v2) value_fake_binary(v1,v2)
00641 #undef value_pdiv
00642 #define value_pdiv(v1,v2) value_fake_binary(v1,v2)
00643 #undef value_div
00644 #define value_div(v1,v2) value_fake_binary(v1,v2)
00645 #undef value_mod
00646 #define value_mod(v1,v2) value_fake_binary(v1,v2)
00647 #undef value_addto
00648 #define value_addto(v1,v2) value_assign(v1,value_plus(v1,v2))
00649 #undef value_subtract
00650 #define value_subtract(v1,v2) value_addto(v1,v2)
00651 #undef value_product
00652 #define value_product(v1,v2) value_addto(v1,v2)
00653 #undef value_modulus
00654 #define value_modulus(v1,v2) value_addto(v1,v2)
00655 #undef value_division
00656 #define value_division(v1,v2) value_addto(v1,v2)
00657 #undef value_divexact
00658 #define value_divexact(v1,v2) value_addto(v1,v2)
00659 #undef value_increment
00660 #define value_increment(v) value_addto(v,VALUE_ONE)
00661 #undef value_decrement
00662 #define value_decrement(v) value_addto(v,VALUE_MONE)
00663 #undef value_orto
00664 #define value_orto(ref,val) value_addto(v1,v2)
00665 #undef value_andto
00666 #define value_andto(ref,val) value_addto(v1,v2)
00667 #undef value_or
00668 #define value_or(v1,v2) value_fake_binary(v1,v2)
00669 #undef value_and
00670 #define value_and(v1,v2) value_fake_binary(v1,v2)
00671 #undef value_lshift
00672 #define value_lshift(v1,v2) value_fake_binary(v1,v2)
00673 #undef value_rshift
00674 #define value_rshift(v1,v2) value_fake_binary(v1,v2)
00675 #endif
00676
00677
00678 #define value_substract(ref,val1,val2) (value_subtract((ref),(val1),(val2)))
00679
00680
00681
00682 #ifndef ABS
00683 #define ABS(x) (((x)>=0) ? (x) : -(x))
00684 #endif
00685
00686
00687
00688
00689
00690 #ifndef MIN
00691 #define MIN(x,y) (((x)>=(y))?(y):(x))
00692 #endif
00693 #ifndef MAX
00694 #define MAX(x,y) (((x)>=(y))?(x):(y))
00695 #endif
00696
00697
00698 #define SIGN(x) (((x)>0)? 1 : ((x)==0? 0 : -1))
00699
00700
00701
00702
00703
00704
00705
00706 #define DIVIDE(x,y) ((y)>0? POSITIVE_DIVIDE(x,y) : \
00707 -POSITIVE_DIVIDE((x),(-(y))))
00708
00709
00710 #define POSITIVE_DIVIDE(x,y) ((x)>0 ? (x)/(y) : - (-(x)+(y)-1)/(y))
00711
00712
00713 #define MODULO(x,y) ((y)>0 ? POSITIVE_MODULO(x,y) : POSITIVE_MODULO(-x,-y))
00714
00715
00716
00717
00718
00719
00720
00721 #define POSITIVE_MODULO(x,y) ((x) > 0 ? (x)%(y) : \
00722 ((x)%(y) == 0 ? 0 : ((y)-(-(x))%(y))))
00723
00724
00725 extern unsigned int overflow_error;
00726 extern unsigned int simplex_arithmetic_error;
00727 extern unsigned int user_exception_error;
00728 extern unsigned int parser_exception_error;
00729 extern unsigned int any_exception_error;
00730 extern unsigned int the_last_just_thrown_exception;
00731 extern void dump_exception_stack_to_file(FILE * );
00732 extern void dump_exception_stack(void);
00733 extern jmp_buf *push_exception_on_stack(int , const char * , const char * , int );
00734 extern void pop_exception_from_stack(int , const char * , const char * , int );
00735 extern void throw_exception(int , const char * , const char * , int );
00736
00737 #endif
00738
00739
00740