Comparators and arithmetic logic units (ALUs) are the decision-making blocks of a datapath. An equality comparator checks every bit pair with an XNOR and combines the results; a magnitude comparator decides which value is larger, working from the most significant bit down. An ALU wraps a single adder, a bitwise logic unit, and a result multiplexer into one block that performs whichever operation its control bits select. Every comparison and every addition in a chip is built from these same structures.

14 min read | Intermediate Level

What You'll Learn

  • How equality and magnitude comparators are built from XNOR gates and priority logic
  • Why a magnitude comparison is often computed with a subtractor's carry chain
  • How an ALU shares one adder for addition, subtraction, and comparison, and how its flags are formed
  • What hardware each part of an 8-bit ALU needs, and where comparators and ALUs are used

Equality Comparator

Two numbers are equal when every bit pair matches. An XNOR gate outputs 1 when its two inputs are the same, so equality is the AND of one XNOR per bit:

4-bit equality:   eq = XNOR(a3,b3) AND XNOR(a2,b2) AND XNOR(a1,b1) AND XNOR(a0,b0)

  per bit : e_i = 1 when a_i == b_i
  combine : all e_i must be 1 -> AND of every e_i

  n-bit comparator = n XNOR (or XOR) gates + an n-input AND tree
  delay grows with log2(n): the AND tree is built from small gates in levels

In practice the circuit is usually built as XOR gates (1 when bits differ) feeding a NOR tree, which is the same function with inverting gates that suit CMOS better. Comparing against a constant is even cheaper: checking A = 10100101 needs no XOR gates at all, just an AND of each bit or its inverse.

Magnitude Comparator: MSB First

To decide whether A > B, look at the most significant bit first. If the MSBs differ, that bit decides the answer. If they are equal, move to the next bit down, and so on. The equality signals ei from the XNOR gates tell each lower bit whether all the bits above it matched.

4-bit A > B, working from the MSB down (e_i = XNOR(a_i, b_i))

  gt = (a3 & ~b3)                          MSB decides
     | (e3 & a2 & ~b2)                     MSBs equal, bit 2 decides
     | (e3 & e2 & a1 & ~b1)                top two equal, bit 1 decides
     | (e3 & e2 & e1 & a0 & ~b0)           top three equal, bit 0 decides

  eq = e3 & e2 & e1 & e0
  lt = ~gt & ~eq

Each term is gated by the equality of every bit above it: the chain of XNOR results runs from the MSB toward the LSB. Written out like this, the structure grows with the square of the width, so wide comparators are built hierarchically - compare 4-bit groups, then combine the group results with the same MSB-first rule.

Two 4-bit comparators make an 8-bit comparator (hi = upper nibble, lo = lower nibble)

  A > B  =  (A_hi > B_hi)  +  (A_hi = B_hi) . (A_lo > B_lo)
  A = B  =  (A_hi = B_hi) . (A_lo = B_lo)

  the lower comparator only matters when the upper nibbles are equal

Comparing With a Subtractor

Real designs rarely build a magnitude comparator gate by gate. A comparison is a subtraction in which only the borrow (or carry) out is kept: A > B exactly when B - A produces a borrow. That turns the comparison into a carry chain, so it can use the same fast carry structures as an adder (see Full-Adder).

ComparisonTypical hardwareDelay grows with width as
A = BXOR per bit + NOR/NAND treelog2(n)
A > B, A < B (unsigned)Carry chain of a subtractor, borrow out onlyn (ripple) or log2(n) (fast carry structure)
A > constantSmall constant-specific logicSmall
A > B (signed)Same carry chain, with the sign bits treated as negative weightSame as unsigned

Where Are Comparators Used?

Timers compare a free-running counter against a programmed value to raise an interrupt. FIFO controllers compare read and write pointers to detect full and empty. Branch units in processors compare register values every cycle, and network switches compare packet header fields against table entries for classification. In each case the comparator often sits on a timing-critical path, which is why wide comparisons use fast carry structures.

Quick Check

Q: A = 1010 and B = 1001. Which term of the MSB-first gt equation is true?

Show Answer

Bits 3 and 2 are equal (1/1 and 0/0), so e3 = e2 = 1. At bit 1, a1 = 1 and b1 = 0, so the third term (e3 & e2 & a1 & ~b1) is true and gt = 1. Bit 0 is never consulted.

Inside an ALU

An arithmetic logic unit performs one of several operations on two operands, chosen by an opcode. The key design idea is to share one adder for everything arithmetic:

ALU built around one shared adder
A simple ALU. One adder handles both add and subtract: for subtraction, B is inverted by XOR with SUB and the carry-in is set to 1. A logic unit computes bitwise operations, and a mux selected by the opcode picks the result. Flags are derived from the result and the adder's carry.
One adder, several operations

  ADD : Y = A + B                 B passes through, carry-in = 0
  SUB : Y = A - B = A + ~B + 1    invert B (XOR with SUB = 1), carry-in = 1
  SLT : Y = (A < B) ? 1 : 0       subtract, then read the sign and overflow
  AND / OR / XOR                  bitwise, from the logic unit, no adder needed
  result mux picks one output, selected by the opcode

The ALU also produces flags that describe the result. Branch instructions and comparisons use them:

FlagMeaningHow it is formed
Z (zero)Result is zeroNOR of all result bits
N (negative)Result is negative (signed)The result's MSB
C (carry)Unsigned overflow on ADD; on SUB, 1 means no borrow (A ≥ B unsigned)Adder carry out
V (overflow)Signed result does not fitBoth adder inputs have the same sign, but the sum's sign differs

A Worked 8-Bit ALU

Take an 8-bit ALU with six operations. The opcode decides whether the adder subtracts and which result the output multiplexer passes:

OperationAdder subtracts? (SUB)Result taken fromFlags that matter
ADDNoAdder sumC, V, N, Z
SUBYesAdder sumC, V, N, Z
AND, OR, XORNoLogic unit (bitwise)N, Z
SLT (signed A < B)YesN xor V, zero-extended to 8 bitsNone needed
Adder inputs  : A and (B xor SUB), carry-in = SUB     (9-bit sum, bit 8 = carry out)
Signed A < B  : sign bit of (A - B), corrected by overflow  ->  N xor V
Flags         : Z = result is zero, N = result MSB, C = carry out, V = overflow

The table shows four example operations and the flags they produce:

opabyFlags
ADD10050150C = 0, V = 1 (150 does not fit in signed 8-bit)
SUB550Z = 1, C = 1 (no borrow)
SUB35FE hex (-2)N = 1, C = 0 (borrow)
SLT-3 (FD hex)21-3 < 2 signed

What Hardware Each Part Needs

Part of the ALUHardware
Invert B when subtracting8 XOR gates (a conditional inverter)
Add with carry-inOne 8-bit adder: ripple, carry-lookahead or parallel-prefix, depending on the speed needed
Choose the resultA parallel multiplexer per bit, driven by the decoded opcode
Zero flagAn 8-input NOR, built as a small tree

Sharing matters. An ALU drawn with a separate adder and a separate subtractor needs two arithmetic units plus a multiplexer to pick between them. Sharing one adder with an XOR gate in front of B costs only eight XOR gates and removes the second unit.

Where Are ALUs Used?

Every processor core contains one or more integer ALUs; superscalar cores have several so that multiple instructions execute per cycle. Microcontrollers often have a single ALU shared by all instructions. The same shared-adder structure also appears in address generation units, loop counters in DSP engines, and the arithmetic stages of network and storage controllers.

Common Mistakes

Mistake #1: Comparing signed values with unsigned logic

If the numbers are signed, an unsigned comparison is wrong. Treated as unsigned, -1 (11111111) is 255 and looks larger than 1. Use the signed rule (N xor V after a subtraction), not the carry flag, when the operands are signed.

Mistake #2: Confusing the carry flag with the overflow flag

Carry (C) reports unsigned overflow; overflow (V) reports signed overflow. 100 + 50 in 8 bits sets V (150 exceeds +127 signed) but not C (150 fits in 255 unsigned). Branch conditions for signed and unsigned comparisons use different flags.

Mistake #3: Building separate add and subtract units

A separate adder and subtractor with an output multiplexer cost two arithmetic units. Share one adder with an inverted B and a carry-in, and the second unit disappears.

Mistake #4: Losing the carry by keeping too few sum bits

The sum of two 8-bit numbers can need nine bits. Keeping only the eight sum bits drops the carry, and without it you cannot form the carry flag or detect unsigned overflow.

Practice Exercise

Challenge: Add an Unsigned Compare to the ALU

Add an operation SLTU that returns 1 when A < B as unsigned numbers, reusing the shared adder.

  1. Which adder output tells you A < B unsigned during a subtraction?
  2. What control changes are needed in the ALU?
Hint

During A - B computed as A + ~B + 1, the carry out is 1 when there is no borrow, which means A ≥ B.

Solution
1. A < B unsigned exactly when the subtraction borrows,
   i.e. when the carry out sum[8] is 0.

2. Changes:
   - make the adder subtract for SLTU (SUB = 1), as for SUB and SLT
   - add one result-mux input: the borrow (NOT of carry out C),
     zero-extended to 8 bits
  

No new arithmetic hardware is needed: the same adder, one more mux input, and one inverter on the carry.

Summary

In this tutorial, you learned:

  • An equality comparator is one XNOR (or XOR) per bit combined by an AND (or NOR) tree
  • A magnitude comparator decides MSB first, gating each lower bit by the equality of all bits above it
  • A magnitude comparison can be built from a subtractor's carry chain, using fast carry structures for wide operands
  • An ALU shares one adder for add, subtract, and compare by inverting B and setting the carry-in
  • Z, N, C, and V flags describe the result; C is unsigned overflow and V is signed overflow
  • The opcode selects the result through a parallel multiplexer, and sharing the adder avoids duplicate arithmetic units
Did you find what you were looking for?

Quiz

No quiz questions available for this article.