This page is a mirror of Tepples' nesdev forum mirror (URL TBD).
Last updated on Oct-18-2019 Download

How do I support signed numbers for CA65?

How do I support signed numbers for CA65?
by on (#122838)
For example X816, ASM6 and NESASM supports the - and + symbol in numbers from data (Opcodes, .Bytes, .Words, etc) to add/subtract the number values easily, but in CA65, It is much harder to do unless someone adds support for it,

For example, LDA #-8 does not work in CA65, but LDA #$F8 does

How should I do away with this without recompiling CA65 to support it?

[Subject fixed by MOD]
Re: How do I support Floating point numbers for CA65?
by on (#122839)
Recent ca65 checks that immediate operands and .byte values lie within the unsigned 8-bit range. To skip the check once, use the < operator: lda #<-8 To skip the check throughout, as in earlier versions of ca65, use .feature force_range.
Re: How do I support Floating point numbers for CA65?
by on (#122840)
I've never had a problem with e.g. LDA #-8 in ca65. If it gives an error now it's a regression and needs to be fixed. -8 can be represented in as little as 4 bits in two's complement, so 8 bits is more than enough. force_range is not what you ant, since as it says, "Be very careful with this one, since it will completely disable error checks." You don't want to disable error checks. Even < is a poor solution since it also disables error checks, e.g. LDA #<-512 gives no diagnostics.

What version of ca65 you using?

Wow, 2.13.3 accepted this without a peep: LDA #-71923892

Confidence shaken.
Re: How do I support Floating point numbers for CA65?
by on (#122841)
The behavior changed when I upgraded from 2.12.something to 2.14.0 while investigating macros. In any case, .feature force_range is supposed to restore the old behavior of accepting negative numbers.
Re: How do I support Floating point numbers for CA65?
by on (#122847)
I'm still wondering what the floating-point reference was about. wla-dx supports floating-point in all calculations.
Re: How do I support Floating point numbers for CA65?
by on (#122851)
I think Hamtaro126 meant "signed numbers", not "floating-point numbers".
Re: How do I support Floating point numbers for CA65?
by on (#122853)
I am wondering what floating point has to do with it; so far the thread seems more related to signed integers. Am I missing something?
Re: How do I support Floating point numbers for CA65?
by on (#122857)
Whoops... Made a major typo, I meant Signed numbers, Have to get more used to studying this stuff...

Well anyways... It works again, Thanks to all who helped!
Re: How do I support Floating point numbers for CA65?
by on (#122858)
I can't remember exactly which assembler this helps, but I do remember running into that problem before, and I changed stuff like LDA #-1 into LDA #0-1 to get around it.
Re: How do I support signed numbers for CA65?
by on (#123045)
(Some?) expressions in ca65 are evaluated in 32 bits. This includes negation (~) and two's compliment (leading -) evaluations. Kind of annoying but that is what is happening.

Some background on .feature force_range: http://www.cc65.org/mailarchive/2011-12/9838.html
Re: How do I support signed numbers for CA65?
by on (#123051)
32 bits would be fine if it were signed, because -1 in 32 bits is still within the range of an 8-bit signed byte.
Re: How do I support signed numbers for CA65?
by on (#123052)
Yes, but it is sign extended into 32 bits. -1 becomes: $FFFFFFFF
So something like .byte -1 becomes .byte $FFFFFFFF and the assemblers stops with 'out of range'.
Re: How do I support signed numbers for CA65?
by on (#123053)
0xffffffff in signed 32-bit is still -1 though. In the assembler they'd do something like
Code:
if ( val < -128 || val > 127 )
    error( "Value won't fit into 8 bits" );

The error isn't using 32 bits, it's treating it as unsigned. It sounds more like it just does it all as 32-bit unsigned, where naturally -1 is really just 0xffffffff, i.e. 0u-1, and thus it's never negative to begin with, which is unfortunate. Either way, once the sign information is lost, you have a sort of aliasing, where you can't differentiate the range 0x80000000 to 0xffffffff from -0x80000000 to -1. A half-fix, if the representation can't be changed, would be to reinterpret the unsigned value as a signed one. Then code like LDA #-1 would work as desired, and obscure things like LDA #0xFFFFFF80 would also work. Seems better than the current choice between only unsigned 8-bit values accepted or no checking at all.
Re: How do I support signed numbers for CA65?
by on (#123081)
I see better what you mean. Yes I suppose it would make sense to check for an explicit negative value. But regardless this is why it behaves this way.