blob: 53d4dfaf9e74c61b24c3edd431effc20a9edd1a5 [file] [log] [blame]
Bill Buzbee3b0b4b92016-02-02 13:45:36 +00001 /*
2 * Generic two-operand compare-and-branch operation. Provide a "revcmp"
3 * fragment that specifies the *reverse* comparison to perform, e.g.
4 * for "if-le" you would use "gt".
5 *
6 * For: if-eq, if-ne, if-lt, if-ge, if-gt, if-le
7 */
8 /* if-cmp vA, vB, +CCCC */
9#if MTERP_SUSPEND
10 mov w1, wINST, lsr #12 // w1<- B
11 ubfx w0, wINST, #8, #4 // w0<- A
12 GET_VREG w3, w1 // w3<- vB
13 GET_VREG w2, w0 // w2<- vA
14 FETCH_S w1, 1 // w1<- branch offset, in code units
15 cmp w2, w3 // compare (vA, vB)
16 mov${condition} w1, #2 // w1<- BYTE branch dist for not-taken
17 adds w2, w1, w1 // convert to bytes, check sign
18 FETCH_ADVANCE_INST_RB w2 // update rPC, load wINST
19 ldrmi rIBASE, [xSELF, #THREAD_CURRENT_IBASE_OFFSET] // refresh rIBASE
20 GET_INST_OPCODE ip // extract opcode from wINST
21 GOTO_OPCODE ip // jump to next instruction
22#else
23 lsr w1, wINST, #12 // w1<- B
24 ubfx w0, wINST, #8, #4 // w0<- A
25 GET_VREG w3, w1 // w3<- vB
26 GET_VREG w2, w0 // w2<- vA
27 FETCH_S w1, 1 // w1<- branch offset, in code units
Bill Buzbee3b0b4b92016-02-02 13:45:36 +000028 mov w0, #2 // Offset if branch not taken
29 cmp w2, w3 // compare (vA, vB)
buzbeea0a16102016-02-03 15:23:56 -080030 csel wINST, w1, w0, ${condition} // Branch if true, stashing result in callee save reg.
31#if MTERP_PROFILE_BRANCHES
32 mov x0, xSELF
33 add x1, xFP, #OFF_FP_SHADOWFRAME
34 sbfm x2, xINST, 0, 31 // Sign extend branch offset
35 bl MterpProfileBranch // (self, shadow_frame, offset)
36 cbnz w0, MterpOnStackReplacement // Note: offset must be in xINST
37#endif
38 ldr w7, [xSELF, #THREAD_FLAGS_OFFSET]
39 adds w2, wINST, wINST // convert to bytes, check sign
Bill Buzbee3b0b4b92016-02-02 13:45:36 +000040 FETCH_ADVANCE_INST_RB w2 // update rPC, load wINST
41 b.mi MterpCheckSuspendAndContinue
42 GET_INST_OPCODE ip // extract opcode from wINST
43 GOTO_OPCODE ip // jump to next instruction
44#endif