arith.h 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123
  1. /* Simple arithmetic for numbers greater than a long int, for GNU tar.
  2. Copyright (C) 1996, 1997 Free Software Foundation, Inc.
  3. This program is free software; you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation; either version 2, or (at your option)
  6. any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program; if not, write to the Free Software Foundation,
  13. Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. */
  14. /* Also, see comments at beginning of arith.c. */
  15. #define BITS_PER_BYTE 8 /* number of bits in each sizeof unit */
  16. #define BITS_PER_TARLONG 42 /* wanted number of bits in each tarlong */
  17. /* In all cases, tarlong is the proper type for a big number.
  18. For simulated arithmetic, SUPERDIGIT is the base, TARLONG_FORMAT is the
  19. format to print a single super-digit filled with zeroes to the left, and
  20. BITS_PER_SUPERDIGIT is the smallest number of bits required to fully
  21. represent each super-digit. LONGS_PER_TARLONG says how many longs are
  22. required for a full tarlong, and SIZEOF_TARLONG is the size of a tarlong
  23. in bytes.
  24. For straight compiler arithmetic, SUPERDIGIT is zero and TARLONG_FORMAT
  25. is the format to directly print a tarlong (without zero-filling).
  26. The values of SIZEOF_LONG_LONG and SIZEOF_UNSIGNED_LONG, below, are
  27. obtained through the configuration process. */
  28. #if BITS_PER_BYTE * SIZEOF_UNSIGNED_LONG >= BITS_PER_TARLONG
  29. # define SUPERDIGIT 0
  30. # define TARLONG_FORMAT "%uld"
  31. typedef unsigned long tarlong;
  32. #else
  33. # if BITS_PER_BYTE * SIZEOF_LONG_LONG >= BITS_PER_TARLONG + 1
  34. # define SUPERDIGIT 0
  35. # define TARLONG_FORMAT "%lld"
  36. typedef long long tarlong;
  37. # else
  38. # if BITS_PER_BYTE * SIZEOF_UNSIGNED_LONG >= 64
  39. # define SUPERDIGIT 1000000000L
  40. # define BITS_PER_SUPERDIGIT 29
  41. # define TARLONG_FORMAT "%09uld"
  42. # else
  43. # if BITS_PER_BYTE * SIZEOF_UNSIGNED_LONG >= 32
  44. # define SUPERDIGIT 10000L
  45. # define BITS_PER_SUPERDIGIT 14
  46. # define TARLONG_FORMAT "%04uld"
  47. # endif
  48. # endif
  49. # endif
  50. #endif
  51. #if SUPERDIGIT
  52. # define LONGS_PER_TARLONG \
  53. ((BITS_PER_TARLONG + BITS_PER_SUPERDIGIT - 1) / BITS_PER_SUPERDIGIT)
  54. # define SIZEOF_TARLONG (LONGS_PER_TARLONG * sizeof (unsigned long))
  55. /* The NEC EWS 4.2 C compiler gets confused by a pointer to a typedef that
  56. is an array. So we wrap the array into a struct. (Pouah!) */
  57. struct tarlong
  58. {
  59. unsigned long digit[LONGS_PER_TARLONG];
  60. };
  61. typedef struct tarlong tarlong;
  62. int zerop_tarlong_helper PARAMS ((unsigned long *));
  63. int lessp_tarlong_helper PARAMS ((unsigned long *, unsigned long *));
  64. void clear_tarlong_helper PARAMS ((unsigned long *));
  65. void add_to_tarlong_helper PARAMS ((unsigned long *, int));
  66. void mult_tarlong_helper PARAMS ((unsigned long *, int));
  67. void print_tarlong_helper PARAMS ((unsigned long *, FILE *));
  68. # define zerop_tarlong(Accumulator) \
  69. zerop_tarlong_helper (&(Accumulator).digit[0])
  70. # define lessp_tarlong(First, Second) \
  71. lessp_tarlong_helper (&(First).digit[0], &(Second).digit[0])
  72. # define clear_tarlong(Accumulator) \
  73. clear_tarlong_helper (&(Accumulator).digit[0])
  74. # define add_to_tarlong(Accumulator, Value) \
  75. add_to_tarlong_helper (&(Accumulator).digit[0], (Value))
  76. # define mult_tarlong(Accumulator, Value) \
  77. mult_tarlong_helper (&(Accumulator).digit[0], (Value))
  78. # define print_tarlong(Accumulator, File) \
  79. print_tarlong_helper (&(Accumulator).digit[0], (File))
  80. #else /* not SUPERDIGIT */
  81. # define zerop_tarlong(Accumulator) \
  82. ((Accumulator) == 0)
  83. # define lessp_tarlong(First, Second) \
  84. ((First) < (Second))
  85. # define clear_tarlong(Accumulator) \
  86. ((Accumulator) = 0)
  87. # define add_to_tarlong(Accumulator, Value) \
  88. ((Accumulator) += (Value))
  89. # define mult_tarlong(Accumulator, Value) \
  90. ((Accumulator) *= (Value))
  91. # define print_tarlong(Accumulator, File) \
  92. (fprintf ((File), TARLONG_FORMAT, (Accumulator)))
  93. #endif /* not SUPERDIGIT */