~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/lib/math/rational.c

Version: ~ [ linux-6.11-rc3 ] ~ [ linux-6.10.4 ] ~ [ linux-6.9.12 ] ~ [ linux-6.8.12 ] ~ [ linux-6.7.12 ] ~ [ linux-6.6.45 ] ~ [ linux-6.5.13 ] ~ [ linux-6.4.16 ] ~ [ linux-6.3.13 ] ~ [ linux-6.2.16 ] ~ [ linux-6.1.104 ] ~ [ linux-6.0.19 ] ~ [ linux-5.19.17 ] ~ [ linux-5.18.19 ] ~ [ linux-5.17.15 ] ~ [ linux-5.16.20 ] ~ [ linux-5.15.164 ] ~ [ linux-5.14.21 ] ~ [ linux-5.13.19 ] ~ [ linux-5.12.19 ] ~ [ linux-5.11.22 ] ~ [ linux-5.10.223 ] ~ [ linux-5.9.16 ] ~ [ linux-5.8.18 ] ~ [ linux-5.7.19 ] ~ [ linux-5.6.19 ] ~ [ linux-5.5.19 ] ~ [ linux-5.4.281 ] ~ [ linux-5.3.18 ] ~ [ linux-5.2.21 ] ~ [ linux-5.1.21 ] ~ [ linux-5.0.21 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.319 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.336 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.337 ] ~ [ linux-4.4.302 ] ~ [ linux-3.10.108 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.9 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

Diff markup

Differences between /lib/math/rational.c (Version linux-6.11-rc3) and /lib/math/rational.c (Version linux-2.6.0)


  1 // SPDX-License-Identifier: GPL-2.0                 1 
  2 /*                                                
  3  * rational fractions                             
  4  *                                                
  5  * Copyright (C) 2009 emlix GmbH, Oskar Schirm    
  6  * Copyright (C) 2019 Trent Piepho <tpiepho@gm    
  7  *                                                
  8  * helper functions when coping with rational     
  9  */                                               
 10                                                   
 11 #include <linux/rational.h>                       
 12 #include <linux/compiler.h>                       
 13 #include <linux/export.h>                         
 14 #include <linux/minmax.h>                         
 15 #include <linux/limits.h>                         
 16 #include <linux/module.h>                         
 17                                                   
 18 /*                                                
 19  * calculate best rational approximation for a    
 20  * taking into account restricted register siz    
 21  * appropriate values for a pll with 5 bit den    
 22  * 8 bit numerator register fields, trying to     
 23  * frequency ratio of 3.1415, one would say:      
 24  *                                                
 25  * rational_best_approximation(31415, 10000,      
 26  *              (1 << 8) - 1, (1 << 5) - 1, &n    
 27  *                                                
 28  * you may look at given_numerator as a fixed     
 29  * with the fractional part size described in     
 30  *                                                
 31  * for theoretical background, see:               
 32  * https://en.wikipedia.org/wiki/Continued_fra    
 33  */                                               
 34                                                   
 35 void rational_best_approximation(                 
 36         unsigned long given_numerator, unsigne    
 37         unsigned long max_numerator, unsigned     
 38         unsigned long *best_numerator, unsigne    
 39 {                                                 
 40         /* n/d is the starting rational, which    
 41          * decreased each iteration using the     
 42          *                                        
 43          * dp is the value of d from the prior    
 44          *                                        
 45          * n2/d2, n1/d1, and n0/d0 are our suc    
 46          * approximations of the rational.  Th    
 47          * the current, previous, and two prio    
 48          *                                        
 49          * a is current term of the continued     
 50          */                                       
 51         unsigned long n, d, n0, d0, n1, d1, n2    
 52         n = given_numerator;                      
 53         d = given_denominator;                    
 54         n0 = d1 = 0;                              
 55         n1 = d0 = 1;                              
 56                                                   
 57         for (;;) {                                
 58                 unsigned long dp, a;              
 59                                                   
 60                 if (d == 0)                       
 61                         break;                    
 62                 /* Find next term in continued    
 63                  * Euclidean algorithm.           
 64                  */                               
 65                 dp = d;                           
 66                 a = n / d;                        
 67                 d = n % d;                        
 68                 n = dp;                           
 69                                                   
 70                 /* Calculate the current ratio    
 71                  * convergent), n2/d2, using t    
 72                  * the two prior approximation    
 73                  */                               
 74                 n2 = n0 + a * n1;                 
 75                 d2 = d0 + a * d1;                 
 76                                                   
 77                 /* If the current convergent e    
 78                  * return either the previous     
 79                  * largest semi-convergent, th    
 80                  * found below as 't'.            
 81                  */                               
 82                 if ((n2 > max_numerator) || (d    
 83                         unsigned long t = ULON    
 84                                                   
 85                         if (d1)                   
 86                                 t = (max_denom    
 87                         if (n1)                   
 88                                 t = min(t, (ma    
 89                                                   
 90                         /* This tests if the s    
 91                          * convergent.  If d1     
 92                          * is the 1st iteratio    
 93                          */                       
 94                         if (!d1 || 2u * t > a     
 95                                 n1 = n0 + t *     
 96                                 d1 = d0 + t *     
 97                         }                         
 98                         break;                    
 99                 }                                 
100                 n0 = n1;                          
101                 n1 = n2;                          
102                 d0 = d1;                          
103                 d1 = d2;                          
104         }                                         
105         *best_numerator = n1;                     
106         *best_denominator = d1;                   
107 }                                                 
108                                                   
109 EXPORT_SYMBOL(rational_best_approximation);       
110                                                   
111 MODULE_DESCRIPTION("Rational fraction support     
112 MODULE_LICENSE("GPL v2");                         
113                                                   

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

sflogo.php