diff options
-rw-r--r-- | big.c | 70 |
1 files changed, 48 insertions, 22 deletions
@@ -815,42 +815,68 @@ word digitval(char c) return isdigit(c) ? c - '0' : 10 + tolower(c) - 'a'; } -word strtobig(z, base) /* numeral (as Miranda string) to big number */ - /* does NOT check for malformed numeral, assumes - done and that z fully evaluated */ -word z; -int base; -{ - word s = 0, r = make(INT, 0, 0), PBASE = PTEN; - if (base == 16) +/* numeral (as Miranda string) to big number */ +/* does NOT check for malformed numeral, assumes + done and that z fully evaluated */ +word strtobig(word z, int base) +{ + word s = 0; + word r = make(INT, 0, 0); + + word PBASE = PTEN; + if (base == 16) { PBASE = PSIXTEEN; - else if (base == 8) + } else if (base == 8) { PBASE = PEIGHT; - if (z != NIL && hd[z] == '-') - s = 1, z = tl[z]; /* optional leading `-' (for NUMVAL) */ - if (base != 10) - z = tl[tl[z]]; /* remove "0x" or "0o" */ + } + + /* optional leading `-' (for NUMVAL) */ + if (z != NIL && hd[z] == '-') { + s = 1; + z = tl[z]; + } + + /* remove "0x" or "0o" */ + if (base != 10) { + z = tl[tl[z]]; + } + while (z != NIL) { - word d = digitval(hd[z]), f = base; + word d = digitval(hd[z]); + word f = base; z = tl[z]; - while (z != NIL && f < PBASE) - d = base * d + digitval(hd[z]), f = base * f, z = tl[z]; + + while (z != NIL && f < PBASE) { + d = base * d + digitval(hd[z]); + f = base * f; + z = tl[z]; + } + /* rest of loop does r=f*r+d; (in situ) */ d = f * digit(r) + d; { word carry = d >> DIGITWIDTH; word *x = &rest(r); digit(r) = d & MAXDIGIT; - while (*x) - d = f * digit(*x) + carry, - digit(*x) = d & MAXDIGIT, carry = d >> DIGITWIDTH, x = &rest(*x); - if (carry) + + while (*x) { + d = f * digit(*x) + carry; + digit(*x) = d & MAXDIGIT; + carry = d >> DIGITWIDTH; + x = &rest(*x); + } + + if (carry) { *x = make(INT, carry, 0); + } } } - if (s && !bigzero(r)) + + if (s && !bigzero(r)) { digit(r) = digit(r) | SIGNBIT; - return (r); + } + + return r; } extern char *dicp; |