YJDoc2 / 8086-emulator-web

Repository for 8086 emulator web implementation
Apache License 2.0
227 stars 26 forks source link

Overflow flag wrong #30

Closed joshudson closed 1 year ago

joshudson commented 1 year ago

I tried:

start:
    MOV AX, 0xFFFF
    ADD AX, AX

Expected: AX = 0xFFFE, CF = 1, OF = 0 Got: AX = 0xFFFE, CF = 1, OF = 1

More details, see here

pcordes commented 1 year ago

There's a separate project for the 8086-Emulator library. The bug is obvious in the source for word_add - https://github.com/YJDoc2/8086-Emulator/blob/master/src/lib/instructions/arithmetic.rs#L578

The code sets both CF and OF according to the same condition: zero-extend the inputs to 32-bit, add, then check for greater than 0xffff unsigned. That should work for carry-out, but it'll fail to detect signed overflow in 0x7fff + anything, as well as false-positive when adding two small negative numbers like you are. CF and OF are different flags for a reason.

SF setting is also wrong. See my answer on the Stack Overflow question; I won't copy more of it here since this is the wrong github project for the bug, but Rust has so many ways to get this right, like i16.overflowing_add. https://doc.rust-lang.org/std/primitive.i16.html#method.overflowing_add Or sign-extend both inputs to 32-bit, and check that the result of that can be truncated back to i16 without changing the value. That's how you'd do it in C, where you don't have access to checked_add or overflowing_add without GNU extensions.

YJDoc2 commented 1 year ago

moved to : https://github.com/YJDoc2/8086-Emulator/issues/14

YJDoc2 commented 1 year ago

ref https://github.com/YJDoc2/8086-Emulator/pull/18