English Amiga Board

English Amiga Board (https://eab.abime.net/index.php)
-   Coders. Asm / Hardware (https://eab.abime.net/forumdisplay.php?f=112)
-   -   Whats wrong with this line of assembly? (https://eab.abime.net/showthread.php?t=90988)

pipper 25 February 2018 23:22

Whats wrong with this line of assembly?
 
NF_SUBSECTOR = $8000
...(some code)...
and #~NF_SUBSECTOR,d0


results in:

/home/matze/amigatoolchain/amiga-gcc-out/bin/vasmm68k_mot -Fhunk -phxass -warncomm -nosym -ldots -spaces -m68030 -m68882 -I/home/matze/amigatoolchain/amiga-gcc-out/m68k-amigaos/sys-include -I/home/matze/amigatoolchain/amiga-gcc-out/m68k-amigaos/ndk/include amigaasm/r_engine.asm -o r_engine.o
vasm 1.8b (c) in 2002-2017 Volker Barthelmann
vasm M68k/CPU32/ColdFire cpu backend 2.3b (c) 2002-2017 Frank Wille
vasm motorola syntax module 3.11b (c) 2002-2017 Frank Wille
vasm hunk format output module 2.9b (c) 2002-2017 Frank Wille

error 2037 in line 2529 of "amigaasm/r_engine.asm": immediate operand out of range
> and #~NF_SUBSECTOR,d0
Makefile:163: recipe for target 'r_engine.o' failed


I believe the ~ somehow turns the value into a 32bit value... but how can I convey to vasm to just use it as word sized?

ross 25 February 2018 23:37

Nf_subsector = -$8000

EDIT: for some reason the editor convert NF_SUBSECTOR to Nf_subsector... why?!

EDIT2: verbose mode
I think it's due to the fact that instructions default to .w operations
So in a 16 bit two's complement logic $8000 cannot exist..
-$8000 yes

alkis 25 February 2018 23:37

try and #~NF_SUBSECTOR&$FFFF,d0

Galahad/FLT 25 February 2018 23:42

Try adjusting the value $8000 to $7fff

pipper 26 February 2018 03:19

Both Alkis and Galahad's solutions work, though I chose Alki's in the end (to stick with a named symbol rather than a magic number)

What I don't understand: why bitwise negating a 16bit number does not result in a 16bit number - is this a bug in vasm maybe?

PeterK 26 February 2018 03:48

Quote:

Originally Posted by pipper (Post 1222380)
why bitwise negating a 16bit number does not result in a 16bit number - is this a bug in vasm maybe?

Where did you ever say that you want to deal with only 16 bits and not with 32 bits? I can't see that in your example.

NF_SUBSECTOR = $8000 = $00008000

and #~NF_SUBSECTOR,d0
= and #~$00008000,d0
= and #$FFFF7FFF,d0


pipper 26 February 2018 03:54

I thought the 'and' without .w defaults to .w - no?

Adding .w yields the same error message.

If its an error in the declaration of NF_SUBSECTOR, how do I change it so it would become a 16bit number?

PeterK 26 February 2018 03:58

Quote:

Originally Posted by pipper (Post 1222385)
I thought the 'and' without .w defaults to .w - no?

Adding .w yields the same error message.

If its an error in the declaration of NF_SUBSECTOR, how do I change it so it would become a 16bit number?

AND.W won't help because it will not delete the upper 16 bits, of course.

pipper 26 February 2018 04:01

So the question remains: how to declare less-than-32bit symbols then?

PeterK 26 February 2018 04:07

No, the problem is that you cannot filter a longword reliable in D0 with only 16 bits. You have to expand it to 32 bits as shown by alkis.

In case that you want to process the contents of D0 later only as a word in your code, you may have to ask Frank Wille why this error message appears. I'm not a user of VASM, I still prefer the good old PhxAss, but never had to fight with such a problem yet (because anything similar newer existed in my code).

Did you already try
NF_SUBSECTOR DC.W $8000
but that's not a preprocessor declaration

maybe
NF_SUBSECTOR = $8000.w ????

pipper 26 February 2018 04:59

Quote:

Did you already try
NF_SUBSECTOR DC.W $8000
That would defeat the purpose. This is supposed to be a constant, not tied to a memory location.

Alkis method is truncating back to 16bit, not expanding to 32bit.

I think what happens is that NF_SUBSECTOR is treated as 32bit constant (that just happens to fit into 16bit). When the ~ operator is applied, the result is $FFFF7FFF (as you showed), which doesn't fit into 16bits anymore.

Anyways, thanks for your input... its working now. This thread is already way too long for a single assembly line ;-(

PeterK 26 February 2018 05:16

Quote:

Originally Posted by pipper (Post 1222389)
That would defeat the purpose. This is supposed to be a constant, not tied to a memory location.

Alkis method is truncating back to 16bit, not expanding to 32bit.

Yeah, I think you're right. Sorry for my confusion at night time, too much red wine, as always.

Best you could do is to ask Frank Wille (phx)

Cheers ...
Peter

meynaf 26 February 2018 08:31

Operators in vasm, as well as in phxass, use longwords regardless of instruction size. I guess most assemblers will do the same.
This behaviour is perfectly normal.

You can use exclusive or to perform the "~" operation on a word (this is for phxass, i don't know if vasm uses the same character for eor) :
Code:

NF_SUBSECTOR = $8000
 and.w #NF_SUBSECTOR^$ffff,d0

But instead of all this, you could do :
Code:

NB_SUBSECTOR = 15
 bclr #NB_SUBSECTOR,d0


ross 26 February 2018 13:06

But the problem lies in the fact that you use the constant NF_SUBSECTOR both as 16 and 32 bit?

Because otherwise no problems arose.
If you define as -$8000 the value is the same both 16 or 32 bit: $FFFF8000 or $8000, sign extended

And if you use
and.w #~NF_SUBSECTOR,d0
or
and.l #~NF_SUBSECTOR,d0
or
and #~NF_SUBSECTOR,d0
result is one:
and.x #$7fff,d
0,
that is the requested operation (logically for .w upper bits are untouched).

So, even if assembler default to 32bit, result is correct.

What's wrong with this?

StingRay 26 February 2018 13:34

Quote:

Originally Posted by ross (Post 1222468)
What's wrong with this?

Nothing. I use exactly the same trick.

meynaf 26 February 2018 13:37

Quote:

Originally Posted by ross (Post 1222468)
What's wrong with this?

With AND, nothing. Now try using OR for more fun :p

ross 26 February 2018 13:58

Quote:

Originally Posted by StingRay (Post 1222481)
Nothing. I use exactly the same trick.

:great


Quote:

Originally Posted by meynaf (Post 1222482)
With AND, nothing. Now try using OR for more fun :p

:D :great

phx 26 February 2018 16:57

Quote:

Originally Posted by pipper (Post 1222380)
What I don't understand: why bitwise negating a 16bit number does not result in a 16bit number - is this a bug in vasm maybe?

The expression evaluation routine doesn't know anything about the instruction and it always works with the CPU's native target-address-type, which is 32 bits for M68k (would be 16 bits for 6502, for example).

So equates are always stored as 32 bit values. And eval_expression() always returns $ffff7fff for ~$8000. Then the AND.W instruction checks its immediate operand, which doesn't match its current operation size...

Yes, I think all assemblers work that way. Otherwise I have to fix it. :)


All times are GMT +2. The time now is 14:59.

Powered by vBulletin® Version 3.8.11
Copyright ©2000 - 2024, vBulletin Solutions Inc.

Page generated in 0.06279 seconds with 11 queries