dosseg
.model small
.stack 100h
.data
array db -1, -2, -3, -4, 1,2, 3, -5
.code
main PROC
mov ax, @data
mov ds, ax
xor ax, ax
xor dx, dx ; reset dx
lea si, array
mov cx, 8
back:
mov bl, [si]
cmp al, bl
jc continue ; carry will be generated if number in bl is positive
inc dx
continue:
inc si
clc
loop back
mov ah, 4ch
int 21h
main ENDP
end main
I wrote the above program to find the number of negative integers in an array.
Debugging showed that when SI is pointing at -1, the carry flag becomes 1 but it should not as the value at that instant in BL is FFh (negative) and in AL is 00h, so subtracting negative number from 0 should not generate a carry. What am I doing wrong?
Edit: I replaced the erroneous part with :
test bl, bl
jns continue
and now it works as expected but I still don't know why the cmp method did not work.
When you compare
al=0withbl, carry flag (alias Below flag) will be set for any value inblexcept forbl=0, because 0 is below any unsigned number in the range 0x01..0xFF.Your array contains 8bit signed integer numbers. When we compare signed numbers, instead of adverbs below|above we use lower|greater which take into account Signum flag and Overflow flag.
Instead of
jc continue ; carry will be generated if number in bl is positiveusejle continue ; Jump if al=bl or if SF<>OF.Better readable solution is to replace
cmp al,blwithtest bl,bljns continue ; Skip incrementing dx when signum of bl is not set.See also Jcc. You might output the result from DX using the returned errorlevel, just
mov al,dlbeforeint 21h.