Open MSlockbo opened 3 years ago
Yeah, this is why I've been putting off fractional number support. Another issue is that there's the split between fixed- and floating-point representations, so we'd need more ways to disambiguate between the two. Maybe we should be using suffixes to specify the format? Such as:
#d 1.1_f32 ; IEEE 32-bit float
#d 2.2_f64 ; IEEE 64-bit float
#d 3.3_fx16p16 ; 16.16 fixed-point
#d 4.4_fs3p28 ; custom signed 3-bit exponent 28-bit mantissa floating-point format?!
It gets complicated very quickly. What if you need to convert between formats, or do arithmetic? I'd need a whole custom floating-point arithmetic library to handle these. We could also ignore these extra features and just implement basic literal support, which the assembler could simply reinterpret as integers internally.
Or maybe all fractional literals could be infinite-precision (like integer literals already are), and you must use "function syntax" to convert them down to a fixed-size representation before using them elsewhere. Like so:
#d f32(1.5)
#d f64(0x12ab.34cd)
If you make all fractional literals infinite precision, reducing them down into each format isn't as bad as having to interpret each one differently. You could also support multiple custom formats like say for whatever reason I wanted to do make an unsigned 16 bit float with a 4 bit exponent and 12 bit mantissa, or a 32 bit fixed precision with an 8 bit int and 24 bit fraction.
You could probably get away with reading in the decimal and fraction parts separately using f64s and then when a conversion comes along run a bit conversion using the two.
I did do a little bit of reading on this and parsing these values is a lot trickier than I thought it was. I was only really thinking of the IEEE format since that is supported natively by rust.
The only issue I would see is whether to prioritize the int part or the fraction part when converting.
If you prioritize the int part all you have to do to combine two IEEE 64 into one IEEE 32 or 64 or whatever format float it is, fit the integer part into the new storage type first and then shift the fraction right by the difference in exponents, then run a logical or with the two mantissas.
To do this with a fixed precision value you just slap the mantissa bits of the fraction part shifted by the exponent into the right hand side of the result and convert the int part into an i64 and slap that into the left hand side of the result.
what about a way users could define their own formats? you could have something similar to #ruledef to define a custom data format which could allow users to do whatever bit manipulation or arithmetic they need to represent whatever data format they want.. certainly not the most convenient method, but it would be extremely versatile
what about a way users could define their own formats? you could have something similar to #ruledef to define a custom data format which could allow users to do whatever bit manipulation or arithmetic they need to represent whatever data format they want.. certainly not the most convenient method, but it would be extremely versatile
that would be awesome as you could also have custom pre/sufixes for binary, hexadecimal, decimal, etc
what about a way users could define their own formats? you could have something similar to #ruledef to define a custom data format which could allow users to do whatever bit manipulation or arithmetic they need to represent whatever data format they want.. certainly not the most convenient method, but it would be extremely versatile
that would be awesome as you could also have custom pre/sufixes for binary, hexadecimal, decimal, etc
I think he's implementing it
I suggested it again in #93 and he expressed interest and now hasn't said anything for 15 days, which I think means he's thinking of how it could be implemented
This is not exactly a necessary feature.
It seems there is not exactly a good way of representing a floating point value in the Assembler without converting it to a hex value first.
Say I wanted to do something such as this:
mov r1, #1.1
The assembler does not recognize 1.1 as a valid value so to store it correctly I would have to store it like this:
mov r1, #0x3f8ccccd ; hexadecimal IEEE-754 32-bit representation of 1.1
I don't know how easy this will be to implement with the assembler since
mov r1, #1.1
is ambiguous with it's bit depth.Fortunately most instruction sets do not actually support commands like this or have type specifiers such as ARM with
vmul.f32
andvmul.f64
. I think a good starting point would be to add a data directive for it. So for example:This would at least allow easily defining a float in memory and then being able to move it around. This would also work really well with x86 for example which does not allow floating point operations on registers and it's floating point operations take memory locations.