[Negate multiple-word numbers]                        [Assembler][/][80386]

In order to negate multiple-word integers it would be nice if the x86
instruction set had an equivalent to the 68K NEGX instruction (basically a
negate with carry in). This would allow negation in a single pass. The best
substitute I came up with is this technique. It's basic approach is to
compute the 2's complement by first computing the 1's complement and than
adding 1, which requires carry propagation all the way to the most
significant part. We get a slight break here in that we can use the NEG
instruction for the least significant part. Remember that NEG sets the
carry if the source is not 0.
To negate a 64 bit number in EDX:EAX (EDX has nost significant part):

;
; negate a 64 bit number
;
; input:
;   edx:eax = 64 bit number
;
; output:
;   edx:eax = negated 64 bit number
;
; destroys:
;   eflags
;

        not    edx
        neg    eax
        sbb    edx, -1

To negate a 96-bit number in EDX:EBX:EAX (EDX has nost significant part):

;
; negate a 96 bit number
;
; input:
;   edx:ebx:eax = 96 bit number
;
; output:
;   edx:ebx:eax = negated 96 bit number
;
; destroys:
;   eflags
;

        not     edx
        not     ebx
        neg     eax
        sbb     ebx,-1
        sbb     edx,-1

To negate a 128-bit number in EDX:EAX:ECX:EBX (EDX has nost significant
part):

;
; negate a 128 bit number
;
; input:
;   edx:eax:ecx:ebx = 128 bit number
;
; output:
;   edx:eax:ecx:ebx = negated 128 bit number
;
; destroys:
;   eflags
;

        not     edx
        not     eax
        not     ecx
        neg     ebx
        sbb     ecx,-1
        sbb     eax,-1
        sbb     edx,-1

Note that this gem may be used and CPUs lower than 386, just use 16 bit
registers instead.
                                                  Gem writer: Norbert Juffa
                                                   last updated: 1998-03-16
