Skip Menu |
Report information
Id: 133677
Status: resolved
Priority: 0/
Queue: perl5

Owner: Nobody
Requestors: me [at] xenu.pl
Cc:
AdminCc:

Operating System: (no value)
PatchStatus: (no value)
Severity: low
Type:
Perl Version: (no value)
Fixed In: (no value)



From: Tomasz Konojacki <me [...] xenu.pl>
Date: Wed, 21 Nov 2018 09:55:38 +0100
Subject: [PATCH] optimize IV -> UV conversions
CC: davem [...] iabyn.com
To: perlbug [...] perl.org
Download (untitled) / with headers
text/plain 3.1k
In 2014 Dave fixed mishandling of IVs equal to IV_MIN in maaaaany places in the perl codebase (that's why I'm CC-ing him). There were many commits, for example 53e2bfb7c6a2e8a3171dabe7dbdc24eba77e4bf0. While the fix was perfectly good, it can be done in a bit more optimal way. The commit message of my patch should explain the issue: --- optimize IV -> UV conversions This commit replaces all instances of code that looks like this: uv = (iv == IV_MIN) ? (UV)iv : (UV)(-iv) with simpler and more optimal: uv = -(UV)iv While -iv indeed results in an undefined behaviour when iv == IV_MIN, -(UV)iv is perfectly well defined and does the right thing. C standard guarantees that the result of (UV)iv (for negative iv) is equal to iv + UV_MAX + 1 (see 6.3.1.3, paragraph 2 in C11). It also guarantees that the result of -uv is UV_MAX - uv + 1 (6.2.5, paragraph 9). That means that the result of -(UV)iv is UV_MAX - (iv + UV_MAX + 1) + 1 which is equal to -iv for *all* possible negative values of iv. --- I have implemented this change in all places where I found that construct. One of them was pp_divide, here's an example benchmark of division (its source code will be attached in the next post): Key: Ir Instruction read Dr Data read Dw Data write COND conditional branches IND indirect branches _m branch predict miss _m1 level 1 cache miss _mm last cache (e.g. L3) miss - indeterminate percentage (e.g. 1/0) The numbers represent relative counts per loop iteration, compared to blead at 100.0%. Higher is better: for example, using half as many instructions gives 200%, while using twice as many gives 50%. positive_ints 4 / 2 blead my_patch ------ -------- Ir 100.00 101.40 Dr 100.00 100.00 Dw 100.00 100.00 COND 100.00 100.00 IND 100.00 100.00 COND_m 100.00 100.00 IND_m 100.00 100.00 Ir_m1 100.00 100.00 Dr_m1 100.00 100.00 Dw_m1 100.00 100.00 Ir_mm 100.00 100.00 Dr_mm 100.00 100.00 Dw_mm 100.00 100.00 one_negative_int -4 / 2 blead my_patch ------ -------- Ir 100.00 104.14 Dr 100.00 100.00 Dw 100.00 100.00 COND 100.00 104.00 IND 100.00 100.00 COND_m 100.00 100.00 IND_m 100.00 100.00 Ir_m1 100.00 100.00 Dr_m1 100.00 100.00 Dw_m1 100.00 100.00 Ir_mm 100.00 100.00 Dr_mm 100.00 100.00 Dw_mm 100.00 100.00 two_negative_ints -4 / -2 blead my_patch ------ -------- Ir 100.00 106.90 Dr 100.00 100.00 Dw 100.00 100.00 COND 100.00 104.17 IND 100.00 100.00 COND_m 100.00 100.00 IND_m 100.00 100.00 Ir_m1 100.00 100.00 Dr_m1 100.00 100.00 Dw_m1 100.00 100.00 Ir_mm 100.00 100.00 Dr_mm 100.00 100.00 Dw_mm 100.00 100.00 AVERAGE blead my_patch ------ -------- Ir 100.00 104.10 Dr 100.00 100.00 Dw 100.00 100.00 COND 100.00 102.69 IND 100.00 100.00 COND_m 100.00 100.00 IND_m 100.00 100.00 Ir_m1 100.00 100.00 Dr_m1 100.00 100.00 Dw_m1 100.00 100.00 Ir_mm 100.00 100.00 Dr_mm 100.00 100.00 Dw_mm 100.00 100.00
CC: davem [...] iabyn.com
From: Tomasz Konojacki <me [...] xenu.pl>
To: perl5-porters [...] perl.org
Subject: Re: [perl #133677] [PATCH] optimize IV -> UV conversions
Date: Wed, 21 Nov 2018 10:05:59 +0100
The patch and source code of the benchmark are attached.

Message body is not shown because sender requested not to inline it.

Download div_bench
application/octet-stream 388b

Message body not shown because it is not plain text.

From: Dave Mitchell <davem [...] iabyn.com>
Subject: Re: [perl #133677] [PATCH] optimize IV -> UV conversions
Date: Wed, 21 Nov 2018 13:41:55 +0000
To: perl5-porters [...] perl.org
Download (untitled) / with headers
text/plain 785b
On Wed, Nov 21, 2018 at 01:02:02AM -0800, Tomasz Konojacki (via RT) wrote: Show quoted text
> In 2014 Dave fixed mishandling of IVs equal to IV_MIN in maaaaany places > in the perl codebase (that's why I'm CC-ing him). There were many > commits, for example 53e2bfb7c6a2e8a3171dabe7dbdc24eba77e4bf0. > > While the fix was perfectly good, it can be done in a bit more optimal > way. The commit message of my patch should explain the issue: > > --- > optimize IV -> UV conversions > > This commit replaces all instances of code that looks like this: > > uv = (iv == IV_MIN) ? (UV)iv : (UV)(-iv) > > with simpler and more optimal: > > uv = -(UV)iv
Thanks, applied as v5.29.5-9-gad9b9a4926 -- In economics, the exam questions are the same every year. They just change the answers.
RT-Send-CC: perl5-porters [...] perl.org
Download (untitled) / with headers
text/plain 110b
On Wed, 21 Nov 2018 05:42:27 -0800, davem wrote: Show quoted text
> Thanks, applied as v5.29.5-9-gad9b9a4926
Now closed. Tony
Download (untitled) / with headers
text/plain 313b
Thank you for filing this report. You have helped make Perl better. With the release today of Perl 5.30.0, this and 160 other issues have been resolved. Perl 5.30.0 may be downloaded via: https://metacpan.org/release/XSAWYERX/perl-5.30.0 If you find that the problem persists, feel free to reopen this ticket.


This service is sponsored and maintained by Best Practical Solutions and runs on Perl.org infrastructure.

For issues related to this RT instance (aka "perlbug"), please contact perlbug-admin at perl.org