summaryrefslogtreecommitdiff
path: root/lib/math/rational.c
diff options
context:
space:
mode:
authorDmitry Torokhov <dmitry.torokhov@gmail.com>2022-01-15 12:09:44 -0800
committerDmitry Torokhov <dmitry.torokhov@gmail.com>2022-01-15 12:09:44 -0800
commit762f99f4f3cb41a775b5157dd761217beba65873 (patch)
tree2e93410a577dfff1202ea5b0d109460b97650e58 /lib/math/rational.c
parentcf73ed894ee939d6706d65e0cd186e4a64e3af6d (diff)
parentb6e43dddaea3dbfa93327f986beb3ec5e8157c4c (diff)
Merge branch 'next' into for-linus
Prepare input updates for 5.17 merge window.
Diffstat (limited to 'lib/math/rational.c')
-rw-r--r--lib/math/rational.c19
1 files changed, 14 insertions, 5 deletions
diff --git a/lib/math/rational.c b/lib/math/rational.c
index 9781d521963d..ec59d426ea63 100644
--- a/lib/math/rational.c
+++ b/lib/math/rational.c
@@ -12,6 +12,8 @@
#include <linux/compiler.h>
#include <linux/export.h>
#include <linux/minmax.h>
+#include <linux/limits.h>
+#include <linux/module.h>
/*
* calculate best rational approximation for a given fraction
@@ -78,13 +80,18 @@ void rational_best_approximation(
* found below as 't'.
*/
if ((n2 > max_numerator) || (d2 > max_denominator)) {
- unsigned long t = min((max_numerator - n0) / n1,
- (max_denominator - d0) / d1);
+ unsigned long t = ULONG_MAX;
- /* This tests if the semi-convergent is closer
- * than the previous convergent.
+ if (d1)
+ t = (max_denominator - d0) / d1;
+ if (n1)
+ t = min(t, (max_numerator - n0) / n1);
+
+ /* This tests if the semi-convergent is closer than the previous
+ * convergent. If d1 is zero there is no previous convergent as this
+ * is the 1st iteration, so always choose the semi-convergent.
*/
- if (2u * t > a || (2u * t == a && d0 * dp > d1 * d)) {
+ if (!d1 || 2u * t > a || (2u * t == a && d0 * dp > d1 * d)) {
n1 = n0 + t * n1;
d1 = d0 + t * d1;
}
@@ -100,3 +107,5 @@ void rational_best_approximation(
}
EXPORT_SYMBOL(rational_best_approximation);
+
+MODULE_LICENSE("GPL v2");