smlalbt
Signed Multiply Accumulate Long (Bottom x Top)
SMLALBT<c> <RdLo>, <RdHi>, <Rn>, <Rm>
Accumulates (Rn.B * Rm.T) into 64-bit pair.
Details
Signed Multiply Accumulate Long (Bottom × Top) multiplies the bottom 16 bits of Rn by the top 16 bits of Rm, treating both as signed, and accumulates the 32-bit result into the 64-bit value formed by RdHi:RdLo. This A32 DSP extension instruction does not update condition flags and is not available in AArch64.
Pseudocode Operation
operand1 ← SignExtend(Rn[15:0], 32);
operand2 ← SignExtend(Rm[31:16], 32);
result ← operand1 * operand2;
RdHi:RdLo ← RdHi:RdLo + result;
Example
SMLALBT r1, r0, r1, r2
Encoding
Binary Layout
cond
00010
10
0
RdHi
RdLo
Rm
1
1
0
0
Rn
Operands
-
RdLo
Lo -
RdHi
Hi -
Rn
First source / base general-purpose register -
Rm
Second source / offset general-purpose register
Reference (Arm AArch32 ISA)
Instruction Forms
| Encoding | Instruction | ISA | Bit pattern | ||
|---|---|---|---|---|---|
| 0x014000C0 | SMLALBT{<c>}{<q>} <RdLo>, <RdHi>, <Rn>, <Rm> | A32 | cond | 00010 | 10 | 0 | RdHi | RdLo | Rm | 1 | 1 | 0 | 0 | Rn | ||
| 0xFBC00090 | SMLALBT{<c>}{<q>} <RdLo>, <RdHi>, <Rn>, <Rm> | T32 | 111110111 | 100 | Rn | RdLo | RdHi | 10 | 0 | 1 | Rm |
Description
Signed Multiply Accumulate Long (halfwords) multiplies two signed 16-bit values to produce a 32-bit value, and accumulates this with a 64-bit value. The multiply acts on two signed 16-bit quantities, taken from either the bottom or the top half of their respective source registers. The other halves of these source registers are ignored. The 32-bit product is sign-extended and accumulated with a 64-bit accumulate value.
Overflow is possible during this instruction, but only as a result of the 64-bit addition. This overflow is not detected if it occurs. Instead, the result wraps around modulo 264.
Operation
if ConditionPassed() then
EncodingSpecificOperations();
operand1 = if n_high then R[n]<31:16> else R[n]<15:0>;
operand2 = if m_high then R[m]<31:16> else R[m]<15:0>;
result = SInt(operand1) * SInt(operand2) + SInt(R[dHi]:R[dLo]);
R[dHi] = result<63:32>;
R[dLo] = result<31:0>;