
The ALU 16 component is a simple 16-bit Arithmetic Logic Unit.
Inputs A and B are the bus inputs and are the values that the arithemetic operations are performed on. O is the bus output result. Bus input C determines the operation that is performed. See the table below for the value values of C. Cin is the carry input for carry-based operations. CPSR is the output for a current program status register. It is not a register value and output values are only valid as long as the ALU is configured for the appropriate computation.
The bits of the CPSR are:
| Bit | Name | Description | |
|---|---|---|---|
| 0 | N | Negative | True when the high-order bit of O is true (negative). |
| 1 | Z | Zero | True when O is a zero. |
| 2 | C | Carry | True when there is a carry out of an add or subtract. |
| 3 | V | Overflow | True when there is an overflow in a signed operation. |
The values of C and their ALU operations are:
| C | Thumb instruction | ARM equivalent | Action | ALU |
|---|---|---|---|---|
| 000000 | and Rd,Rs | ands Rd,Rd,Rs | Rd ← Rd & Rs | A & B |
| 000001 | eor Rd,Rs | eors Rd,Rd,Rs | Rd ← Rd ^ Rs | A ^ B |
| 000010 | lsl Rd,Rs | lsl Rd,Rd,Rs | Rd ← Rd << Rs | A << B |
| 000011 | lsr Rd,Rs | lsr Rd,Rd,Rs | Rd ← Rd >> Rs | A >> B |
| 000100 | asr Rd,Rs | adcs Rd,Rd,Rs | Rd ← Rd asr Rs | A asr B |
| 000101 | adc Rd,Rs | adcs Rd,Rd,Rs | Rd←Rd+Rs+Cin | A+B+Cin |
| 000110 | sbc Rd,Rs | sbcs Rd,Rd,Rs | Rd←Rd-Rs-~Cin | A-B-~Cin |
| 000111 | ror Rd,Rs | ror Rd,Rd,Rs | Rd ← Rd ror Rs | A ror B |
| 001000 | tst Rd,Rs | tst Rd,Rs | Rd & Rs | A & B |
| 001001 | neg Rd,Rs | rsbs Rd,Rs,#0 | Rd ← -Rs | -A |
| 001010 | cmp Rd,Rs | cmp Rd,Rs | Rd-Rs | A - B |
| 001011 | cmn Rd,Rs | cmn Rd,Rs | Rd+Rs | A + B |
| 001100 | orr Rd,Rs | orrs Rd,Rd,Rs | Rd ← Rd | Rs | A | B |
| 001101 | mul Rd,Rs | muls Rd,Rd,Rs | Rd ← Rd * Rs | A * B |
| 001110 | bic Rd,Rs | bics Rd,Rd,Rs | Rd ← Rd & ~Rs | A & ~B |
| 001111 | mvn Rd,Rs | mvns Rd,Rs | Rd ← ~Rs | ~A |
| 010000 | add Rd,Rs,Rn | add Rd,Rs,Rn | Rd ← Rd + Rn | A + B |
| 010001 | sub Rd,Rs,Rn | sub Rd,Rs,Rn | Rd ← Rd - Rn | A - B |
| 010010 | see note 1 | *none* | Rd←(Rd*Rn)>>16 | (A*B)>>16 |
| 100000 | mov Rd,#imm | mov Rd,#imm | Rd ←imm | B |
| 100001 | cmp Rd,#imm | cmp Rd,#imm | Rd - imm | A - B |
| 100010 | add Rd,#imm | add Rd,Rd,#imm | Rd ← Rd + imm | A + B |
| 100011 | sub Rd,#imm | sub Rd,Rd,#imm | Rd ← Rd - imm | A - B |
Note 1: The command 010010 is an unsigned multiply that returns the high 16 bits of a 32-bit result. It has no equivalent in the ARM instruction set, since ARM include multiply instructions that produce 64-bit results.