[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Stable-7.2.7 02/62] host-utils: Add muldiv64_round_up
From: |
Michael Tokarev |
Subject: |
[Stable-7.2.7 02/62] host-utils: Add muldiv64_round_up |
Date: |
Thu, 9 Nov 2023 16:58:30 +0300 |
From: Nicholas Piggin <npiggin@gmail.com>
This will be used for converting time intervals in different base units
to host units, for the purpose of scheduling timers to emulate target
timers. Timers typically must not fire before their requested expiry
time but may fire some time afterward, so rounding up is the right way
to implement these.
Signed-off-by: Nicholas Piggin <npiggin@gmail.com>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
[ clg: renamed __muldiv64() to muldiv64_rounding() ]
Signed-off-by: Cédric Le Goater <clg@kaod.org>
(cherry picked from commit 47de6c4c287079744ceb96f606b3c0457addf380)
Signed-off-by: Michael Tokarev <mjt@tls.msk.ru>
diff --git a/include/qemu/host-utils.h b/include/qemu/host-utils.h
index b3434ec0bc..09daf58787 100644
--- a/include/qemu/host-utils.h
+++ b/include/qemu/host-utils.h
@@ -57,6 +57,11 @@ static inline uint64_t muldiv64(uint64_t a, uint32_t b,
uint32_t c)
return (__int128_t)a * b / c;
}
+static inline uint64_t muldiv64_round_up(uint64_t a, uint32_t b, uint32_t c)
+{
+ return ((__int128_t)a * b + c - 1) / c;
+}
+
static inline uint64_t divu128(uint64_t *plow, uint64_t *phigh,
uint64_t divisor)
{
@@ -84,7 +89,8 @@ void mulu64(uint64_t *plow, uint64_t *phigh, uint64_t a,
uint64_t b);
uint64_t divu128(uint64_t *plow, uint64_t *phigh, uint64_t divisor);
int64_t divs128(uint64_t *plow, int64_t *phigh, int64_t divisor);
-static inline uint64_t muldiv64(uint64_t a, uint32_t b, uint32_t c)
+static inline uint64_t muldiv64_rounding(uint64_t a, uint32_t b, uint32_t c,
+ bool round_up)
{
union {
uint64_t ll;
@@ -100,12 +106,25 @@ static inline uint64_t muldiv64(uint64_t a, uint32_t b,
uint32_t c)
u.ll = a;
rl = (uint64_t)u.l.low * (uint64_t)b;
+ if (round_up) {
+ rl += c - 1;
+ }
rh = (uint64_t)u.l.high * (uint64_t)b;
rh += (rl >> 32);
res.l.high = rh / c;
res.l.low = (((rh % c) << 32) + (rl & 0xffffffff)) / c;
return res.ll;
}
+
+static inline uint64_t muldiv64(uint64_t a, uint32_t b, uint32_t c)
+{
+ return muldiv64_rounding(a, b, c, false);
+}
+
+static inline uint64_t muldiv64_round_up(uint64_t a, uint32_t b, uint32_t c)
+{
+ return muldiv64_rounding(a, b, c, true);
+}
#endif
/**
--
2.39.2
- [Stable-7.2.7 00/62] Patch Round-up for stable 7.2.7, freeze on 2023-11-19, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 01/62] hw/ppc: Introduce functions for conversion between timebase and nanoseconds, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 03/62] hw/ppc: Round up the decrementer interval when converting to ns, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 02/62] host-utils: Add muldiv64_round_up,
Michael Tokarev <=
- [Stable-7.2.7 04/62] hw/ppc: Avoid decrementer rounding errors, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 08/62] linux-user/hppa: clear the PSW 'N' bit when delivering signals, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 09/62] linux-user/hppa: lock both words of function descriptor, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 07/62] hw/ppc: Always store the decrementer value, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 05/62] target/ppc: Sign-extend large decrementer to 64-bits, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 22/62] target/i386: Fix and add some comments next to SSE/AVX instructions., Michael Tokarev, 2023/11/09
- [Stable-7.2.7 13/62] hw/scsi/scsi-disk: Disallow block sizes smaller than 512 [CVE-2023-42467], Michael Tokarev, 2023/11/09
- [Stable-7.2.7 06/62] target/ppc: Decrementer fix BookE semantics, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 10/62] hw/cxl: Fix CFMW config memory leak, Michael Tokarev, 2023/11/09
- [Stable-7.2.7 15/62] ui/vnc: fix handling of VNC_FEATURE_XVP, Michael Tokarev, 2023/11/09