~drizzle-trunk/drizzle/development

« back to all changes in this revision

Viewing changes to drizzled/decimal.cc

  • Committer: Monty Taylor
  • Date: 2010-10-13 17:53:36 UTC
  • mto: This revision was merged to the branch mainline in revision 1845.
  • Revision ID: mordred@inaugust.com-20101013175336-amzhjftgztblvua5
Updated pandora-build files to version 0.161

Show diffs side-by-side

added added

removed removed

Lines of Context:
209
209
    fixed_prec will be 0, and my_decimal_string_length() will be called
210
210
    instead to calculate the required size of the buffer.
211
211
  */
212
 
  int length= (int)(fixed_prec
213
 
                    ? (uint32_t)(fixed_prec + ((fixed_prec == fixed_dec) ? 1 : 0) + 1)
214
 
                    : (uint32_t)my_decimal_string_length(d));
 
212
  int length= (fixed_prec
 
213
               ? (fixed_prec + ((fixed_prec == fixed_dec) ? 1 : 0) + 1)
 
214
               : my_decimal_string_length(d));
215
215
  int result;
216
216
  if (str->alloc(length))
217
217
    return check_result(mask, E_DEC_OOM);
363
363
#define DIG_MASK     100000000
364
364
#define DIG_BASE     1000000000
365
365
#define DIG_MAX      (DIG_BASE-1)
366
 
 
367
 
template<typename T> 
368
 
inline static T round_up(const T &x)
369
 
{
370
 
  return (x+DIG_PER_DEC1-1)/DIG_PER_DEC1;
371
 
}
372
 
 
 
366
#define ROUND_UP(X)  (((X)+DIG_PER_DEC1-1)/DIG_PER_DEC1)
373
367
static const dec1 powers10[DIG_PER_DEC1+1]={
374
368
  1, 10, 100, 1000, 10000, 100000, 1000000, 10000000, 100000000, 1000000000};
375
369
static const int dig2bytes[DIG_PER_DEC1+1]={0, 1, 1, 2, 2, 3, 3, 4, 4, 4};
378
372
  999900000, 999990000, 999999000,
379
373
  999999900, 999999990 };
380
374
 
381
 
#ifdef HAVE_VALGRIND
 
375
#ifdef HAVE_purify
382
376
#define sanity(d) assert((d)->len > 0)
383
377
#else
384
378
#define sanity(d) assert((d)->len >0 && ((d)->buf[0] | \
385
379
                              (d)->buf[(d)->len-1] | 1))
386
380
#endif
387
381
 
388
 
inline static void fix_intg_frac_error(const int len, int &intg1, int &frac1, int &error)
389
 
{
390
 
  if (unlikely(intg1+frac1 > len))
391
 
  {
392
 
    if (unlikely(intg1 > len))
393
 
    {
394
 
      intg1=(len);
395
 
      frac1=0;
396
 
      error=E_DEC_OVERFLOW;
397
 
    }
398
 
    else
399
 
    {
400
 
      frac1=(len)-intg1;
401
 
      error=E_DEC_TRUNCATED;
402
 
    }
403
 
  }
404
 
  else
405
 
    error=E_DEC_OK;
406
 
}
407
 
 
408
 
/* assume carry <= 1 */
409
 
inline static void add(dec1 &to, const dec1 &from1, const dec1& from2, dec1 &carry)
410
 
{
411
 
  dec1 a=from1+from2+carry;
412
 
  assert(carry <= 1);
413
 
  if ((carry= (a >= DIG_BASE))) /* no division here! */
414
 
    a-=DIG_BASE;
415
 
  to=a;
416
 
}
417
 
 
418
 
inline static void add2(dec1 &to, const dec1 &from1, const dec1 &from2, dec1 &carry)
419
 
{
420
 
  dec2 a=dec2(from1)+from2+carry;
421
 
  if ((carry= (a >= DIG_BASE)))
422
 
    a-=DIG_BASE;
423
 
  if (unlikely(a >= DIG_BASE))
424
 
  {
425
 
    a-=DIG_BASE;
426
 
    carry++;
427
 
  }
428
 
  to=dec1(a);
429
 
}
430
 
 
431
 
/* to=from1-from2 */
432
 
inline static void sub(dec1 &to, const dec1 &from1, const dec1 &from2, dec1 &carry)
433
 
{
434
 
  dec1 a=from1-from2-carry;
435
 
  if ((carry= (a < 0)))
436
 
    a+=DIG_BASE;
437
 
  to=a;
438
 
}
439
 
 
440
 
/* to=from1-from2 */
441
 
inline static void sub2(dec1 &to, const dec1 &from1, const dec1 &from2, dec1 &carry)
442
 
{
443
 
  dec1 a=from1-from2-carry;
444
 
  if ((carry= (a < 0)))
445
 
    a+=DIG_BASE;
446
 
  if (unlikely(a < 0))
447
 
  {
448
 
    a+=DIG_BASE;
449
 
    carry++;
450
 
  }
451
 
  to=a;
452
 
}
 
382
#define FIX_INTG_FRAC_ERROR(len, intg1, frac1, error)                   \
 
383
        do                                                              \
 
384
        {                                                               \
 
385
          if (unlikely(intg1+frac1 > (len)))                            \
 
386
          {                                                             \
 
387
            if (unlikely(intg1 > (len)))                                \
 
388
            {                                                           \
 
389
              intg1=(len);                                              \
 
390
              frac1=0;                                                  \
 
391
              error=E_DEC_OVERFLOW;                                     \
 
392
            }                                                           \
 
393
            else                                                        \
 
394
            {                                                           \
 
395
              frac1=(len)-intg1;                                        \
 
396
              error=E_DEC_TRUNCATED;                                    \
 
397
            }                                                           \
 
398
          }                                                             \
 
399
          else                                                          \
 
400
            error=E_DEC_OK;                                             \
 
401
        } while(0)
 
402
 
 
403
#define ADD(to, from1, from2, carry)  /* assume carry <= 1 */           \
 
404
        do                                                              \
 
405
        {                                                               \
 
406
          dec1 a=(from1)+(from2)+(carry);                               \
 
407
          assert((carry) <= 1);                                    \
 
408
          if (((carry)= a >= DIG_BASE)) /* no division here! */         \
 
409
            a-=DIG_BASE;                                                \
 
410
          (to)=a;                                                       \
 
411
        } while(0)
 
412
 
 
413
#define ADD2(to, from1, from2, carry)                                   \
 
414
        do                                                              \
 
415
        {                                                               \
 
416
          dec2 a=((dec2)(from1))+(from2)+(carry);                       \
 
417
          if (((carry)= a >= DIG_BASE))                                 \
 
418
            a-=DIG_BASE;                                                \
 
419
          if (unlikely(a >= DIG_BASE))                                  \
 
420
          {                                                             \
 
421
            a-=DIG_BASE;                                                \
 
422
            carry++;                                                    \
 
423
          }                                                             \
 
424
          (to)=(dec1) a;                                                \
 
425
        } while(0)
 
426
 
 
427
#define SUB(to, from1, from2, carry) /* to=from1-from2 */               \
 
428
        do                                                              \
 
429
        {                                                               \
 
430
          dec1 a=(from1)-(from2)-(carry);                               \
 
431
          if (((carry)= a < 0))                                         \
 
432
            a+=DIG_BASE;                                                \
 
433
          (to)=a;                                                       \
 
434
        } while(0)
 
435
 
 
436
#define SUB2(to, from1, from2, carry) /* to=from1-from2 */              \
 
437
        do                                                              \
 
438
        {                                                               \
 
439
          dec1 a=(from1)-(from2)-(carry);                               \
 
440
          if (((carry)= a < 0))                                         \
 
441
            a+=DIG_BASE;                                                \
 
442
          if (unlikely(a < 0))                                          \
 
443
          {                                                             \
 
444
            a+=DIG_BASE;                                                \
 
445
            carry++;                                                    \
 
446
          }                                                             \
 
447
          (to)=a;                                                       \
 
448
        } while(0)
 
449
 
 
450
/**
 
451
  Swap the contents of two variables.
 
452
 */
 
453
#define swap_variables(TYPE, a, b) \
 
454
  do {                             \
 
455
    TYPE dummy;                    \
 
456
    dummy= a;                      \
 
457
    a= b;                          \
 
458
    b= dummy;                      \
 
459
  } while (0)
 
460
 
 
461
 
453
462
 
454
463
/**
455
464
  @brief  Get maximum value for given precision and scale
518
527
int decimal_actual_fraction(decimal_t *from)
519
528
{
520
529
  int frac= from->frac, i;
521
 
  dec1 *buf0= from->buf + round_up(from->intg) + round_up(frac) - 1;
 
530
  dec1 *buf0= from->buf + ROUND_UP(from->intg) + ROUND_UP(frac) - 1;
522
531
 
523
532
  if (frac == 0)
524
533
    return 0;
623
632
  {
624
633
    char *s1= s + intg_len;
625
634
    fill= frac_len - frac;
626
 
    buf=buf0+round_up(intg);
 
635
    buf=buf0+ROUND_UP(intg);
627
636
    *s1++='.';
628
637
    for (; frac>0; frac-=DIG_PER_DEC1)
629
638
    {
648
657
  if (intg)
649
658
  {
650
659
    s+=intg;
651
 
    for (buf=buf0+round_up(intg); intg>0; intg-=DIG_PER_DEC1)
 
660
    for (buf=buf0+ROUND_UP(intg); intg>0; intg-=DIG_PER_DEC1)
652
661
    {
653
662
      dec1 x=*--buf;
654
663
      for (i=min(intg, DIG_PER_DEC1); i; i--)
678
687
{
679
688
  int start, stop, i;
680
689
  dec1 *buf_beg= from->buf;
681
 
  dec1 *end= from->buf + round_up(from->intg) + round_up(from->frac);
 
690
  dec1 *end= from->buf + ROUND_UP(from->intg) + ROUND_UP(from->frac);
682
691
  dec1 *buf_end= end - 1;
683
692
 
684
693
  /* find non-zero digit from number begining */
744
753
*/
745
754
static void do_mini_left_shift(decimal_t *dec, int shift, int beg, int last)
746
755
{
747
 
  dec1 *from= dec->buf + round_up(beg + 1) - 1;
748
 
  dec1 *end= dec->buf + round_up(last) - 1;
 
756
  dec1 *from= dec->buf + ROUND_UP(beg + 1) - 1;
 
757
  dec1 *end= dec->buf + ROUND_UP(last) - 1;
749
758
  int c_shift= DIG_PER_DEC1 - shift;
750
759
  assert(from >= dec->buf);
751
760
  assert(end < dec->buf + dec->len);
772
781
*/
773
782
static void do_mini_right_shift(decimal_t *dec, int shift, int beg, int last)
774
783
{
775
 
  dec1 *from= dec->buf + round_up(last) - 1;
776
 
  dec1 *end= dec->buf + round_up(beg + 1) - 1;
 
784
  dec1 *from= dec->buf + ROUND_UP(last) - 1;
 
785
  dec1 *end= dec->buf + ROUND_UP(beg + 1) - 1;
777
786
  int c_shift= DIG_PER_DEC1 - shift;
778
787
  assert(from < dec->buf + dec->len);
779
788
  assert(end >= dec->buf);
809
818
  /* index of position after last decimal digit */
810
819
  int end;
811
820
  /* index of digit position just after point */
812
 
  int point= round_up(dec->intg) * DIG_PER_DEC1;
 
821
  int point= ROUND_UP(dec->intg) * DIG_PER_DEC1;
813
822
  /* new point position */
814
823
  int new_point= point + shift;
815
824
  /* number of digits in result */
836
845
  digits_frac= end - new_point;
837
846
  set_if_bigger(digits_frac, 0);
838
847
 
839
 
  if ((new_len= round_up(digits_int) + (new_frac_len= round_up(digits_frac))) >
 
848
  if ((new_len= ROUND_UP(digits_int) + (new_frac_len= ROUND_UP(digits_frac))) >
840
849
      dec->len)
841
850
  {
842
851
    int lack= new_len - dec->len;
896
905
    if (do_left)
897
906
    {
898
907
      do_mini_left_shift(dec, l_mini_shift, beg, end);
899
 
      mini_shift= (-l_mini_shift);
 
908
      mini_shift=- l_mini_shift;
900
909
    }
901
910
    else
902
911
    {
929
938
    {
930
939
      /* move left */
931
940
      d_shift= new_front / DIG_PER_DEC1;
932
 
      to= dec->buf + (round_up(beg + 1) - 1 - d_shift);
933
 
      barier= dec->buf + (round_up(end) - 1 - d_shift);
 
941
      to= dec->buf + (ROUND_UP(beg + 1) - 1 - d_shift);
 
942
      barier= dec->buf + (ROUND_UP(end) - 1 - d_shift);
934
943
      assert(to >= dec->buf);
935
944
      assert(barier + d_shift < dec->buf + dec->len);
936
945
      for(; to <= barier; to++)
943
952
    {
944
953
      /* move right */
945
954
      d_shift= (1 - new_front) / DIG_PER_DEC1;
946
 
      to= dec->buf + round_up(end) - 1 + d_shift;
947
 
      barier= dec->buf + round_up(beg + 1) - 1 + d_shift;
 
955
      to= dec->buf + ROUND_UP(end) - 1 + d_shift;
 
956
      barier= dec->buf + ROUND_UP(beg + 1) - 1 + d_shift;
948
957
      assert(to < dec->buf + dec->len);
949
958
      assert(barier - d_shift >= dec->buf);
950
959
      for(; to >= barier; to--)
963
972
 
964
973
    Only one of following 'for' loops will work becouse beg <= end
965
974
  */
966
 
  beg= round_up(beg + 1) - 1;
967
 
  end= round_up(end) - 1;
 
975
  beg= ROUND_UP(beg + 1) - 1;
 
976
  end= ROUND_UP(end) - 1;
968
977
  assert(new_point >= 0);
969
978
 
970
979
  /* We don't want negative new_point below */
971
980
  if (new_point != 0)
972
 
    new_point= round_up(new_point) - 1;
 
981
    new_point= ROUND_UP(new_point) - 1;
973
982
 
974
983
  if (new_point > end)
975
984
  {
1064
1073
      error=E_DEC_OVERFLOW;
1065
1074
      intg=to->intg;
1066
1075
    }
1067
 
    intg1=round_up(intg);
1068
 
    frac1=round_up(frac);
 
1076
    intg1=ROUND_UP(intg);
 
1077
    frac1=ROUND_UP(frac);
1069
1078
    if (intg1+frac1 > to->len)
1070
1079
    {
1071
1080
      error= E_DEC_OOM;
1074
1083
  }
1075
1084
  else
1076
1085
  {
1077
 
    intg1=round_up(intg);
1078
 
    frac1=round_up(frac);
1079
 
    fix_intg_frac_error(to->len, intg1, frac1, error);
 
1086
    intg1=ROUND_UP(intg);
 
1087
    frac1=ROUND_UP(frac);
 
1088
    FIX_INTG_FRAC_ERROR(to->len, intg1, frac1, error);
1080
1089
    if (unlikely(error))
1081
1090
    {
1082
1091
      frac=frac1*DIG_PER_DEC1;
1540
1549
  d_copy[0]^= 0x80;
1541
1550
  from= d_copy;
1542
1551
 
1543
 
  fix_intg_frac_error(to->len, intg1, frac1, error);
 
1552
  FIX_INTG_FRAC_ERROR(to->len, intg1, frac1, error);
1544
1553
  if (unlikely(error))
1545
1554
  {
1546
1555
    if (intg1 < intg0+(intg0x>0))
1660
1669
decimal_round(const decimal_t *from, decimal_t *to, int scale,
1661
1670
              decimal_round_mode mode)
1662
1671
{
1663
 
  int frac0=scale>0 ? round_up(scale) : scale/DIG_PER_DEC1,
1664
 
      frac1=round_up(from->frac), round_digit= 0,
1665
 
      intg0=round_up(from->intg), error=E_DEC_OK, len=to->len,
1666
 
      intg1=round_up(from->intg +
 
1672
  int frac0=scale>0 ? ROUND_UP(scale) : scale/DIG_PER_DEC1,
 
1673
      frac1=ROUND_UP(from->frac), round_digit= 0,
 
1674
      intg0=ROUND_UP(from->intg), error=E_DEC_OK, len=to->len,
 
1675
      intg1=ROUND_UP(from->intg +
1667
1676
                     (((intg0 + frac0)>0) && (from->buf[0] == DIG_MAX)));
1668
1677
  dec1 *buf0=from->buf, *buf1=to->buf, x, y, carry=0;
1669
1678
  int first_dig;
1798
1807
    carry=1;
1799
1808
    *buf1-=DIG_BASE;
1800
1809
    while (carry && --buf1 >= to->buf)
1801
 
      add(*buf1, *buf1, 0, carry);
 
1810
      ADD(*buf1, *buf1, 0, carry);
1802
1811
    if (unlikely(carry))
1803
1812
    {
1804
1813
      /* shifting the number to create space for new digit */
1851
1860
 
1852
1861
static int do_add(const decimal_t *from1, const decimal_t *from2, decimal_t *to)
1853
1862
{
1854
 
  int intg1=round_up(from1->intg), intg2=round_up(from2->intg),
1855
 
      frac1=round_up(from1->frac), frac2=round_up(from2->frac),
 
1863
  int intg1=ROUND_UP(from1->intg), intg2=ROUND_UP(from2->intg),
 
1864
      frac1=ROUND_UP(from1->frac), frac2=ROUND_UP(from2->frac),
1856
1865
      frac0=max(frac1, frac2), intg0=max(intg1, intg2), error;
1857
1866
  dec1 *buf1, *buf2, *buf0, *stop, *stop2, x, carry;
1858
1867
 
1868
1877
    to->buf[0]=0; /* safety */
1869
1878
  }
1870
1879
 
1871
 
  fix_intg_frac_error(to->len, intg0, frac0, error);
 
1880
  FIX_INTG_FRAC_ERROR(to->len, intg0, frac0, error);
1872
1881
  if (unlikely(error == E_DEC_OVERFLOW))
1873
1882
  {
1874
1883
    max_decimal(to->len * DIG_PER_DEC1, 0, to);
1911
1920
  carry=0;
1912
1921
  while (buf1 > stop2)
1913
1922
  {
1914
 
    add(*--buf0, *--buf1, *--buf2, carry);
 
1923
    ADD(*--buf0, *--buf1, *--buf2, carry);
1915
1924
  }
1916
1925
 
1917
1926
  /* part 3 - cmin(intg) ... cmax(intg) */
1919
1928
                        ((stop=from2->buf)+intg2-intg1) ;
1920
1929
  while (buf1 > stop)
1921
1930
  {
1922
 
    add(*--buf0, *--buf1, 0, carry);
 
1931
    ADD(*--buf0, *--buf1, 0, carry);
1923
1932
  }
1924
1933
 
1925
1934
  if (unlikely(carry))
1933
1942
   if to==0, return -1/0/+1 - the result of the comparison */
1934
1943
static int do_sub(const decimal_t *from1, const decimal_t *from2, decimal_t *to)
1935
1944
{
1936
 
  int intg1=round_up(from1->intg), intg2=round_up(from2->intg),
1937
 
      frac1=round_up(from1->frac), frac2=round_up(from2->frac);
 
1945
  int intg1=ROUND_UP(from1->intg), intg2=ROUND_UP(from2->intg),
 
1946
      frac1=ROUND_UP(from1->frac), frac2=ROUND_UP(from2->frac);
1938
1947
  int frac0=max(frac1, frac2), error;
1939
1948
  dec1 *buf1, *buf2, *buf0, *stop1, *stop2, *start1, *start2, carry=0;
1940
1949
 
2000
2009
  /* ensure that always from1 > from2 (and intg1 >= intg2) */
2001
2010
  if (carry)
2002
2011
  {
2003
 
    swap(from1, from2);
2004
 
    swap(start1, start2);
2005
 
    swap(intg1, intg2);
2006
 
    swap(frac1, frac2);
 
2012
    swap_variables(const decimal_t *,from1, from2);
 
2013
    swap_variables(dec1 *,start1, start2);
 
2014
    swap_variables(int,intg1,intg2);
 
2015
    swap_variables(int,frac1,frac2);
2007
2016
    to->sign= 1 - to->sign;
2008
2017
  }
2009
2018
 
2010
 
  fix_intg_frac_error(to->len, intg1, frac0, error);
 
2019
  FIX_INTG_FRAC_ERROR(to->len, intg1, frac0, error);
2011
2020
  buf0=to->buf+intg1+frac0;
2012
2021
 
2013
2022
  to->frac=max(from1->frac, from2->frac);
2041
2050
      *--buf0=0;
2042
2051
    while (buf2 > stop2)
2043
2052
    {
2044
 
      sub(*--buf0, 0, *--buf2, carry);
 
2053
      SUB(*--buf0, 0, *--buf2, carry);
2045
2054
    }
2046
2055
  }
2047
2056
 
2048
2057
  /* part 2 - cmin(frac) ... intg2 */
2049
2058
  while (buf2 > start2)
2050
2059
  {
2051
 
    sub(*--buf0, *--buf1, *--buf2, carry);
 
2060
    SUB(*--buf0, *--buf1, *--buf2, carry);
2052
2061
  }
2053
2062
 
2054
2063
  /* part 3 - intg2 ... intg1 */
2055
2064
  while (carry && buf1 > start1)
2056
2065
  {
2057
 
    sub(*--buf0, *--buf1, 0, carry);
 
2066
    SUB(*--buf0, *--buf1, 0, carry);
2058
2067
  }
2059
2068
 
2060
2069
  while (buf1 > start1)
2098
2107
int decimal_is_zero(const decimal_t *from)
2099
2108
{
2100
2109
  dec1 *buf1=from->buf,
2101
 
       *end=buf1+round_up(from->intg)+round_up(from->frac);
 
2110
       *end=buf1+ROUND_UP(from->intg)+ROUND_UP(from->frac);
2102
2111
  while (buf1 < end)
2103
2112
    if (*buf1++)
2104
2113
      return 0;
2127
2136
*/
2128
2137
int decimal_mul(const decimal_t *from1, const decimal_t *from2, decimal_t *to)
2129
2138
{
2130
 
  int intg1=round_up(from1->intg), intg2=round_up(from2->intg),
2131
 
      frac1=round_up(from1->frac), frac2=round_up(from2->frac),
2132
 
      intg0=round_up(from1->intg+from2->intg),
 
2139
  int intg1=ROUND_UP(from1->intg), intg2=ROUND_UP(from2->intg),
 
2140
      frac1=ROUND_UP(from1->frac), frac2=ROUND_UP(from2->frac),
 
2141
      intg0=ROUND_UP(from1->intg+from2->intg),
2133
2142
      frac0=frac1+frac2, error, i, j, d_to_move;
2134
2143
  dec1 *buf1=from1->buf+intg1, *buf2=from2->buf+intg2, *buf0,
2135
2144
       *start2, *stop2, *stop1, *start0, carry;
2138
2147
 
2139
2148
  i=intg0;
2140
2149
  j=frac0;
2141
 
  fix_intg_frac_error(to->len, intg0, frac0, error);
 
2150
  FIX_INTG_FRAC_ERROR(to->len, intg0, frac0, error);
2142
2151
  to->sign=from1->sign != from2->sign;
2143
2152
  to->frac=from1->frac+from2->frac;
2144
2153
  to->intg=intg0*DIG_PER_DEC1;
2179
2188
      dec2 p= ((dec2)*buf1) * ((dec2)*buf2);
2180
2189
      hi=(dec1)(p/DIG_BASE);
2181
2190
      lo=(dec1)(p-((dec2)hi)*DIG_BASE);
2182
 
      add2(*buf0, *buf0, lo, carry);
 
2191
      ADD2(*buf0, *buf0, lo, carry);
2183
2192
      carry+=hi;
2184
2193
    }
2185
2194
    if (carry)
2186
2195
    {
2187
2196
      if (buf0 < to->buf)
2188
2197
        return E_DEC_OVERFLOW;
2189
 
      add2(*buf0, *buf0, 0, carry);
 
2198
      ADD2(*buf0, *buf0, 0, carry);
2190
2199
    }
2191
2200
    for (buf0--; carry; buf0--)
2192
2201
    {
2193
2202
      if (buf0 < to->buf)
2194
2203
        return E_DEC_OVERFLOW;
2195
 
      add(*buf0, *buf0, 0, carry);
 
2204
      ADD(*buf0, *buf0, 0, carry);
2196
2205
    }
2197
2206
  }
2198
2207
 
2215
2224
    }
2216
2225
  }
2217
2226
  buf1= to->buf;
2218
 
  d_to_move= intg0 + round_up(to->frac);
 
2227
  d_to_move= intg0 + ROUND_UP(to->frac);
2219
2228
  while (!*buf1 && (to->intg > DIG_PER_DEC1))
2220
2229
  {
2221
2230
    buf1++;
2245
2254
static int do_div_mod(const decimal_t *from1, const decimal_t *from2,
2246
2255
                       decimal_t *to, decimal_t *mod, int scale_incr)
2247
2256
{
2248
 
  int frac1=round_up(from1->frac)*DIG_PER_DEC1, prec1=from1->intg+frac1,
2249
 
      frac2=round_up(from2->frac)*DIG_PER_DEC1, prec2=from2->intg+frac2,
 
2257
  int frac1=ROUND_UP(from1->frac)*DIG_PER_DEC1, prec1=from1->intg+frac1,
 
2258
      frac2=ROUND_UP(from2->frac)*DIG_PER_DEC1, prec2=from2->intg+frac2,
2250
2259
      error= 0, i, intg0, frac0, len1, len2, dintg, div_mod=(!mod);
2251
2260
  dec1 *buf0, *buf1=from1->buf, *buf2=from2->buf, *tmp1,
2252
2261
       *start2, *stop2, *stop1, *stop0, norm2, carry, *start1, dcarry;
2296
2305
    intg0=0;
2297
2306
  }
2298
2307
  else
2299
 
    intg0=round_up(dintg);
 
2308
    intg0=ROUND_UP(dintg);
2300
2309
  if (mod)
2301
2310
  {
2302
2311
    /* we're calculating N1 % N2.
2315
2324
      N2 is in the buf2, has prec2 digits. Scales are frac1 and
2316
2325
      frac2 accordingly.
2317
2326
      Thus, the result will have
2318
 
         frac = round_up(frac1+frac2+scale_incr)
 
2327
         frac = ROUND_UP(frac1+frac2+scale_incr)
2319
2328
      and
2320
2329
         intg = (prec1-frac1) - (prec2-frac2) + 1
2321
2330
         prec = intg+frac
2322
2331
    */
2323
 
    frac0=round_up(frac1+frac2+scale_incr);
2324
 
    fix_intg_frac_error(to->len, intg0, frac0, error);
 
2332
    frac0=ROUND_UP(frac1+frac2+scale_incr);
 
2333
    FIX_INTG_FRAC_ERROR(to->len, intg0, frac0, error);
2325
2334
    to->sign=from1->sign != from2->sign;
2326
2335
    to->intg=intg0*DIG_PER_DEC1;
2327
2336
    to->frac=frac0*DIG_PER_DEC1;
2332
2341
    while (dintg++ < 0)
2333
2342
      *buf0++=0;
2334
2343
 
2335
 
  len1=(i=round_up(prec1))+round_up(2*frac2+scale_incr+1) + 1;
 
2344
  len1=(i=ROUND_UP(prec1))+ROUND_UP(2*frac2+scale_incr+1) + 1;
2336
2345
  set_if_bigger(len1, 3);
2337
2346
  if (!(tmp1=(dec1 *)alloca(len1*sizeof(dec1))))
2338
2347
    return E_DEC_OOM;
2342
2351
  start1=tmp1;
2343
2352
  stop1=start1+len1;
2344
2353
  start2=buf2;
2345
 
  stop2=buf2+round_up(prec2)-1;
 
2354
  stop2=buf2+ROUND_UP(prec2)-1;
2346
2355
 
2347
2356
  /* removing end zeroes */
2348
2357
  while (*stop2 == 0 && stop2 >= start2)
2401
2410
        x=guess * (*--buf2);
2402
2411
        hi=(dec1)(x/DIG_BASE);
2403
2412
        lo=(dec1)(x-((dec2)hi)*DIG_BASE);
2404
 
        sub2(*buf1, *buf1, lo, carry);
 
2413
        SUB2(*buf1, *buf1, lo, carry);
2405
2414
        carry+=hi;
2406
2415
      }
2407
2416
      carry= dcarry < carry;
2415
2424
        buf1=start1+len2;
2416
2425
        for (carry=0; buf2 > start2; buf1--)
2417
2426
        {
2418
 
          add(*buf1, *buf1, *--buf2, carry);
 
2427
          ADD(*buf1, *buf1, *--buf2, carry);
2419
2428
        }
2420
2429
      }
2421
2430
    }
2434
2443
    if (dcarry)
2435
2444
      *--start1=dcarry;
2436
2445
    buf0=to->buf;
2437
 
    intg0=(int) (round_up(prec1-frac1)-(start1-tmp1));
2438
 
    frac0=round_up(to->frac);
 
2446
    intg0=(int) (ROUND_UP(prec1-frac1)-(start1-tmp1));
 
2447
    frac0=ROUND_UP(to->frac);
2439
2448
    error=E_DEC_OK;
2440
2449
    if (unlikely(frac0==0 && intg0==0))
2441
2450
    {
2465
2474
        error=E_DEC_OVERFLOW;
2466
2475
        goto done;
2467
2476
      }
2468
 
      assert(intg0 <= round_up(from2->intg));
 
2477
      assert(intg0 <= ROUND_UP(from2->intg));
2469
2478
      stop1=start1+frac0+intg0;
2470
2479
      to->intg=min(intg0*DIG_PER_DEC1, from2->intg);
2471
2480
    }
2545
2554
{
2546
2555
  int i;
2547
2556
  printf("/* intg=%d, frac=%d, sign=%d, buf[]={", d->intg, d->frac, d->sign);
2548
 
  for (i=0; i < round_up(d->frac)+round_up(d->intg)-1; i++)
 
2557
  for (i=0; i < ROUND_UP(d->frac)+ROUND_UP(d->intg)-1; i++)
2549
2558
    printf("%09d, ", d->buf[i]);
2550
2559
  printf("%09d} */ ", d->buf[i]);
2551
2560
}