1*795d594fSAndroid Build Coastguard Worker%def fpcmp(suff="d", nanval="pos"): 2*795d594fSAndroid Build Coastguard Worker/* 3*795d594fSAndroid Build Coastguard Worker * Compare two floating-point values. Puts 0, 1, or -1 into the 4*795d594fSAndroid Build Coastguard Worker * destination register based on the results of the comparison. 5*795d594fSAndroid Build Coastguard Worker * 6*795d594fSAndroid Build Coastguard Worker * int compare(x, y) { 7*795d594fSAndroid Build Coastguard Worker * if (x == y) { 8*795d594fSAndroid Build Coastguard Worker * return 0; 9*795d594fSAndroid Build Coastguard Worker * } else if (x < y) { 10*795d594fSAndroid Build Coastguard Worker * return -1; 11*795d594fSAndroid Build Coastguard Worker * } else if (x > y) { 12*795d594fSAndroid Build Coastguard Worker * return 1; 13*795d594fSAndroid Build Coastguard Worker * } else { 14*795d594fSAndroid Build Coastguard Worker * return nanval ? 1 : -1; 15*795d594fSAndroid Build Coastguard Worker * } 16*795d594fSAndroid Build Coastguard Worker * } 17*795d594fSAndroid Build Coastguard Worker */ 18*795d594fSAndroid Build Coastguard Worker /* op vAA, vBB, vCC */ 19*795d594fSAndroid Build Coastguard Worker movzbl 3(rPC), %ecx # ecx<- CC 20*795d594fSAndroid Build Coastguard Worker movzbl 2(rPC), %eax # eax<- BB 21*795d594fSAndroid Build Coastguard Worker GET_VREG_XMM${suff} %xmm0, %eax 22*795d594fSAndroid Build Coastguard Worker xor %eax, %eax 23*795d594fSAndroid Build Coastguard Worker ucomis${suff} VREG_ADDRESS(%ecx), %xmm0 24*795d594fSAndroid Build Coastguard Worker jp .L${opcode}_nan_is_${nanval} 25*795d594fSAndroid Build Coastguard Worker je .L${opcode}_finish 26*795d594fSAndroid Build Coastguard Worker jb .L${opcode}_less 27*795d594fSAndroid Build Coastguard Worker.L${opcode}_nan_is_pos: 28*795d594fSAndroid Build Coastguard Worker incl %eax 29*795d594fSAndroid Build Coastguard Worker jmp .L${opcode}_finish 30*795d594fSAndroid Build Coastguard Worker.L${opcode}_nan_is_neg: 31*795d594fSAndroid Build Coastguard Worker.L${opcode}_less: 32*795d594fSAndroid Build Coastguard Worker decl %eax 33*795d594fSAndroid Build Coastguard Worker.L${opcode}_finish: 34*795d594fSAndroid Build Coastguard Worker SET_VREG %eax, rINST 35*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 2 36*795d594fSAndroid Build Coastguard Worker 37*795d594fSAndroid Build Coastguard Worker%def fpcvt(instr="", load="", store="", wide="0"): 38*795d594fSAndroid Build Coastguard Worker/* 39*795d594fSAndroid Build Coastguard Worker * Generic 32-bit FP conversion operation. 40*795d594fSAndroid Build Coastguard Worker */ 41*795d594fSAndroid Build Coastguard Worker /* unop vA, vB */ 42*795d594fSAndroid Build Coastguard Worker movzbl rINSTbl, %ecx # ecx <- A+ 43*795d594fSAndroid Build Coastguard Worker sarl $$4, rINST # rINST <- B 44*795d594fSAndroid Build Coastguard Worker $load VREG_ADDRESS(rINST) # %st0 <- vB 45*795d594fSAndroid Build Coastguard Worker andb $$0xf, %cl # ecx <- A 46*795d594fSAndroid Build Coastguard Worker $instr 47*795d594fSAndroid Build Coastguard Worker $store VREG_ADDRESS(%ecx) # vA <- %st0 48*795d594fSAndroid Build Coastguard Worker .if $wide 49*795d594fSAndroid Build Coastguard Worker CLEAR_WIDE_REF %ecx 50*795d594fSAndroid Build Coastguard Worker .else 51*795d594fSAndroid Build Coastguard Worker CLEAR_REF %ecx 52*795d594fSAndroid Build Coastguard Worker .endif 53*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 1 54*795d594fSAndroid Build Coastguard Worker 55*795d594fSAndroid Build Coastguard Worker%def sseBinop(instr="", suff=""): 56*795d594fSAndroid Build Coastguard Worker movzbl 2(rPC), %ecx # ecx <- BB 57*795d594fSAndroid Build Coastguard Worker movzbl 3(rPC), %eax # eax <- CC 58*795d594fSAndroid Build Coastguard Worker GET_VREG_XMM${suff} %xmm0, %ecx # %xmm0 <- 1st src 59*795d594fSAndroid Build Coastguard Worker#ifdef MTERP_USE_AVX 60*795d594fSAndroid Build Coastguard Worker v${instr}${suff} VREG_ADDRESS(%eax), %xmm0, %xmm0 61*795d594fSAndroid Build Coastguard Worker SET_VREG_XMM${suff} %xmm0, rINST # vAA <- %xmm0 62*795d594fSAndroid Build Coastguard Worker vpxor %xmm0, %xmm0, %xmm0 63*795d594fSAndroid Build Coastguard Worker vmovs${suff} %xmm0, VREG_REF_ADDRESS(rINST) # clear ref 64*795d594fSAndroid Build Coastguard Worker#else 65*795d594fSAndroid Build Coastguard Worker ${instr}${suff} VREG_ADDRESS(%eax), %xmm0 66*795d594fSAndroid Build Coastguard Worker SET_VREG_XMM${suff} %xmm0, rINST # vAA <- %xmm0 67*795d594fSAndroid Build Coastguard Worker pxor %xmm0, %xmm0 68*795d594fSAndroid Build Coastguard Worker movs${suff} %xmm0, VREG_REF_ADDRESS(rINST) # clear ref 69*795d594fSAndroid Build Coastguard Worker#endif 70*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 2 71*795d594fSAndroid Build Coastguard Worker 72*795d594fSAndroid Build Coastguard Worker%def sseBinop2Addr(instr="", suff=""): 73*795d594fSAndroid Build Coastguard Worker movzx rINSTbl, %ecx # ecx <- A+ 74*795d594fSAndroid Build Coastguard Worker andl $$0xf, %ecx # ecx <- A 75*795d594fSAndroid Build Coastguard Worker GET_VREG_XMM${suff} %xmm0, %ecx # %xmm0 <- 1st src 76*795d594fSAndroid Build Coastguard Worker sarl $$4, rINST # rINST<- B 77*795d594fSAndroid Build Coastguard Worker#ifdef MTERP_USE_AVX 78*795d594fSAndroid Build Coastguard Worker v${instr}${suff} VREG_ADDRESS(rINST), %xmm0, %xmm0 79*795d594fSAndroid Build Coastguard Worker SET_VREG_XMM${suff} %xmm0, %ecx # vAA<- %xmm0 80*795d594fSAndroid Build Coastguard Worker vpxor %xmm0, %xmm0, %xmm0 81*795d594fSAndroid Build Coastguard Worker vmovs${suff} %xmm0, VREG_REF_ADDRESS(rINST) # clear ref 82*795d594fSAndroid Build Coastguard Worker#else 83*795d594fSAndroid Build Coastguard Worker ${instr}${suff} VREG_ADDRESS(rINST), %xmm0 84*795d594fSAndroid Build Coastguard Worker SET_VREG_XMM${suff} %xmm0, %ecx # vAA<- %xmm0 85*795d594fSAndroid Build Coastguard Worker pxor %xmm0, %xmm0 86*795d594fSAndroid Build Coastguard Worker movs${suff} %xmm0, VREG_REF_ADDRESS(rINST) # clear ref 87*795d594fSAndroid Build Coastguard Worker#endif 88*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 1 89*795d594fSAndroid Build Coastguard Worker 90*795d594fSAndroid Build Coastguard Worker%def op_add_double(): 91*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="adds", suff="d") 92*795d594fSAndroid Build Coastguard Worker 93*795d594fSAndroid Build Coastguard Worker%def op_add_double_2addr(): 94*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="adds", suff="d") 95*795d594fSAndroid Build Coastguard Worker 96*795d594fSAndroid Build Coastguard Worker%def op_add_float(): 97*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="adds", suff="s") 98*795d594fSAndroid Build Coastguard Worker 99*795d594fSAndroid Build Coastguard Worker%def op_add_float_2addr(): 100*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="adds", suff="s") 101*795d594fSAndroid Build Coastguard Worker 102*795d594fSAndroid Build Coastguard Worker%def op_cmpg_double(): 103*795d594fSAndroid Build Coastguard Worker% fpcmp(suff="d", nanval="pos") 104*795d594fSAndroid Build Coastguard Worker 105*795d594fSAndroid Build Coastguard Worker%def op_cmpg_float(): 106*795d594fSAndroid Build Coastguard Worker% fpcmp(suff="s", nanval="pos") 107*795d594fSAndroid Build Coastguard Worker 108*795d594fSAndroid Build Coastguard Worker%def op_cmpl_double(): 109*795d594fSAndroid Build Coastguard Worker% fpcmp(suff="d", nanval="neg") 110*795d594fSAndroid Build Coastguard Worker 111*795d594fSAndroid Build Coastguard Worker%def op_cmpl_float(): 112*795d594fSAndroid Build Coastguard Worker% fpcmp(suff="s", nanval="neg") 113*795d594fSAndroid Build Coastguard Worker 114*795d594fSAndroid Build Coastguard Worker%def op_div_double(): 115*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="divs", suff="d") 116*795d594fSAndroid Build Coastguard Worker 117*795d594fSAndroid Build Coastguard Worker%def op_div_double_2addr(): 118*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="divs", suff="d") 119*795d594fSAndroid Build Coastguard Worker 120*795d594fSAndroid Build Coastguard Worker%def op_div_float(): 121*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="divs", suff="s") 122*795d594fSAndroid Build Coastguard Worker 123*795d594fSAndroid Build Coastguard Worker%def op_div_float_2addr(): 124*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="divs", suff="s") 125*795d594fSAndroid Build Coastguard Worker 126*795d594fSAndroid Build Coastguard Worker%def op_double_to_float(): 127*795d594fSAndroid Build Coastguard Worker% fpcvt(load="fldl", store="fstps") 128*795d594fSAndroid Build Coastguard Worker 129*795d594fSAndroid Build Coastguard Worker%def op_double_to_int(): 130*795d594fSAndroid Build Coastguard Worker% cvtfp_int(srcdouble="1", tgtlong="0") 131*795d594fSAndroid Build Coastguard Worker 132*795d594fSAndroid Build Coastguard Worker%def op_double_to_long(): 133*795d594fSAndroid Build Coastguard Worker% cvtfp_int(srcdouble="1", tgtlong="1") 134*795d594fSAndroid Build Coastguard Worker 135*795d594fSAndroid Build Coastguard Worker%def op_float_to_double(): 136*795d594fSAndroid Build Coastguard Worker% fpcvt(load="flds", store="fstpl", wide="1") 137*795d594fSAndroid Build Coastguard Worker 138*795d594fSAndroid Build Coastguard Worker%def op_float_to_int(): 139*795d594fSAndroid Build Coastguard Worker% cvtfp_int(srcdouble="0", tgtlong="0") 140*795d594fSAndroid Build Coastguard Worker 141*795d594fSAndroid Build Coastguard Worker%def op_float_to_long(): 142*795d594fSAndroid Build Coastguard Worker% cvtfp_int(srcdouble="0", tgtlong="1") 143*795d594fSAndroid Build Coastguard Worker 144*795d594fSAndroid Build Coastguard Worker%def op_int_to_double(): 145*795d594fSAndroid Build Coastguard Worker% fpcvt(load="fildl", store="fstpl", wide="1") 146*795d594fSAndroid Build Coastguard Worker 147*795d594fSAndroid Build Coastguard Worker%def op_int_to_float(): 148*795d594fSAndroid Build Coastguard Worker% fpcvt(load="fildl", store="fstps") 149*795d594fSAndroid Build Coastguard Worker 150*795d594fSAndroid Build Coastguard Worker%def op_long_to_double(): 151*795d594fSAndroid Build Coastguard Worker% fpcvt(load="fildll", store="fstpl", wide="1") 152*795d594fSAndroid Build Coastguard Worker 153*795d594fSAndroid Build Coastguard Worker%def op_long_to_float(): 154*795d594fSAndroid Build Coastguard Worker% fpcvt(load="fildll", store="fstps") 155*795d594fSAndroid Build Coastguard Worker 156*795d594fSAndroid Build Coastguard Worker%def op_mul_double(): 157*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="muls", suff="d") 158*795d594fSAndroid Build Coastguard Worker 159*795d594fSAndroid Build Coastguard Worker%def op_mul_double_2addr(): 160*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="muls", suff="d") 161*795d594fSAndroid Build Coastguard Worker 162*795d594fSAndroid Build Coastguard Worker%def op_mul_float(): 163*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="muls", suff="s") 164*795d594fSAndroid Build Coastguard Worker 165*795d594fSAndroid Build Coastguard Worker%def op_mul_float_2addr(): 166*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="muls", suff="s") 167*795d594fSAndroid Build Coastguard Worker 168*795d594fSAndroid Build Coastguard Worker%def op_neg_double(): 169*795d594fSAndroid Build Coastguard Worker% fpcvt(instr="fchs", load="fldl", store="fstpl", wide="1") 170*795d594fSAndroid Build Coastguard Worker 171*795d594fSAndroid Build Coastguard Worker%def op_neg_float(): 172*795d594fSAndroid Build Coastguard Worker% fpcvt(instr="fchs", load="flds", store="fstps") 173*795d594fSAndroid Build Coastguard Worker 174*795d594fSAndroid Build Coastguard Worker%def op_rem_double(): 175*795d594fSAndroid Build Coastguard Worker /* rem_double vAA, vBB, vCC */ 176*795d594fSAndroid Build Coastguard Worker movzbl 3(rPC), %ecx # ecx <- BB 177*795d594fSAndroid Build Coastguard Worker movzbl 2(rPC), %eax # eax <- CC 178*795d594fSAndroid Build Coastguard Worker fldl VREG_ADDRESS(%ecx) # %st1 <- fp[vBB] 179*795d594fSAndroid Build Coastguard Worker fldl VREG_ADDRESS(%eax) # %st0 <- fp[vCC] 180*795d594fSAndroid Build Coastguard Worker1: 181*795d594fSAndroid Build Coastguard Worker fprem 182*795d594fSAndroid Build Coastguard Worker fstsw %ax 183*795d594fSAndroid Build Coastguard Worker sahf 184*795d594fSAndroid Build Coastguard Worker jp 1b 185*795d594fSAndroid Build Coastguard Worker fstp %st(1) 186*795d594fSAndroid Build Coastguard Worker fstpl VREG_ADDRESS(rINST) # fp[vAA] <- %st 187*795d594fSAndroid Build Coastguard Worker CLEAR_WIDE_REF rINST 188*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 2 189*795d594fSAndroid Build Coastguard Worker 190*795d594fSAndroid Build Coastguard Worker%def op_rem_double_2addr(): 191*795d594fSAndroid Build Coastguard Worker /* rem_double/2addr vA, vB */ 192*795d594fSAndroid Build Coastguard Worker movzx rINSTbl, %ecx # ecx <- A+ 193*795d594fSAndroid Build Coastguard Worker sarl $$4, rINST # rINST <- B 194*795d594fSAndroid Build Coastguard Worker fldl VREG_ADDRESS(rINST) # vB to fp stack 195*795d594fSAndroid Build Coastguard Worker andb $$0xf, %cl # ecx <- A 196*795d594fSAndroid Build Coastguard Worker fldl VREG_ADDRESS(%ecx) # vA to fp stack 197*795d594fSAndroid Build Coastguard Worker1: 198*795d594fSAndroid Build Coastguard Worker fprem 199*795d594fSAndroid Build Coastguard Worker fstsw %ax 200*795d594fSAndroid Build Coastguard Worker sahf 201*795d594fSAndroid Build Coastguard Worker jp 1b 202*795d594fSAndroid Build Coastguard Worker fstp %st(1) 203*795d594fSAndroid Build Coastguard Worker fstpl VREG_ADDRESS(%ecx) # %st to vA 204*795d594fSAndroid Build Coastguard Worker CLEAR_WIDE_REF %ecx 205*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 1 206*795d594fSAndroid Build Coastguard Worker 207*795d594fSAndroid Build Coastguard Worker%def op_rem_float(): 208*795d594fSAndroid Build Coastguard Worker /* rem_float vAA, vBB, vCC */ 209*795d594fSAndroid Build Coastguard Worker movzbl 3(rPC), %ecx # ecx <- BB 210*795d594fSAndroid Build Coastguard Worker movzbl 2(rPC), %eax # eax <- CC 211*795d594fSAndroid Build Coastguard Worker flds VREG_ADDRESS(%ecx) # vBB to fp stack 212*795d594fSAndroid Build Coastguard Worker flds VREG_ADDRESS(%eax) # vCC to fp stack 213*795d594fSAndroid Build Coastguard Worker1: 214*795d594fSAndroid Build Coastguard Worker fprem 215*795d594fSAndroid Build Coastguard Worker fstsw %ax 216*795d594fSAndroid Build Coastguard Worker sahf 217*795d594fSAndroid Build Coastguard Worker jp 1b 218*795d594fSAndroid Build Coastguard Worker fstp %st(1) 219*795d594fSAndroid Build Coastguard Worker fstps VREG_ADDRESS(rINST) # %st to vAA 220*795d594fSAndroid Build Coastguard Worker CLEAR_REF rINST 221*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 2 222*795d594fSAndroid Build Coastguard Worker 223*795d594fSAndroid Build Coastguard Worker%def op_rem_float_2addr(): 224*795d594fSAndroid Build Coastguard Worker /* rem_float/2addr vA, vB */ 225*795d594fSAndroid Build Coastguard Worker movzx rINSTbl, %ecx # ecx <- A+ 226*795d594fSAndroid Build Coastguard Worker sarl $$4, rINST # rINST <- B 227*795d594fSAndroid Build Coastguard Worker flds VREG_ADDRESS(rINST) # vB to fp stack 228*795d594fSAndroid Build Coastguard Worker andb $$0xf, %cl # ecx <- A 229*795d594fSAndroid Build Coastguard Worker flds VREG_ADDRESS(%ecx) # vA to fp stack 230*795d594fSAndroid Build Coastguard Worker1: 231*795d594fSAndroid Build Coastguard Worker fprem 232*795d594fSAndroid Build Coastguard Worker fstsw %ax 233*795d594fSAndroid Build Coastguard Worker sahf 234*795d594fSAndroid Build Coastguard Worker jp 1b 235*795d594fSAndroid Build Coastguard Worker fstp %st(1) 236*795d594fSAndroid Build Coastguard Worker fstps VREG_ADDRESS(%ecx) # %st to vA 237*795d594fSAndroid Build Coastguard Worker CLEAR_REF %ecx 238*795d594fSAndroid Build Coastguard Worker ADVANCE_PC_FETCH_AND_GOTO_NEXT 1 239*795d594fSAndroid Build Coastguard Worker 240*795d594fSAndroid Build Coastguard Worker%def op_sub_double(): 241*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="subs", suff="d") 242*795d594fSAndroid Build Coastguard Worker 243*795d594fSAndroid Build Coastguard Worker%def op_sub_double_2addr(): 244*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="subs", suff="d") 245*795d594fSAndroid Build Coastguard Worker 246*795d594fSAndroid Build Coastguard Worker%def op_sub_float(): 247*795d594fSAndroid Build Coastguard Worker% sseBinop(instr="subs", suff="s") 248*795d594fSAndroid Build Coastguard Worker 249*795d594fSAndroid Build Coastguard Worker%def op_sub_float_2addr(): 250*795d594fSAndroid Build Coastguard Worker% sseBinop2Addr(instr="subs", suff="s") 251