From 5f1ea6c04cd438b13144c264a402e55f1baf203d Mon Sep 17 00:00:00 2001
From: Thomas Harte <thomas.harte@gmail.com>
Date: Wed, 8 Nov 2023 22:30:39 -0500
Subject: [PATCH] Unify AAA and AAS.

---
 InstructionSets/x86/Implementation/BCD.hpp    | 66 +++----------------
 .../Implementation/PerformImplementation.hpp  |  6 +-
 2 files changed, 13 insertions(+), 59 deletions(-)

diff --git a/InstructionSets/x86/Implementation/BCD.hpp b/InstructionSets/x86/Implementation/BCD.hpp
index 97519cc6a..26fd87056 100644
--- a/InstructionSets/x86/Implementation/BCD.hpp
+++ b/InstructionSets/x86/Implementation/BCD.hpp
@@ -15,67 +15,21 @@
 
 namespace InstructionSet::x86::Primitive {
 
-template <typename ContextT>
-void aaa(
-	CPU::RegisterPair16 &ax,
-	ContextT &context
-) {	// P. 313
-	/*
-		IF ((AL AND 0FH) > 9) OR (AF = 1)
-			THEN
-				AL ← (AL + 6);
-				AH ← AH + 1;
-				AF ← 1;
-				CF ← 1;
-			ELSE
-				AF ← 0;
-				CF ← 0;
-			FI;
-		AL ← AL AND 0FH;
-	*/
-	/*
-		The AF and CF flags are set to 1 if the adjustment results in a decimal carry;
-		otherwise they are cleared to 0. The OF, SF, ZF, and PF flags are undefined.
-	*/
-	if((ax.halves.low & 0x0f) > 9 || context.flags.template flag<Flag::AuxiliaryCarry>()) {
-		ax.halves.low += 6;
-		++ax.halves.high;
-		context.flags.template set_from<Flag::Carry, Flag::AuxiliaryCarry>(1);
-	} else {
-		context.flags.template set_from<Flag::Carry, Flag::AuxiliaryCarry>(0);
-	}
-	ax.halves.low &= 0x0f;
-}
-
-
-template <typename ContextT>
-void aas(
+/// If @c add is @c true, performs an AAA; otherwise perfoms an AAS.
+template <bool add, typename ContextT>
+void aaas(
 	CPU::RegisterPair16 &ax,
 	ContextT &context
 ) {
-	/*
-		IF ((AL AND 0FH) > 9) OR (AF = 1)
-		THEN
-			AL ← AL – 6;
-			AH ← AH – 1;
-			AF ← 1;
-			CF ← 1;
-		ELSE
-			CF ← 0;
-			AF ← 0;
-		FI;
-		AL ← AL AND 0FH;
-	*/
-	/*
-		The AF and CF flags are set to 1 if there is a decimal borrow;
-		otherwise, they are cleared to 0. The OF, SF, ZF, and PF flags are undefined.
-	*/
 	if((ax.halves.low & 0x0f) > 9 || context.flags.template flag<Flag::AuxiliaryCarry>()) {
-		ax.halves.low -= 6;
-		--ax.halves.high;
+		if constexpr (add) {
+			ax.halves.low += 6;
+			++ax.halves.high;
+		} else {
+			ax.halves.low -= 6;
+			--ax.halves.high;
+		}
 		context.flags.template set_from<Flag::Carry, Flag::AuxiliaryCarry>(1);
-	} else {
-		context.flags.template set_from<Flag::Carry, Flag::AuxiliaryCarry>(0);
 	}
 	ax.halves.low &= 0x0f;
 }
diff --git a/InstructionSets/x86/Implementation/PerformImplementation.hpp b/InstructionSets/x86/Implementation/PerformImplementation.hpp
index 6a13c2254..a28073a1b 100644
--- a/InstructionSets/x86/Implementation/PerformImplementation.hpp
+++ b/InstructionSets/x86/Implementation/PerformImplementation.hpp
@@ -175,10 +175,10 @@ template <
 		case Operation::ESC:
 		case Operation::NOP:	return;
 
-		case Operation::AAA:	Primitive::aaa(context.registers.axp(), context);							return;
-		case Operation::AAD:	Primitive::aad(context.registers.axp(), instruction.operand(), context);	return;
 		case Operation::AAM:	Primitive::aam(context.registers.axp(), instruction.operand(), context);	return;
-		case Operation::AAS:	Primitive::aas(context.registers.axp(), context);							return;
+		case Operation::AAD:	Primitive::aad(context.registers.axp(), instruction.operand(), context);	return;
+		case Operation::AAA:	Primitive::aaas<true>(context.registers.axp(), context);					return;
+		case Operation::AAS:	Primitive::aaas<false>(context.registers.axp(), context);					return;
 		case Operation::DAA:	Primitive::daas<true>(context.registers.al(), context);						return;
 		case Operation::DAS:	Primitive::daas<false>(context.registers.al(), context);					return;