diff --git a/src/frontend/A32/decoder/asimd.inc b/src/frontend/A32/decoder/asimd.inc
index 093a5ff6..cafe265c 100644
--- a/src/frontend/A32/decoder/asimd.inc
+++ b/src/frontend/A32/decoder/asimd.inc
@@ -52,7 +52,7 @@ INST(asimd_VRSQRTS,         "VRSQRTS",                  "111100100D1znnnndddd111
 
 // Two registers and a scalar
 INST(arm_UDF,               "UNALLOCATED",              "1111001-1-11-------------1-0----") // ASIMD
-//INST(asimd_VMLA_scalar,     "VMLA (scalar)",            "1111001U1-BB--------0x0x-1-0----") // ASIMD
+INST(asimd_VMLA_scalar,     "VMLA (scalar)",            "1111001Q1Dzznnnndddd0o0FN1M0mmmm") // ASIMD
 //INST(asimd_VMLAL_scalar,    "VMLAL (scalar)",           "1111001U1-BB--------0x10-1-0----") // ASIMD
 //INST(asimd_VQDMLAL,         "VQDMLAL/VQDMLSL",          "111100101-BB--------0x11-1-0----") // ASIMD
 INST(asimd_VMUL_scalar,     "VMUL (scalar)",            "1111001Q1Dzznnnndddd100FN1M0mmmm") // ASIMD
diff --git a/src/frontend/A32/translate/impl/asimd_two_regs_scalar.cpp b/src/frontend/A32/translate/impl/asimd_two_regs_scalar.cpp
index 1a276fee..c73d7ed7 100644
--- a/src/frontend/A32/translate/impl/asimd_two_regs_scalar.cpp
+++ b/src/frontend/A32/translate/impl/asimd_two_regs_scalar.cpp
@@ -9,30 +9,64 @@
 #include "frontend/A32/translate/impl/translate_arm.h"
 
 namespace Dynarmic::A32 {
+namespace {
+enum class MultiplyBehavior {
+    Multiply,
+    MultiplyAccumulate,
+    MultiplySubtract,
+};
 
-bool ArmTranslatorVisitor::asimd_VMUL_scalar(bool Q, bool D, size_t sz, size_t Vn, size_t Vd, bool F, bool N, bool M, size_t Vm) {
+bool ScalarMultiply(ArmTranslatorVisitor& v, bool Q, bool D, size_t sz, size_t Vn, size_t Vd, bool F, bool N, bool M, size_t Vm,
+                    MultiplyBehavior multiply) {
     ASSERT_MSG(sz != 0b11, "Decode error");
     if (sz == 0b00 || (F && sz == 0b01)) {
-        return UndefinedInstruction();
-    }
-    if (Q && (Common::Bit<0>(Vd) || Common::Bit<0>(Vn))) {
-        return UndefinedInstruction();
+        return v.UndefinedInstruction();
     }
 
+    if (Q && (Common::Bit<0>(Vd) || Common::Bit<0>(Vn))) {
+        return v.UndefinedInstruction();
+    }
+
+    const size_t esize = 8U << sz;
     const auto d = ToVector(Q, Vd, D);
     const auto n = ToVector(Q, Vn, N);
-    const size_t esize = 8u << sz;
 
     const auto m = ExtReg::Q0 + ((Vm >> 1) & (esize == 16 ? 0b11 : 0b111));
     const auto index = concatenate(Imm<1>{Common::Bit<0>(Vm)}, Imm<1>{M}, Imm<1>{Common::Bit<3>(Vm)}).ZeroExtend() >> (esize == 16 ? 0 : 1);
-    const auto scalar = ir.VectorGetElement(esize, ir.GetVector(m), index);
+    const auto scalar = v.ir.VectorGetElement(esize, v.ir.GetVector(m), index);
 
-    const auto reg_n = ir.GetVector(n);
-    const auto reg_m = ir.VectorBroadcast(esize, scalar);
-    const auto result = F ? ir.FPVectorMul(esize, reg_n, reg_m, false) : ir.VectorMultiply(esize, reg_n, reg_m);
+    const auto reg_n = v.ir.GetVector(n);
+    const auto reg_m = v.ir.VectorBroadcast(esize, scalar);
+    const auto addend = F ? v.ir.FPVectorMul(esize, reg_n, reg_m, false)
+                          : v.ir.VectorMultiply(esize, reg_n, reg_m);
+    const auto result = [&] {
+        switch (multiply) {
+        case MultiplyBehavior::Multiply:
+            return addend;
+        case MultiplyBehavior::MultiplyAccumulate:
+            return F ? v.ir.FPVectorAdd(esize, v.ir.GetVector(d), addend, false)
+                     : v.ir.VectorAdd(esize, v.ir.GetVector(d), addend);
+        case MultiplyBehavior::MultiplySubtract:
+            return F ? v.ir.FPVectorSub(esize, v.ir.GetVector(d), addend, false)
+                     : v.ir.VectorSub(esize, v.ir.GetVector(d), addend);
+        default:
+            return IR::U128{};
+        }
+    }();
 
-    ir.SetVector(d, result);
+    v.ir.SetVector(d, result);
     return true;
 }
+} // Anonymous namespace
+
+bool ArmTranslatorVisitor::asimd_VMLA_scalar(bool Q, bool D, size_t sz, size_t Vn, size_t Vd, bool op, bool F, bool N, bool M, size_t Vm) {
+    const auto behavior = op ? MultiplyBehavior::MultiplySubtract
+                             : MultiplyBehavior::MultiplyAccumulate;
+    return ScalarMultiply(*this, Q, D, sz, Vn, Vd, F, N, M, Vm, behavior);
+}
+
+bool ArmTranslatorVisitor::asimd_VMUL_scalar(bool Q, bool D, size_t sz, size_t Vn, size_t Vd, bool F, bool N, bool M, size_t Vm) {
+    return ScalarMultiply(*this, Q, D, sz, Vn, Vd, F, N, M, Vm, MultiplyBehavior::Multiply);
+}
 
 } // namespace Dynarmic::A32
diff --git a/src/frontend/A32/translate/impl/translate_arm.h b/src/frontend/A32/translate/impl/translate_arm.h
index 7bce33c1..1bcd4e17 100644
--- a/src/frontend/A32/translate/impl/translate_arm.h
+++ b/src/frontend/A32/translate/impl/translate_arm.h
@@ -492,6 +492,7 @@ struct ArmTranslatorVisitor final {
     bool asimd_VRSQRTS(bool D, bool sz, size_t Vn, size_t Vd, bool N, bool Q, bool M, size_t Vm);
 
     // Advanced SIMD two registers and a scalar
+    bool asimd_VMLA_scalar(bool Q, bool D, size_t sz, size_t Vn, size_t Vd, bool op, bool F, bool N, bool M, size_t Vm);
     bool asimd_VMUL_scalar(bool Q, bool D, size_t sz, size_t Vn, size_t Vd, bool F, bool N, bool M, size_t Vm);
 
     // Two registers and a shift amount