Annotation of researchv10no/libc/stdio/_fconv.c, revision 1.1

1.1     ! root        1: /* Common routines for _dtoa and strtod */
        !             2: 
        !             3: #include "fconv.h"
        !             4: 
        !             5: #ifdef DEBUG
        !             6: #include <stdio.h>
        !             7: #define Bug(x) {fprintf(stderr, "%s\n", x); exit(1);}
        !             8: #endif
        !             9: 
        !            10:  double
        !            11: _tens[] = {
        !            12:                1e0, 1e1, 1e2, 1e3, 1e4, 1e5, 1e6, 1e7, 1e8, 1e9,
        !            13:                1e10, 1e11, 1e12, 1e13, 1e14, 1e15, 1e16, 1e17, 1e18, 1e19,
        !            14:                1e20, 1e21, 1e22
        !            15: #ifdef VAX
        !            16:                , 1e23, 1e24
        !            17: #endif
        !            18:                };
        !            19: 
        !            20: 
        !            21: #ifdef IEEE_Arith
        !            22: double _bigtens[] = { 1e16, 1e32, 1e64, 1e128, 1e256 };
        !            23: double _tinytens[] = { 1e-16, 1e-32, 1e-64, 1e-128, 1e-256 };
        !            24: #else
        !            25: #ifdef IBM
        !            26: double _bigtens[] = { 1e16, 1e32, 1e64 };
        !            27: double _tinytens[] = { 1e-16, 1e-32, 1e-64 };
        !            28: #else
        !            29: double _bigtens[] = { 1e16, 1e32 };
        !            30: double _tinytens[] = { 1e-16, 1e-32 };
        !            31: #endif
        !            32: #endif
        !            33: 
        !            34:  static Bigint *freelist[Kmax+1];
        !            35: 
        !            36:  Bigint *
        !            37: _Balloc(int k)
        !            38: {
        !            39:        int x;
        !            40:        Bigint *rv;
        !            41: 
        !            42:        if (rv = freelist[k]) {
        !            43:                freelist[k] = rv->next;
        !            44:                }
        !            45:        else {
        !            46:                x = 1 << k;
        !            47:                rv = (Bigint *)malloc(sizeof(Bigint) + (x-1)*sizeof(long));
        !            48:                rv->k = k;
        !            49:                rv->maxwds = x;
        !            50:                }
        !            51:        rv->sign = rv->wds = 0;
        !            52:        return rv;
        !            53:        }
        !            54: 
        !            55:  void
        !            56: _Bfree(Bigint *v)
        !            57: {
        !            58:        if (v) {
        !            59:                v->next = freelist[v->k];
        !            60:                freelist[v->k] = v;
        !            61:                }
        !            62:        }
        !            63: 
        !            64: 
        !            65:  Bigint *
        !            66: _multadd(Bigint *b, int m, int a)      /* multiply by m and add a */
        !            67: {
        !            68:        int i, wds;
        !            69:        unsigned long *x, y;
        !            70: #ifdef Pack_32
        !            71:        unsigned long xi, z;
        !            72: #endif
        !            73:        Bigint *b1;
        !            74: 
        !            75:        wds = b->wds;
        !            76:        x = b->x;
        !            77:        i = 0;
        !            78:        do {
        !            79: #ifdef Pack_32
        !            80:                xi = *x;
        !            81:                y = (xi & 0xffff) * m + a;
        !            82:                z = (xi >> 16) * m + (y >> 16);
        !            83:                a = (int)(z >> 16);
        !            84:                *x++ = (z << 16) + (y & 0xffff);
        !            85: #else
        !            86:                y = *x * m + a;
        !            87:                a = (int)(y >> 16);
        !            88:                *x++ = y & 0xffff;
        !            89: #endif
        !            90:                }
        !            91:                while(++i < wds);
        !            92:        if (a) {
        !            93:                if (wds >= b->maxwds) {
        !            94:                        b1 = Balloc(b->k+1);
        !            95:                        Bcopy(b1, b);
        !            96:                        Bfree(b);
        !            97:                        b = b1;
        !            98:                        }
        !            99:                b->x[wds++] = a;
        !           100:                b->wds = wds;
        !           101:                }
        !           102:        return b;
        !           103:        }
        !           104: 
        !           105:  int
        !           106: _hi0bits(register unsigned long x)
        !           107: {
        !           108:        register int k = 0;
        !           109: 
        !           110:        if (!(x & 0xffff0000)) {
        !           111:                k = 16;
        !           112:                x <<= 16;
        !           113:                }
        !           114:        if (!(x & 0xff000000)) {
        !           115:                k += 8;
        !           116:                x <<= 8;
        !           117:                }
        !           118:        if (!(x & 0xf0000000)) {
        !           119:                k += 4;
        !           120:                x <<= 4;
        !           121:                }
        !           122:        if (!(x & 0xc0000000)) {
        !           123:                k += 2;
        !           124:                x <<= 2;
        !           125:                }
        !           126:        if (!(x & 0x80000000)) {
        !           127:                k++;
        !           128:                if (!(x & 0x40000000))
        !           129:                        return 32;
        !           130:                }
        !           131:        return k;
        !           132:        }
        !           133: 
        !           134:  static int
        !           135: lo0bits(unsigned long *y)
        !           136: {
        !           137:        register int k;
        !           138:        register unsigned long x = *y;
        !           139: 
        !           140:        if (x & 7) {
        !           141:                if (x & 1)
        !           142:                        return 0;
        !           143:                if (x & 2) {
        !           144:                        *y = x >> 1;
        !           145:                        return 1;
        !           146:                        }
        !           147:                *y = x >> 2;
        !           148:                return 2;
        !           149:                }
        !           150:        k = 0;
        !           151:        if (!(x & 0xffff)) {
        !           152:                k = 16;
        !           153:                x >>= 16;
        !           154:                }
        !           155:        if (!(x & 0xff)) {
        !           156:                k += 8;
        !           157:                x >>= 8;
        !           158:                }
        !           159:        if (!(x & 0xf)) {
        !           160:                k += 4;
        !           161:                x >>= 4;
        !           162:                }
        !           163:        if (!(x & 0x3)) {
        !           164:                k += 2;
        !           165:                x >>= 2;
        !           166:                }
        !           167:        if (!(x & 1)) {
        !           168:                k++;
        !           169:                x >>= 1;
        !           170:                if (!x & 1)
        !           171:                        return 32;
        !           172:                }
        !           173:        *y = x;
        !           174:        return k;
        !           175:        }
        !           176: 
        !           177:  Bigint *
        !           178: _i2b(int i)
        !           179: {
        !           180:        Bigint *b;
        !           181: 
        !           182:        b = Balloc(1);
        !           183:        b->x[0] = i;
        !           184:        b->wds = 1;
        !           185:        return b;
        !           186:        }
        !           187: 
        !           188:  Bigint *
        !           189: _mult(Bigint *a, Bigint *b)
        !           190: {
        !           191:        Bigint *c;
        !           192:        int k, wa, wb, wc;
        !           193:        unsigned long carry, y, z;
        !           194:        unsigned long *x, *xa, *xae, *xb, *xbe, *xc, *xc0;
        !           195: #ifdef Pack_32
        !           196:        unsigned long z2;
        !           197: #endif
        !           198: 
        !           199:        if (a->wds < b->wds) {
        !           200:                c = a;
        !           201:                a = b;
        !           202:                b = c;
        !           203:                }
        !           204:        k = a->k;
        !           205:        wa = a->wds;
        !           206:        wb = b->wds;
        !           207:        wc = wa + wb;
        !           208:        if (wc > a->maxwds)
        !           209:                k++;
        !           210:        c = Balloc(k);
        !           211:        for(x = c->x, xa = x + wc; x < xa; x++)
        !           212:                *x = 0;
        !           213:        xa = a->x;
        !           214:        xae = xa + wa;
        !           215:        xb = b->x;
        !           216:        xbe = xb + wb;
        !           217:        xc0 = c->x;
        !           218: #ifdef Pack_32
        !           219:        for(; xb < xbe; xb++, xc0++) {
        !           220:                if (y = *xb & 0xffff) {
        !           221:                        x = xa;
        !           222:                        xc = xc0;
        !           223:                        carry = 0;
        !           224:                        do {
        !           225:                                z = (*x & 0xffff) * y + (*xc & 0xffff) + carry;
        !           226:                                carry = z >> 16;
        !           227:                                z2 = (*x++ >> 16) * y + (*xc >> 16) + carry;
        !           228:                                carry = z2 >> 16;
        !           229:                                Storeinc(xc, z2, z);
        !           230:                                }
        !           231:                                while(x < xae);
        !           232:                        *xc = carry;
        !           233:                        }
        !           234:                if (y = *xb >> 16) {
        !           235:                        x = xa;
        !           236:                        xc = xc0;
        !           237:                        carry = 0;
        !           238:                        z2 = *xc;
        !           239:                        do {
        !           240:                                z = (*x & 0xffff) * y + (*xc >> 16) + carry;
        !           241:                                carry = z >> 16;
        !           242:                                Storeinc(xc, z, z2);
        !           243:                                z2 = (*x++ >> 16) * y + (*xc & 0xffff) + carry;
        !           244:                                carry = z2 >> 16;
        !           245:                                }
        !           246:                                while(x < xae);
        !           247:                        *xc = z2;
        !           248:                        }
        !           249:                }
        !           250: #else
        !           251:        for(; xb < xbe; xc0++) {
        !           252:                if (y = *xb++) {
        !           253:                        x = xa;
        !           254:                        xc = xc0;
        !           255:                        carry = 0;
        !           256:                        do {
        !           257:                                z = *x++ * y + *xc + carry;
        !           258:                                carry = z >> 16;
        !           259:                                *xc++ = z & 0xffff;
        !           260:                                }
        !           261:                                while(x < xae);
        !           262:                        *xc = carry;
        !           263:                        }
        !           264:                }
        !           265: #endif
        !           266:        for(xc0 = c->x, xc = xc0 + wc; wc > 0 && !*--xc; --wc) ;
        !           267:        c->wds = wc;
        !           268:        return c;
        !           269:        }
        !           270: 
        !           271:  static Bigint *p5s;
        !           272: 
        !           273:  Bigint *
        !           274: _pow5mult(Bigint *b, int k)
        !           275: {
        !           276:        Bigint *b1, *p5, *p51;
        !           277:        int i;
        !           278:        static int p05[3] = { 5, 25, 125 };
        !           279: 
        !           280:        if (i = k & 3)
        !           281:                b = multadd(b, p05[i-1], 0);
        !           282: 
        !           283:        if (!(k >>= 2))
        !           284:                return b;
        !           285:        if (!(p5 = p5s)) {
        !           286:                /* first time */
        !           287:                p5 = p5s = i2b(625);
        !           288:                p5->next = 0;
        !           289:                }
        !           290:        for(;;) {
        !           291:                if (k & 1) {
        !           292:                        b1 = mult(b, p5);
        !           293:                        Bfree(b);
        !           294:                        b = b1;
        !           295:                        }
        !           296:                if (!(k >>= 1))
        !           297:                        break;
        !           298:                if (!(p51 = p5->next)) {
        !           299:                        p51 = p5->next = mult(p5,p5);
        !           300:                        p51->next = 0;
        !           301:                        }
        !           302:                p5 = p51;
        !           303:                }
        !           304:        return b;
        !           305:        }
        !           306: 
        !           307:  Bigint *
        !           308: _lshift(Bigint *b, int k)
        !           309: {
        !           310:        int i, k1, n, n1;
        !           311:        Bigint *b1;
        !           312:        unsigned long *x, *x1, *xe, z;
        !           313: 
        !           314: #ifdef Pack_32
        !           315:        n = k >> 5;
        !           316: #else
        !           317:        n = k >> 4;
        !           318: #endif
        !           319:        k1 = b->k;
        !           320:        n1 = n + b->wds + 1;
        !           321:        for(i = b->maxwds; n1 > i; i <<= 1)
        !           322:                k1++;
        !           323:        b1 = Balloc(k1);
        !           324:        x1 = b1->x;
        !           325:        for(i = 0; i < n; i++)
        !           326:                *x1++ = 0;
        !           327:        x = b->x;
        !           328:        xe = x + b->wds;
        !           329: #ifdef Pack_32
        !           330:        if (k &= 0x1f) {
        !           331:                k1 = 32 - k;
        !           332:                z = 0;
        !           333:                do {
        !           334:                        *x1++ = *x << k | z;
        !           335:                        z = *x++ >> k1;
        !           336:                        }
        !           337:                        while(x < xe);
        !           338:                if (*x1 = z)
        !           339:                        ++n1;
        !           340:                }
        !           341: #else
        !           342:        if (k &= 0xf) {
        !           343:                k1 = 16 - k;
        !           344:                z = 0;
        !           345:                do {
        !           346:                        *x1++ = *x << k  & 0xffff | z;
        !           347:                        z = *x++ >> k1;
        !           348:                        }
        !           349:                        while(x < xe);
        !           350:                if (*x1 = z)
        !           351:                        ++n1;
        !           352:                }
        !           353: #endif
        !           354:        else do
        !           355:                *x1++ = *x++;
        !           356:                while(x < xe);
        !           357:        b1->wds = n1 - 1;
        !           358:        Bfree(b);
        !           359:        return b1;
        !           360:        }
        !           361: 
        !           362:  int
        !           363: _cmp(Bigint *a, Bigint *b)
        !           364: {
        !           365:        unsigned long *xa, *xa0, *xb, *xb0;
        !           366:        int i, j;
        !           367: 
        !           368:        i = a->wds;
        !           369:        j = b->wds;
        !           370: #ifdef DEBUG
        !           371:        if (i > 1 && !a->x[i-1])
        !           372:                Bug("cmp called with a->x[a->wds-1] == 0");
        !           373:        if (j > 1 && !b->x[j-1])
        !           374:                Bug("cmp called with b->x[b->wds-1] == 0");
        !           375: #endif
        !           376:        if (i -= j)
        !           377:                return i;
        !           378:        xa0 = a->x;
        !           379:        xa = xa0 + j;
        !           380:        xb0 = b->x;
        !           381:        xb = xb0 + j;
        !           382:        for(;;) {
        !           383:                if (*--xa != *--xb)
        !           384:                        return *xa < *xb ? -1 : 1;
        !           385:                if (xa <= xa0)
        !           386:                        break;
        !           387:                }
        !           388:        return 0;
        !           389:        }
        !           390: 
        !           391:  Bigint *
        !           392: _diff(Bigint *a, Bigint *b)
        !           393: {
        !           394:        Bigint *c;
        !           395:        int i, wa, wb;
        !           396:        long borrow, y; /* We need signed shifts here. */
        !           397:        unsigned long *xa, *xae, *xb, *xbe, *xc;
        !           398: #ifdef Pack_32
        !           399:        long z;
        !           400: #endif
        !           401: 
        !           402:        i = cmp(a,b);
        !           403:        if (!i) {
        !           404:                c = Balloc(0);
        !           405:                c->wds = 1;
        !           406:                c->x[0] = 0;
        !           407:                return c;
        !           408:                }
        !           409:        if (i < 0) {
        !           410:                c = a;
        !           411:                a = b;
        !           412:                b = c;
        !           413:                i = 1;
        !           414:                }
        !           415:        else
        !           416:                i = 0;
        !           417:        c = Balloc(a->k);
        !           418:        c->sign = i;
        !           419:        wa = a->wds;
        !           420:        xa = a->x;
        !           421:        xae = xa + wa;
        !           422:        wb = b->wds;
        !           423:        xb = b->x;
        !           424:        xbe = xb + wb;
        !           425:        xc = c->x;
        !           426:        borrow = 0;
        !           427: #ifdef Pack_32
        !           428:        do {
        !           429:                y = (*xa & 0xffff) - (*xb & 0xffff) + borrow;
        !           430:                borrow = y >> 16;
        !           431:                Sign_Extend(borrow, y);
        !           432:                z = (*xa++ >> 16) - (*xb++ >> 16) + borrow;
        !           433:                borrow = z >> 16;
        !           434:                Sign_Extend(borrow, z);
        !           435:                Storeinc(xc, z, y);
        !           436:                }
        !           437:                while(xb < xbe);
        !           438:        while(xa < xae) {
        !           439:                y = (*xa & 0xffff) + borrow;
        !           440:                borrow = y >> 16;
        !           441:                Sign_Extend(borrow, y);
        !           442:                z = (*xa++ >> 16) + borrow;
        !           443:                borrow = z >> 16;
        !           444:                Sign_Extend(borrow, z);
        !           445:                Storeinc(xc, z, y);
        !           446:                }
        !           447: #else
        !           448:        do {
        !           449:                y = *xa++ - *xb++ + borrow;
        !           450:                borrow = y >> 16;
        !           451:                Sign_Extend(borrow, y);
        !           452:                *xc++ = y & 0xffff;
        !           453:                }
        !           454:                while(xb < xbe);
        !           455:        while(xa < xae) {
        !           456:                y = *xa++ + borrow;
        !           457:                borrow = y >> 16;
        !           458:                Sign_Extend(borrow, y);
        !           459:                *xc++ = y & 0xffff;
        !           460:                }
        !           461: #endif
        !           462:        while(!*--xc)
        !           463:                wa--;
        !           464:        c->wds = wa;
        !           465:        return c;
        !           466:        }
        !           467: 
        !           468:  Bigint *
        !           469: _d2b(double darg, int *e, int *bits)
        !           470: {
        !           471:        Bigint *b;
        !           472:        int de, i, k;
        !           473:        unsigned long *x, y, z;
        !           474:        Dul d;
        !           475: #ifdef VAX
        !           476:        unsigned long d0, d1;
        !           477:        d.d = darg;
        !           478:        d0 = word0(d) >> 16 | word0(d) << 16;
        !           479:        d1 = word1(d) >> 16 | word1(d) << 16;
        !           480: #else
        !           481:        d.d = darg;
        !           482: #define d0 word0(d)
        !           483: #define d1 word1(d)
        !           484: #endif
        !           485: 
        !           486: #ifdef Pack_32
        !           487:        b = Balloc(1);
        !           488: #else
        !           489:        b = Balloc(2);
        !           490: #endif
        !           491:        x = b->x;
        !           492: 
        !           493:        z = d0 & Frac_mask;
        !           494:        d0 &= 0x7fffffff;       /* clear sign bit, which we ignore */
        !           495: #ifdef Sudden_Underflow
        !           496:        de = (int)(d0 >> Exp_shift);
        !           497: #ifndef IBM
        !           498:        z |= Exp_msk11;
        !           499: #endif
        !           500: #else
        !           501:        if (de = (int)(d0 >> Exp_shift))
        !           502:                z |= Exp_msk1;
        !           503: #endif
        !           504: #ifdef Pack_32
        !           505:        if (y = d1) {
        !           506:                if (k = lo0bits(&y)) {
        !           507:                        x[0] = y | z << 32 - k;
        !           508:                        z >>= k;
        !           509:                        }
        !           510:                else
        !           511:                        x[0] = y;
        !           512:                i = b->wds = (x[1] = z) ? 2 : 1;
        !           513:                }
        !           514:        else {
        !           515: #ifdef DEBUG
        !           516:                if (!z)
        !           517:                        Bug("Zero passed to d2b");
        !           518: #endif
        !           519:                k = lo0bits(&z);
        !           520:                x[0] = z;
        !           521:                i = b->wds = 1;
        !           522:                k += 32;
        !           523:                }
        !           524: #else
        !           525:        if (y = d1) {
        !           526:                if (k = lo0bits(&y))
        !           527:                        if (k >= 16) {
        !           528:                                x[0] = y | z << 32 - k & 0xffff;
        !           529:                                x[1] = z >> k - 16 & 0xffff;
        !           530:                                x[2] = z >> k;
        !           531:                                i = 2;
        !           532:                                }
        !           533:                        else {
        !           534:                                x[0] = y & 0xffff;
        !           535:                                x[1] = y >> 16 | z << 16 - k & 0xffff;
        !           536:                                x[2] = z >> k & 0xffff;
        !           537:                                x[3] = z >> k+16;
        !           538:                                i = 3;
        !           539:                                }
        !           540:                else {
        !           541:                        x[0] = y & 0xffff;
        !           542:                        x[1] = y >> 16;
        !           543:                        x[2] = z & 0xffff;
        !           544:                        x[3] = z >> 16;
        !           545:                        i = 3;
        !           546:                        }
        !           547:                }
        !           548:        else {
        !           549: #ifdef DEBUG
        !           550:                if (!z)
        !           551:                        Bug("Zero passed to d2b");
        !           552: #endif
        !           553:                k = lo0bits(&z);
        !           554:                if (k >= 16) {
        !           555:                        x[0] = z;
        !           556:                        i = 0;
        !           557:                        }
        !           558:                else {
        !           559:                        x[0] = z & 0xffff;
        !           560:                        x[1] = z >> 16;
        !           561:                        i = 1;
        !           562:                        }
        !           563:                k += 32;
        !           564:                }
        !           565:        while(!x[i])
        !           566:                --i;
        !           567:        b->wds = i + 1;
        !           568: #endif
        !           569: #ifndef Sudden_Underflow
        !           570:        if (de) {
        !           571: #endif
        !           572: #ifdef IBM
        !           573:                *e = (de - Bias - (P-1) << 2) + k;
        !           574:                *bits = 4*P + 8 - k - hi0bits(word0(d) & Frac_mask);
        !           575: #else
        !           576:                *e = de - Bias - (P-1) + k;
        !           577:                *bits = P - k;
        !           578: #endif
        !           579: #ifndef Sudden_Underflow
        !           580:                }
        !           581:        else {
        !           582:                *e = de - Bias - (P-1) + 1 + k;
        !           583: #ifdef Pack_32
        !           584:                *bits = 32*i - hi0bits(x[i-1]);
        !           585: #else
        !           586:                *bits = (i+2)*16 - hi0bits(x[i]);
        !           587: #endif
        !           588:                }
        !           589: #endif
        !           590:        return b;
        !           591:        }
        !           592: #undef d0
        !           593: #undef d1

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.