GP-1378 make add with carry/subtract with borrow macros

decompiler-friendly
This commit is contained in:
James 2021-10-09 18:42:44 +00:00
parent 0aff58812f
commit 02d827b859
3 changed files with 49 additions and 45 deletions

View file

@ -215,14 +215,21 @@ macro th_addflags(op1,op2) {
#See ARM Architecture reference section "Pseudocode details of addition and subtraction"
macro th_add_with_carry_flags(op1,op2){
local CYz = zext(CY);
local CYa = carry( op1, op2 );
local OVa = scarry( op1, op2 );
local result = op1 + op2;
tmpCY = CYa || carry( result, CYz );
tmpOV = OVa ^^ scarry( result, CYz );
local CYz = zext(CY);
local result = op1 + op2;
tmpCY = carry( op1, op2 ) || carry( result, CYz );
tmpOV = scarry( op1, op2) ^^ scarry( result, CYz );
}
#Note: used for subtraction op1 - (op2 + !CY)
#sets tmpCY if there is NO borrow
macro th_sub_with_carry_flags(op1, op2){
local result = op1 - op2;
tmpCY = (op1 > op2) || (result < zext(CY));
tmpOV = sborrow(op1,op2) ^^ sborrow(result,zext(!CY));
}
macro th_test_flags(result){
ZR = (result == 0);
NG = (result s< 0);
@ -3688,7 +3695,7 @@ macro th_set_carry_for_ror(result, count) {
:sbc^CheckInIT_CZNO^ItCond Rd0002,Rm0305 is TMode=1 & ItCond & op6=0x106 & Rm0305 & Rd0002 & CheckInIT_CZNO
{
build ItCond;
th_add_with_carry_flags(Rd0002,~Rm0305);
th_sub_with_carry_flags(Rd0002,Rm0305);
Rd0002 = Rd0002 - Rm0305 - zext(!CY);
resflags(Rd0002);
build CheckInIT_CZNO;
@ -3700,7 +3707,7 @@ macro th_set_carry_for_ror(result, count) {
{
build ItCond;
build ThumbExpandImm12;
th_add_with_carry_flags(Rn0003,~ThumbExpandImm12);
th_sub_with_carry_flags(Rn0003,ThumbExpandImm12);
Rd0811 = Rn0003 - ThumbExpandImm12 - zext(!CY);
resflags(Rd0811);
build thSBIT_CZNO;
@ -3710,7 +3717,7 @@ macro th_set_carry_for_ror(result, count) {
{
build ItCond;
build thshift2;
th_add_with_carry_flags(Rn0003,~thshift2);
th_sub_with_carry_flags(Rn0003,thshift2);
Rd0811 = Rn0003 - thshift2 - zext(!CY);
resflags(Rd0811);
build thSBIT_CZNO;

View file

@ -1878,14 +1878,21 @@ SetMode: "#"^31 is c0004=0x1f { setSystemMode(); }
#See ARM Architecture reference section "Pseudocode details of addition and subtraction"
macro add_with_carry_flags(op1,op2){
local CYz = zext(CY);
local CYa = carry( op1, op2 );
local OVa = scarry( op1, op2 );
local result = op1 + op2;
tmpCY = CYa || carry( result, CYz );
tmpOV = OVa ^^ scarry( result, CYz );
local CYz = zext(CY);
local result = op1 + op2;
tmpCY = carry( op1, op2) || carry( result, CYz );
tmpOV = scarry( op1, op2 ) ^^ scarry( result, CYz );
}
#Note: used for subtraction op1 - (op2 + !CY)
#sets tmpCY if there is NO borrow
macro sub_with_carry_flags(op1, op2){
local result = op1 - op2;
tmpCY = (op1 > op2) || (result < zext(CY));
tmpOV = sborrow(op1,op2) ^^ sborrow(result,zext(!CY));
}
:adc^COND^SBIT_CZNO Rd,rn,shift1 is $(AMODE) & COND & c2124=5 & SBIT_CZNO & rn & Rd & c2627=0 & shift1
{
build COND;
@ -4653,7 +4660,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift1;
add_with_carry_flags(~rn,shift1);
sub_with_carry_flags(shift1,rn);
Rd=shift1-(rn+zext(!CY));
resultflags(Rd);
build SBIT_CZNO;
@ -4664,7 +4671,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift2;
add_with_carry_flags(~rn,shift2);
sub_with_carry_flags(shift2,rn);
Rd=shift2-(rn+zext(!CY));
resultflags(Rd);
build SBIT_CZNO;
@ -4675,7 +4682,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift3;
add_with_carry_flags(~rn,shift3);
sub_with_carry_flags(shift3,rn);
Rd=shift3-(rn+zext(!CY));
resultflags(Rd);
build SBIT_CZNO;
@ -4686,7 +4693,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift1;
add_with_carry_flags(~rn,shift1);
sub_with_carry_flags(shift1,rn);
local dest:4=shift1-(rn+zext(!CY));
resultflags(dest);
build SBIT_CZNO;
@ -4699,7 +4706,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift2;
add_with_carry_flags(~rn,shift2);
sub_with_carry_flags(shift2,rn);
local dest:4=shift2-(rn + zext(!CY));
resultflags(dest);
build SBIT_CZNO;
@ -4712,7 +4719,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift3;
add_with_carry_flags(~rn,shift3);
sub_with_carry_flags(shift3,rn);
local dest:4=shift3-(rn + zext(!CY));
resultflags(dest);
build SBIT_CZNO;
@ -4785,7 +4792,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift1;
add_with_carry_flags(rn,~shift1);
sub_with_carry_flags(rn,shift1);
Rd = rn-(shift1+zext(!CY));
resultflags(Rd);
build SBIT_CZNO;
@ -4796,7 +4803,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift2;
add_with_carry_flags(rn,~shift2);
sub_with_carry_flags(rn,shift2);
Rd = rn-(shift2 + zext(!CY));
resultflags(Rd);
build SBIT_CZNO;
@ -4807,7 +4814,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift3;
add_with_carry_flags(rn,~shift3);
sub_with_carry_flags(rn,shift3);
Rd = rn-(shift3+zext(!CY));
resultflags(Rd);
build SBIT_CZNO;
@ -4818,7 +4825,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift1;
add_with_carry_flags(rn,~shift1);
sub_with_carry_flags(rn,shift1);
local dest:4 = rn-(shift1 + zext(!CY));
resultflags(dest);
build SBIT_CZNO;
@ -4831,7 +4838,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift2;
add_with_carry_flags(rn,~shift2);
sub_with_carry_flags(rn,shift2);
local dest:4 = rn-(shift2+zext(!CY));
resultflags(dest);
build SBIT_CZNO;
@ -4844,7 +4851,7 @@ macro BitReverse_arm(val) {
build COND;
build rn;
build shift3;
add_with_carry_flags(rn,~shift3);
sub_with_carry_flags(rn,shift3);
local dest:4 = rn-(shift3 + zext(!CY));
resultflags(dest);
build SBIT_CZNO;

View file

@ -408,34 +408,24 @@ macro addCarryFlags ( op1, op2 ) {
local op1_low_32:4 = op1:4;
local op2_low_32:4 = op2:4;
local CFcopy:$(SIZE) = zext(i_cf);
local CFcopy_32:4 = zext(i_cf);
i_cf = carry( op1_low_32, op2_low_32);
x_cf = carry(op1,op2);
i_vf = scarry( op1_low_32, op2_low_32);
x_vf = scarry(op1, op2);
local result:$(SIZE) = op1 + op2;
local result_low_32:4 = op1_low_32 + op2_low_32;
i_cf = i_cf || carry( result_low_32, CFcopy_32 );
x_cf = x_cf || carry(result,CFcopy);
i_vf = i_vf ^^ scarry( result_low_32, CFcopy_32 );
x_vf = x_vf ^^ scarry(result,CFcopy);
i_cf = carry( op1_low_32, op2_low_32) || carry( result_low_32, CFcopy:4 );
x_cf = carry(op1,op2) || carry(result,CFcopy);
i_vf = scarry( op1_low_32, op2_low_32) ^^ scarry( result_low_32, CFcopy:4 );
x_vf = scarry(op1, op2) ^^ scarry(result,CFcopy);
}
macro subCarryFlags ( op1, op2 ) {
local op1_low_32:4 = op1:4;
local op2_low_32:4 = op2:4;
local CFcopy:$(SIZE) = zext(i_cf);
local CFCopy_32:4 = zext(i_cf);
i_cf = op1_low_32 < op2_low_32;
x_cf = op1 < op2;
i_vf = sborrow( op1_low_32, op2_low_32);
x_vf = sborrow(op1, op2);
local result:$(SIZE) = op1 - op2;
local result_low_32:4 = op1_low_32 - op2_low_32;
i_cf = i_cf || (result_low_32 < CFCopy_32);
x_cf = x_cf || (result < CFcopy);
i_vf = i_vf ^^ sborrow( result_low_32, CFCopy_32);
x_vf = x_vf ^^ sborrow(result,CFcopy);
i_cf = (op1_low_32 < op2_low_32) || (result_low_32 < CFcopy:4);
x_cf = (op1 < op2) || (result < CFcopy);
i_vf = sborrow( op1_low_32, op2_low_32) ^^ sborrow( result_low_32, CFcopy:4);
x_vf = sborrow(op1, op2) ^^ sborrow(result,CFcopy);
}
macro logicflags() {