[php-src] PR #23940: JIT: Make overflow add/sub cheaper

From: Date: Sat, 26 Sep 2026 23:51:03 +0000
Subject: [php-src] PR #23940: JIT: Make overflow add/sub cheaper
Groups: php.git-pulls 
Request: Send a blank email to git-pulls+get-38851@lists.php.net to get a copy of this message
Pull Request: https://github.com/php/php-src/pull/23940 Author: ndossche PHP code: ```php <?php function sum($n) { $s = 0; for ($i = 0; $i < $n; $i++) { $s += $i; } return $s; } var_dump(sum(10000000)); ``` Old x86-64 code: ```asm TRACE-1$sum$4: subq $0x30, %rsp movabsq $EG(jit_trace_num), %rax movl $1, (%rax) cmpb $4, 0x58(%r14) jne jit$$trace_exit_0 cmpb $4, 0x68(%r14) jne jit$$trace_exit_1 cmpb $4, 0x78(%r14) jne jit$$trace_exit_2 movq 0x50(%r14), %rax movq 0x60(%r14), %rcx movq 0x70(%r14), %rdx .L1: cmpq %rax, %rdx jge jit$$trace_exit_3 movq %rdx, %rsi addq %rcx, %rsi jo jit$$trace_exit_4 leaq 1(%rdx), %rdx movabsq $EG(vm_interrupt), %rcx movb (%rcx), %cl testb %cl, %cl jne jit$$trace_exit_5 movq %rsi, %rcx jmp .L1 ``` Note that this code uses an extra register and 2 extra moves (for %rcx) to carry the result. This is because the trace exit wants the old result. But we can avoid the extra register and extra moves if we simply reconstruct the old value upon exit. This patch implements that idea, which results in the following new code: ```asm TRACE-1$sum$4: subq $0x30, %rsp movabsq $EG(jit_trace_num), %rax movl $1, (%rax) cmpb $4, 0x58(%r14) jne jit$$trace_exit_0 cmpb $4, 0x68(%r14) jne jit$$trace_exit_1 cmpb $4, 0x78(%r14) jne jit$$trace_exit_2 movq 0x50(%r14), %rax movq 0x60(%r14), %rcx movq 0x70(%r14), %rdx jmp .L2 ; ... nops for alignment .L1: leaq 1(%rdx), %rdx movabsq $EG(vm_interrupt), %rsi movb (%rsi), %sil testb %sil, %sil jne jit$$trace_exit_5 .L2: cmpq %rax, %rdx jge jit$$trace_exit_3 addq %rdx, %rcx jno .L1 subq %rdx, %rcx jmp jit$$trace_exit_4 ``` Notice how the addition now no longer needs extra moves and how the result is kept in %rcx all the time. The cold path under jno restores the old value right before jumping to the trace exit.

« previous php.git-pulls (#38851) next »