mirror of
https://github.com/TomHarte/CLK.git
synced 2024-11-26 23:52:26 +00:00
Corrects byte increment/decrement actions for A7.
This commit is contained in:
parent
11bf706aa2
commit
bb9424d944
@ -76,13 +76,17 @@ struct ProcessorStorageConstructor {
|
|||||||
return int(((mode & 0xff) == XXXw) ? Action::AssembleWordDataFromPrefetch : Action::AssembleLongWordDataFromPrefetch);
|
return int(((mode & 0xff) == XXXw) ? Action::AssembleWordDataFromPrefetch : Action::AssembleLongWordDataFromPrefetch);
|
||||||
}
|
}
|
||||||
|
|
||||||
int increment_action(bool is_long_word_access, bool is_byte_access) const {
|
int increment_action(bool is_long_word_access, bool is_byte_access, int reg) const {
|
||||||
using Action = ProcessorBase::MicroOp::Action;
|
using Action = ProcessorBase::MicroOp::Action;
|
||||||
|
// Special case: stack pointer byte accesses adjust by two. Cf. http://www.scarpaz.com/Attic/Didattica/Scarpazza-2005-68k-1-addressing.pdf
|
||||||
|
if(reg == 7 && is_byte_access) return int(Action::Increment2);
|
||||||
return int(is_long_word_access ? Action::Increment4 : (is_byte_access ? Action::Increment1 : Action::Increment2));
|
return int(is_long_word_access ? Action::Increment4 : (is_byte_access ? Action::Increment1 : Action::Increment2));
|
||||||
}
|
}
|
||||||
|
|
||||||
int decrement_action(bool is_long_word_access, bool is_byte_access) const {
|
int decrement_action(bool is_long_word_access, bool is_byte_access, int reg) const {
|
||||||
using Action = ProcessorBase::MicroOp::Action;
|
using Action = ProcessorBase::MicroOp::Action;
|
||||||
|
// Special case: stack pointer byte accesses adjust by two. Ibid.
|
||||||
|
if(reg == 7 && is_byte_access) return int(Action::Decrement2);
|
||||||
return int(is_long_word_access ? Action::Decrement4 : (is_byte_access ? Action::Decrement1 : Action::Decrement2));
|
return int(is_long_word_access ? Action::Decrement4 : (is_byte_access ? Action::Decrement1 : Action::Decrement2));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -652,12 +656,9 @@ struct ProcessorStorageConstructor {
|
|||||||
// by the few deviations.
|
// by the few deviations.
|
||||||
bool is_byte_access = (op_mode&3) == 0;
|
bool is_byte_access = (op_mode&3) == 0;
|
||||||
bool is_long_word_access = (op_mode&3) == 2;
|
bool is_long_word_access = (op_mode&3) == 2;
|
||||||
int dec = decrement_action(is_long_word_access, is_byte_access);
|
|
||||||
int inc = increment_action(is_long_word_access, is_byte_access);
|
|
||||||
|
|
||||||
if(instruction == 0x4eda) {
|
#define dec(n) decrement_action(is_long_word_access, is_byte_access, n)
|
||||||
printf("");
|
#define inc(n) increment_action(is_long_word_access, is_byte_access, n)
|
||||||
}
|
|
||||||
|
|
||||||
switch(mapping.decoder) {
|
switch(mapping.decoder) {
|
||||||
case Decoder::SWAP: {
|
case Decoder::SWAP: {
|
||||||
@ -733,12 +734,12 @@ struct ProcessorStorageConstructor {
|
|||||||
op(Action::None, seq("nr", { a(ea_register) }, !is_byte_access));
|
op(Action::None, seq("nr", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::DestinationMask);
|
op(inc(ea_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // [AND/OR/EOR].bw Dn, -(An)
|
case bw(PreDec): // [AND/OR/EOR].bw Dn, -(An)
|
||||||
op(int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::SourceMask, seq("n nrd", { a(ea_register) }, !is_byte_access));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n nrd", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -802,12 +803,12 @@ struct ProcessorStorageConstructor {
|
|||||||
op(Action::None, seq("nr", { a(ea_register) }, !is_byte_access));
|
op(Action::None, seq("nr", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np"));
|
op(Action::PerformOperation, seq("np"));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::SourceMask);
|
op(inc(ea_register) | MicroOp::SourceMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // [AND/OR].bw -(An), Dn
|
case bw(PreDec): // [AND/OR].bw -(An), Dn
|
||||||
op(int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::SourceMask, seq("n nr", { a(ea_register) }, !is_byte_access));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n nr", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np"));
|
op(Action::PerformOperation, seq("np"));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -950,7 +951,7 @@ struct ProcessorStorageConstructor {
|
|||||||
seq("np nrd np", { a(ea_register) }, !is_byte_access));
|
seq("np nrd np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::DestinationMask);
|
op(inc(ea_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -966,7 +967,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // [EORI/ORI/ANDI/SUBI/ADDI].bw #, -(An)
|
case bw(PreDec): // [EORI/ORI/ANDI/SUBI/ADDI].bw #, -(An)
|
||||||
op(int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::DestinationMask);
|
op(dec(ea_register) | MicroOp::DestinationMask);
|
||||||
op( int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask,
|
op( int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask,
|
||||||
seq("np n nrd np", { a(ea_register) }, !is_byte_access));
|
seq("np n nrd np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
||||||
@ -1069,7 +1070,7 @@ struct ProcessorStorageConstructor {
|
|||||||
case bw(PostInc): // ADD/SUB.bw (An)+, Dn
|
case bw(PostInc): // ADD/SUB.bw (An)+, Dn
|
||||||
op(Action::None, seq("nr np", { a(ea_register) }, !is_byte_access));
|
op(Action::None, seq("nr np", { a(ea_register) }, !is_byte_access));
|
||||||
if(ea_mode == PostInc) {
|
if(ea_mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::SourceMask);
|
op(inc(ea_register) | MicroOp::SourceMask);
|
||||||
}
|
}
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
break;
|
break;
|
||||||
@ -1085,7 +1086,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // ADD/SUB.bw -(An), Dn
|
case bw(PreDec): // ADD/SUB.bw -(An), Dn
|
||||||
op( int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::SourceMask,
|
op( dec(ea_register) | MicroOp::SourceMask,
|
||||||
seq("n nr np", { a(ea_register) }, !is_byte_access));
|
seq("n nr np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
break;
|
break;
|
||||||
@ -1158,7 +1159,7 @@ struct ProcessorStorageConstructor {
|
|||||||
op(Action::None, seq("nrd np", { a(destination_register) }, !is_byte_access));
|
op(Action::None, seq("nrd np", { a(destination_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw", { a(destination_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw", { a(destination_register) }, !is_byte_access));
|
||||||
if(ea_mode == PostInc) {
|
if(ea_mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::DestinationMask);
|
op(inc(destination_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1172,7 +1173,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // ADD/SUB.bw Dn, -(An)
|
case bw(PreDec): // ADD/SUB.bw Dn, -(An)
|
||||||
op( int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::DestinationMask,
|
op( dec(destination_register) | MicroOp::DestinationMask,
|
||||||
seq("n nrd np", { a(destination_register) }, !is_byte_access));
|
seq("n nrd np", { a(destination_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw", { a(destination_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw", { a(destination_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
@ -1346,7 +1347,7 @@ struct ProcessorStorageConstructor {
|
|||||||
op(Action::None, seq("nrd np", { a(ea_register) }, !is_byte_access));
|
op(Action::None, seq("nrd np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::DestinationMask);
|
op(inc(ea_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1362,7 +1363,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // [ADD/SUB]Q.bw #, -(An)
|
case bw(PreDec): // [ADD/SUB]Q.bw #, -(An)
|
||||||
op( int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::DestinationMask,
|
op( dec(ea_register) | MicroOp::DestinationMask,
|
||||||
seq("n nrd np", { a(ea_register) }, !is_byte_access));
|
seq("n nrd np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw", { a(ea_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
@ -1445,12 +1446,12 @@ struct ProcessorStorageConstructor {
|
|||||||
op(Action::None, seq("nrd np", { a(ea_register) }, false));
|
op(Action::None, seq("nrd np", { a(ea_register) }, false));
|
||||||
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(Action::Increment1) | MicroOp::DestinationMask);
|
op(inc(ea_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case PreDec: // BTST.b Dn, -(An)
|
case PreDec: // BTST.b Dn, -(An)
|
||||||
op(int(Action::Decrement1) | MicroOp::DestinationMask, seq("n nrd np", { a(ea_register) }, false));
|
op(dec(ea_register) | MicroOp::DestinationMask, seq("n nrd np", { a(ea_register) }, false));
|
||||||
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1501,13 +1502,13 @@ struct ProcessorStorageConstructor {
|
|||||||
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np nrd np", { a(ea_register) }, false));
|
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np nrd np", { a(ea_register) }, false));
|
||||||
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(Action::Increment1) | MicroOp::DestinationMask);
|
op(inc(ea_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case PreDec: // BTST.b #, -(An)
|
case PreDec: // BTST.b #, -(An)
|
||||||
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np"));
|
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np"));
|
||||||
op(int(Action::Decrement1) | MicroOp::DestinationMask, seq("n nrd np", { a(ea_register) }, false));
|
op(dec(ea_register) | MicroOp::DestinationMask, seq("n nrd np", { a(ea_register) }, false));
|
||||||
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
op(Action::PerformOperation, is_bclr ? seq("nw", { a(ea_register) }, false) : nullptr);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1547,7 +1548,16 @@ struct ProcessorStorageConstructor {
|
|||||||
storage_.instructions[instruction].source_address = &storage_.address_[ea_register];
|
storage_.instructions[instruction].source_address = &storage_.address_[ea_register];
|
||||||
storage_.instructions[instruction].destination_address = &storage_.address_[destination_register];
|
storage_.instructions[instruction].destination_address = &storage_.address_[destination_register];
|
||||||
|
|
||||||
op( int(Action::Decrement1) | MicroOp::SourceMask | MicroOp::DestinationMask,
|
const int source_dec = dec(ea_register);
|
||||||
|
const int destination_dec = dec(destination_register);
|
||||||
|
|
||||||
|
int first_action = source_dec | MicroOp::SourceMask | MicroOp::DestinationMask;
|
||||||
|
if(source_dec != destination_dec) {
|
||||||
|
first_action = source_dec | MicroOp::SourceMask;
|
||||||
|
op(destination_dec | MicroOp::DestinationMask);
|
||||||
|
}
|
||||||
|
|
||||||
|
op( first_action,
|
||||||
seq("n nr nr np nw", { a(ea_register), a(destination_register), a(destination_register) }, false));
|
seq("n nr nr np nw", { a(ea_register), a(destination_register), a(destination_register) }, false));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
} else {
|
} else {
|
||||||
@ -1628,7 +1638,7 @@ struct ProcessorStorageConstructor {
|
|||||||
op(Action::None, seq("nrd", { a(ea_register) }, !is_byte_access));
|
op(Action::None, seq("nrd", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
||||||
if(ea_mode == PostInc) {
|
if(ea_mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::DestinationMask);
|
op(inc(ea_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1642,7 +1652,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // [CLR/NEG/NEGX/NOT].bw -(An)
|
case bw(PreDec): // [CLR/NEG/NEGX/NOT].bw -(An)
|
||||||
op( int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::DestinationMask,
|
op( dec(ea_register) | MicroOp::DestinationMask,
|
||||||
seq("nrd", { a(ea_register) }, !is_byte_access));
|
seq("nrd", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("np nw", { a(ea_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
@ -1715,7 +1725,7 @@ struct ProcessorStorageConstructor {
|
|||||||
case bw(PostInc): // CMP.bw (An)+, Dn
|
case bw(PostInc): // CMP.bw (An)+, Dn
|
||||||
op(Action::None, seq("nr np", { a(ea_register) }, !is_byte_access));
|
op(Action::None, seq("nr np", { a(ea_register) }, !is_byte_access));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::SourceMask);
|
op(inc(ea_register) | MicroOp::SourceMask);
|
||||||
}
|
}
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
break;
|
break;
|
||||||
@ -1730,7 +1740,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // CMP.bw -(An), Dn
|
case bw(PreDec): // CMP.bw -(An), Dn
|
||||||
op( int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::SourceMask,
|
op( dec(ea_register) | MicroOp::SourceMask,
|
||||||
seq("n nr np", { a(ea_register) }, !is_byte_access));
|
seq("n nr np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
break;
|
break;
|
||||||
@ -1901,7 +1911,7 @@ struct ProcessorStorageConstructor {
|
|||||||
case bw(PostInc): // CMPI.bw #, (An)+
|
case bw(PostInc): // CMPI.bw #, (An)+
|
||||||
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np nrd np", { a(destination_register) }, !is_byte_access));
|
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np nrd np", { a(destination_register) }, !is_byte_access));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::DestinationMask);
|
op(inc(destination_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
break;
|
break;
|
||||||
@ -1918,7 +1928,7 @@ struct ProcessorStorageConstructor {
|
|||||||
|
|
||||||
case bw(PreDec): // CMPI.bw #, -(An)
|
case bw(PreDec): // CMPI.bw #, -(An)
|
||||||
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np n"));
|
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np n"));
|
||||||
op(int(is_byte_access ? Action::Decrement1 : Action::Decrement1) | MicroOp::DestinationMask, seq("nrd np", { a(destination_register) }, !is_byte_access));
|
op(dec(destination_register) | MicroOp::DestinationMask, seq("nrd np", { a(destination_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -1994,7 +2004,7 @@ struct ProcessorStorageConstructor {
|
|||||||
case Operation::CMPw: // CMPM.w, (An)+, (An)+
|
case Operation::CMPw: // CMPM.w, (An)+, (An)+
|
||||||
op(Action::None, seq("nr nr np", {a(source_register), a(destination_register)}, !is_byte_operation));
|
op(Action::None, seq("nr nr np", {a(source_register), a(destination_register)}, !is_byte_operation));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
op(int(is_byte_operation ? Action::Increment1 : Action::Increment2) | MicroOp::SourceMask | MicroOp::DestinationMask);
|
op(inc(destination_register) | MicroOp::SourceMask | MicroOp::DestinationMask);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case Operation::CMPl:
|
case Operation::CMPl:
|
||||||
@ -2036,12 +2046,12 @@ struct ProcessorStorageConstructor {
|
|||||||
case PostInc:
|
case PostInc:
|
||||||
op(Action::PerformOperation, seq("nr np nw", { a(ea_register), a(ea_register) }, false));
|
op(Action::PerformOperation, seq("nr np nw", { a(ea_register), a(ea_register) }, false));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(Action::Increment1) | MicroOp::DestinationMask);
|
op(inc(ea_register) | MicroOp::DestinationMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case PreDec:
|
case PreDec:
|
||||||
op(int(Action::Decrement1) | MicroOp::DestinationMask);
|
op(dec(ea_register) | MicroOp::DestinationMask);
|
||||||
op(Action::PerformOperation, seq("n nr np nw", { a(ea_register), a(ea_register) }, false));
|
op(Action::PerformOperation, seq("n nr np nw", { a(ea_register), a(ea_register) }, false));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -2316,8 +2326,6 @@ struct ProcessorStorageConstructor {
|
|||||||
// These don't come from the usual place.
|
// These don't come from the usual place.
|
||||||
is_byte_access = mapping.operation == Operation::MOVEb;
|
is_byte_access = mapping.operation == Operation::MOVEb;
|
||||||
is_long_word_access = mapping.operation == Operation::MOVEl;
|
is_long_word_access = mapping.operation == Operation::MOVEl;
|
||||||
dec = decrement_action(is_long_word_access, is_byte_access);
|
|
||||||
inc = increment_action(is_long_word_access, is_byte_access);
|
|
||||||
|
|
||||||
const int combined_source_mode = combined_mode(ea_mode, ea_register, true, true);
|
const int combined_source_mode = combined_mode(ea_mode, ea_register, true, true);
|
||||||
const int combined_destination_mode = combined_mode(destination_mode, destination_register, true, true);
|
const int combined_destination_mode = combined_mode(destination_mode, destination_register, true, true);
|
||||||
@ -2347,7 +2355,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case l2(PreDec, Dn): // MOVE[A].l -(An), [An/Dn]
|
case l2(PreDec, Dn): // MOVE[A].l -(An), [An/Dn]
|
||||||
op(dec | MicroOp::SourceMask, seq("n"));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n"));
|
||||||
case l2(Ind, Dn): // MOVE[A].l (An)[+], [An/Dn]
|
case l2(Ind, Dn): // MOVE[A].l (An)[+], [An/Dn]
|
||||||
op(int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask, seq("nR+ nr np", { ea(0), ea(0) }));
|
op(int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask, seq("nR+ nr np", { ea(0), ea(0) }));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
@ -2359,7 +2367,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw2(PreDec, Dn): // MOVE[A].bw -(An), [An/Dn]
|
case bw2(PreDec, Dn): // MOVE[A].bw -(An), [An/Dn]
|
||||||
op(dec | MicroOp::SourceMask, seq("n nr np", { a(ea_register) }, !is_byte_access));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n nr np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -2413,7 +2421,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case l2(PreDec, Ind): // MOVE.l -(An), (An)[+]
|
case l2(PreDec, Ind): // MOVE.l -(An), (An)[+]
|
||||||
op(dec | MicroOp::SourceMask, seq("n"));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n"));
|
||||||
case l2(Ind, Ind): // MOVE.l (An)[+], (An)[+]
|
case l2(Ind, Ind): // MOVE.l (An)[+], (An)[+]
|
||||||
op( int(Action::CopyToEffectiveAddress) | MicroOp::DestinationMask | MicroOp::SourceMask,
|
op( int(Action::CopyToEffectiveAddress) | MicroOp::DestinationMask | MicroOp::SourceMask,
|
||||||
seq("nR+ nr", { ea(0), ea(0) }));
|
seq("nR+ nr", { ea(0), ea(0) }));
|
||||||
@ -2426,7 +2434,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw2(PreDec, Ind): // MOVE.bw -(An), (An)[+]
|
case bw2(PreDec, Ind): // MOVE.bw -(An), (An)[+]
|
||||||
op(dec | MicroOp::SourceMask, seq("n nr", { a(ea_register) }, !is_byte_access));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n nr", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw np", { a(destination_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw np", { a(destination_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -2481,7 +2489,7 @@ struct ProcessorStorageConstructor {
|
|||||||
|
|
||||||
case bw2(Dn, PreDec): // MOVE.bw [An/Dn], -(An)
|
case bw2(Dn, PreDec): // MOVE.bw [An/Dn], -(An)
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
op( dec| MicroOp::DestinationMask,
|
op( dec(destination_register) | MicroOp::DestinationMask,
|
||||||
seq("np nw", { a(destination_register) }, !is_byte_access));
|
seq("np nw", { a(destination_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -2496,14 +2504,14 @@ struct ProcessorStorageConstructor {
|
|||||||
// e.g. MOVE.w -(A6), -(A6)
|
// e.g. MOVE.w -(A6), -(A6)
|
||||||
|
|
||||||
case bw2(PreDec, PreDec): // MOVE.bw -(An), -(An)
|
case bw2(PreDec, PreDec): // MOVE.bw -(An), -(An)
|
||||||
op(dec | MicroOp::SourceMask, seq("n"));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n"));
|
||||||
case bw2(Ind, PreDec): // MOVE.bw (An)[+], -(An)
|
case bw2(Ind, PreDec): // MOVE.bw (An)[+], -(An)
|
||||||
op(dec | MicroOp::DestinationMask, seq("nr", { a(ea_register) }, !is_byte_access));
|
op(dec(destination_register) | MicroOp::DestinationMask, seq("nr", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np nw", { a(destination_register) }, !is_byte_access));
|
op(Action::PerformOperation, seq("np nw", { a(destination_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case l2(PreDec, PreDec): // MOVE.l -(An), -(An)
|
case l2(PreDec, PreDec): // MOVE.l -(An), -(An)
|
||||||
op(dec | MicroOp::SourceMask, seq("n"));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n"));
|
||||||
case l2(Ind, PreDec): // MOVE.l (An)[+], -(An)
|
case l2(Ind, PreDec): // MOVE.l (An)[+], -(An)
|
||||||
op(int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask, seq("nR+ nr", { ea(0), ea(0) } ));
|
op(int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask, seq("nR+ nr", { ea(0), ea(0) } ));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
@ -2522,7 +2530,7 @@ struct ProcessorStorageConstructor {
|
|||||||
op( address_action_for_mode(combined_source_mode) | MicroOp::SourceMask,
|
op( address_action_for_mode(combined_source_mode) | MicroOp::SourceMask,
|
||||||
seq(pseq("np nr", combined_source_mode), { ea(0) }, !is_byte_access ));
|
seq(pseq("np nr", combined_source_mode), { ea(0) }, !is_byte_access ));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
op(dec | MicroOp::DestinationMask, seq("np nw", { a(destination_register) }, !is_byte_access));
|
op(dec(destination_register) | MicroOp::DestinationMask, seq("np nw", { a(destination_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case l2(XXXl, PreDec): // MOVE.l (xxx).w, -(An)
|
case l2(XXXl, PreDec): // MOVE.l (xxx).w, -(An)
|
||||||
@ -2543,7 +2551,7 @@ struct ProcessorStorageConstructor {
|
|||||||
case bw2(Imm, PreDec): // MOVE.bw #, -(An)
|
case bw2(Imm, PreDec): // MOVE.bw #, -(An)
|
||||||
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np"));
|
op(int(Action::AssembleWordDataFromPrefetch) | MicroOp::SourceMask, seq("np"));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
op(dec | MicroOp::DestinationMask, seq("np nw", { a(destination_register) }, !is_byte_access));
|
op(dec(destination_register) | MicroOp::DestinationMask, seq("np nw", { a(destination_register) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case l2(Imm, PreDec): // MOVE.l #, -(An)
|
case l2(Imm, PreDec): // MOVE.l #, -(An)
|
||||||
@ -2587,13 +2595,13 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw2d(PreDec): // MOVE.bw -(An), (d16, An)/(d8, An, Xn)/(d16, PC)/(d8, PC, Xn)
|
case bw2d(PreDec): // MOVE.bw -(An), (d16, An)/(d8, An, Xn)/(d16, PC)/(d8, PC, Xn)
|
||||||
op(dec | MicroOp::SourceMask, seq("n nr", { a(ea_register) }, !is_byte_access));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n nr", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
op(calc_action_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np nw np", { ea(1) }, !is_byte_access));
|
op(calc_action_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np nw np", { ea(1) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case l2d(PreDec): // MOVE.l -(An), (d16, An)/(d8, An, Xn)/(d16, PC)/(d8, PC, Xn)
|
case l2d(PreDec): // MOVE.l -(An), (d16, An)/(d8, An, Xn)/(d16, PC)/(d8, PC, Xn)
|
||||||
op(dec | MicroOp::SourceMask, seq("n"));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n"));
|
||||||
op(int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask, seq("nR+ nr", { ea(0), ea(0) }));
|
op(int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask, seq("nR+ nr", { ea(0), ea(0) }));
|
||||||
op(Action::PerformOperation);
|
op(Action::PerformOperation);
|
||||||
op(calc_action_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np nW+ nw np", { ea(1), ea(1) }));
|
op(calc_action_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np nW+ nw np", { ea(1), ea(1) }));
|
||||||
@ -2684,20 +2692,20 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw2(PreDec, XXXw): // MOVE.bw -(An), (xxx).W
|
case bw2(PreDec, XXXw): // MOVE.bw -(An), (xxx).W
|
||||||
op( dec | MicroOp::SourceMask);
|
op( dec(ea_register) | MicroOp::SourceMask);
|
||||||
op( address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask,
|
op( address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask,
|
||||||
seq("n nr np", { a(ea_register) }, !is_byte_access));
|
seq("n nr np", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("nw np", { ea(1) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw np", { ea(1) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case bw2(PreDec, XXXl): // MOVE.bw -(An), (xxx).L
|
case bw2(PreDec, XXXl): // MOVE.bw -(An), (xxx).L
|
||||||
op(dec | MicroOp::SourceMask, seq("n nr np", { a(ea_register) }, !is_byte_access));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n nr np", { a(ea_register) }, !is_byte_access));
|
||||||
op(address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask);
|
op(address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask);
|
||||||
op(Action::PerformOperation, seq("nw np np", { ea(1) }, !is_byte_access));
|
op(Action::PerformOperation, seq("nw np np", { ea(1) }, !is_byte_access));
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case l2(PreDec, XXXw): // MOVE.l -(An), (xxx).W
|
case l2(PreDec, XXXw): // MOVE.l -(An), (xxx).W
|
||||||
op( dec | MicroOp::SourceMask);
|
op( dec(ea_register) | MicroOp::SourceMask);
|
||||||
op( int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask,
|
op( int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask,
|
||||||
seq("n nR+ nr", { ea(0), ea(0) } ));
|
seq("n nR+ nr", { ea(0), ea(0) } ));
|
||||||
op( address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np"));
|
op( address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np"));
|
||||||
@ -2706,7 +2714,7 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case l2(PreDec, XXXl): // MOVE.l -(An), (xxx).L
|
case l2(PreDec, XXXl): // MOVE.l -(An), (xxx).L
|
||||||
op( dec | MicroOp::SourceMask);
|
op( dec(ea_register) | MicroOp::SourceMask);
|
||||||
op( int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask,
|
op( int(Action::CopyToEffectiveAddress) | MicroOp::SourceMask,
|
||||||
seq("n nR+ nr np", { ea(0), ea(0) } ));
|
seq("n nR+ nr np", { ea(0), ea(0) } ));
|
||||||
op( address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np"));
|
op( address_assemble_for_mode(combined_destination_mode) | MicroOp::DestinationMask, seq("np"));
|
||||||
@ -2835,10 +2843,22 @@ struct ProcessorStorageConstructor {
|
|||||||
|
|
||||||
// If any post-incrementing was involved, do the post increment(s).
|
// If any post-incrementing was involved, do the post increment(s).
|
||||||
if(ea_mode == PostInc || destination_mode == PostInc) {
|
if(ea_mode == PostInc || destination_mode == PostInc) {
|
||||||
op(
|
if(ea_mode == destination_mode) {
|
||||||
inc |
|
const int ea_inc = inc(ea_mode);
|
||||||
(ea_mode == PostInc ? MicroOp::SourceMask : 0) |
|
const int destination_inc = inc(destination_mode);
|
||||||
(destination_mode == PostInc ? MicroOp::DestinationMask : 0));
|
if(ea_inc == destination_inc) {
|
||||||
|
op(ea_inc | MicroOp::SourceMask | MicroOp::DestinationMask);
|
||||||
|
} else {
|
||||||
|
op(ea_inc | MicroOp::SourceMask);
|
||||||
|
op(destination_inc | MicroOp::DestinationMask);
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if(ea_mode == PostInc) {
|
||||||
|
op(inc(ea_mode) | MicroOp::SourceMask);
|
||||||
|
} else {
|
||||||
|
op(inc(destination_mode) | MicroOp::DestinationMask);
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
} break;
|
} break;
|
||||||
|
|
||||||
@ -2868,13 +2888,13 @@ struct ProcessorStorageConstructor {
|
|||||||
break;
|
break;
|
||||||
|
|
||||||
case bw(PreDec): // TST.bw -(An)
|
case bw(PreDec): // TST.bw -(An)
|
||||||
op(int(is_byte_access ? Action::Decrement1 : Action::Decrement2) | MicroOp::SourceMask, seq("n"));
|
op(dec(ea_register) | MicroOp::SourceMask, seq("n"));
|
||||||
case bw(Ind): // TST.bw (An)
|
case bw(Ind): // TST.bw (An)
|
||||||
case bw(PostInc): // TST.bw (An)+
|
case bw(PostInc): // TST.bw (An)+
|
||||||
op(Action::None, seq("nr", { a(ea_register) }, !is_byte_access));
|
op(Action::None, seq("nr", { a(ea_register) }, !is_byte_access));
|
||||||
op(Action::PerformOperation, seq("np"));
|
op(Action::PerformOperation, seq("np"));
|
||||||
if(mode == PostInc) {
|
if(mode == PostInc) {
|
||||||
op(int(is_byte_access ? Action::Increment1 : Action::Increment2) | MicroOp::SourceMask);
|
op(inc(ea_register) | MicroOp::SourceMask);
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -2952,6 +2972,9 @@ struct ProcessorStorageConstructor {
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#undef inc
|
||||||
|
#undef dec
|
||||||
}
|
}
|
||||||
|
|
||||||
#undef Dn
|
#undef Dn
|
||||||
|
Loading…
Reference in New Issue
Block a user