mirror of
https://github.com/justinethier/cyclone.git
synced 2025-05-23 20:15:05 +02:00
WIP on bignum2string
This commit is contained in:
parent
c68c60f007
commit
141e9ed7b5
2 changed files with 36 additions and 8 deletions
|
@ -858,8 +858,8 @@ typedef struct {
|
|||
// # define C_HALF_WORD_SIZE 32
|
||||
// #else
|
||||
// # define C_MOST_POSITIVE_FIXNUM 0x3fffffff
|
||||
// # define C_WORD_SIZE 32
|
||||
// # define C_HALF_WORD_SIZE 16
|
||||
#define C_WORD_SIZE 32
|
||||
#define C_HALF_WORD_SIZE 16
|
||||
// #endif
|
||||
//
|
||||
// /* Tunable performance-related constants */
|
||||
|
@ -884,13 +884,13 @@ typedef struct {
|
|||
// #endif
|
||||
//
|
||||
// /* These might fit better in runtime.c? */
|
||||
// #define C_fitsinbignumhalfdigitp(n) (C_BIGNUM_DIGIT_HI_HALF(n) == 0)
|
||||
#define Cyc_fitsinbignumhalfdigitp(n) (C_BIGNUM_DIGIT_HI_HALF(n) == 0)
|
||||
// #define C_BIGNUM_DIGIT_LENGTH C_WORD_SIZE
|
||||
// #define C_BIGNUM_HALF_DIGIT_LENGTH C_HALF_WORD_SIZE
|
||||
#define C_BIGNUM_HALF_DIGIT_LENGTH C_HALF_WORD_SIZE
|
||||
// #define C_BIGNUM_BITS_TO_DIGITS(n) \
|
||||
// (((n) + (C_BIGNUM_DIGIT_LENGTH - 1)) / C_BIGNUM_DIGIT_LENGTH)
|
||||
// #define C_BIGNUM_DIGIT_LO_HALF(d) (C_uhword)(d)
|
||||
// #define C_BIGNUM_DIGIT_HI_HALF(d) (C_uhword)((d) >> C_BIGNUM_HALF_DIGIT_LENGTH)
|
||||
#define C_BIGNUM_DIGIT_HI_HALF(d) (uint16_t)((d) >> C_BIGNUM_HALF_DIGIT_LENGTH)
|
||||
// #define C_BIGNUM_DIGIT_COMBINE(h,l) ((C_uword)(h) << C_BIGNUM_HALF_DIGIT_LENGTH|(C_uhword)(l))
|
||||
//
|
||||
// #define C_MOST_POSITIVE_32_BIT_FIXNUM 0x3fffffff
|
||||
|
|
34
runtime.c
34
runtime.c
|
@ -2449,10 +2449,10 @@ void bignum2string(void *data, object cont, bignum2_type *bn, int radix)
|
|||
printf("radix power of two\n");
|
||||
// TODO:
|
||||
} else {
|
||||
uint32_t base, *start, *scan, *end;
|
||||
uint32_t base, *start, *scan, big_digit;
|
||||
int steps, i;
|
||||
|
||||
// working copy??
|
||||
// TODO: make a working copy of the bignum so we can perform destructive operations (??)
|
||||
|
||||
start = &(bn->sign);
|
||||
start += 1;
|
||||
|
@ -2461,11 +2461,39 @@ void bignum2string(void *data, object cont, bignum2_type *bn, int radix)
|
|||
/* Calculate the largest power of radix that fits a halfdigit:
|
||||
* steps = log10(2^halfdigit_bits), base = 10^steps
|
||||
*/
|
||||
for(steps = 0, base = radix; C_fitsinbignumhalfdigitp(base); base *= radix)
|
||||
for(steps = 0, base = radix; Cyc_fitsinbignumhalfdigitp(base); base *= radix)
|
||||
steps++;
|
||||
|
||||
base /= radix; /* Back down: we overshot in the loop */
|
||||
|
||||
while (scan > start) {
|
||||
big_digit = bignum_digits_destructive_scale_down(start, scan, base);
|
||||
|
||||
if (*(scan-1) == 0) scan--; /* Adjust if we exhausted the highest digit */
|
||||
|
||||
for(i = 0; i < steps && index >= buf; ++i) {
|
||||
C_word tmp = big_digit / radix;
|
||||
*index-- = characters[big_digit - (tmp*radix)]; /* big_digit % radix */
|
||||
big_digit = tmp;
|
||||
}
|
||||
}
|
||||
assert(index >= buf-1);
|
||||
free_tmp_bignum(working_copy);
|
||||
|
||||
/* Move index onto first nonzero digit. We're writing a bignum
|
||||
here: it can't consist of only zeroes. */
|
||||
while(*++index == '0');
|
||||
|
||||
if (negp) *--index = '-';
|
||||
|
||||
/* Shorten with distance between start and index. */
|
||||
if (buf != index) {
|
||||
i = C_header_size(string) - (index - buf);
|
||||
C_memmove(buf, index, i); /* Move start of number to beginning. */
|
||||
C_block_header(string) = C_STRING_TYPE | i; /* Mutate strlength. */
|
||||
}
|
||||
}
|
||||
// TODO: call into cont with string
|
||||
}
|
||||
|
||||
object Cyc_symbol2string(void *data, object cont, object sym)
|
||||
|
|
Loading…
Add table
Reference in a new issue