| From c1d337d45ec0a802299688e17d568c4e3a585895 Mon Sep 17 00:00:00 2001 |
| From: "Maciej W. Rozycki" <macro@orcam.me.uk> |
| Date: Tue, 20 Apr 2021 04:50:48 +0200 |
| Subject: MIPS: Avoid DIVU in `__div64_32' is result would be zero |
| |
| From: Maciej W. Rozycki <macro@orcam.me.uk> |
| |
| commit c1d337d45ec0a802299688e17d568c4e3a585895 upstream. |
| |
| We already check the high part of the divident against zero to avoid the |
| costly DIVU instruction in that case, needed to reduce the high part of |
| the divident, so we may well check against the divisor instead and set |
| the high part of the quotient to zero right away. We need to treat the |
| high part the divident in that case though as the remainder that would |
| be calculated by the DIVU instruction we avoided. |
| |
| This has passed correctness verification with test_div64 and reduced the |
| module's average execution time down to 1.0445s and 0.2619s from 1.0668s |
| and 0.2629s respectively for an R3400 CPU @40MHz and a 5Kc CPU @160MHz. |
| |
| Signed-off-by: Maciej W. Rozycki <macro@orcam.me.uk> |
| Signed-off-by: Thomas Bogendoerfer <tsbogend@alpha.franken.de> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |
| --- |
| arch/mips/include/asm/div64.h | 6 ++++-- |
| 1 file changed, 4 insertions(+), 2 deletions(-) |
| |
| --- a/arch/mips/include/asm/div64.h |
| +++ b/arch/mips/include/asm/div64.h |
| @@ -68,9 +68,11 @@ |
| \ |
| __high = __div >> 32; \ |
| __low = __div; \ |
| - __upper = __high; \ |
| \ |
| - if (__high) { \ |
| + if (__high < __radix) { \ |
| + __upper = __high; \ |
| + __high = 0; \ |
| + } else { \ |
| __asm__("divu $0, %z1, %z2" \ |
| : "=x" (__modquot) \ |
| : "Jr" (__high), "Jr" (__radix)); \ |