home *** CD-ROM | disk | FTP | other *** search
/ Source Code 1994 March / Source_Code_CD-ROM_Walnut_Creek_March_1994.iso / compsrcs / unix / volume26 / calc / part15 < prev    next >
Encoding:
Text File  |  1992-05-09  |  34.8 KB  |  1,825 lines

  1. Newsgroups: comp.sources.unix
  2. From: dbell@pdact.pd.necisa.oz.au (David I. Bell)
  3. Subject: v26i041: CALC - An arbitrary precision C-like calculator, Part15/21
  4. Sender: unix-sources-moderator@pa.dec.com
  5. Approved: vixie@pa.dec.com
  6.  
  7. Submitted-By: dbell@pdact.pd.necisa.oz.au (David I. Bell)
  8. Posting-Number: Volume 26, Issue 41
  9. Archive-Name: calc/part15
  10.  
  11. #! /bin/sh
  12. # This is a shell archive.  Remove anything before this line, then unpack
  13. # it by saving it into a file and typing "sh file".  To overwrite existing
  14. # files, type "sh file -c".  You can also feed this as standard input via
  15. # unshar, or by typing "sh <file", e.g..  If this archive is complete, you
  16. # will see the following message at the end:
  17. #        "End of archive 15 (of 21)."
  18. # Contents:  zmath.c
  19. # Wrapped by dbell@elm on Tue Feb 25 15:21:13 1992
  20. PATH=/bin:/usr/bin:/usr/ucb ; export PATH
  21. if test -f 'zmath.c' -a "${1}" != "-c" ; then 
  22.   echo shar: Will not clobber existing file \"'zmath.c'\"
  23. else
  24. echo shar: Extracting \"'zmath.c'\" \(32210 characters\)
  25. sed "s/^X//" >'zmath.c' <<'END_OF_FILE'
  26. X/*
  27. X * Copyright (c) 1992 David I. Bell
  28. X * Permission is granted to use, distribute, or modify this source,
  29. X * provided that this copyright notice remains intact.
  30. X *
  31. X * Extended precision integral arithmetic primitives
  32. X */
  33. X
  34. X#include <stdio.h>
  35. X#include "math.h"
  36. X
  37. X
  38. XHALF _twoval_[] = { 2 };
  39. XHALF _zeroval_[] = { 0 };
  40. XHALF _oneval_[] = { 1 };
  41. XHALF _tenval_[] = { 10 };
  42. X
  43. XZVALUE _zero_ = { _zeroval_, 1, 0};
  44. XZVALUE _one_ = { _oneval_, 1, 0 };
  45. XZVALUE _ten_ = { _tenval_, 1, 0 };
  46. X
  47. X/*
  48. X * mask of given bits, rotated thru all bit positions twice
  49. X *
  50. X * bitmask[i]      (1 << (i-1)),  for  -BASEB*4<=i<=BASEB*4
  51. X * rotmask[j][k] (1 << ((j+k-1)%BASEB)),  for  -BASEB*2<=j,k<=BASEB*2
  52. X */
  53. Xstatic HALF *bmask;        /* actual rotation thru 8 cycles */
  54. Xstatic HALF **rmask;        /* actual rotation pointers thru 2 cycles */
  55. XHALF *bitmask;            /* bit rotation, norm 0 */
  56. X#if 0
  57. Xstatic HALF **rotmask;        /* pointers to bit rotations, norm index */
  58. X#endif
  59. X
  60. XBOOL _math_abort_;        /* nonzero to abort calculations */
  61. X
  62. X
  63. Xstatic char *abortmsg = "Calculation aborted";
  64. Xstatic char *memmsg = "Not enough memory";
  65. X
  66. Xstatic void dadd proto((ZVALUE z1, ZVALUE z2, long y, long n));
  67. Xstatic BOOL dsub proto((ZVALUE z1, ZVALUE z2, long y, long n));
  68. Xstatic void dmul proto((ZVALUE z, FULL x, ZVALUE *dest));
  69. X
  70. X
  71. X#ifdef ALLOCTEST
  72. Xstatic long nalloc = 0;
  73. Xstatic long nfree = 0;
  74. X#endif
  75. X
  76. X
  77. XHALF *
  78. Xalloc(len)
  79. X    long len;
  80. X{
  81. X    HALF *hp;
  82. X
  83. X    if (_math_abort_)
  84. X        error(abortmsg);
  85. X    hp = (HALF *) malloc(len * sizeof(HALF) + 2);
  86. X    if (hp == 0)
  87. X        error(memmsg);
  88. X#ifdef ALLOCTEST
  89. X    ++nalloc;
  90. X#endif
  91. X    return hp;
  92. X}
  93. X
  94. X#ifdef ALLOCTEST
  95. Xvoid
  96. Xfreeh(h)
  97. X    HALF *h;
  98. X{
  99. X    if ((h != _zeroval_) && (h != _oneval_)) {
  100. X        free(h);
  101. X        ++nfree;
  102. X    }
  103. X}
  104. X
  105. X
  106. Xvoid
  107. XallocStat()
  108. X{
  109. X    fprintf(stderr, "nalloc: %ld nfree: %ld kept: %ld\n",
  110. X        nalloc, nfree, nalloc - nfree);
  111. X}
  112. X#endif
  113. X
  114. X
  115. X/*
  116. X * Convert a normal integer to a number.
  117. X */
  118. Xvoid
  119. Xitoz(i, res)
  120. X    long i;
  121. X    ZVALUE *res;
  122. X{
  123. X    long diddle, len;
  124. X
  125. X    res->len = 1;
  126. X    res->sign = 0;
  127. X    diddle = 0;
  128. X    if (i == 0) {
  129. X        res->v = _zeroval_;
  130. X        return;
  131. X    }
  132. X    if (i < 0) {
  133. X        res->sign = 1;
  134. X        i = -i;
  135. X        if (i < 0) {    /* fix most negative number */
  136. X            diddle = 1;
  137. X            i--;
  138. X        }
  139. X    }
  140. X    if (i == 1) {
  141. X        res->v = _oneval_;
  142. X        return;
  143. X    }
  144. X    len = 1 + (((FULL) i) >= BASE);
  145. X    res->len = len;
  146. X    res->v = alloc(len);
  147. X    res->v[0] = (HALF) (i + diddle);
  148. X    if (len == 2)
  149. X        res->v[1] = (HALF) (i / BASE);
  150. X}
  151. X
  152. X
  153. X/*
  154. X * Convert a number to a normal integer, as far as possible.
  155. X * If the number is out of range, the largest number is returned.
  156. X */
  157. Xlong
  158. Xztoi(z)
  159. X    ZVALUE z;
  160. X{
  161. X    long i;
  162. X
  163. X    if (isbig(z)) {
  164. X        i = MAXFULL;
  165. X        return (z.sign ? -i : i);
  166. X    }
  167. X    i = (istiny(z) ? z1tol(z) : z2tol(z));
  168. X    return (z.sign ? -i : i);
  169. X}
  170. X
  171. X
  172. X/*
  173. X * Make a copy of an integer value
  174. X */
  175. Xvoid
  176. Xzcopy(z, res)
  177. X    ZVALUE z, *res;
  178. X{
  179. X    res->sign = z.sign;
  180. X    res->len = z.len;
  181. X    if (isleone(z)) {    /* zero or plus or minus one are easy */
  182. X        res->v = (z.v[0] ? _oneval_ : _zeroval_);
  183. X        return;
  184. X    }
  185. X    res->v = alloc(z.len);
  186. X    copyval(z, *res);
  187. X}
  188. X
  189. X
  190. X/*
  191. X * Add together two integers.
  192. X */
  193. Xvoid
  194. Xzadd(z1, z2, res)
  195. X    ZVALUE z1, z2, *res;
  196. X{
  197. X    ZVALUE dest;
  198. X    HALF *p1, *p2, *pd;
  199. X    long len;
  200. X    FULL carry;
  201. X    SIUNION sival;
  202. X
  203. X    if (z1.sign && !z2.sign) {
  204. X        z1.sign = 0;
  205. X        zsub(z2, z1, res);
  206. X        return;
  207. X    }
  208. X    if (z2.sign && !z1.sign) {
  209. X        z2.sign = 0;
  210. X        zsub(z1, z2, res);
  211. X        return;
  212. X    }
  213. X    if (z2.len > z1.len) {
  214. X        pd = z1.v; z1.v = z2.v; z2.v = pd;
  215. X        len = z1.len; z1.len = z2.len; z2.len = len;
  216. X    }
  217. X    dest.len = z1.len + 1;
  218. X    dest.v = alloc(dest.len);
  219. X    dest.sign = z1.sign;
  220. X    carry = 0;
  221. X    pd = dest.v;
  222. X    p1 = z1.v;
  223. X    p2 = z2.v;
  224. X    len = z2.len;
  225. X    while (len--) {
  226. X        sival.ivalue = ((FULL) *p1++) + ((FULL) *p2++) + carry;
  227. X        *pd++ = sival.silow;
  228. X        carry = sival.sihigh;
  229. X    }
  230. X    len = z1.len - z2.len;
  231. X    while (len--) {
  232. X        sival.ivalue = ((FULL) *p1++) + carry;
  233. X        *pd++ = sival.silow;
  234. X        carry = sival.sihigh;
  235. X    }
  236. X    *pd = (HALF)carry;
  237. X    quicktrim(dest);
  238. X    *res = dest;
  239. X}
  240. X
  241. X
  242. X/*
  243. X * Subtract two integers.
  244. X */
  245. Xvoid
  246. Xzsub(z1, z2, res)
  247. X    ZVALUE z1, z2, *res;
  248. X{
  249. X    register HALF *h1, *h2, *hd;
  250. X    long len1, len2;
  251. X    FULL carry;
  252. X    SIUNION sival;
  253. X    ZVALUE dest;
  254. X
  255. X    if (z1.sign != z2.sign) {
  256. X        z2.sign = z1.sign;
  257. X        zadd(z1, z2, res);
  258. X        return;
  259. X    }
  260. X    len1 = z1.len;
  261. X    len2 = z2.len;
  262. X    if (len1 == len2) {
  263. X        h1 = z1.v + len1 - 1;
  264. X        h2 = z2.v + len2 - 1;
  265. X        while ((len1 > 0) && ((FULL)*h1 == (FULL)*h2)) {
  266. X            len1--;
  267. X            h1--;
  268. X            h2--;
  269. X        }
  270. X        if (len1 == 0) {
  271. X            *res = _zero_;
  272. X            return;
  273. X        }
  274. X        len2 = len1;
  275. X    }
  276. X    dest.sign = z1.sign;
  277. X    carry = ((len1 < len2) || ((len1 == len2) && ((FULL)*h1 < (FULL)*h2)));
  278. X    h1 = z1.v;
  279. X    h2 = z2.v;
  280. X    if (carry) {
  281. X        carry = len1;
  282. X        len1 = len2;
  283. X        len2 = carry;
  284. X        h1 = z2.v;
  285. X        h2 = z1.v;
  286. X        dest.sign = !dest.sign;
  287. X    }
  288. X    hd = alloc(len1);
  289. X    dest.v = hd;
  290. X    dest.len = len1;
  291. X    len1 -= len2;
  292. X    carry = 0;
  293. X    while (--len2 >= 0) {
  294. X        sival.ivalue = (BASE1 - ((FULL) *h1++)) + *h2++ + carry;
  295. X        *hd++ = BASE1 - sival.silow;
  296. X        carry = sival.sihigh;
  297. X    }
  298. X    while (--len1 >= 0) {
  299. X        sival.ivalue = (BASE1 - ((FULL) *h1++)) + carry;
  300. X        *hd++ = BASE1 - sival.silow;
  301. X        carry = sival.sihigh;
  302. X    }
  303. X    if (hd[-1] == 0)
  304. X        trim(&dest);
  305. X    *res = dest;
  306. X}
  307. X
  308. X
  309. X#if 0
  310. X/*
  311. X * Multiply two integers together.
  312. X */
  313. Xvoid
  314. Xzmul(z1, z2, res)
  315. X    ZVALUE z1, z2, *res;
  316. X{
  317. X    register HALF *s1, *s2, *sd, *h1;
  318. X    FULL mul, carry;
  319. X    long len1, len2;
  320. X    SIUNION sival;
  321. X    ZVALUE dest;
  322. X
  323. X    if (iszero(z1) || iszero(z2)) {
  324. X        *res = _zero_;
  325. X        return;
  326. X    }
  327. X    if (isone(z1)) {
  328. X        zcopy(z2, res);
  329. X        return;
  330. X    }
  331. X    if (isone(z2)) {
  332. X        zcopy(z1, res);
  333. X        return;
  334. X    }
  335. X    dest.len = z1.len + z2.len;
  336. X    dest.v = alloc(dest.len);
  337. X    dest.sign = (z1.sign != z2.sign);
  338. X    clearval(dest);
  339. X    /*
  340. X     * Swap the numbers if necessary to make the second one smaller.
  341. X     */
  342. X    if (z1.len < z2.len) {
  343. X        len1 = z1.len;
  344. X        z1.len = z2.len;
  345. X        z2.len = len1;
  346. X        s1 = z1.v;
  347. X        z1.v = z2.v;
  348. X        z2.v = s1;
  349. X    }
  350. X    /*
  351. X     * Multiply the first number by each 'digit' of the second number
  352. X     * and add the result to the total.
  353. X     */
  354. X    sd = dest.v;
  355. X    s2 = z2.v;
  356. X    for (len2 = z2.len; len2--; sd++) {
  357. X        mul = (FULL) *s2++;
  358. X        if (mul == 0)
  359. X            continue;
  360. X        h1 = sd;
  361. X        s1 = z1.v;
  362. X        carry = 0;
  363. X        len1 = z1.len;
  364. X        while (len1 >= 4) {    /* expand the loop some */
  365. X            len1 -= 4;
  366. X            sival.ivalue = (mul * ((FULL) *s1++)) + ((FULL) *h1) + carry;
  367. X            *h1++ = sival.silow;
  368. X            sival.ivalue = (mul * ((FULL) *s1++)) + ((FULL) *h1) + ((FULL) sival.sihigh);
  369. X            *h1++ = sival.silow;
  370. X            sival.ivalue = (mul * ((FULL) *s1++)) + ((FULL) *h1) + ((FULL) sival.sihigh);
  371. X            *h1++ = sival.silow;
  372. X            sival.ivalue = (mul * ((FULL) *s1++)) + ((FULL) *h1) + ((FULL) sival.sihigh);
  373. X            *h1++ = sival.silow;
  374. X            carry = sival.sihigh;
  375. X        }
  376. X        while (--len1 >= 0) {
  377. X            sival.ivalue = (mul * ((FULL) *s1++)) + ((FULL) *h1) + carry;
  378. X            *h1++ = sival.silow;
  379. X            carry = sival.sihigh;
  380. X        }
  381. X        while (carry) {
  382. X            sival.ivalue = ((FULL) *h1) + carry;
  383. X            *h1++ = sival.silow;
  384. X            carry = sival.sihigh;
  385. X        }
  386. X    }
  387. X    trim(&dest);
  388. X    *res = dest;
  389. X}
  390. X#endif
  391. X
  392. X
  393. X/*
  394. X * Multiply an integer by a small number.
  395. X */
  396. Xvoid
  397. Xzmuli(z, n, res)
  398. X    ZVALUE z;
  399. X    long n;
  400. X    ZVALUE *res;
  401. X{
  402. X    register HALF *h1, *sd;
  403. X    FULL low;
  404. X    FULL high;
  405. X    FULL carry;
  406. X    long len;
  407. X    SIUNION sival;
  408. X    ZVALUE dest;
  409. X
  410. X    if ((n == 0) || iszero(z)) {
  411. X        *res = _zero_;
  412. X        return;
  413. X    }
  414. X    if (n < 0) {
  415. X        n = -n;
  416. X        z.sign = !z.sign;
  417. X    }
  418. X    if (n == 1) {
  419. X        zcopy(z, res);
  420. X        return;
  421. X    }
  422. X    low = ((FULL) n) & BASE1;
  423. X    high = ((FULL) n) >> BASEB;
  424. X    dest.len = z.len + 2;
  425. X    dest.v = alloc(dest.len);
  426. X    dest.sign = z.sign;
  427. X    /*
  428. X     * Multiply by the low digit.
  429. X     */
  430. X    h1 = z.v;
  431. X    sd = dest.v;
  432. X    len = z.len;
  433. X    carry = 0;
  434. X    while (len--) {
  435. X        sival.ivalue = ((FULL) *h1++) * low + carry;
  436. X        *sd++ = sival.silow;
  437. X        carry = sival.sihigh;
  438. X    }
  439. X    *sd = (HALF)carry;
  440. X    /*
  441. X     * If there was only one digit, then we are all done except
  442. X     * for trimming the number if there was no last carry.
  443. X     */
  444. X    if (high == 0) {
  445. X        dest.len--;
  446. X        if (carry == 0)
  447. X            dest.len--;
  448. X        *res = dest;
  449. X        return;
  450. X    }
  451. X    /*
  452. X     * Need to multiply by the high digit and add it into the
  453. X     * previous value.  Clear the final word of rubbish first.
  454. X     */
  455. X    *(++sd) = 0;
  456. X    h1 = z.v;
  457. X    sd = dest.v + 1;
  458. X    len = z.len;
  459. X    carry = 0;
  460. X    while (len--) {
  461. X        sival.ivalue = ((FULL) *h1++) * high + ((FULL) *sd) + carry;
  462. X        *sd++ = sival.silow;
  463. X        carry = sival.sihigh;
  464. X    }
  465. X    *sd = (HALF)carry;
  466. X    quicktrim(dest);
  467. X    *res = dest;
  468. X}
  469. X
  470. X
  471. X/*
  472. X * Divide two numbers by their greatest common divisor.
  473. X * This is useful for reducing the numerator and denominator of
  474. X * a fraction to its lowest terms.
  475. X */
  476. Xvoid
  477. Xzreduce(z1, z2, z1res, z2res)
  478. X    ZVALUE z1, z2, *z1res, *z2res;
  479. X{
  480. X    ZVALUE tmp;
  481. X
  482. X    if (isleone(z1) || isleone(z2))
  483. X        tmp = _one_;
  484. X    else
  485. X        zgcd(z1, z2, &tmp);
  486. X    if (isunit(tmp)) {
  487. X        zcopy(z1, z1res);
  488. X        zcopy(z2, z2res);
  489. X    } else {
  490. X        zquo(z1, tmp, z1res);
  491. X        zquo(z2, tmp, z2res);
  492. X    }
  493. X    freeh(tmp.v);
  494. X}
  495. X
  496. X
  497. X/*
  498. X * Divide two numbers to obtain a quotient and remainder.
  499. X * This algorithm is taken from
  500. X * Knuth, The Art of Computer Programming, vol 2: Seminumerical Algorithms.
  501. X * Slight modifications were made to speed this mess up.
  502. X */
  503. Xvoid
  504. Xzdiv(z1, z2, res, rem)
  505. X    ZVALUE z1, z2, *res, *rem;
  506. X{
  507. X    long i, j, k;
  508. X    register HALF *q, *pp;
  509. X    SIUNION pair;        /* pair of halfword values */
  510. X    HALF h2, v2;
  511. X    long y;
  512. X    FULL x;
  513. X    ZVALUE ztmp1, ztmp2, ztmp3, quo;
  514. X
  515. X    if (iszero(z2))
  516. X        error("Division by zero");
  517. X    if (iszero(z1)) {
  518. X        *res = _zero_;
  519. X        *rem = _zero_;
  520. X        return;
  521. X    }
  522. X    if (isone(z2)) {
  523. X        zcopy(z1, res);
  524. X        *rem = _zero_;
  525. X        return;
  526. X    }
  527. X    i = 32768;
  528. X    j = 0;
  529. X    k = (long) z2.v[z2.len - 1];
  530. X    while (! (k & i)) {
  531. X        j ++;
  532. X        i >>= 1;
  533. X    }
  534. X    ztmp1.v = alloc(z1.len + 1);
  535. X    ztmp1.len = z1.len + 1;
  536. X    copyval(z1, ztmp1);
  537. X    ztmp1.v[z1.len] = 0;
  538. X    ztmp1.sign = 0;
  539. X    ztmp2.v = alloc(z2.len);
  540. X    ztmp2.len = z2.len;
  541. X    ztmp2.sign = 0;
  542. X    copyval(z2, ztmp2);
  543. X    if (zrel(ztmp1, ztmp2) < 0) {
  544. X        rem->v = ztmp1.v;
  545. X        rem->sign = z1.sign;
  546. X        rem->len = z1.len;
  547. X        freeh(ztmp2.v);
  548. X        *res = _zero_;
  549. X        return;
  550. X    }
  551. X    quo.len = z1.len - z2.len + 1;
  552. X    quo.v = alloc(quo.len);
  553. X    quo.sign = z1.sign != z2.sign;
  554. X    clearval(quo);
  555. X
  556. X    ztmp3.v = zalloctemp(z2.len + 1);
  557. X
  558. X    /*
  559. X     * Normalize z1 and z2
  560. X     */
  561. X    shiftl(ztmp1, j);
  562. X    shiftl(ztmp2, j);
  563. X
  564. X    k = ztmp1.len - ztmp2.len;
  565. X    q = quo.v + quo.len;
  566. X    y = ztmp1.len - 1;
  567. X    h2 = ztmp2.v [ztmp2.len - 1];
  568. X    v2 = 0;
  569. X    if (ztmp2.len >= 2)
  570. X        v2 = ztmp2.v [ztmp2.len - 2];
  571. X    for (;k--; --y) {
  572. X        pp = ztmp1.v + y - 1;
  573. X        pair.silow = pp[0];
  574. X        pair.sihigh = pp[1];
  575. X        if (ztmp1.v[y] == h2)
  576. X            x = BASE1;
  577. X        else
  578. X            x = pair.ivalue / h2;
  579. X        if (x) {
  580. X            while (pair.ivalue - x * h2 < BASE &&
  581. X                v2 * x > (pair.ivalue - x * h2) * BASE + ztmp1.v [y-2]) {
  582. X                    --x;
  583. X            }
  584. X            dmul(ztmp2, x, &ztmp3);
  585. X#ifdef divblab
  586. X            printf(" x: %ld\n", x);
  587. X            printf("ztmp1: ");
  588. X            printz(ztmp1);
  589. X            printf("ztmp2: ");
  590. X            printz(ztmp2);
  591. X            printf("ztmp3: ");
  592. X            printz(ztmp3);
  593. X#endif
  594. X            if (dsub(ztmp1, ztmp3, y, ztmp2.len)) {
  595. X                --x;
  596. X                /*
  597. X                printf("adding back\n");
  598. X                */
  599. X                dadd(ztmp1, ztmp2, y, ztmp2.len);
  600. X            }
  601. X        }
  602. X        trim(&ztmp1);
  603. X        *--q = (HALF)x;
  604. X    }
  605. X    shiftr(ztmp1, j);
  606. X    *rem = ztmp1;
  607. X    trim(rem);
  608. X    freeh(ztmp2.v);
  609. X    trim(&quo);
  610. X    *res = quo;
  611. X}
  612. X
  613. X
  614. X/*
  615. X * Return the quotient and remainder of an integer divided by a small
  616. X * number.  A nonzero remainder is only meaningful when both numbers
  617. X * are positive.
  618. X */
  619. Xlong
  620. Xzdivi(z, n, res)
  621. X    ZVALUE z, *res;
  622. X    long n;
  623. X{
  624. X    register HALF *h1, *sd;
  625. X    FULL val;
  626. X    HALF divval[2];
  627. X    ZVALUE div;
  628. X    ZVALUE dest;
  629. X    long len;
  630. X
  631. X    if (n == 0)
  632. X        error("Division by zero");
  633. X    if (iszero(z)) {
  634. X        *res = _zero_;
  635. X        return 0;
  636. X    }
  637. X    if (n < 0) {
  638. X        n = -n;
  639. X        z.sign = !z.sign;
  640. X    }
  641. X    if (n == 1) {
  642. X        zcopy(z, res);
  643. X        return 0;
  644. X    }
  645. X    /*
  646. X     * If the division is by a large number, then call the normal
  647. X     * divide routine.
  648. X     */
  649. X    if (n & ~BASE1) {
  650. X        div.sign = 0;
  651. X        div.len = 2;
  652. X        div.v = divval;
  653. X        divval[0] = (HALF) n;
  654. X        divval[1] = ((FULL) n) >> BASEB;
  655. X        zdiv(z, div, res, &dest);
  656. X        n = (istiny(dest) ? z1tol(dest) : z2tol(dest));
  657. X        freeh(dest.v);
  658. X        return n;
  659. X    }
  660. X    /*
  661. X     * Division is by a small number, so we can be quick about it.
  662. X     */
  663. X    len = z.len;
  664. X    dest.sign = z.sign;
  665. X    dest.len = len;
  666. X    dest.v = alloc(len);
  667. X    h1 = z.v + len - 1;
  668. X    sd = dest.v + len - 1;
  669. X    val = 0;
  670. X    while (len--) {
  671. X        val = ((val << BASEB) + ((FULL) *h1--));
  672. X        *sd-- = val / n;
  673. X        val %= n;
  674. X    }
  675. X    quicktrim(dest);
  676. X    *res = dest;
  677. X    return val;
  678. X}
  679. X
  680. X
  681. X/*
  682. X * Return the quotient of two numbers.
  683. X * This works the same as zdiv, except that the remainer is not returned.
  684. X */
  685. Xvoid
  686. Xzquo(z1, z2, res)
  687. X    ZVALUE z1, z2, *res;
  688. X{
  689. X    long i, j, k;
  690. X    register HALF *q, *pp;
  691. X    SIUNION pair;            /* pair of halfword values */
  692. X    HALF h2, v2;
  693. X    long y;
  694. X    FULL x;
  695. X    ZVALUE ztmp1, ztmp2, ztmp3, quo;
  696. X
  697. X    if (iszero(z2))
  698. X        error("Division by zero");
  699. X    if (iszero(z1)) {
  700. X        *res = _zero_;
  701. X        return;
  702. X    }
  703. X    if (isone(z2)) {
  704. X        zcopy(z1, res);
  705. X        return;
  706. X    }
  707. X    i = 32768;
  708. X    j = 0;
  709. X    k = (long) z2.v[z2.len - 1];
  710. X    while (! (k & i)) {
  711. X        j ++;
  712. X        i >>= 1;
  713. X    }
  714. X    ztmp1.v = alloc(z1.len + 1);
  715. X    ztmp1.len = z1.len + 1;
  716. X    copyval(z1, ztmp1);
  717. X    ztmp1.v[z1.len] = 0;
  718. X    ztmp1.sign = 0;
  719. X    ztmp2.v = alloc(z2.len);
  720. X    ztmp2.len = z2.len;
  721. X    ztmp2.sign = 0;
  722. X    copyval(z2, ztmp2);
  723. X    if (zrel(ztmp1, ztmp2) < 0) {
  724. X        freeh(ztmp1.v);
  725. X        freeh(ztmp2.v);
  726. X        *res = _zero_;
  727. X        return;
  728. X    }
  729. X    quo.len = z1.len - z2.len + 1;
  730. X    quo.v = alloc(quo.len);
  731. X    quo.sign = z1.sign != z2.sign;
  732. X    clearval(quo);
  733. X
  734. X    ztmp3.v = zalloctemp(z2.len + 1);
  735. X
  736. X    /*
  737. X     * Normalize z1 and z2
  738. X     */
  739. X    shiftl(ztmp1, j);
  740. X    shiftl(ztmp2, j);
  741. X
  742. X    k = ztmp1.len - ztmp2.len;
  743. X    q = quo.v + quo.len;
  744. X    y = ztmp1.len - 1;
  745. X    h2 = ztmp2.v [ztmp2.len - 1];
  746. X    v2 = 0;
  747. X    if (ztmp2.len >= 2)
  748. X        v2 = ztmp2.v [ztmp2.len - 2];
  749. X    for (;k--; --y) {
  750. X        pp = ztmp1.v + y - 1;
  751. X        pair.silow = pp[0];
  752. X        pair.sihigh = pp[1];
  753. X        if (ztmp1.v[y] == h2)
  754. X            x = BASE1;
  755. X        else
  756. X            x = pair.ivalue / h2;
  757. X        if (x) {
  758. X            while (pair.ivalue - x * h2 < BASE &&
  759. X                v2 * x > (pair.ivalue - x * h2) * BASE + ztmp1.v [y-2]) {
  760. X                    --x;
  761. X            }
  762. X            dmul(ztmp2, x, &ztmp3);
  763. X            if (dsub(ztmp1, ztmp3, y, ztmp2.len)) {
  764. X                --x;
  765. X                dadd(ztmp1, ztmp2, y, ztmp2.len);
  766. X            }
  767. X        }
  768. X        trim(&ztmp1);
  769. X        *--q = (HALF)x;
  770. X    }
  771. X    freeh(ztmp1.v);
  772. X    freeh(ztmp2.v);
  773. X    trim(&quo);
  774. X    *res = quo;
  775. X}
  776. X
  777. X
  778. X/*
  779. X * Compute the remainder after dividing one number by another.
  780. X * This is only defined for positive z2 values.
  781. X * The result is normalized to lie in the range 0 to z2-1.
  782. X */
  783. Xvoid
  784. Xzmod(z1, z2, rem)
  785. X    ZVALUE z1, z2, *rem;
  786. X{
  787. X    long i, j, k, neg;
  788. X    register HALF *pp;
  789. X    SIUNION pair;            /* pair of halfword values */
  790. X    HALF h2, v2;
  791. X    long y;
  792. X    FULL x;
  793. X    ZVALUE ztmp1, ztmp2, ztmp3;
  794. X
  795. X    if (iszero(z2))
  796. X        error("Division by zero");
  797. X    if (isneg(z2))
  798. X        error("Non-positive modulus");
  799. X    if (iszero(z1) || isunit(z2)) {
  800. X        *rem = _zero_;
  801. X        return;
  802. X    }
  803. X    if (istwo(z2)) {
  804. X        if (isodd(z1))
  805. X            *rem = _one_;
  806. X        else
  807. X            *rem = _zero_;
  808. X        return;
  809. X    }
  810. X    neg = z1.sign;
  811. X    z1.sign = 0;
  812. X
  813. X    /*
  814. X     * Do a quick check to see if the absolute value of the number
  815. X     * is less than the modulus.  If so, then the result is just a
  816. X     * subtract or a copy.
  817. X     */
  818. X    h2 = z1.v[z1.len - 1];
  819. X    v2 = z2.v[z2.len - 1];
  820. X    if ((z1.len < z2.len) || ((z1.len == z2.len) && (h2 < v2))) {
  821. X        if (neg)
  822. X            zsub(z2, z1, rem);
  823. X        else
  824. X            zcopy(z1, rem);
  825. X        return;
  826. X    }
  827. X
  828. X    /*
  829. X     * Do another quick check to see if the number is positive and
  830. X     * between the size of the modulus and twice the modulus.
  831. X     * If so, then the answer is just another subtract.
  832. X     */
  833. X    if (!neg && (z1.len == z2.len) && (h2 > v2) &&
  834. X        (((FULL) h2) < 2 * ((FULL) v2)))
  835. X    {
  836. X        zsub(z1, z2, rem);
  837. X        return;
  838. X    }
  839. X
  840. X    /*
  841. X     * If the modulus is an exact power of two, then the result
  842. X     * can be obtained by ignoring the high bits of the number.
  843. X     * This truncation assumes that the number of words for the
  844. X     * number is at least as large as the number of words in the
  845. X     * modulus, which is true at this point.
  846. X     */
  847. X    if (((v2 & -v2) == v2) && zisonebit(z2)) {    /* ASSUMES 2'S COMP */
  848. X        i = zhighbit(z2);
  849. X        z1.len = (i + BASEB - 1) / BASEB;
  850. X        zcopy(z1, &ztmp1);
  851. X        i %= BASEB;
  852. X        if (i)
  853. X            ztmp1.v[ztmp1.len - 1] &= ((((HALF) 1) << i) - 1);
  854. X        ztmp2.len = 0;
  855. X        goto gotanswer;
  856. X    }
  857. X
  858. X    /*
  859. X     * If the modulus is one less than an exact power of two, then
  860. X     * the result can be simplified similarly to "casting out 9's".
  861. X     * Only do this simplification for large enough modulos.
  862. X     */
  863. X    if ((z2.len > 1) && (z2.v[0] == BASE1) && zisallbits(z2)) {
  864. X        i = -(zhighbit(z2) + 1);
  865. X        zcopy(z1, &ztmp1);
  866. X        z1 = ztmp1;
  867. X        while ((k = zrel(z1, z2)) > 0) {
  868. X            ztmp1 = _zero_;
  869. X            while (!iszero(z1)) {
  870. X                zand(z1, z2, &ztmp2);
  871. X                zadd(ztmp2, ztmp1, &ztmp3);
  872. X                freeh(ztmp1.v);
  873. X                freeh(ztmp2.v);
  874. X                ztmp1 = ztmp3;
  875. X                zshift(z1, i, &ztmp2);
  876. X                freeh(z1.v);
  877. X                z1 = ztmp2;
  878. X            }
  879. X            freeh(z1.v);
  880. X            z1 = ztmp1;
  881. X        }
  882. X        if (k == 0) {
  883. X            freeh(ztmp1.v);
  884. X            *rem = _zero_;
  885. X            return;
  886. X        }
  887. X        ztmp2.len = 0;
  888. X        goto gotanswer;
  889. X    }
  890. X
  891. X    /*
  892. X     * Must actually do the divide.
  893. X     */
  894. X    i = 32768;
  895. X    j = 0;
  896. X    k = (long) z2.v[z2.len - 1];
  897. X    while (! (k & i)) {
  898. X        j ++;
  899. X        i >>= 1;
  900. X    }
  901. X    ztmp1.v = alloc(z1.len + 1);
  902. X    ztmp1.len = z1.len + 1;
  903. X    copyval(z1, ztmp1);
  904. X    ztmp1.v[z1.len] = 0;
  905. X    ztmp1.sign = 0;
  906. X    ztmp2.v = alloc(z2.len);
  907. X    ztmp2.len = z2.len;
  908. X    ztmp2.sign = 0;
  909. X    copyval(z2, ztmp2);
  910. X    if (zrel(ztmp1, ztmp2) < 0)
  911. X        goto gotanswer;
  912. X
  913. X    ztmp3.v = zalloctemp(z2.len + 1);
  914. X
  915. X    /*
  916. X     * Normalize z1 and z2
  917. X     */
  918. X    shiftl(ztmp1, j);
  919. X    shiftl(ztmp2, j);
  920. X
  921. X    k = ztmp1.len - ztmp2.len;
  922. X    y = ztmp1.len - 1;
  923. X    h2 = ztmp2.v [ztmp2.len - 1];
  924. X    v2 = 0;
  925. X    if (ztmp2.len >= 2)
  926. X        v2 = ztmp2.v [ztmp2.len - 2];
  927. X    for (;k--; --y) {
  928. X        pp = ztmp1.v + y - 1;
  929. X        pair.silow = pp[0];
  930. X        pair.sihigh = pp[1];
  931. X        if (ztmp1.v[y] == h2)
  932. X            x = BASE1;
  933. X        else
  934. X            x = pair.ivalue / h2;
  935. X        if (x) {
  936. X            while (pair.ivalue - x * h2 < BASE &&
  937. X                v2 * x > (pair.ivalue - x * h2) * BASE + ztmp1.v [y-2]) {
  938. X                    --x;
  939. X            }
  940. X            dmul(ztmp2, x, &ztmp3);
  941. X            if (dsub(ztmp1, ztmp3, y, ztmp2.len))
  942. X                dadd(ztmp1, ztmp2, y, ztmp2.len);
  943. X        }
  944. X        trim(&ztmp1);
  945. X    }
  946. X    shiftr(ztmp1, j);
  947. X
  948. Xgotanswer:
  949. X    trim(&ztmp1);
  950. X    if (ztmp2.len)
  951. X        freeh(ztmp2.v);
  952. X    if (neg && !iszero(ztmp1)) {
  953. X        zsub(z2, ztmp1, rem);
  954. X        freeh(ztmp1.v);
  955. X    } else
  956. X        *rem = ztmp1;
  957. X}
  958. X
  959. X
  960. X/*
  961. X * Calculate the mod of an integer by a small number.
  962. X * This is only defined for positive moduli.
  963. X */
  964. Xlong
  965. Xzmodi(z, n)
  966. X    ZVALUE z;
  967. X    long n;
  968. X{
  969. X    register HALF *h1;
  970. X    FULL val;
  971. X    HALF divval[2];
  972. X    ZVALUE div;
  973. X    ZVALUE temp;
  974. X    long len;
  975. X
  976. X    if (n == 0)
  977. X        error("Division by zero");
  978. X    if (n < 0)
  979. X        error("Non-positive modulus");
  980. X    if (iszero(z) || (n == 1))
  981. X        return 0;
  982. X    if (isone(z))
  983. X        return 1;
  984. X    /*
  985. X     * If the modulus is by a large number, then call the normal
  986. X     * modulo routine.
  987. X     */
  988. X    if (n & ~BASE1) {
  989. X        div.sign = 0;
  990. X        div.len = 2;
  991. X        div.v = divval;
  992. X        divval[0] = (HALF) n;
  993. X        divval[1] = ((FULL) n) >> BASEB;
  994. X        zmod(z, div, &temp);
  995. X        n = (istiny(temp) ? z1tol(temp) : z2tol(temp));
  996. X        freeh(temp.v);
  997. X        return n;
  998. X    }
  999. X    /*
  1000. X     * The modulus is by a small number, so we can do this quickly.
  1001. X     */
  1002. X    len = z.len;
  1003. X    h1 = z.v + len - 1;
  1004. X    val = 0;
  1005. X    while (len--)
  1006. X        val = ((val << BASEB) + ((FULL) *h1--)) % n;
  1007. X    if (z.sign)
  1008. X        val = n - val;
  1009. X    return val;
  1010. X}
  1011. X
  1012. X
  1013. X/*
  1014. X * Return whether or not one number exactly divides another one.
  1015. X * Returns TRUE if division occurs with no remainder.
  1016. X * z1 is the number to be divided by z2.
  1017. X */
  1018. XBOOL
  1019. Xzdivides(z1, z2)
  1020. X    ZVALUE z1, z2;        /* numbers to test division into and by */
  1021. X{
  1022. X    ZVALUE temp;
  1023. X    long cv;
  1024. X
  1025. X    z1.sign = 0;
  1026. X    z2.sign = 0;
  1027. X    /*
  1028. X     * Take care of obvious cases first
  1029. X     */
  1030. X    if (isleone(z2)) {    /* division by zero or one */
  1031. X        if (*z2.v == 0)
  1032. X            error("Division by zero");
  1033. X        return TRUE;
  1034. X    }
  1035. X    if (iszero(z1))    /* everything divides zero */
  1036. X        return TRUE;
  1037. X    if (z1.len < z2.len)    /* quick size comparison */
  1038. X        return FALSE;
  1039. X    if ((z1.len == z2.len) && (z1.v[z1.len-1] < z2.v[z2.len-1]))    /* more */
  1040. X        return FALSE;
  1041. X    if (isodd(z1) && iseven(z2))    /* can't divide odd by even */
  1042. X        return FALSE;
  1043. X    if (zlowbit(z1) < zlowbit(z2))    /* can't have smaller power of two */
  1044. X        return FALSE;
  1045. X    cv = zrel(z1, z2);    /* can't divide smaller number */
  1046. X    if (cv <= 0)
  1047. X        return (cv == 0);
  1048. X    /*
  1049. X     * Now do the real work.  Divisor divides dividend if the gcd of the
  1050. X     * two numbers equals the divisor.
  1051. X     */
  1052. X    zgcd(z1, z2, &temp);
  1053. X    cv = zcmp(z2, temp);
  1054. X    freeh(temp.v);
  1055. X    return (cv == 0);
  1056. X}
  1057. X
  1058. X
  1059. X/*
  1060. X * Compute the logical OR of two numbers
  1061. X */
  1062. Xvoid
  1063. Xzor(z1, z2, res)
  1064. X    ZVALUE z1, z2, *res;
  1065. X{
  1066. X    register HALF *sp, *dp;
  1067. X    long len;
  1068. X    ZVALUE bz, lz, dest;
  1069. X
  1070. X    if (z1.len >= z2.len) {
  1071. X        bz = z1;
  1072. X        lz = z2;
  1073. X    } else {
  1074. X        bz = z2;
  1075. X        lz = z1;
  1076. X    }
  1077. X    dest.len = bz.len;
  1078. X    dest.v = alloc(dest.len);
  1079. X    dest.sign = 0;
  1080. X    copyval(bz, dest);
  1081. X    len = lz.len;
  1082. X    sp = lz.v;
  1083. X    dp = dest.v;
  1084. X    while (len--)
  1085. X        *dp++ |= *sp++;
  1086. X    *res = dest;
  1087. X}
  1088. X
  1089. X
  1090. X/*
  1091. X * Compute the logical AND of two numbers.
  1092. X */
  1093. Xvoid
  1094. Xzand(z1, z2, res)
  1095. X    ZVALUE z1, z2, *res;
  1096. X{
  1097. X    register HALF *h1, *h2, *hd;
  1098. X    register long len;
  1099. X    ZVALUE dest;
  1100. X
  1101. X    len = ((z1.len <= z2.len) ? z1.len : z2.len);
  1102. X    h1 = &z1.v[len-1];
  1103. X    h2 = &z2.v[len-1];
  1104. X    while ((len > 1) && ((*h1 & *h2) == 0)) {
  1105. X        h1--;
  1106. X        h2--;
  1107. X        len--;
  1108. X    }
  1109. X    dest.len = len;
  1110. X    dest.v = alloc(len);
  1111. X    dest.sign = 0;
  1112. X    h1 = z1.v;
  1113. X    h2 = z2.v;
  1114. X    hd = dest.v;
  1115. X    while (len--)
  1116. X        *hd++ = (*h1++ & *h2++);
  1117. X    *res = dest;
  1118. X}
  1119. X
  1120. X
  1121. X/*
  1122. X * Compute the logical XOR of two numbers.
  1123. X */
  1124. Xvoid
  1125. Xzxor(z1, z2, res)
  1126. X    ZVALUE z1, z2, *res;
  1127. X{
  1128. X    register HALF *sp, *dp;
  1129. X    long len;
  1130. X    ZVALUE bz, lz, dest;
  1131. X
  1132. X    if (z1.len == z2.len) {
  1133. X        for (len = z1.len; ((len > 1) && (z1.v[len-1] == z2.v[len-1])); len--) ;
  1134. X        z1.len = len;
  1135. X        z2.len = len;
  1136. X    }
  1137. X    if (z1.len >= z2.len) {
  1138. X        bz = z1;
  1139. X        lz = z2;
  1140. X    } else {
  1141. X        bz = z2;
  1142. X        lz = z1;
  1143. X    }
  1144. X    dest.len = bz.len;
  1145. X    dest.v = alloc(dest.len);
  1146. X    dest.sign = 0;
  1147. X    copyval(bz, dest);
  1148. X    len = lz.len;
  1149. X    sp = lz.v;
  1150. X    dp = dest.v;
  1151. X    while (len--)
  1152. X        *dp++ ^= *sp++;
  1153. X    *res = dest;
  1154. X}
  1155. X
  1156. X
  1157. X/*
  1158. X * Shift a number left (or right) by the specified number of bits.
  1159. X * Positive shift means to the left.  When shifting right, rightmost
  1160. X * bits are lost.  The sign of the number is preserved.
  1161. X */
  1162. Xvoid
  1163. Xzshift(z, n, res)
  1164. X    ZVALUE z, *res;
  1165. X    long n;
  1166. X{
  1167. X    ZVALUE ans;
  1168. X    long hc;        /* number of halfwords shift is by */
  1169. X
  1170. X    if (iszero(z)) {
  1171. X        *res = _zero_;
  1172. X        return;
  1173. X    }
  1174. X    if (n == 0) {
  1175. X        zcopy(z, res);
  1176. X        return;
  1177. X    }
  1178. X    /*
  1179. X     * If shift value is negative, then shift right.
  1180. X     * Check for large shifts, and handle word-sized shifts quickly.
  1181. X     */
  1182. X    if (n < 0) {
  1183. X        n = -n;
  1184. X        if ((n < 0) || (n >= (z.len * BASEB))) {
  1185. X            *res = _zero_;
  1186. X            return;
  1187. X        }
  1188. X        hc = n / BASEB;
  1189. X        n %= BASEB;
  1190. X        z.v += hc;
  1191. X        z.len -= hc;
  1192. X        ans.len = z.len;
  1193. X        ans.v = alloc(ans.len);
  1194. X        ans.sign = z.sign;
  1195. X        copyval(z, ans);
  1196. X        if (n > 0) {
  1197. X            shiftr(ans, n);
  1198. X            trim(&ans);
  1199. X        }
  1200. X        if (iszero(ans)) {
  1201. X            freeh(ans.v);
  1202. X            ans = _zero_;
  1203. X        }
  1204. X        *res = ans;
  1205. X        return;
  1206. X    }
  1207. X    /*
  1208. X     * Shift value is positive, so shift leftwards.
  1209. X     * Check specially for a shift of the value 1, since this is common.
  1210. X     * Also handle word-sized shifts quickly.
  1211. X     */
  1212. X    if (isunit(z)) {
  1213. X        zbitvalue(n, res);
  1214. X        res->sign = z.sign;
  1215. X        return;
  1216. X    }
  1217. X    hc = n / BASEB;
  1218. X    n %= BASEB;
  1219. X    ans.len = z.len + hc + 1;
  1220. X    ans.v = alloc(ans.len);
  1221. X    ans.sign = z.sign;
  1222. X    if (hc > 0)
  1223. X        memset((char *) ans.v, 0, hc * sizeof(HALF));
  1224. X    memcpy((char *) (ans.v + hc), 
  1225. X        (char *) z.v, z.len * sizeof(HALF));
  1226. X    ans.v[ans.len - 1] = 0;
  1227. X    if (n > 0) {
  1228. X        ans.v += hc;
  1229. X        ans.len -= hc;
  1230. X        shiftl(ans, n);
  1231. X        ans.v -= hc;
  1232. X        ans.len += hc;
  1233. X    }
  1234. X    trim(&ans);
  1235. X    *res = ans;
  1236. X}
  1237. X
  1238. X
  1239. X/*
  1240. X * Return the position of the lowest bit which is set in the binary
  1241. X * representation of a number (counting from zero).  This is the highest
  1242. X * power of two which evenly divides the number.
  1243. X */
  1244. Xlong
  1245. Xzlowbit(z)
  1246. X    ZVALUE z;
  1247. X{
  1248. X    register HALF *zp;
  1249. X    long n;
  1250. X    HALF dataval;
  1251. X    HALF *bitval;
  1252. X
  1253. X    n = 0;
  1254. X    for (zp = z.v; *zp == 0; zp++)
  1255. X        if (++n >= z.len)
  1256. X            return 0;
  1257. X    dataval = *zp;
  1258. X    bitval = bitmask;
  1259. X    while ((*(bitval++) & dataval) == 0) {
  1260. X    }
  1261. X    return (n*BASEB)+(bitval-bitmask-1);
  1262. X}
  1263. X
  1264. X
  1265. X/*
  1266. X * Return the position of the highest bit which is set in the binary
  1267. X * representation of a number (counting from zero).  This is the highest power
  1268. X * of two which is less than or equal to the number (which is assumed nonzero).
  1269. X */
  1270. Xlong
  1271. Xzhighbit(z)
  1272. X    ZVALUE z;
  1273. X{
  1274. X    HALF dataval;
  1275. X    HALF *bitval;
  1276. X
  1277. X    dataval = z.v[z.len-1];
  1278. X    if (dataval) {
  1279. X        bitval = bitmask+BASEB;
  1280. X        while ((*(--bitval) & dataval) == 0) {
  1281. X        }
  1282. X    }
  1283. X    return (z.len*BASEB)+(bitval-bitmask-BASEB);
  1284. X}
  1285. X
  1286. X
  1287. X#if 0
  1288. X/*
  1289. X * Reverse the bits of a particular range of bits of a number.
  1290. X *
  1291. X * This function returns an integer with bits a thru b swapped.
  1292. X * That is, bit a is swapped with bit b, bit a+1 is swapped with b-1,
  1293. X * and so on.
  1294. X *
  1295. X * As a special case, if the ending bit position is < 0, is it taken to 
  1296. X * mean the highest bit set.  Thus zbitrev(0, -1, z, &res) will 
  1297. X * perform a complete bit reverse of the number 'z'.
  1298. X *
  1299. X * As a special case, if the starting bit position is < 0, is it taken to 
  1300. X * mean the lowest bit set.  Thus zbitrev(-1, -1, z, &res) is the
  1301. X * same as zbitrev(lowbit(z), highbit(z), z, &res).
  1302. X *
  1303. X * Note that the low order bit number is taken to be 0.  Also, bitrev
  1304. X * ignores the sign of the number.
  1305. X *
  1306. X * Bits beyond the highest bit are taken to be zero.  Thus the calling
  1307. X * bitrev(0, 100, _one_, &res) will result in a value of 2^100.
  1308. X */
  1309. Xvoid
  1310. Xzbitrev(low, high, z, res)
  1311. X    long low;    /* lowest bit to reverse, <0 => lowbit(z) */
  1312. X    long high;    /* highest bit to reverse, <0 => highbit(z) */
  1313. X    ZVALUE z;    /* value to bit reverse */
  1314. X    ZVALUE *res;    /* resulting bit reverse number */
  1315. X{
  1316. X}
  1317. X#endif
  1318. X
  1319. X
  1320. X/*
  1321. X * Return whether or not the specifed bit number is set in a number.
  1322. X * Rightmost bit of a number is bit 0.
  1323. X */
  1324. XBOOL
  1325. Xzisset(z, n)
  1326. X    ZVALUE z;
  1327. X    long n;
  1328. X{
  1329. X    if ((n < 0) || ((n / BASEB) >= z.len))
  1330. X        return FALSE;
  1331. X    return ((z.v[n / BASEB] & (((HALF) 1) << (n % BASEB))) != 0);
  1332. X}
  1333. X
  1334. X
  1335. X/*
  1336. X * Check whether or not a number has exactly one bit set, and
  1337. X * thus is an exact power of two.  Returns TRUE if so.
  1338. X */
  1339. XBOOL
  1340. Xzisonebit(z)
  1341. X    ZVALUE z;
  1342. X{
  1343. X    register HALF *hp;
  1344. X    register LEN len;
  1345. X
  1346. X    if (iszero(z) || isneg(z))
  1347. X        return FALSE;
  1348. X    hp = z.v;
  1349. X    len = z.len;
  1350. X    while (len > 4) {
  1351. X        len -= 4;
  1352. X        if (*hp++ || *hp++ || *hp++ || *hp++)
  1353. X            return FALSE;
  1354. X    }
  1355. X    while (--len > 0) {
  1356. X        if (*hp++)
  1357. X            return FALSE;
  1358. X    }
  1359. X    return ((*hp & -*hp) == *hp);        /* NEEDS 2'S COMPLEMENT */
  1360. X}
  1361. X
  1362. X
  1363. X/*
  1364. X * Check whether or not a number has all of its bits set below some
  1365. X * bit position, and thus is one less than an exact power of two.
  1366. X * Returns TRUE if so.
  1367. X */
  1368. XBOOL
  1369. Xzisallbits(z)
  1370. X    ZVALUE z;
  1371. X{
  1372. X    register HALF *hp;
  1373. X    register LEN len;
  1374. X    HALF digit;
  1375. X
  1376. X    if (iszero(z) || isneg(z))
  1377. X        return FALSE;
  1378. X    hp = z.v;
  1379. X    len = z.len;
  1380. X    while (len > 4) {
  1381. X        len -= 4;
  1382. X        if ((*hp++ != BASE1) || (*hp++ != BASE1) ||
  1383. X            (*hp++ != BASE1) || (*hp++ != BASE1))
  1384. X                return FALSE;
  1385. X    }
  1386. X    while (--len > 0) {
  1387. X        if (*hp++ != BASE1)
  1388. X            return FALSE;
  1389. X    }
  1390. X    digit = *hp + 1;
  1391. X    return ((digit & -digit) == digit);    /* NEEDS 2'S COMPLEMENT */
  1392. X}
  1393. X
  1394. X
  1395. X/*
  1396. X * Return the number whose binary representation contains only one bit which
  1397. X * is in the specified position (counting from zero).  This is equivilant
  1398. X * to raising two to the given power.
  1399. X */
  1400. Xvoid
  1401. Xzbitvalue(n, res)
  1402. X    long n;
  1403. X    ZVALUE *res;
  1404. X{
  1405. X    ZVALUE z;
  1406. X
  1407. X    if (n < 0) n = 0;
  1408. X    z.sign = 0;
  1409. X    z.len = (n / BASEB) + 1;
  1410. X    z.v = alloc(z.len);
  1411. X    clearval(z);
  1412. X    z.v[z.len-1] = (((HALF) 1) << (n % BASEB));
  1413. X    *res = z;
  1414. X}
  1415. X
  1416. X
  1417. X/*
  1418. X * Compare a number against zero.
  1419. X * Returns the sgn function of the number (-1, 0, or 1).
  1420. X */
  1421. XFLAG
  1422. Xztest(z)
  1423. X    ZVALUE z;
  1424. X{
  1425. X    register int sign;
  1426. X    register HALF *h;
  1427. X    register long len;
  1428. X
  1429. X    sign = 1;
  1430. X    if (z.sign)
  1431. X        sign = -sign;
  1432. X    h = z.v;
  1433. X    len = z.len;
  1434. X    while (len--)
  1435. X        if (*h++)
  1436. X            return sign;
  1437. X    return 0;
  1438. X}
  1439. X
  1440. X
  1441. X/*
  1442. X * Compare two numbers to see which is larger.
  1443. X * Returns -1 if first number is smaller, 0 if they are equal, and 1 if
  1444. X * first number is larger.  This is the same result as ztest(z2-z1).
  1445. X */
  1446. XFLAG
  1447. Xzrel(z1, z2)
  1448. X    ZVALUE z1, z2;
  1449. X{
  1450. X    register HALF *h1, *h2;
  1451. X    register long len1, len2;
  1452. X    int sign;
  1453. X
  1454. X    sign = 1;
  1455. X    if (z1.sign < z2.sign)
  1456. X        return 1;
  1457. X    if (z2.sign < z1.sign)
  1458. X        return -1;
  1459. X    if (z2.sign)
  1460. X        sign = -1;
  1461. X    len1 = z1.len;
  1462. X    len2 = z2.len;
  1463. X    h1 = z1.v + z1.len - 1;
  1464. X    h2 = z2.v + z2.len - 1;
  1465. X    while (len1 > len2) {
  1466. X        if (*h1--)
  1467. X            return sign;
  1468. X        len1--;
  1469. X    }
  1470. X    while (len2 > len1) {
  1471. X        if (*h2--)
  1472. X            return -sign;
  1473. X        len2--;
  1474. X    }
  1475. X    while (len1--) {
  1476. X        if (*h1-- != *h2--)
  1477. X            break;
  1478. X    }
  1479. X    if ((len1 = *++h1) > (len2 = *++h2))
  1480. X        return sign;
  1481. X    if (len1 < len2)
  1482. X        return -sign;
  1483. X    return 0;
  1484. X}
  1485. X
  1486. X
  1487. X/*
  1488. X * Compare two numbers to see if they are equal or not.
  1489. X * Returns TRUE if they differ.
  1490. X */
  1491. XBOOL
  1492. Xzcmp(z1, z2)
  1493. X    ZVALUE z1, z2;
  1494. X{
  1495. X    register HALF *h1, *h2;
  1496. X    register long len;
  1497. X
  1498. X    if ((z1.sign != z2.sign) || (z1.len != z2.len) || (*z1.v != *z2.v))
  1499. X        return TRUE;
  1500. X    len = z1.len;
  1501. X    h1 = z1.v;
  1502. X    h2 = z2.v;
  1503. X    while (len-- > 0) {
  1504. X        if (*h1++ != *h2++)
  1505. X            return TRUE;
  1506. X    }
  1507. X    return FALSE;
  1508. X}
  1509. X
  1510. X
  1511. X/*
  1512. X * Internal utility subroutines
  1513. X */
  1514. Xstatic void
  1515. Xdadd(z1, z2, y, n)
  1516. X    ZVALUE z1, z2;
  1517. X    long y, n;
  1518. X{
  1519. X    HALF *s1, *s2;
  1520. X    short carry;
  1521. X    long sum;
  1522. X
  1523. X    s1 = z1.v + y - n;
  1524. X    s2 = z2.v;
  1525. X    carry = 0;
  1526. X    while (n--) {
  1527. X        sum = (long)*s1 + (long)*s2 + carry;
  1528. X        carry = 0;
  1529. X        if (sum >= BASE) {
  1530. X            sum -= BASE;
  1531. X            carry = 1;
  1532. X        }
  1533. X        *s1 = (HALF)sum;
  1534. X        ++s1;
  1535. X        ++s2;
  1536. X    }
  1537. X    sum = (long)*s1 + carry;
  1538. X    *s1 = (HALF)sum;
  1539. X}
  1540. X
  1541. X
  1542. X/*
  1543. X * Do subtract for divide, returning TRUE if subtraction went negative.
  1544. X */
  1545. Xstatic BOOL
  1546. Xdsub(z1, z2, y, n)
  1547. X    ZVALUE z1, z2;
  1548. X    long y, n;
  1549. X{
  1550. X    HALF *s1, *s2, *s3;
  1551. X    FULL i1;
  1552. X    BOOL neg;
  1553. X
  1554. X    neg = FALSE;
  1555. X    s1 = z1.v + y - n;
  1556. X    s2 = z2.v;
  1557. X    if (++n > z2.len)
  1558. X        n = z2.len;
  1559. X    while (n--) {
  1560. X        i1 = (FULL) *s1;
  1561. X        if (i1 < (FULL) *s2) {
  1562. X            s3 = s1 + 1;
  1563. X            while (s3 < z1.v + z1.len && !(*s3)) {
  1564. X                *s3 = BASE1;
  1565. X                ++s3;
  1566. X            }
  1567. X            if (s3 >= z1.v + z1.len)
  1568. X                neg = TRUE;
  1569. X            else
  1570. X                --(*s3);
  1571. X            i1 += BASE;
  1572. X        }
  1573. X        *s1 = i1 - (FULL) *s2;
  1574. X        ++s1;
  1575. X        ++s2;
  1576. X    }
  1577. X    return neg;
  1578. X}
  1579. X
  1580. X
  1581. X/*
  1582. X * Multiply a number by a single 'digit'.
  1583. X * This is meant to be used only by the divide routine, and so the
  1584. X * destination area must already be allocated and be large enough.
  1585. X */
  1586. Xstatic void
  1587. Xdmul(z, mul, dest)
  1588. X    ZVALUE z;
  1589. X    FULL mul;
  1590. X    ZVALUE *dest;
  1591. X{
  1592. X    register HALF *zp, *dp;
  1593. X    SIUNION sival;
  1594. X    FULL carry;
  1595. X    long len;
  1596. X
  1597. X    dp = dest->v;
  1598. X    dest->sign = 0;
  1599. X    if (mul == 0) {
  1600. X        dest->len = 1;
  1601. X        *dp = 0;
  1602. X        return;
  1603. X    }
  1604. X    len = z.len;
  1605. X    zp = z.v + len - 1;
  1606. X    while ((*zp == 0) && (len > 1)) {
  1607. X        len--;
  1608. X        zp--;
  1609. X    }
  1610. X    dest->len = len;
  1611. X    zp = z.v;
  1612. X    carry = 0;
  1613. X    while (len >= 4) {
  1614. X        len -= 4;
  1615. X        sival.ivalue = (mul * ((FULL) *zp++)) + carry;
  1616. X        *dp++ = sival.silow;
  1617. X        sival.ivalue = (mul * ((FULL) *zp++)) + ((FULL) sival.sihigh);
  1618. X        *dp++ = sival.silow;
  1619. X        sival.ivalue = (mul * ((FULL) *zp++)) + ((FULL) sival.sihigh);
  1620. X        *dp++ = sival.silow;
  1621. X        sival.ivalue = (mul * ((FULL) *zp++)) + ((FULL) sival.sihigh);
  1622. X        *dp++ = sival.silow;
  1623. X        carry = sival.sihigh;
  1624. X    }
  1625. X    while (--len >= 0) {
  1626. X        sival.ivalue = (mul * ((FULL) *zp++)) + carry;
  1627. X        *dp++ = sival.silow;
  1628. X        carry = sival.sihigh;
  1629. X    }
  1630. X    if (carry) {
  1631. X        *dp = (HALF)carry;
  1632. X        dest->len++;
  1633. X    }
  1634. X}
  1635. X
  1636. X
  1637. X/*
  1638. X * Utility to calculate the gcd of two small integers.
  1639. X */
  1640. Xlong
  1641. Xiigcd(i1, i2)
  1642. X    long i1, i2;
  1643. X{
  1644. X    FULL f1, f2, temp;
  1645. X
  1646. X    f1 = (FULL) ((i1 >= 0) ? i1 : -i1);
  1647. X    f2 = (FULL) ((i2 >= 0) ? i2 : -i2);
  1648. X    while (f1) {
  1649. X        temp = f2 % f1;
  1650. X        f2 = f1;
  1651. X        f1 = temp;
  1652. X    }
  1653. X    return (long) f2;
  1654. X}
  1655. X
  1656. X
  1657. Xvoid
  1658. Xtrim(z)
  1659. X    ZVALUE *z;
  1660. X{
  1661. X    register HALF *h;
  1662. X    register long len;
  1663. X
  1664. X    h = z->v + z->len - 1;
  1665. X    len = z->len;
  1666. X    while (*h == 0 && len > 1) {
  1667. X        --h;
  1668. X        --len;
  1669. X    }
  1670. X    z->len = len;
  1671. X}
  1672. X
  1673. X
  1674. X/*
  1675. X * Utility routine to shift right.
  1676. X */
  1677. Xvoid
  1678. Xshiftr(z, n)
  1679. X    ZVALUE z;
  1680. X    long n;
  1681. X{
  1682. X    register HALF *h, *lim;
  1683. X    FULL mask, maskt;
  1684. X    long len;
  1685. X
  1686. X    if (n >= BASEB) {
  1687. X        len = n / BASEB;
  1688. X        h = z.v;
  1689. X        lim = z.v + z.len - len;
  1690. X        while (h < lim) {
  1691. X            h[0] = h[len];
  1692. X            ++h;
  1693. X        }
  1694. X        n -= BASEB * len;
  1695. X        lim = z.v + z.len;
  1696. X        while (h < lim)
  1697. X            *h++ = 0;
  1698. X    }
  1699. X    if (n) {
  1700. X        len = z.len;
  1701. X        h = z.v + len - 1;
  1702. X        mask = 0;
  1703. X        while (len--) {
  1704. X            maskt = (((FULL) *h) << (BASEB - n)) & BASE1;
  1705. X            *h = (*h >> n) | mask;
  1706. X            mask = maskt;
  1707. X            --h;
  1708. X        }
  1709. X    }
  1710. X}
  1711. X
  1712. X
  1713. X/*
  1714. X * Utility routine to shift left.
  1715. X */
  1716. Xvoid
  1717. Xshiftl(z, n)
  1718. X    ZVALUE z;
  1719. X    long n;
  1720. X{
  1721. X    register HALF *h;
  1722. X    FULL mask, i;
  1723. X    long len;
  1724. X
  1725. X    if (n >= BASEB) {
  1726. X        len = n / BASEB;
  1727. X        h = z.v + z.len - 1;
  1728. X        while (!*h)
  1729. X            --h;
  1730. X        while (h >= z.v) {
  1731. X            h[len] = h[0];
  1732. X            --h;
  1733. X        }
  1734. X        n -= BASEB * len;
  1735. X        while (len)
  1736. X            h[len--] = 0;
  1737. X    }
  1738. X    if (n > 0) {
  1739. X        len = z.len;
  1740. X        h = z.v;
  1741. X        mask = 0;
  1742. X        while (len--) {
  1743. X            i = (((FULL) *h) << n) | mask;
  1744. X            if (i > BASE1) {
  1745. X                mask = i >> BASEB;
  1746. X                i &= BASE1;
  1747. X            } else
  1748. X                mask = 0;
  1749. X            *h = (HALF) i;
  1750. X            ++h;
  1751. X        }
  1752. X    }
  1753. X}
  1754. X
  1755. X/*
  1756. X * initmasks - init the bitmask rotation arrays
  1757. X *
  1758. X * bitmask[i]      (1 << (i-1)),  for  -BASEB*4<=i<=BASEB*4
  1759. X * rotmask[j][k] (1 << ((j+k-1)%BASEB)),  for  -BASEB*2<=j,k<=BASEB*2
  1760. X *
  1761. X * The bmask array contains 8 cycles of rotations of a bit mask.
  1762. X * We point bitmask and the rotmask pointers into the middle to
  1763. X * ensure that we can have a complete two cycle swing forward
  1764. X * and backward.
  1765. X */
  1766. Xvoid
  1767. Xinitmasks()
  1768. X{
  1769. X    int i;
  1770. X
  1771. X    /*
  1772. X     * setup the bmask array
  1773. X     */
  1774. X    bmask = alloc((8*BASEB)+1);
  1775. X    for (i=0; i < (8*BASEB)+1; ++i) {
  1776. X        bmask[i] = 1 << (i%BASEB);
  1777. X    }
  1778. X
  1779. X    /*
  1780. X     * setup the rmask pointers
  1781. X     */
  1782. X    rmask = (HALF **)malloc(sizeof(HALF *)*((BASEB*4)+2));
  1783. X    for (i = 0; i <= (4*BASEB)+1; ++i) {
  1784. X        rmask[i] = &bmask[(2*BASEB)+i];
  1785. X    }
  1786. X
  1787. X#if 0
  1788. X    /* 
  1789. X     * setup the rotmask array, allow for -2*BASEB thru 2*BASEB indexing
  1790. X     */
  1791. X    rotmask = &rmask[2*BASEB];
  1792. X#endif
  1793. X
  1794. X    /*
  1795. X     * setup the bitmask array to allow -4*BASEB thru 4*BASEB indexing
  1796. X     */
  1797. X    bitmask = &bmask[4*BASEB];
  1798. X    return;
  1799. X}
  1800. X
  1801. X/* END CODE */
  1802. END_OF_FILE
  1803. if test 32210 -ne `wc -c <'zmath.c'`; then
  1804.     echo shar: \"'zmath.c'\" unpacked with wrong size!
  1805. fi
  1806. # end of 'zmath.c'
  1807. fi
  1808. echo shar: End of archive 15 \(of 21\).
  1809. cp /dev/null ark15isdone
  1810. MISSING=""
  1811. for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 ; do
  1812.     if test ! -f ark${I}isdone ; then
  1813.     MISSING="${MISSING} ${I}"
  1814.     fi
  1815. done
  1816. if test "${MISSING}" = "" ; then
  1817.     echo You have unpacked all 21 archives.
  1818.     rm -f ark[1-9]isdone ark[1-9][0-9]isdone
  1819. else
  1820.     echo You still need to unpack the following archives:
  1821.     echo "        " ${MISSING}
  1822. fi
  1823. ##  End of shell archive.
  1824. exit 0
  1825.