Can't we use the ADD instruction to add two 16-bit numbers in 8086?

As 8086 has a 16-bit ALU with 16-bit registers, this is how I pictured adding two 16-bit numbers:

MOV CX,0001h

But my professor said that 8086 did this operation in two steps instead of one by adding the numbers in pairs of 8-bit numbers. She said that the carry generated by lower sum won’t be carried over if we used ADD instruction directly. This is how she solved it:

MOV CX,0001h

Is her solution the only accepted way of adding two 16-bit numbers?

>Solution :

Your first code block produces identical results in BX to your second code block. (And in CF and SF, and I think OF. Not ZF, PF, or AF, though, for obvious reasons.)

16-bit add is not SIMD addition of two separate byte adds. If you want that, use movd xmm0, ebx / movd xmm1, ecx / paddb xmm0, xmm1. MMX / SSE2 paddb is SIMD addition with separate byte elements. Scalar integer add is a single integer addition operation on the entire operand-size, with CF and OF determined according to the top of the register, whatever that is.

You can trivially prove this by constructing a test case where carry propagates across the 8-bit boundary. Single-step this in a debugger and look at registers after the add.

   mov  ax, 0x80
   add  ax, ax          ; ax = 0x0100  = 0x0080 << 1

Or look at compiler output, like where GCC uses add eax, edx to implement addition of two short variables, or any existing examples of code using add to do pointer math, for example.

Perhaps your professor has had to learn assembly herself to teach a course, and doesn’t have much experience with it. The fact that add and other integer-register operations are single operations on the whole number is pretty fundamental, and is like that across all(?) ISAs. (Although 8086 is one of the few with partial registers that alias onto low/high halves). Hopefully she can correct her misunderstanding and let the class know how assembly works.

Leave a Reply