1
0
mirror of https://github.com/TomHarte/CLK.git synced 2024-11-26 08:49:37 +00:00

Implement INC, DEC.

This commit is contained in:
Thomas Harte 2023-10-10 15:57:33 -04:00
parent 3d08953103
commit f083eab011
2 changed files with 129 additions and 5 deletions

View File

@ -533,6 +533,43 @@ void imul(IntT &destination_high, IntT &destination_low, IntT source, Status &st
template <typename IntT, typename FlowControllerT>
void div(IntT &destination_high, IntT &destination_low, IntT source, FlowControllerT &flow_controller) {
/*
IF SRC = 0
THEN #DE; (* divide error *)
FI;
IF OperandSize = 8 (* word/byte operation *)
THEN
temp AX / SRC;
IF temp > FFH
THEN #DE; (* divide error *) ;
ELSE
AL temp;
AH AX MOD SRC;
FI;
ELSE
IF OperandSize = 16 (* doubleword/word operation *)
THEN
temp DX:AX / SRC;
IF temp > FFFFH
THEN #DE; (* divide error *) ;
ELSE
AX temp;
DX DX:AX MOD SRC;
FI;
ELSE (* quadword/doubleword operation *)
temp EDX:EAX / SRC;
IF temp > FFFFFFFFH
THEN #DE; (* divide error *) ;
ELSE
EAX temp;
EDX EDX:EAX MOD SRC;
FI;
FI;
FI;
*/
/*
The CF, OF, SF, ZF, AF, and PF flags are undefined.
*/
if(!source) {
flow_controller.interrupt(Interrupt::DivideError);
return;
@ -552,6 +589,43 @@ void div(IntT &destination_high, IntT &destination_low, IntT source, FlowControl
template <typename IntT, typename FlowControllerT>
void idiv(IntT &destination_high, IntT &destination_low, IntT source, FlowControllerT &flow_controller) {
/*
IF SRC = 0
THEN #DE; (* divide error *)
FI;
IF OperandSize = 8 (* word/byte operation *)
THEN
temp AX / SRC; (* signed division *)
IF (temp > 7FH) OR (temp < 80H) (* if a positive result is greater than 7FH or a negative result is less than 80H *)
THEN #DE; (* divide error *) ;
ELSE
AL temp;
AH AX MOD SRC;
FI;
ELSE
IF OperandSize = 16 (* doubleword/word operation *)
THEN
temp DX:AX / SRC; (* signed division *)
IF (temp > 7FFFH) OR (temp < 8000H) (* if a positive result is greater than 7FFFH or a negative result is less than 8000H *)
THEN #DE; (* divide error *) ;
ELSE
AX temp;
DX DX:AX MOD SRC;
FI;
ELSE (* quadword/doubleword operation *)
temp EDX:EAX / SRC; (* signed division *)
IF (temp > 7FFFFFFFH) OR (temp < 80000000H) (* if a positive result is greater than 7FFFFFFFH or a negative result is less than 80000000H *)
THEN #DE; (* divide error *) ;
ELSE
EAX temp;
EDX EDX:EAX MOD SRC;
FI;
FI;
FI;
*/
/*
The CF, OF, SF, ZF, AF, and PF flags are undefined.
*/
if(!source) {
flow_controller.interrupt(Interrupt::DivideError);
return;
@ -570,6 +644,41 @@ void idiv(IntT &destination_high, IntT &destination_low, IntT source, FlowContro
destination_high = dividend % sIntT(source);
}
template <typename IntT>
void inc(IntT &destination, Status &status) {
/*
DEST DEST + 1;
*/
/*
The CF flag is not affected.
The OF, SF, ZF, AF, and PF flags are set according to the result.
*/
++destination;
status.overflow = destination == top_bit<IntT>();
status.sign = destination & top_bit<IntT>();
status.zero = status.parity = destination;
status.auxiliary_carry = ((destination - 1) ^ destination) & 0x10;
}
template <typename IntT>
void dec(IntT &destination, Status &status) {
/*
DEST DEST - 1;
*/
/*
The CF flag is not affected.
The OF, SF, ZF, AF, and PF flags are set according to the result.
*/
status.overflow = destination == top_bit<IntT>();
--destination;
status.sign = destination & top_bit<IntT>();
status.zero = status.parity = destination;
status.auxiliary_carry = ((destination + 1) ^ destination) & 0x10;
}
template <typename IntT>
void and_(IntT &destination, IntT source, Status &status) {
/*
@ -776,6 +885,9 @@ template <
}
return;
case Operation::INC: Primitive::inc(destination(), status); break;
case Operation::DEC: Primitive::dec(destination(), status); break;
case Operation::AND: Primitive::and_(destination(), source(), status); break;
case Operation::CALLrel:

View File

@ -278,7 +278,7 @@ struct FailedExecution {
- (NSArray<NSString *> *)testFiles {
NSString *path = [NSString stringWithUTF8String:TestSuiteHome];
NSSet *allowList = [NSSet setWithArray:@[
@"37.json.gz", // AAA
/* @"37.json.gz", // AAA
@"3F.json.gz", // AAS
@"D4.json.gz", // AAM
@"D5.json.gz", // AAD
@ -320,14 +320,25 @@ struct FailedExecution {
@"F6.6.json.gz", @"F7.6.json.gz",
// IDIV
@"F6.7.json.gz", @"F7.7.json.gz",
@"F6.7.json.gz", @"F7.7.json.gz",*/
// INC
@"40.json.gz", @"41.json.gz", @"42.json.gz", @"43.json.gz",
@"44.json.gz", @"45.json.gz", @"46.json.gz", @"47.json.gz",
@"FE.0.json.gz",
@"FF.0.json.gz",
// DEC
@"48.json.gz", @"49.json.gz", @"4A.json.gz", @"4B.json.gz",
@"4C.json.gz", @"4D.json.gz", @"4E.json.gz", @"4F.json.gz",
@"FE.1.json.gz",
@"FF.1.json.gz",
// TODO: INC, DEC
// TODO: IN, OUT
// TODO: JO, JNO, JB, JNB, JZ, JNZ, JBE, JNBE, JS, JNS, JP, JNP, JL, JNL, JLE, JNLE,
// CALL
@"E8.json.gz", @"FF.2.json.gz",
/* @"E8.json.gz", @"FF.2.json.gz",
@"9A.json.gz", @"FF.3.json.gz",
// TODO: IRET
@ -364,11 +375,12 @@ struct FailedExecution {
@"FD.json.gz", // STD
@"FB.json.gz", // STI
@"F5.json.gz", // CMC
*/
// TODO: CMP, TEST
// TODO: XCHG, XLAT
// TODO: SALC, SETMO, SETMOC
]];
NSSet *ignoreList = nil;