more complicated floats working so far

This commit is contained in:
pommicket 2022-01-12 15:34:00 -05:00
parent f17720731d
commit ee3c461e6e
2 changed files with 47 additions and 6 deletions

View file

@ -2,4 +2,4 @@
char * = "How are you"" d""o""i""ng today?\n";
hi
_TEST _ING _1
1.00001
50.1e100

View file

@ -267,6 +267,7 @@ function tokenize
data = n
goto token_output
:tokenize_float
; @NONSTANDARD: this doesn't allow for floats whose integral part is >=2^64, e.g. 1000000000000000000000000.0
significand = 0
exponent = 0
pow10 = 0
@ -312,16 +313,19 @@ function tokenize
significand = right_shift(significand, n)
exponent = new_exponent
significand += right_shift(integer, exponent)
if *1in != 'e goto float_no_exponent
:float_no_integer
if *1in == 'e goto float_exponent
if *1in == 'E goto float_exponent
:float_no_exponent
:float_have_significand_and_exponent
if significand == 0 goto float_zero
normalize_float(&significand, &exponent)
putn(significand)
putc(32)
putn_signed(exponent)
putc(10)
; reduce to 53-bit significant (top bit is removed to get 52)
significand += 15 ; ensure number rounds to the nearest representable float (this is what gcc does)
; reduce to 53-bit significand (top bit is removed to get 52)
significand >= 5
exponent += 5
exponent += 52 ; 1001010111... => 1.001010111...
@ -333,15 +337,52 @@ function tokenize
data |= exponent < 52
:float_have_data
*1out = TOKEN_CONSTANT_FLOAT
out += 1
; suffix
*1out = read_number_suffix(file, line_number, &in)
out += 1
goto token_output
:float_no_integer
byte 0xcc
:float_exponent
in += 1
if *1in == '+ goto float_exponent_plus
if *1in == '- goto float_exponent_minus
; e.g. 1e100
pow10 = strtoi(&in, 10)
:float_have_exponent
p = powers_of_10
p += pow10 < 4
full_multiply_signed(significand, *8p, &lower, &upper)
if upper == 0 goto fmultiply2_no_upper
n = leftmost_1bit(upper)
n += 1
significand = lower > n
exponent += n
n = 64 - n
significand |= upper < n
goto fmultiply2_cont
:fmultiply2_no_upper
significand = lower
goto fmultiply2_cont
:fmultiply2_cont
p += 8
exponent += *8p
goto float_have_significand_and_exponent
:float_exponent_plus
; e.g. 1e+100
in += 1
pow10 = strtoi(&in, 10)
goto float_have_exponent
:float_exponent_minus
; e.g. 1e-100
in += 1
pow10 = strtoi(&in, 10)
pow10 = 0 - pow10
goto float_have_exponent
:float_zero
data = 0
goto float_have_data
:tokenize_loop_end
return 0