1
Fork 0
mirror of https://git.savannah.gnu.org/git/guile.git synced 2025-04-30 11:50:28 +02:00

* numbers.c (scm_mkbig): Add cast, and note that signed/unsigned

comparison is okay here.
* numbers.c (scm_istr2int): Add cast; len is known to be positive.
* numbers.c (scm_bigcomp): Clarify logic, and avoid relying on the
(true, but confusing) fact that -1 == ((unsigned) 0 - 1).
* numbers.c (scm_adjbig): Make nsiz an scm_sizet, to avoid mixing
signed/unsigned.
This commit is contained in:
Jim Blandy 1998-09-06 18:15:59 +00:00
parent c7023c693a
commit 2bf746cc9f

View file

@ -712,7 +712,8 @@ scm_mkbig(nlen, sign)
int sign; int sign;
{ {
SCM v = nlen; SCM v = nlen;
if (((v << 16) >> 16) != nlen) /* Cast to SCM to avoid signed/unsigned comparison warnings. */
if (((v << 16) >> 16) != (SCM) nlen)
scm_wta(SCM_MAKINUM(nlen), (char *)SCM_NALLOC, s_bignum); scm_wta(SCM_MAKINUM(nlen), (char *)SCM_NALLOC, s_bignum);
SCM_NEWCELL(v); SCM_NEWCELL(v);
SCM_DEFER_INTS; SCM_DEFER_INTS;
@ -746,13 +747,21 @@ scm_adjbig(b, nlen)
SCM b; SCM b;
scm_sizet nlen; scm_sizet nlen;
{ {
long nsiz = nlen; scm_sizet nsiz = nlen;
if (((nsiz << 16) >> 16) != nlen) scm_wta(SCM_MAKINUM(nsiz), (char *)SCM_NALLOC, s_adjbig); if (((nsiz << 16) >> 16) != nlen)
scm_wta (scm_ulong2num (nsiz), (char *)SCM_NALLOC, s_adjbig);
SCM_DEFER_INTS; SCM_DEFER_INTS;
SCM_SETCHARS(b, (SCM_BIGDIG *)scm_must_realloc((char *)SCM_CHARS(b), {
(long)(SCM_NUMDIGS(b)*sizeof(SCM_BIGDIG)), SCM_BIGDIG *digits
(long)(nsiz*sizeof(SCM_BIGDIG)), s_adjbig)); = ((SCM_BIGDIG *)
SCM_SETNUMDIGS(b, nsiz, SCM_TYP16(b)); scm_must_realloc((char *)SCM_CHARS(b),
(long)(SCM_NUMDIGS(b)*sizeof(SCM_BIGDIG)),
(long)(nsiz*sizeof(SCM_BIGDIG)), s_adjbig));
SCM_SETCHARS (b, digits);
SCM_SETNUMDIGS (b, nsiz, SCM_TYP16(b));
}
SCM_ALLOW_INTS; SCM_ALLOW_INTS;
return b; return b;
} }
@ -903,14 +912,32 @@ scm_bigcomp(x, y)
int xsign = SCM_BIGSIGN(x); int xsign = SCM_BIGSIGN(x);
int ysign = SCM_BIGSIGN(y); int ysign = SCM_BIGSIGN(y);
scm_sizet xlen, ylen; scm_sizet xlen, ylen;
/* Look at the signs, first. */
if (ysign < xsign) return 1; if (ysign < xsign) return 1;
if (ysign > xsign) return -1; if (ysign > xsign) return -1;
if ((ylen = SCM_NUMDIGS(y)) > (xlen = SCM_NUMDIGS(x))) return (xsign) ? -1 : 1;
/* They're the same sign, so see which one has more digits. Note
that, if they are negative, the longer number is the lesser. */
ylen = SCM_NUMDIGS(y);
xlen = SCM_NUMDIGS(x);
if (ylen > xlen)
return (xsign) ? -1 : 1;
if (ylen < xlen) return (xsign) ? 1 : -1; if (ylen < xlen) return (xsign) ? 1 : -1;
while(xlen-- && (SCM_BDIGITS(y)[xlen]==SCM_BDIGITS(x)[xlen]));
if (-1==xlen) return 0; /* They have the same number of digits, so find the most significant
return (SCM_BDIGITS(y)[xlen] > SCM_BDIGITS(x)[xlen]) ? digit where they differ. */
(xsign ? -1 : 1) : (xsign ? 1 : -1); while (xlen)
{
--xlen;
if (SCM_BDIGITS (y)[xlen] != SCM_BDIGITS (x)[xlen])
/* Make the discrimination based on the digit that differs. */
return (SCM_BDIGITS(y)[xlen] > SCM_BDIGITS(x)[xlen]) ?
(xsign ? -1 : 1) : (xsign ? 1 : -1);
}
/* The numbers are identical. */
return 0;
} }
#ifndef SCM_DIGSTOOBIG #ifndef SCM_DIGSTOOBIG
@ -1550,7 +1577,9 @@ scm_istr2int(str, len, radix)
else j = 1+(len*sizeof(char))/(SCM_BITSPERDIG); else j = 1+(len*sizeof(char))/(SCM_BITSPERDIG);
switch (str[0]) { /* leading sign */ switch (str[0]) { /* leading sign */
case '-': case '-':
case '+': if (++i==len) return SCM_BOOL_F; /* bad if lone `+' or `-' */ case '+':
if (++i==(unsigned) len)
return SCM_BOOL_F; /* bad if lone `+' or `-' */
} }
res = scm_mkbig(j, '-'==str[0]); res = scm_mkbig(j, '-'==str[0]);
ds = SCM_BDIGITS(res); ds = SCM_BDIGITS(res);
@ -1583,7 +1612,7 @@ scm_istr2int(str, len, radix)
default: default:
return SCM_BOOL_F; /* not a digit */ return SCM_BOOL_F; /* not a digit */
} }
} while (i < len); } while (i < (unsigned) len);
if (blen * SCM_BITSPERDIG/SCM_CHAR_BIT <= sizeof(SCM)) if (blen * SCM_BITSPERDIG/SCM_CHAR_BIT <= sizeof(SCM))
if SCM_INUMP(res = scm_big2inum(res, blen)) return res; if SCM_INUMP(res = scm_big2inum(res, blen)) return res;
if (j==blen) return res; if (j==blen) return res;