How do I support signed numbers for CA65?

Discuss technical or other issues relating to programming the Nintendo Entertainment System, Famicom, or compatible systems. See the NESdev wiki for more information.

Moderator: Moderators

Post Reply
User avatar
Hamtaro126
Posts: 823
Joined: Thu Jan 19, 2006 5:08 pm

How do I support signed numbers for CA65?

Post by Hamtaro126 »

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]
AKA SmilyMZX/AtariHacker.
tepples
Posts: 22862
Joined: Sun Sep 19, 2004 11:12 pm
Location: NE Indiana, USA (NTSC)
Contact:

Re: How do I support Floating point numbers for CA65?

Post by tepples »

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.
User avatar
blargg
Posts: 3715
Joined: Mon Sep 27, 2004 8:33 am
Location: Central Texas, USA
Contact:

Re: How do I support Floating point numbers for CA65?

Post by blargg »

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.
Last edited by blargg on Mon Dec 23, 2013 6:50 pm, edited 2 times in total.
tepples
Posts: 22862
Joined: Sun Sep 19, 2004 11:12 pm
Location: NE Indiana, USA (NTSC)
Contact:

Re: How do I support Floating point numbers for CA65?

Post by tepples »

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.
User avatar
blargg
Posts: 3715
Joined: Mon Sep 27, 2004 8:33 am
Location: Central Texas, USA
Contact:

Re: How do I support Floating point numbers for CA65?

Post by blargg »

I'm still wondering what the floating-point reference was about. wla-dx supports floating-point in all calculations.
Last edited by blargg on Tue Dec 24, 2013 12:02 pm, edited 1 time in total.
Joe
Posts: 688
Joined: Mon Apr 01, 2013 11:17 pm

Re: How do I support Floating point numbers for CA65?

Post by Joe »

I think Hamtaro126 meant "signed numbers", not "floating-point numbers".
User avatar
mikejmoffitt
Posts: 1353
Joined: Sun May 27, 2012 8:43 pm

Re: How do I support Floating point numbers for CA65?

Post by mikejmoffitt »

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?
User avatar
Hamtaro126
Posts: 823
Joined: Thu Jan 19, 2006 5:08 pm

Re: How do I support Floating point numbers for CA65?

Post by Hamtaro126 »

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!
AKA SmilyMZX/AtariHacker.
User avatar
Memblers
Posts: 4100
Joined: Mon Sep 20, 2004 6:04 am
Location: Indianapolis
Contact:

Re: How do I support Floating point numbers for CA65?

Post by Memblers »

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.
User avatar
Movax12
Posts: 541
Joined: Sun Jan 02, 2011 11:50 am

Re: How do I support signed numbers for CA65?

Post by Movax12 »

(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
User avatar
blargg
Posts: 3715
Joined: Mon Sep 27, 2004 8:33 am
Location: Central Texas, USA
Contact:

Re: How do I support signed numbers for CA65?

Post by blargg »

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.
User avatar
Movax12
Posts: 541
Joined: Sun Jan 02, 2011 11:50 am

Re: How do I support signed numbers for CA65?

Post by Movax12 »

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'.
User avatar
blargg
Posts: 3715
Joined: Mon Sep 27, 2004 8:33 am
Location: Central Texas, USA
Contact:

Re: How do I support signed numbers for CA65?

Post by blargg »

0xffffffff in signed 32-bit is still -1 though. In the assembler they'd do something like

Code: Select all

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.
User avatar
Movax12
Posts: 541
Joined: Sun Jan 02, 2011 11:50 am

Re: How do I support signed numbers for CA65?

Post by Movax12 »

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.
Post Reply