Welcome to the Parallax Discussion Forums, sign-up to participate.

- 101.5K All Categories
- 812 Announcements
- 53 Propeller Code
- 23 PASM2/Spin2 (P2)
- 5 PASM/Spin (P1)
- 14 BASIC (for Propeller)
- 61 Forth
- 10 C/C++
- 2.8K Propeller 2
- 27.6K Propeller 1
- 18.9K BASIC Stamp
- 10 micro:bit
- 21.1K General Discussion
- 2K Learn with BlocklyProp
- 8.2K Robotics
- 124 Customer Projects
- 3.3K Accessories

## Comments

12,20912,2092,99513,689That is how I see it. Also, it is important to know after a subtract or a compare if D was less than S. This test is different for signed and unsigned cases. I think that is more important than overflow. Overflow is an error condition that should be designed around, not detected and then dealt with.

2,995An overflow flag would be nice, but not in some hacky weird way, a proper separate flag. That would require complete reworking of instructions and should absolutely not happen for P2.

13,6891,808Many thanks for the test results, Evan. No need to do them on a P1.

Correct.

An overflow can occur without a carry from the lower words, e.g. $8000_0000_0000_0000 + $8000_0000_0000_0000.

Right again. Once you get to the most significant word you cannot go any higher, which is why using "carry" for signed arithmetic is confusing and wrong. There is nowhere else for a "carry" to go. If the result can't fit, that's an overflow.

1,808C after CMPS is what I'd call the "corrected sign" or "correct sign". It is, or should be, the correct sign for the D-S operation, whether or not there has been overflow.

If no overflow, C is the sign bit of the result.

If overflow, C is the negated sign bit of the result.

Chip, could you please confirm this is how your logic works?

The add/subtract logic is the same for unsigned and signed values. Only the C flag is different.

13,689With the way it works now, C always holds the sign of the result, even during overflow.

12,209And the new collector code:

EDIT: included code showing equation result at tail of collector code

1,808reg1 = $8000_0000, reg2 = $8000_0001

reg1 = $8000_0001, reg2 = $8000_0000

EDIT:

Numbers changed!

12,20912,2091,808D[31] = 1, indicating that +2147483647 is less than -1 due to overflow

C = 0, indicating that +2147483647 is not less than -1

C has been corrected to give the right sign for this subtraction, as follows:

C = !D[31] if overflow, else C = D[31]

Let V = 0 if no overflow, V = 1 if overflow, then

C = D[31] XOR V

V = D[31] XOR C

Converting C into V requires one more instruction:

An assembler alias would be handy:

For ADDS/ADDSX/SUBS/SUBSX:

P1 and P2 v20 and earlier have overflow and extra instruction needed to get sign

P2 v21 has (corrected) sign and extra instruction needed to get overflow

12,209I like "corrected sign" too. Is a distinct term that won't be confused.

13,68912,209ADD: C = Sm . Dm + Dm . !Rm + Sm . !Rm

+ is OR

. is AND

! is NOT

C is carry flag.

m is most significant bit of the register.

S, D, R are Source, Destination and Result respectively.

That's pretty much verbatim copied from the 68k manual.

13,689ADD:

sum[32:0] = d[31:0] + s[31:0]

c = sum[32]

SUB/CMP:

sum[32:0] = d[31:0] - s[31:0]

c = !sum[32]

ADDS:

sum[32:0] = d[31:0] + s[31:0]

c = sum[32] XOR d[31] XOR s[31]

SUBS/CMPS:

sum[32:0] = d[31:0] - s[31:0]

c = sum[32] XOR d[31] XOR !s[31]

12,209So then you're thinking those XORs change the carry into a valid extended sign bit.

13,689They certainly seem to.

I remember writing down all the cases for 4-bit values, then I saw the pattern.

1,808CforCarry (ADD/SUB/CMP)CforCorrect sign (ADDS/SUBS/CMPS)13,6891,808I think so, Chip. It would be good to have confirmation that TESTB D,#31 XORC does convert C from correct sign to overflow successfully. On September 10th, I wrote:

so I knew then that correct sign should be a function of overflow. Afterwards I did get a bit worked up about what I thought was the total loss of the overflow flag, as I think users should have the ability to test for overflow and I wasn't sure what "signed carry" meant.

Could somebody please try the following? I don't have anything P2, sorry.

13,689Good work!

The result in flags is %10_10_10_10_10_10_10_10, which is what you'd want.

I changed all the $7FFF_FFFF's to $7FFF_FFFE and all the $8000_0000's to $8000_0001 and the result became %00_00_00_00_00_00_00_00, which is also correct.

It never occurred to me use those blasted flag operators to get an overflow indicator. Good thinking!

1,808I was looking for a single instruction to do D[31] XOR C and TESTB almost chose itself. TESTB D,#31 XORC is a bit long-winded, mind you, and the XORC suffix is unfamiliar, which is why I mentioned an alias. TESTB is a great instruction, blessed rather than blasted!

I complained about losing the overflow flag, others said it is not that important and none of us realised that it had not gone away at all. Many thanks for considering my C & Z overflow idea. You politely declined it, which was the right thing to do as your change to ADDS/ADDSX/SUBS/SUBSX is definitely better.

Could "C = correct sign" be adopted officially? It is what it says. No other CPU I know corrects the sign after overflow. It's interesting that detecting overflow after CMPS/CMPSX is impossible, but the only thing that matters here is that the correct sign is reported. This lack of redundancy tells me that v21 is the way the P2 should be.

We've given signed arithmetic a really good examination and all's well that ends well, I think. I just need to edit some posts now and re-write history!

13,689Is there such a thing as overflow when doing CMPS/CMPSX? Because you are just comparing, and not producing a 'difference', I think there's nothing that could be called overflow. Is that right? $8000_0000 compared to $0000_0001 is 'less than', so C=1. I'm a little punch drunk from all this signed stuff.

We could call it "correct sign", but maybe just "sign" would suffice. On the other hand, "correct sign" doesn't get mentally dismissed as easily.

3,496Nice!

Mike

13,689Agreed. I need to look into shortening those instructions by doing something like this with them:

WAIT.... Never mind. Both C and Z can be recipients of the operation, so it needs to stay as it is.

1,808but perhaps a macro could be used?

13,689Good idea!!!!