Skip to content

Commit f1bb0d3

Browse files
committed
JIT/AArch64: Support shifted immediate
As pointed out by MikePall in [1], shifted immediate value is supported. See [2]. For example, `add x0, x1, php#4096` would be encoded by DynASM into `add x0, x1, php#1, lsl php#12` directly. In this patch, a helper is added to check whether an immediate value is in the two allowed ranges: (1) 0 to 4095, and (2) LSL php#12 on all the values from the first range. Note that this helper works for add/adds/sub/subs/cmp/cmn instructions. [1] LuaJIT/LuaJIT#718 [2] https://github.com/LuaJIT/LuaJIT/blob/v2.1/dynasm/dasm_arm64.lua#L342 Change-Id: I4870048b9b8e6c429b73a4803af2a3b2d5ec0fbb
1 parent 6318040 commit f1bb0d3

File tree

1 file changed

+15
-10
lines changed

1 file changed

+15
-10
lines changed

ext/opcache/jit/zend_jit_arm64.dasc

Lines changed: 15 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -122,7 +122,7 @@ typedef struct TLVDescriptor TLVDescriptor;
122122

123123
#define IS_SIGNED_32BIT(val) ((((intptr_t)(val)) <= 0x7fffffff) && (((intptr_t)(val)) >= (-2147483647 - 1)))
124124

125-
/* Encoding of immediate. TODO: shift mode may be supported in the near future. */
125+
/* Encoding of immediate. */
126126
#define MAX_IMM12 0xfff // maximum value for imm12
127127
#define MAX_IMM16 0xffff // maximum value for imm16
128128
#define CMP_IMM MAX_IMM12 // cmp insn
@@ -172,6 +172,11 @@ static bool arm64_may_use_adrp(const void *addr)
172172
return 0;
173173
}
174174

175+
static bool arm64_may_encode_imm12(const int64_t val)
176+
{
177+
return (val >= 0 && (val < (1<<12) || !(val & 0xffffffffff000fff)));
178+
}
179+
175180
/* Determine whether an immediate value can be encoded as the immediate operand of logical instructions. */
176181
static bool logical_immediate_p(uint64_t value, uint32_t reg_size)
177182
{
@@ -364,9 +369,9 @@ static bool logical_immediate_p(uint64_t value, uint32_t reg_size)
364369
|.macro CMP_32_WITH_CONST, reg, val, tmp_reg
365370
|| if (val == 0) {
366371
| cmp reg, wzr
367-
|| } else if (((int32_t)(val)) > 0 && ((int32_t)(val)) <= CMP_IMM) {
372+
|| } else if (arm64_may_encode_imm12((int64_t)(val))) {
368373
| cmp reg, #val
369-
|| } else if (((int32_t)(val)) < 0 && ((int32_t)(val)) >= -CMP_IMM) {
374+
|| } else if (arm64_may_encode_imm12((int64_t)(-val))) {
370375
| cmn reg, #-val
371376
|| } else {
372377
| LOAD_32BIT_VAL tmp_reg, val
@@ -377,9 +382,9 @@ static bool logical_immediate_p(uint64_t value, uint32_t reg_size)
377382
|.macro CMP_64_WITH_CONST_32, reg, val, tmp_reg
378383
|| if (val == 0) {
379384
| cmp reg, xzr
380-
|| } else if (((int32_t)(val)) > 0 && ((int32_t)(val)) <= CMP_IMM) {
385+
|| } else if (arm64_may_encode_imm12((int64_t)(val))) {
381386
| cmp reg, #val
382-
|| } else if (((int32_t)(val)) < 0 && ((int32_t)(val)) >= -CMP_IMM) {
387+
|| } else if (arm64_may_encode_imm12((int64_t)(-val))) {
383388
| cmn reg, #-val
384389
|| } else {
385390
| LOAD_32BIT_VAL tmp_reg, val
@@ -390,9 +395,9 @@ static bool logical_immediate_p(uint64_t value, uint32_t reg_size)
390395
|.macro CMP_64_WITH_CONST, reg, val, tmp_reg
391396
|| if (val == 0) {
392397
| cmp reg, xzr
393-
|| } else if (((int64_t)(val)) > 0 && ((int64_t)(val)) <= CMP_IMM) {
398+
|| } else if (arm64_may_encode_imm12((int64_t)(val))) {
394399
| cmp reg, #val
395-
|| } else if (((int64_t)(val)) < 0 && ((int64_t)(val)) >= -CMP_IMM) {
400+
|| } else if (arm64_may_encode_imm12((int64_t)(-val))) {
396401
| cmn reg, #-val
397402
|| } else {
398403
| LOAD_64BIT_VAL tmp_reg, val
@@ -406,7 +411,7 @@ static bool logical_immediate_p(uint64_t value, uint32_t reg_size)
406411
|.macro ADD_SUB_32_WITH_CONST, add_sub_ins, dst_reg, src_reg1, val, tmp_reg
407412
|| if (val == 0) {
408413
| add_sub_ins dst_reg, src_reg1, wzr
409-
|| } else if (((int32_t)(val)) > 0 && ((int32_t)(val)) <= ADD_SUB_IMM) {
414+
|| } else if (arm64_may_encode_imm12((int64_t)(val))) {
410415
| add_sub_ins dst_reg, src_reg1, #val
411416
|| } else {
412417
| LOAD_32BIT_VAL tmp_reg, val
@@ -417,7 +422,7 @@ static bool logical_immediate_p(uint64_t value, uint32_t reg_size)
417422
|.macro ADD_SUB_64_WITH_CONST_32, add_sub_ins, dst_reg, src_reg1, val, tmp_reg
418423
|| if (val == 0) {
419424
| add_sub_ins dst_reg, src_reg1, xzr
420-
|| } else if (((int32_t)(val)) > 0 && ((int32_t)(val)) <= ADD_SUB_IMM) {
425+
|| } else if (arm64_may_encode_imm12((int64_t)(val))) {
421426
| add_sub_ins dst_reg, src_reg1, #val
422427
|| } else {
423428
| LOAD_32BIT_VAL tmp_reg, val
@@ -428,7 +433,7 @@ static bool logical_immediate_p(uint64_t value, uint32_t reg_size)
428433
|.macro ADD_SUB_64_WITH_CONST, add_sub_ins, dst_reg, src_reg1, val, tmp_reg
429434
|| if (val == 0) {
430435
| add_sub_ins dst_reg, src_reg1, xzr
431-
|| } else if (((int64_t)(val)) > 0 && ((int64_t)(val)) <= ADD_SUB_IMM) {
436+
|| } else if (arm64_may_encode_imm12((int64_t)(val))) {
432437
| add_sub_ins dst_reg, src_reg1, #val
433438
|| } else {
434439
| LOAD_64BIT_VAL tmp_reg, val

0 commit comments

Comments
 (0)