~ubuntu-branches/ubuntu/utopic/cloog/utopic

« back to all changes in this revision

Viewing changes to osl/source/int.c

  • Committer: Package Import Robot
  • Author(s): Matthias Klose
  • Date: 2014-02-26 14:21:11 UTC
  • mfrom: (3.1.8 sid)
  • Revision ID: package-import@ubuntu.com-20140226142111-vsbb1isby30uundd
Tags: 0.18.2-1
New upstream version.

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
 
2
 
    /*+-----------------------------------------------------------------**
3
 
     **                       OpenScop Library                          **
4
 
     **-----------------------------------------------------------------**
5
 
     **                             int.c                               **
6
 
     **-----------------------------------------------------------------**
7
 
     **                   First version: 18/07/2011                     **
8
 
     **-----------------------------------------------------------------**
9
 
 
10
 
 
11
 
 *****************************************************************************
12
 
 * OpenScop: Structures and formats for polyhedral tools to talk together    *
13
 
 *****************************************************************************
14
 
 *    ,___,,_,__,,__,,__,,__,,_,__,,_,__,,__,,___,_,__,,_,__,                *
15
 
 *    /   / /  //  //  //  // /   / /  //  //   / /  // /  /|,_,             *
16
 
 *   /   / /  //  //  //  // /   / /  //  //   / /  // /  / / /\             *
17
 
 *  |~~~|~|~~~|~~~|~~~|~~~|~|~~~|~|~~~|~~~|~~~|~|~~~|~|~~~|/_/  \            *
18
 
 *  | G |C| P | = | L | P |=| = |C| = | = | = |=| = |=| C |\  \ /\           *
19
 
 *  | R |l| o | = | e | l |=| = |a| = | = | = |=| = |=| L | \# \ /\          *
20
 
 *  | A |a| l | = | t | u |=| = |n| = | = | = |=| = |=| o | |\# \  \         *
21
 
 *  | P |n| l | = | s | t |=| = |d| = | = | = | |   |=| o | | \# \  \        *
22
 
 *  | H | | y |   | e | o | | = |l|   |   | = | |   | | G | |  \  \  \       *
23
 
 *  | I | |   |   | e |   | |   | |   |   |   | |   | |   | |   \  \  \      *
24
 
 *  | T | |   |   |   |   | |   | |   |   |   | |   | |   | |    \  \  \     *
25
 
 *  | E | |   |   |   |   | |   | |   |   |   | |   | |   | |     \  \  \    *
26
 
 *  | * |*| * | * | * | * |*| * |*| * | * | * |*| * |*| * | /      \* \  \   *
27
 
 *  | O |p| e | n | S | c |o| p |-| L | i | b |r| a |r| y |/        \  \ /   *
28
 
 *  '---'-'---'---'---'---'-'---'-'---'---'---'-'---'-'---'          '--'    *
29
 
 *                                                                           *
30
 
 * Copyright (C) 2008 University Paris-Sud 11 and INRIA                      *
31
 
 *                                                                           *
32
 
 * (3-clause BSD license)                                                    *
33
 
 * Redistribution and use in source  and binary forms, with or without       *
34
 
 * modification, are permitted provided that the following conditions        *
35
 
 * are met:                                                                  *
36
 
 *                                                                           *
37
 
 * 1. Redistributions of source code must retain the above copyright notice, *
38
 
 *    this list of conditions and the following disclaimer.                  *
39
 
 * 2. Redistributions in binary form must reproduce the above copyright      *
40
 
 *    notice, this list of conditions and the following disclaimer in the    *
41
 
 *    documentation and/or other materials provided with the distribution.   *
42
 
 * 3. The name of the author may not be used to endorse or promote products  *
43
 
 *    derived from this software without specific prior written permission.  *
44
 
 *                                                                           *
45
 
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR      *
46
 
 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES *
47
 
 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.   *
48
 
 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,          *
49
 
 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT  *
50
 
 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, *
51
 
 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY     *
52
 
 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT       *
53
 
 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF  *
54
 
 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.         *
55
 
 *                                                                           *
56
 
 * OpenScop Library, a library to manipulate OpenScop formats and data       *
57
 
 * structures. Written by:                                                   *
58
 
 * Cedric Bastoul     <Cedric.Bastoul@u-psud.fr> and                         *
59
 
 * Louis-Noel Pouchet <Louis-Noel.pouchet@inria.fr>                          *
60
 
 *                                                                           *
61
 
 *****************************************************************************/
62
 
 
63
 
#include <stdlib.h>
64
 
#include <stdio.h>
65
 
#ifdef OSL_GMP_IS_HERE
66
 
# include <gmp.h>
67
 
#endif
68
 
 
69
 
#include <osl/macros.h>
70
 
#include <osl/int.h>
71
 
 
72
 
 
73
 
/*+***************************************************************************
74
 
 *                                Basic Functions                            *
75
 
 *****************************************************************************/
76
 
 
77
 
 
78
 
/**
79
 
 * osl_int_is_precision_supported function:
80
 
 * this function returns 1 if the precision provided as parameter is supported
81
 
 * by the library and 0 otherwise. Possible values for the precision
82
 
 * parameter are OSL_PRECISION_SP for 32 bits (single) precision,
83
 
 * OSL_PRECISION_DP for 64 bits (double) precision and OSL_PRECISION_MP for
84
 
 * multiple precision.
85
 
 * \param[in] precision The precision to check for.
86
 
 * \return 1 if the precision is supported, 0 otherwise.
87
 
 */
88
 
int osl_int_is_precision_supported(int precision) {
89
 
  switch (precision) {
90
 
    case OSL_PRECISION_SP:
91
 
      return 1;
92
 
    case OSL_PRECISION_DP:
93
 
      return 1;
94
 
#ifdef OSL_GMP_IS_HERE
95
 
    case OSL_PRECISION_MP:
96
 
      return 1;
97
 
#endif
98
 
  }
99
 
 
100
 
  return 0;
101
 
}
102
 
 
103
 
 
104
 
/**
105
 
 * osl_int_dump_precision function:
106
 
 * this function prints in a human readable fashion the precision
107
 
 * corresponding to the "precision" parameter.
108
 
 * \param[in] file      The file where to print the precision.
109
 
 * \param[in] precision The precision to print.
110
 
 */
111
 
void osl_int_dump_precision(FILE * file, int precision) {
112
 
  switch (precision) {
113
 
    case OSL_PRECISION_SP:
114
 
      fprintf(file, "32 bits");
115
 
      break;
116
 
    case OSL_PRECISION_DP:
117
 
      fprintf(file, "64 bits");
118
 
      break;
119
 
#ifdef OSL_GMP_IS_HERE
120
 
    case OSL_PRECISION_MP:
121
 
      fprintf(file, "GMP");
122
 
      break;
123
 
#endif
124
 
    default:
125
 
      fprintf(file, "unknown precision %d", precision);
126
 
  }
127
 
}
128
 
 
129
 
 
130
 
void osl_int_init(int precision, osl_int_p variable) {
131
 
  switch (precision) {
132
 
    case OSL_PRECISION_SP:
133
 
      variable->sp = 0;
134
 
      break;
135
 
 
136
 
    case OSL_PRECISION_DP:
137
 
      variable->dp = 0;
138
 
      break;
139
 
 
140
 
#ifdef OSL_GMP_IS_HERE
141
 
    case OSL_PRECISION_MP:
142
 
      OSL_malloc(variable->mp, void*, sizeof(mpz_t)); 
143
 
      mpz_init(*((mpz_t*)variable->mp));
144
 
      break;
145
 
#endif
146
 
 
147
 
    default:
148
 
      OSL_error("unknown precision");
149
 
  }
150
 
}
151
 
 
152
 
 
153
 
osl_int_p osl_int_malloc(int precision) {
154
 
  osl_int_p variable;
155
 
 
156
 
  OSL_malloc(variable, osl_int_p, sizeof(osl_int_t));
157
 
  osl_int_init(precision, variable);
158
 
  return variable;
159
 
}
160
 
 
161
 
 
162
 
/**
163
 
 * variable = value;
164
 
 */
165
 
void osl_int_assign(int precision, osl_int_p variable, osl_int_t value) {
166
 
  switch (precision) {
167
 
    case OSL_PRECISION_SP:
168
 
      variable->sp = value.sp;
169
 
      break;
170
 
 
171
 
    case OSL_PRECISION_DP:
172
 
      variable->dp = value.dp;
173
 
      break;
174
 
 
175
 
#ifdef OSL_GMP_IS_HERE
176
 
    case OSL_PRECISION_MP:
177
 
      mpz_set(*((mpz_t*)variable->mp), *((mpz_t*)value.mp));
178
 
      break;
179
 
#endif
180
 
 
181
 
    default:
182
 
      OSL_error("unknown precision");
183
 
  }
184
 
}
185
 
 
186
 
 
187
 
/**
188
 
 * variable = i;
189
 
 */
190
 
void osl_int_set_si(int precision, osl_int_p variable, int i) {
191
 
  switch (precision) {
192
 
    case OSL_PRECISION_SP:
193
 
      variable->sp = (long int)i;
194
 
      break;
195
 
 
196
 
    case OSL_PRECISION_DP:
197
 
      variable->dp = (long long int)i;
198
 
      break;
199
 
 
200
 
#ifdef OSL_GMP_IS_HERE
201
 
    case OSL_PRECISION_MP:
202
 
      mpz_set_si(*((mpz_t*)variable->mp), i);
203
 
      break;
204
 
#endif
205
 
 
206
 
    default:
207
 
      OSL_error("unknown precision");
208
 
  }
209
 
}
210
 
 
211
 
 
212
 
/**
213
 
 * return value;
214
 
 */
215
 
int osl_int_get_si(int precision, osl_int_t value) {
216
 
  switch (precision) {
217
 
    case OSL_PRECISION_SP:
218
 
      return value.sp;
219
 
 
220
 
    case OSL_PRECISION_DP:
221
 
      return (int)value.dp;
222
 
 
223
 
#ifdef OSL_GMP_IS_HERE
224
 
    case OSL_PRECISION_MP:
225
 
      return mpz_get_si(*((mpz_t*)value.mp));
226
 
#endif
227
 
 
228
 
    default:
229
 
      OSL_error("unknown precision");
230
 
  }
231
 
}
232
 
 
233
 
 
234
 
/**
235
 
 * variable = i; // including initialization for GMP
236
 
 */
237
 
void osl_int_init_set_si(int precision, osl_int_p variable, int i) {
238
 
  switch (precision) {
239
 
    case OSL_PRECISION_SP:
240
 
      variable->sp = (long int)i;
241
 
      break;
242
 
 
243
 
    case OSL_PRECISION_DP:
244
 
      variable->dp = (long long int)i;
245
 
      break;
246
 
 
247
 
#ifdef OSL_GMP_IS_HERE
248
 
    case OSL_PRECISION_MP:
249
 
      OSL_malloc(variable->mp, void*, sizeof(mpz_t)); 
250
 
      mpz_init_set_si(*((mpz_t*)variable->mp), i);
251
 
      break;
252
 
#endif
253
 
 
254
 
    default:
255
 
      OSL_error("unknown precision");
256
 
  }
257
 
}
258
 
 
259
 
 
260
 
/**
261
 
 * var1 <=> var2;
262
 
 */
263
 
void osl_int_swap(int precision, osl_int_p var1, osl_int_p var2) {
264
 
  switch (precision) {
265
 
    case OSL_PRECISION_SP: {
266
 
      long int temp = var1->sp;
267
 
      var1->sp = var2->sp;
268
 
      var2->sp = temp;
269
 
      break;
270
 
    }
271
 
 
272
 
    case OSL_PRECISION_DP: {
273
 
      long long int temp = var1->dp;
274
 
      var1->dp = var2->dp;
275
 
      var2->dp = temp;
276
 
      break;
277
 
    }
278
 
 
279
 
#ifdef OSL_GMP_IS_HERE
280
 
    case OSL_PRECISION_MP: {
281
 
      mpz_t temp;
282
 
      mpz_init(temp);
283
 
      mpz_set(temp, *((mpz_t*)var1->mp));
284
 
      mpz_set(*((mpz_t*)var1->mp), *((mpz_t*)var2->mp));
285
 
      mpz_set(*((mpz_t*)var2->mp), temp);
286
 
      mpz_clear(temp);
287
 
      break;
288
 
    }
289
 
#endif
290
 
 
291
 
    default:
292
 
      OSL_error("unknown precision");
293
 
  }
294
 
}
295
 
 
296
 
 
297
 
/**
298
 
 * variable = 0; // Including cleaning for GMP
299
 
 */
300
 
void osl_int_clear(int precision, osl_int_p variable) {
301
 
  switch (precision) {
302
 
    case OSL_PRECISION_SP:
303
 
      variable->sp = 0;
304
 
      break;
305
 
 
306
 
    case OSL_PRECISION_DP:
307
 
      variable->dp = 0;
308
 
      break;
309
 
 
310
 
#ifdef OSL_GMP_IS_HERE
311
 
    case OSL_PRECISION_MP:
312
 
      mpz_clear(*((mpz_t*)variable->mp));
313
 
      free(variable->mp);
314
 
      break;
315
 
#endif
316
 
 
317
 
    default:
318
 
      OSL_error("unknown precision");
319
 
  }
320
 
}
321
 
 
322
 
 
323
 
void osl_int_free(int precision, osl_int_p variable) {
324
 
  osl_int_clear(precision, variable);
325
 
  free(variable);
326
 
}
327
 
 
328
 
 
329
 
/**
330
 
 * osl_int_print function:
331
 
 * this function displays an integer value into a file (file, possibly stdout).
332
 
 * \param file      The file where the integer has to be printed.
333
 
 * \param precision The precision of the integer.
334
 
 * \param value     The integer element to print.
335
 
 */
336
 
void osl_int_print(FILE * file, int precision, osl_int_t value) {
337
 
  char string[OSL_MAX_STRING];
338
 
  
339
 
  osl_int_sprint(string, precision, value);
340
 
  fprintf(file, "%s", string);
341
 
}
342
 
 
343
 
 
344
 
/**
345
 
 * osl_int_sprint function:
346
 
 * this function prints an integer value into a string, it uses the
347
 
 * OpenScop Library formats OSL_FMT_* to format the printing.
348
 
 * \param string    The string where the integer has to be printed.
349
 
 * \param precision The precision of the integer.
350
 
 * \param value     The integer element to print.
351
 
 */
352
 
void osl_int_sprint(char * string, int precision, osl_int_t value) {
353
 
  switch (precision) {
354
 
    case OSL_PRECISION_SP:
355
 
      sprintf(string, OSL_FMT_SP, value.sp);
356
 
      break;
357
 
 
358
 
    case OSL_PRECISION_DP:
359
 
      sprintf(string, OSL_FMT_DP, value.dp);
360
 
      break;
361
 
 
362
 
#ifdef OSL_GMP_IS_HERE
363
 
    case OSL_PRECISION_MP: {
364
 
      char * str;
365
 
      str = mpz_get_str(0, 10, *((mpz_t*)value.mp)); //TODO: 10 -> #define
366
 
      sprintf(string, OSL_FMT_MP, str);
367
 
      free(str);
368
 
      break;
369
 
    }
370
 
#endif
371
 
 
372
 
    default:
373
 
      OSL_error("unknown precision");
374
 
  }
375
 
}
376
 
 
377
 
 
378
 
/**
379
 
 * osl_int_sprint_txt function:
380
 
 * this function is similar to osl_int_sprintf but it prints the value
381
 
 * using OSL_TMT_TXT_* formats.
382
 
 * \see osl_int_sprintf
383
 
 */
384
 
void osl_int_sprint_txt(char * string, int precision, osl_int_t value) {
385
 
  switch (precision) {
386
 
    case OSL_PRECISION_SP:
387
 
      sprintf(string, OSL_FMT_TXT_SP, value.sp);
388
 
      break;
389
 
 
390
 
    case OSL_PRECISION_DP:
391
 
      sprintf(string, OSL_FMT_TXT_DP, value.dp);
392
 
      break;
393
 
 
394
 
#ifdef OSL_GMP_IS_HERE
395
 
    case OSL_PRECISION_MP: {
396
 
      char * str;
397
 
      str = mpz_get_str(0, 10, *((mpz_t*)value.mp)); //TODO: 10 -> #define
398
 
      sprintf(string, OSL_FMT_TXT_MP, str);
399
 
      free(str);
400
 
      break;
401
 
    }
402
 
#endif
403
 
 
404
 
    default:
405
 
      OSL_error("unknown precision");
406
 
  }
407
 
}
408
 
 
409
 
 
410
 
void osl_int_sread(char ** string, int precision, osl_int_p variable) {
411
 
  int nb_read = 0;
412
 
 
413
 
  switch (precision) {
414
 
    case OSL_PRECISION_SP:
415
 
      nb_read = sscanf(*string, OSL_FMT_TXT_SP, &(variable->sp));
416
 
      if (nb_read == 0)
417
 
        OSL_error("failed to read an integer");
418
 
      break;
419
 
 
420
 
    case OSL_PRECISION_DP:
421
 
      nb_read = sscanf(*string, OSL_FMT_TXT_DP, &(variable->dp));
422
 
      if (nb_read == 0)
423
 
        OSL_error("failed to read an integer");
424
 
      break;
425
 
 
426
 
#ifdef OSL_GMP_IS_HERE
427
 
    case OSL_PRECISION_MP: {
428
 
      long long int tmp;
429
 
      nb_read = sscanf(*string, OSL_FMT_TXT_DP, &tmp);
430
 
      if (nb_read == 0)
431
 
        OSL_error("failed to read an integer");
432
 
      mpz_set_si(*((mpz_t*)variable->mp), tmp);
433
 
      break;
434
 
    }
435
 
#endif
436
 
 
437
 
    default:
438
 
      OSL_error("unknown precision");
439
 
  }
440
 
 
441
 
  // Update the position in the input string.
442
 
  *string = *string + nb_read;
443
 
}
444
 
 
445
 
 
446
 
/*+***************************************************************************
447
 
 *                            Arithmetic Operations                          *
448
 
 *****************************************************************************/
449
 
 
450
 
 
451
 
/**
452
 
 * variable <- value + 1;
453
 
 */
454
 
void osl_int_increment(int precision, osl_int_p variable, osl_int_t value) {
455
 
  switch (precision) {
456
 
    case OSL_PRECISION_SP:
457
 
      variable->sp = value.sp + 1;
458
 
      break;
459
 
 
460
 
    case OSL_PRECISION_DP:
461
 
      variable->dp = value.dp + (long long int)1;
462
 
      break;
463
 
 
464
 
#ifdef OSL_GMP_IS_HERE
465
 
    case OSL_PRECISION_MP:
466
 
      mpz_add_ui(*((mpz_t*)variable->mp), *((mpz_t*)value.mp), 1);
467
 
      break;
468
 
#endif
469
 
 
470
 
    default:
471
 
      OSL_error("unknown precision");
472
 
  }
473
 
}
474
 
 
475
 
 
476
 
/**
477
 
 * variable <- value - 1;
478
 
 */
479
 
void osl_int_decrement(int precision, osl_int_p variable, osl_int_t value) {
480
 
  switch (precision) {
481
 
    case OSL_PRECISION_SP:
482
 
      variable->sp = value.sp - 1;
483
 
      break;
484
 
 
485
 
    case OSL_PRECISION_DP:
486
 
      variable->dp = value.dp - (long long int)1;
487
 
      break;
488
 
 
489
 
#ifdef OSL_GMP_IS_HERE
490
 
    case OSL_PRECISION_MP: {
491
 
      mpz_t one;
492
 
      mpz_init_set_si(one, 1);
493
 
      mpz_sub(*((mpz_t*)variable->mp), *((mpz_t*)value.mp), one);
494
 
      mpz_clear(one);
495
 
      break;
496
 
    }
497
 
#endif
498
 
 
499
 
    default:
500
 
      OSL_error("unknown precision");
501
 
  }
502
 
}
503
 
 
504
 
 
505
 
/**
506
 
 * variable <- val1 + val2;
507
 
 */
508
 
void osl_int_add(int precision,
509
 
                 osl_int_p variable, osl_int_t val1, osl_int_t val2) {
510
 
  switch (precision) {
511
 
    case OSL_PRECISION_SP:
512
 
      variable->sp = val1.sp + val2.sp;
513
 
      break;
514
 
 
515
 
    case OSL_PRECISION_DP:
516
 
      variable->dp = val1.dp + val2.dp;
517
 
      break;
518
 
 
519
 
#ifdef OSL_GMP_IS_HERE
520
 
    case OSL_PRECISION_MP:
521
 
      mpz_add(*((mpz_t*)variable->mp), *((mpz_t*)val1.mp), *((mpz_t*)val2.mp));
522
 
      break;
523
 
#endif
524
 
 
525
 
    default:
526
 
      OSL_error("unknown precision");
527
 
  }
528
 
}
529
 
 
530
 
 
531
 
/**
532
 
 * variable <- value + i;
533
 
 */
534
 
void osl_int_add_si(int precision,
535
 
                    osl_int_p variable, osl_int_t value, int i) {
536
 
  switch (precision) {
537
 
    case OSL_PRECISION_SP:
538
 
      variable->sp = value.sp + (long int)i;
539
 
      break;
540
 
 
541
 
    case OSL_PRECISION_DP:
542
 
      variable->dp = value.dp + (long long int)i;
543
 
      break;
544
 
 
545
 
#ifdef OSL_GMP_IS_HERE
546
 
    case OSL_PRECISION_MP: {
547
 
      mpz_t si;
548
 
      mpz_init_set_si(si, i);
549
 
      mpz_add(*((mpz_t*)variable->mp), *((mpz_t*)value.mp), si);
550
 
      mpz_clear(si);
551
 
      break;
552
 
    }
553
 
#endif
554
 
 
555
 
    default:
556
 
      OSL_error("unknown precision");
557
 
  }
558
 
}
559
 
 
560
 
 
561
 
/**
562
 
 * variable <- val1 * val2;
563
 
 */
564
 
void osl_int_mul(int precision,
565
 
                 osl_int_p variable, osl_int_t val1, osl_int_t val2) {
566
 
  switch (precision) {
567
 
    case OSL_PRECISION_SP:
568
 
      variable->sp = val1.sp * val2.sp;
569
 
      break;
570
 
 
571
 
    case OSL_PRECISION_DP:
572
 
      variable->dp = val1.dp * val2.dp;
573
 
      break;
574
 
 
575
 
#ifdef OSL_GMP_IS_HERE
576
 
    case OSL_PRECISION_MP:
577
 
      mpz_mul(*((mpz_t*)variable->mp), *((mpz_t*)val1.mp), *((mpz_t*)val2.mp));
578
 
      break;
579
 
#endif
580
 
 
581
 
    default:
582
 
      OSL_error("unknown precision");
583
 
  }
584
 
}
585
 
 
586
 
 
587
 
/**
588
 
 * variable <- value * i;
589
 
 */
590
 
void osl_int_mul_si(int precision,
591
 
                    osl_int_p variable, osl_int_t value, int i) {
592
 
  switch (precision) {
593
 
    case OSL_PRECISION_SP:
594
 
      variable->sp = value.sp * (long int)i;
595
 
      break;
596
 
 
597
 
    case OSL_PRECISION_DP:
598
 
      variable->dp = value.dp * (long long int)i;
599
 
      break;
600
 
 
601
 
#ifdef OSL_GMP_IS_HERE
602
 
    case OSL_PRECISION_MP:
603
 
      mpz_mul_si(*((mpz_t*)variable->mp), *((mpz_t*)value.mp), i);
604
 
      break;
605
 
#endif
606
 
 
607
 
    default:
608
 
      OSL_error("unknown precision");
609
 
  }
610
 
}
611
 
 
612
 
 
613
 
/**
614
 
 * variable <- val1 - val2;
615
 
 */
616
 
void osl_int_sub(int precision,
617
 
                 osl_int_p variable, osl_int_t val1, osl_int_t val2) {
618
 
  switch (precision) {
619
 
    case OSL_PRECISION_SP:
620
 
      variable->sp = val1.sp - val2.sp;
621
 
      break;
622
 
 
623
 
    case OSL_PRECISION_DP:
624
 
      variable->dp = val1.dp - val2.dp;
625
 
      break;
626
 
 
627
 
#ifdef OSL_GMP_IS_HERE
628
 
    case OSL_PRECISION_MP:
629
 
      mpz_sub(*((mpz_t*)variable->mp), *((mpz_t*)val1.mp), *((mpz_t*)val2.mp));
630
 
      break;
631
 
#endif
632
 
 
633
 
    default:
634
 
      OSL_error("unknown precision");
635
 
  }
636
 
}
637
 
 
638
 
 
639
 
/**
640
 
 * variable <- -value;
641
 
 */
642
 
void osl_int_oppose(int precision, osl_int_p variable, osl_int_t value) {
643
 
  switch (precision) {
644
 
    case OSL_PRECISION_SP:
645
 
      variable->sp = -value.sp;
646
 
      break;
647
 
 
648
 
    case OSL_PRECISION_DP:
649
 
      variable->dp = -value.dp;
650
 
      break;
651
 
 
652
 
#ifdef OSL_GMP_IS_HERE
653
 
    case OSL_PRECISION_MP:
654
 
      mpz_neg(*((mpz_t*)variable->mp), *((mpz_t*)value.mp));
655
 
      break;
656
 
#endif
657
 
 
658
 
    default:
659
 
      OSL_error("unknown precision");
660
 
  }
661
 
}
662
 
 
663
 
 
664
 
/**
665
 
 * variable <- | value |;
666
 
 */
667
 
void osl_int_abs(int precision, osl_int_p variable, osl_int_t value) {
668
 
  switch (precision) {
669
 
    case OSL_PRECISION_SP:
670
 
      variable->sp = (value.sp > 0) ? value.sp : -value.sp;
671
 
      break;
672
 
 
673
 
    case OSL_PRECISION_DP:
674
 
      variable->dp = (value.dp > 0) ? value.dp : -value.dp;
675
 
      break;
676
 
 
677
 
#ifdef OSL_GMP_IS_HERE
678
 
    case OSL_PRECISION_MP:
679
 
      mpz_abs(*((mpz_t*)variable->mp), *((mpz_t*)value.mp));
680
 
      break;
681
 
#endif
682
 
 
683
 
    default:
684
 
      OSL_error("unknown precision");
685
 
  }
686
 
}
687
 
 
688
 
 
689
 
/*+***************************************************************************
690
 
 *                            Conditional Operations                         *
691
 
 *****************************************************************************/
692
 
 
693
 
 
694
 
/**
695
 
 * (val1 == val2)
696
 
 */
697
 
int osl_int_eq(int precision, osl_int_t val1, osl_int_t val2) {
698
 
  switch (precision) {
699
 
    case OSL_PRECISION_SP:
700
 
      return (val1.sp == val2.sp);
701
 
 
702
 
    case OSL_PRECISION_DP:
703
 
      return (val1.dp == val2.dp);
704
 
 
705
 
#ifdef OSL_GMP_IS_HERE
706
 
    case OSL_PRECISION_MP:
707
 
      return (mpz_cmp(*((mpz_t*)val1.mp), *((mpz_t*)val2.mp)) == 0);
708
 
#endif
709
 
 
710
 
    default:
711
 
      OSL_error("unknown precision");
712
 
  }
713
 
}
714
 
 
715
 
 
716
 
/**
717
 
 * (val1 != val2)
718
 
 */
719
 
int osl_int_ne(int precision, osl_int_t val1, osl_int_t val2) {
720
 
  return !osl_int_eq(precision, val1, val2);
721
 
}
722
 
 
723
 
 
724
 
/**
725
 
 * (value > 0)
726
 
 */
727
 
int osl_int_pos(int precision, osl_int_t value) {
728
 
  switch (precision) {
729
 
    case OSL_PRECISION_SP:
730
 
      return (value.sp > 0);
731
 
 
732
 
    case OSL_PRECISION_DP:
733
 
      return (value.dp > 0);
734
 
 
735
 
#ifdef OSL_GMP_IS_HERE
736
 
    case OSL_PRECISION_MP:
737
 
      return (mpz_sgn(*((mpz_t*)value.mp)) > 0);
738
 
#endif
739
 
 
740
 
    default:
741
 
      OSL_error("unknown precision");
742
 
  }
743
 
}
744
 
 
745
 
 
746
 
/**
747
 
 * (value < 0)
748
 
 */
749
 
int osl_int_neg(int precision, osl_int_t value) {
750
 
  switch (precision) {
751
 
    case OSL_PRECISION_SP:
752
 
      return (value.sp < 0);
753
 
 
754
 
    case OSL_PRECISION_DP:
755
 
      return (value.dp < 0);
756
 
 
757
 
#ifdef OSL_GMP_IS_HERE
758
 
    case OSL_PRECISION_MP:
759
 
      return (mpz_sgn(*((mpz_t*)value.mp)) < 0);
760
 
#endif
761
 
 
762
 
    default:
763
 
      OSL_error("unknown precision");
764
 
  }
765
 
}
766
 
 
767
 
 
768
 
/**
769
 
 * (value == 0)
770
 
 */
771
 
int osl_int_zero(int precision, osl_int_t value) {
772
 
  switch (precision) {
773
 
    case OSL_PRECISION_SP:
774
 
      return (value.sp == 0);
775
 
 
776
 
    case OSL_PRECISION_DP:
777
 
      return (value.dp == 0);
778
 
 
779
 
#ifdef OSL_GMP_IS_HERE
780
 
    case OSL_PRECISION_MP:
781
 
      return (mpz_sgn(*((mpz_t*)value.mp)) == 0);
782
 
#endif
783
 
 
784
 
    default:
785
 
      OSL_error("unknown precision");
786
 
  }
787
 
}
788
 
 
789
 
 
790
 
/**
791
 
 * (value == 1)
792
 
 */
793
 
int osl_int_one(int precision, osl_int_t value) {
794
 
  switch (precision) {
795
 
    case OSL_PRECISION_SP:
796
 
      return (value.sp == (long int)1);
797
 
 
798
 
    case OSL_PRECISION_DP:
799
 
      return (value.dp == (long long int)1);
800
 
 
801
 
#ifdef OSL_GMP_IS_HERE
802
 
    case OSL_PRECISION_MP:
803
 
      return (mpz_cmp_si(*((mpz_t*)value.mp), 1) == 0);
804
 
#endif
805
 
 
806
 
    default:
807
 
      OSL_error("unknown precision");
808
 
  }
809
 
}
810
 
 
811
 
 
812
 
/**
813
 
 * (value == -1)
814
 
 */
815
 
int osl_int_mone(int precision, osl_int_t value) {
816
 
  switch (precision) {
817
 
    case OSL_PRECISION_SP:
818
 
      return (value.sp == (long int)-1);
819
 
 
820
 
    case OSL_PRECISION_DP:
821
 
      return (value.dp == (long long int)-1);
822
 
 
823
 
#ifdef OSL_GMP_IS_HERE
824
 
    case OSL_PRECISION_MP:
825
 
      return (mpz_cmp_si(*((mpz_t*)value.mp), -1) == 0);
826
 
#endif
827
 
 
828
 
    default:
829
 
      OSL_error("unknown precision");
830
 
  }
831
 
}
832
 
 
833
 
 
834
 
/**
835
 
 * ((val1 % val2) == 0)
836
 
 */
837
 
int osl_int_divisible(int precision, osl_int_t val1, osl_int_t val2) {
838
 
  switch (precision) {
839
 
    case OSL_PRECISION_SP:
840
 
      return ((val1.sp % val2.sp) == 0);
841
 
 
842
 
    case OSL_PRECISION_DP:
843
 
      return ((val1.dp % val2.dp) == 0);
844
 
 
845
 
#ifdef OSL_GMP_IS_HERE
846
 
    case OSL_PRECISION_MP:
847
 
      return mpz_divisible_p(*((mpz_t*)val1.mp), *((mpz_t*)val2.mp));
848
 
#endif
849
 
 
850
 
    default:
851
 
      OSL_error("unknown precision");
852
 
  }
853
 
}