17b36286aSmartynas /****************************************************************
27b36286aSmartynas
37b36286aSmartynas The author of this software is David M. Gay.
47b36286aSmartynas
57b36286aSmartynas Copyright (C) 1998, 1999 by Lucent Technologies
67b36286aSmartynas All Rights Reserved
77b36286aSmartynas
87b36286aSmartynas Permission to use, copy, modify, and distribute this software and
97b36286aSmartynas its documentation for any purpose and without fee is hereby
107b36286aSmartynas granted, provided that the above copyright notice appear in all
117b36286aSmartynas copies and that both that the copyright notice and this
127b36286aSmartynas permission notice and warranty disclaimer appear in supporting
137b36286aSmartynas documentation, and that the name of Lucent or any of its entities
147b36286aSmartynas not be used in advertising or publicity pertaining to
157b36286aSmartynas distribution of the software without specific, written prior
167b36286aSmartynas permission.
177b36286aSmartynas
187b36286aSmartynas LUCENT DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
197b36286aSmartynas INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS.
207b36286aSmartynas IN NO EVENT SHALL LUCENT OR ANY OF ITS ENTITIES BE LIABLE FOR ANY
217b36286aSmartynas SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
227b36286aSmartynas WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER
237b36286aSmartynas IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
247b36286aSmartynas ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
257b36286aSmartynas THIS SOFTWARE.
267b36286aSmartynas
277b36286aSmartynas ****************************************************************/
287b36286aSmartynas
297b36286aSmartynas /* Please send bug reports to David M. Gay (dmg at acm dot org,
307b36286aSmartynas * with " at " changed at "@" and " dot " changed to "."). */
317b36286aSmartynas
327b36286aSmartynas #include "gdtoaimp.h"
337b36286aSmartynas
347b36286aSmartynas Bigint *
s2b(s,nd0,nd,y9,dplen)357b36286aSmartynas s2b
367b36286aSmartynas #ifdef KR_headers
37*1a653cbcSmartynas (s, nd0, nd, y9, dplen) CONST char *s; int dplen, nd0, nd; ULong y9;
387b36286aSmartynas #else
39*1a653cbcSmartynas (CONST char *s, int nd0, int nd, ULong y9, int dplen)
407b36286aSmartynas #endif
417b36286aSmartynas {
427b36286aSmartynas Bigint *b;
437b36286aSmartynas int i, k;
447b36286aSmartynas Long x, y;
457b36286aSmartynas
467b36286aSmartynas x = (nd + 8) / 9;
477b36286aSmartynas for(k = 0, y = 1; x > y; y <<= 1, k++) ;
487b36286aSmartynas #ifdef Pack_32
497b36286aSmartynas b = Balloc(k);
50384cfdc1Smartynas if (b == NULL)
51384cfdc1Smartynas return (NULL);
527b36286aSmartynas b->x[0] = y9;
537b36286aSmartynas b->wds = 1;
547b36286aSmartynas #else
557b36286aSmartynas b = Balloc(k+1);
56384cfdc1Smartynas if (b == NULL)
57384cfdc1Smartynas return (NULL);
587b36286aSmartynas b->x[0] = y9 & 0xffff;
597b36286aSmartynas b->wds = (b->x[1] = y9 >> 16) ? 2 : 1;
607b36286aSmartynas #endif
617b36286aSmartynas
627b36286aSmartynas i = 9;
637b36286aSmartynas if (9 < nd0) {
647b36286aSmartynas s += 9;
65384cfdc1Smartynas do {
66384cfdc1Smartynas b = multadd(b, 10, *s++ - '0');
67384cfdc1Smartynas if (b == NULL)
68384cfdc1Smartynas return (NULL);
69384cfdc1Smartynas } while(++i < nd0);
70*1a653cbcSmartynas s += dplen;
717b36286aSmartynas }
727b36286aSmartynas else
73*1a653cbcSmartynas s += dplen + 9;
74384cfdc1Smartynas for(; i < nd; i++) {
757b36286aSmartynas b = multadd(b, 10, *s++ - '0');
76384cfdc1Smartynas if (b == NULL)
77384cfdc1Smartynas return (NULL);
78384cfdc1Smartynas }
797b36286aSmartynas return b;
807b36286aSmartynas }
817b36286aSmartynas
827b36286aSmartynas double
ratio(a,b)837b36286aSmartynas ratio
847b36286aSmartynas #ifdef KR_headers
857b36286aSmartynas (a, b) Bigint *a, *b;
867b36286aSmartynas #else
877b36286aSmartynas (Bigint *a, Bigint *b)
887b36286aSmartynas #endif
897b36286aSmartynas {
90*1a653cbcSmartynas U da, db;
917b36286aSmartynas int k, ka, kb;
927b36286aSmartynas
93*1a653cbcSmartynas dval(&da) = b2d(a, &ka);
94*1a653cbcSmartynas dval(&db) = b2d(b, &kb);
957b36286aSmartynas k = ka - kb + ULbits*(a->wds - b->wds);
967b36286aSmartynas #ifdef IBM
977b36286aSmartynas if (k > 0) {
98*1a653cbcSmartynas word0(&da) += (k >> 2)*Exp_msk1;
997b36286aSmartynas if (k &= 3)
100*1a653cbcSmartynas dval(&da) *= 1 << k;
1017b36286aSmartynas }
1027b36286aSmartynas else {
1037b36286aSmartynas k = -k;
104*1a653cbcSmartynas word0(&db) += (k >> 2)*Exp_msk1;
1057b36286aSmartynas if (k &= 3)
106*1a653cbcSmartynas dval(&db) *= 1 << k;
1077b36286aSmartynas }
1087b36286aSmartynas #else
1097b36286aSmartynas if (k > 0)
110*1a653cbcSmartynas word0(&da) += k*Exp_msk1;
1117b36286aSmartynas else {
1127b36286aSmartynas k = -k;
113*1a653cbcSmartynas word0(&db) += k*Exp_msk1;
1147b36286aSmartynas }
1157b36286aSmartynas #endif
116*1a653cbcSmartynas return dval(&da) / dval(&db);
1177b36286aSmartynas }
1187b36286aSmartynas
1197b36286aSmartynas #ifdef INFNAN_CHECK
1207b36286aSmartynas
1217b36286aSmartynas int
match(sp,t)1227b36286aSmartynas match
1237b36286aSmartynas #ifdef KR_headers
1247b36286aSmartynas (sp, t) char **sp, *t;
1257b36286aSmartynas #else
1267b36286aSmartynas (CONST char **sp, char *t)
1277b36286aSmartynas #endif
1287b36286aSmartynas {
1297b36286aSmartynas int c, d;
1307b36286aSmartynas CONST char *s = *sp;
1317b36286aSmartynas
1327b36286aSmartynas while( (d = *t++) !=0) {
1337b36286aSmartynas if ((c = *++s) >= 'A' && c <= 'Z')
1347b36286aSmartynas c += 'a' - 'A';
1357b36286aSmartynas if (c != d)
1367b36286aSmartynas return 0;
1377b36286aSmartynas }
1387b36286aSmartynas *sp = s + 1;
1397b36286aSmartynas return 1;
1407b36286aSmartynas }
1417b36286aSmartynas #endif /* INFNAN_CHECK */
1427b36286aSmartynas
1437b36286aSmartynas void
1447b36286aSmartynas #ifdef KR_headers
copybits(c,n,b)1457b36286aSmartynas copybits(c, n, b) ULong *c; int n; Bigint *b;
1467b36286aSmartynas #else
1477b36286aSmartynas copybits(ULong *c, int n, Bigint *b)
1487b36286aSmartynas #endif
1497b36286aSmartynas {
1507b36286aSmartynas ULong *ce, *x, *xe;
1517b36286aSmartynas #ifdef Pack_16
1527b36286aSmartynas int nw, nw1;
1537b36286aSmartynas #endif
1547b36286aSmartynas
1557b36286aSmartynas ce = c + ((n-1) >> kshift) + 1;
1567b36286aSmartynas x = b->x;
1577b36286aSmartynas #ifdef Pack_32
1587b36286aSmartynas xe = x + b->wds;
1597b36286aSmartynas while(x < xe)
1607b36286aSmartynas *c++ = *x++;
1617b36286aSmartynas #else
1627b36286aSmartynas nw = b->wds;
1637b36286aSmartynas nw1 = nw & 1;
1647b36286aSmartynas for(xe = x + (nw - nw1); x < xe; x += 2)
1657b36286aSmartynas Storeinc(c, x[1], x[0]);
1667b36286aSmartynas if (nw1)
1677b36286aSmartynas *c++ = *x;
1687b36286aSmartynas #endif
1697b36286aSmartynas while(c < ce)
1707b36286aSmartynas *c++ = 0;
1717b36286aSmartynas }
1727b36286aSmartynas
1737b36286aSmartynas ULong
1747b36286aSmartynas #ifdef KR_headers
any_on(b,k)1757b36286aSmartynas any_on(b, k) Bigint *b; int k;
1767b36286aSmartynas #else
1777b36286aSmartynas any_on(Bigint *b, int k)
1787b36286aSmartynas #endif
1797b36286aSmartynas {
1807b36286aSmartynas int n, nwds;
1817b36286aSmartynas ULong *x, *x0, x1, x2;
1827b36286aSmartynas
1837b36286aSmartynas x = b->x;
1847b36286aSmartynas nwds = b->wds;
1857b36286aSmartynas n = k >> kshift;
1867b36286aSmartynas if (n > nwds)
1877b36286aSmartynas n = nwds;
1887b36286aSmartynas else if (n < nwds && (k &= kmask)) {
1897b36286aSmartynas x1 = x2 = x[n];
1907b36286aSmartynas x1 >>= k;
1917b36286aSmartynas x1 <<= k;
1927b36286aSmartynas if (x1 != x2)
1937b36286aSmartynas return 1;
1947b36286aSmartynas }
1957b36286aSmartynas x0 = x;
1967b36286aSmartynas x += n;
1977b36286aSmartynas while(x > x0)
1987b36286aSmartynas if (*--x)
1997b36286aSmartynas return 1;
2007b36286aSmartynas return 0;
2017b36286aSmartynas }
202