2005-04-17 02:20:36 +04:00
/*
2012-03-24 02:02:24 +04:00
* Aug 8 , 2011 Bob Pearson with help from Joakim Tjernlund and George Spelvin
* cleaned up code to current version of sparse and added the slicing - by - 8
* algorithm to the closely similar existing slicing - by - 4 algorithm .
*
2005-04-17 02:20:36 +04:00
* Oct 15 , 2000 Matt Domsch < Matt_Domsch @ dell . com >
* Nicer crc32 functions / docs submitted by linux @ horizon . com . Thanks !
* Code was from the public domain , copyright abandoned . Code was
* subsequently included in the kernel , thus was re - licensed under the
* GNU GPL v2 .
*
* Oct 12 , 2000 Matt Domsch < Matt_Domsch @ dell . com >
* Same crc32 function was used in 5 other places in the kernel .
* I made one version , and deleted the others .
* There are various incantations of crc32 ( ) . Some use a seed of 0 or ~ 0.
* Some xor at the end with ~ 0. The generic crc32 ( ) function takes
* seed as an argument , and doesn ' t xor at the end . Then individual
* users can do whatever they need .
* drivers / net / smc9194 . c uses seed ~ 0 , doesn ' t xor with ~ 0.
* fs / jffs2 uses seed 0 , doesn ' t xor with ~ 0.
* fs / partitions / efi . c uses seed ~ 0 , xor ' s with ~ 0.
*
* This source code is licensed under the GNU General Public License ,
* Version 2. See the file COPYING for more details .
*/
2012-03-24 02:02:22 +04:00
/* see: Documentation/crc32.txt for a description of algorithms */
2005-04-17 02:20:36 +04:00
# include <linux/crc32.h>
2018-07-17 19:05:36 +03:00
# include <linux/crc32poly.h>
2005-04-17 02:20:36 +04:00
# include <linux/module.h>
# include <linux/types.h>
2013-11-04 20:10:26 +04:00
# include <linux/sched.h>
2005-04-17 02:20:36 +04:00
# include "crc32defs.h"
2012-03-24 02:02:22 +04:00
2012-03-24 02:02:23 +04:00
# if CRC_LE_BITS > 8
2014-06-05 03:11:56 +04:00
# define tole(x) ((__force u32) cpu_to_le32(x))
2005-04-17 02:20:36 +04:00
# else
2010-03-06 00:43:55 +03:00
# define tole(x) (x)
# endif
2012-03-24 02:02:23 +04:00
# if CRC_BE_BITS > 8
2014-06-05 03:11:56 +04:00
# define tobe(x) ((__force u32) cpu_to_be32(x))
2010-03-06 00:43:55 +03:00
# else
# define tobe(x) (x)
2005-04-17 02:20:36 +04:00
# endif
2012-03-24 02:02:22 +04:00
2005-04-17 02:20:36 +04:00
# include "crc32table.h"
MODULE_AUTHOR ( " Matt Domsch <Matt_Domsch@dell.com> " ) ;
2012-03-24 02:02:25 +04:00
MODULE_DESCRIPTION ( " Various CRC32 calculations " ) ;
2005-04-17 02:20:36 +04:00
MODULE_LICENSE ( " GPL " ) ;
2012-03-24 02:02:23 +04:00
# if CRC_LE_BITS > 8 || CRC_BE_BITS > 8
2009-12-15 05:01:33 +03:00
2012-03-24 02:02:24 +04:00
/* implements slicing-by-4 or slicing-by-8 algorithm */
2014-06-23 17:11:56 +04:00
static inline u32 __pure
2010-05-25 01:33:31 +04:00
crc32_body ( u32 crc , unsigned char const * buf , size_t len , const u32 ( * tab ) [ 256 ] )
2009-12-15 05:01:33 +03:00
{
2010-05-26 10:43:03 +04:00
# ifdef __LITTLE_ENDIAN
2012-01-11 03:10:18 +04:00
# define DO_CRC(x) crc = t0[(crc ^ (x)) & 255] ^ (crc >> 8)
2012-03-24 02:02:24 +04:00
# define DO_CRC4 (t3[(q) & 255] ^ t2[(q >> 8) & 255] ^ \
t1 [ ( q > > 16 ) & 255 ] ^ t0 [ ( q > > 24 ) & 255 ] )
# define DO_CRC8 (t7[(q) & 255] ^ t6[(q >> 8) & 255] ^ \
t5 [ ( q > > 16 ) & 255 ] ^ t4 [ ( q > > 24 ) & 255 ] )
2009-12-15 05:01:33 +03:00
# else
2012-01-11 03:10:18 +04:00
# define DO_CRC(x) crc = t0[((crc >> 24) ^ (x)) & 255] ^ (crc << 8)
2012-03-24 02:02:24 +04:00
# define DO_CRC4 (t0[(q) & 255] ^ t1[(q >> 8) & 255] ^ \
t2 [ ( q > > 16 ) & 255 ] ^ t3 [ ( q > > 24 ) & 255 ] )
# define DO_CRC8 (t4[(q) & 255] ^ t5[(q >> 8) & 255] ^ \
t6 [ ( q > > 16 ) & 255 ] ^ t7 [ ( q > > 24 ) & 255 ] )
2009-12-15 05:01:33 +03:00
# endif
2010-03-06 00:43:55 +03:00
const u32 * b ;
2009-12-15 05:01:33 +03:00
size_t rem_len ;
2012-03-24 02:02:24 +04:00
# ifdef CONFIG_X86
size_t i ;
# endif
2012-01-11 03:10:18 +04:00
const u32 * t0 = tab [ 0 ] , * t1 = tab [ 1 ] , * t2 = tab [ 2 ] , * t3 = tab [ 3 ] ;
2012-07-31 01:41:26 +04:00
# if CRC_LE_BITS != 32
2012-03-24 02:02:24 +04:00
const u32 * t4 = tab [ 4 ] , * t5 = tab [ 5 ] , * t6 = tab [ 6 ] , * t7 = tab [ 7 ] ;
2012-07-31 01:41:26 +04:00
# endif
2012-03-24 02:02:24 +04:00
u32 q ;
2009-12-15 05:01:33 +03:00
/* Align it */
2010-03-06 00:43:55 +03:00
if ( unlikely ( ( long ) buf & 3 & & len ) ) {
2009-12-15 05:01:33 +03:00
do {
2010-03-06 00:43:55 +03:00
DO_CRC ( * buf + + ) ;
} while ( ( - - len ) & & ( ( long ) buf ) & 3 ) ;
2009-12-15 05:01:33 +03:00
}
2012-03-24 02:02:24 +04:00
# if CRC_LE_BITS == 32
2009-12-15 05:01:33 +03:00
rem_len = len & 3 ;
len = len > > 2 ;
2012-03-24 02:02:24 +04:00
# else
rem_len = len & 7 ;
len = len > > 3 ;
# endif
2010-03-06 00:43:55 +03:00
b = ( const u32 * ) buf ;
2012-03-24 02:02:24 +04:00
# ifdef CONFIG_X86
- - b ;
for ( i = 0 ; i < len ; i + + ) {
# else
2009-12-15 05:01:33 +03:00
for ( - - b ; len ; - - len ) {
2012-03-24 02:02:24 +04:00
# endif
2012-03-24 02:02:24 +04:00
q = crc ^ * + + b ; /* use pre increment for speed */
# if CRC_LE_BITS == 32
crc = DO_CRC4 ;
# else
crc = DO_CRC8 ;
q = * + + b ;
crc ^ = DO_CRC4 ;
# endif
2009-12-15 05:01:33 +03:00
}
len = rem_len ;
/* And the last few bytes */
if ( len ) {
u8 * p = ( u8 * ) ( b + 1 ) - 1 ;
2012-03-24 02:02:24 +04:00
# ifdef CONFIG_X86
for ( i = 0 ; i < len ; i + + )
DO_CRC ( * + + p ) ; /* use pre increment for speed */
# else
2009-12-15 05:01:33 +03:00
do {
DO_CRC ( * + + p ) ; /* use pre increment for speed */
} while ( - - len ) ;
2012-03-24 02:02:24 +04:00
# endif
2009-12-15 05:01:33 +03:00
}
return crc ;
2010-03-06 00:43:55 +03:00
# undef DO_CRC
2010-05-25 01:33:31 +04:00
# undef DO_CRC4
2012-03-24 02:02:24 +04:00
# undef DO_CRC8
2009-12-15 05:01:33 +03:00
}
# endif
2012-03-24 02:02:22 +04:00
2013-10-30 14:50:49 +04:00
2006-06-25 16:48:59 +04:00
/**
2013-09-12 01:23:52 +04:00
* crc32_le_generic ( ) - Calculate bitwise little - endian Ethernet AUTODIN II
* CRC32 / CRC32C
* @ crc : seed value for computation . ~ 0 for Ethernet , sometimes 0 for other
* uses , or the previous crc32 / crc32c value if computing incrementally .
* @ p : pointer to buffer over which CRC32 / CRC32C is run
2006-06-25 16:48:59 +04:00
* @ len : length of buffer @ p
2013-09-12 01:23:52 +04:00
* @ tab : little - endian Ethernet table
* @ polynomial : CRC32 / CRC32c LE polynomial
2006-06-25 16:48:59 +04:00
*/
2012-03-24 02:02:25 +04:00
static inline u32 __pure crc32_le_generic ( u32 crc , unsigned char const * p ,
size_t len , const u32 ( * tab ) [ 256 ] ,
u32 polynomial )
2005-04-17 02:20:36 +04:00
{
2012-03-24 02:02:22 +04:00
# if CRC_LE_BITS == 1
2005-04-17 02:20:36 +04:00
int i ;
while ( len - - ) {
crc ^ = * p + + ;
for ( i = 0 ; i < 8 ; i + + )
2012-03-24 02:02:25 +04:00
crc = ( crc > > 1 ) ^ ( ( crc & 1 ) ? polynomial : 0 ) ;
2005-04-17 02:20:36 +04:00
}
2012-03-24 02:02:22 +04:00
# elif CRC_LE_BITS == 2
2005-04-17 02:20:36 +04:00
while ( len - - ) {
crc ^ = * p + + ;
2012-03-24 02:02:25 +04:00
crc = ( crc > > 2 ) ^ tab [ 0 ] [ crc & 3 ] ;
crc = ( crc > > 2 ) ^ tab [ 0 ] [ crc & 3 ] ;
crc = ( crc > > 2 ) ^ tab [ 0 ] [ crc & 3 ] ;
crc = ( crc > > 2 ) ^ tab [ 0 ] [ crc & 3 ] ;
2005-04-17 02:20:36 +04:00
}
2012-03-24 02:02:22 +04:00
# elif CRC_LE_BITS == 4
2005-04-17 02:20:36 +04:00
while ( len - - ) {
crc ^ = * p + + ;
2012-03-24 02:02:25 +04:00
crc = ( crc > > 4 ) ^ tab [ 0 ] [ crc & 15 ] ;
crc = ( crc > > 4 ) ^ tab [ 0 ] [ crc & 15 ] ;
2005-04-17 02:20:36 +04:00
}
2012-03-24 02:02:22 +04:00
# elif CRC_LE_BITS == 8
2012-03-24 02:02:23 +04:00
/* aka Sarwate algorithm */
while ( len - - ) {
crc ^ = * p + + ;
2012-03-24 02:02:25 +04:00
crc = ( crc > > 8 ) ^ tab [ 0 ] [ crc & 255 ] ;
2012-03-24 02:02:23 +04:00
}
# else
2012-03-24 02:02:23 +04:00
crc = ( __force u32 ) __cpu_to_le32 ( crc ) ;
2012-03-24 02:02:22 +04:00
crc = crc32_body ( crc , p , len , tab ) ;
2012-03-24 02:02:23 +04:00
crc = __le32_to_cpu ( ( __force __le32 ) crc ) ;
2012-03-24 02:02:22 +04:00
# endif
2005-04-17 02:20:36 +04:00
return crc ;
}
2012-03-24 02:02:25 +04:00
# if CRC_LE_BITS == 1
2018-08-27 14:02:42 +03:00
u32 __pure __weak crc32_le ( u32 crc , unsigned char const * p , size_t len )
2012-03-24 02:02:25 +04:00
{
2018-07-17 19:05:37 +03:00
return crc32_le_generic ( crc , p , len , NULL , CRC32_POLY_LE ) ;
2012-03-24 02:02:25 +04:00
}
2018-08-27 14:02:42 +03:00
u32 __pure __weak __crc32c_le ( u32 crc , unsigned char const * p , size_t len )
2012-03-24 02:02:25 +04:00
{
return crc32_le_generic ( crc , p , len , NULL , CRC32C_POLY_LE ) ;
}
# else
2018-08-27 14:02:42 +03:00
u32 __pure __weak crc32_le ( u32 crc , unsigned char const * p , size_t len )
2012-03-24 02:02:25 +04:00
{
2012-10-05 04:12:15 +04:00
return crc32_le_generic ( crc , p , len ,
2018-07-17 19:05:37 +03:00
( const u32 ( * ) [ 256 ] ) crc32table_le , CRC32_POLY_LE ) ;
2012-03-24 02:02:25 +04:00
}
2018-08-27 14:02:42 +03:00
u32 __pure __weak __crc32c_le ( u32 crc , unsigned char const * p , size_t len )
2012-03-24 02:02:25 +04:00
{
2012-10-05 04:12:15 +04:00
return crc32_le_generic ( crc , p , len ,
( const u32 ( * ) [ 256 ] ) crc32ctable_le , CRC32C_POLY_LE ) ;
2012-03-24 02:02:25 +04:00
}
# endif
2014-06-23 17:11:54 +04:00
EXPORT_SYMBOL ( crc32_le ) ;
EXPORT_SYMBOL ( __crc32c_le ) ;
2018-08-27 14:02:42 +03:00
u32 crc32_le_base ( u32 , unsigned char const * , size_t ) __alias ( crc32_le ) ;
u32 __crc32c_le_base ( u32 , unsigned char const * , size_t ) __alias ( __crc32c_le ) ;
2014-06-23 17:11:54 +04:00
/*
* This multiplies the polynomials x and y modulo the given modulus .
* This follows the " little-endian " CRC convention that the lsbit
* represents the highest power of x , and the msbit represents x ^ 0.
*/
static u32 __attribute_const__ gf2_multiply ( u32 x , u32 y , u32 modulus )
{
u32 product = x & 1 ? y : 0 ;
int i ;
for ( i = 0 ; i < 31 ; i + + ) {
product = ( product > > 1 ) ^ ( product & 1 ? modulus : 0 ) ;
x > > = 1 ;
product ^ = x & 1 ? y : 0 ;
}
return product ;
}
/**
2017-09-09 02:35:55 +03:00
* crc32_generic_shift - Append @ len 0 bytes to crc , in logarithmic time
2014-06-23 17:11:54 +04:00
* @ crc : The original little - endian CRC ( i . e . lsbit is x ^ 31 coefficient )
* @ len : The number of bytes . @ crc is multiplied by x ^ ( 8 * @ len )
* @ polynomial : The modulus used to reduce the result to 32 bits .
*
* It ' s possible to parallelize CRC computations by computing a CRC
* over separate ranges of a buffer , then summing them .
* This shifts the given CRC by 8 * len bits ( i . e . produces the same effect
* as appending len bytes of zero to the data ) , in time proportional
* to log ( len ) .
*/
static u32 __attribute_const__ crc32_generic_shift ( u32 crc , size_t len ,
u32 polynomial )
{
u32 power = polynomial ; /* CRC of x^32 */
int i ;
/* Shift up to 32 bits in the simple linear way */
for ( i = 0 ; i < 8 * ( int ) ( len & 3 ) ; i + + )
crc = ( crc > > 1 ) ^ ( crc & 1 ? polynomial : 0 ) ;
len > > = 2 ;
if ( ! len )
return crc ;
for ( ; ; ) {
/* "power" is x^(2^i), modulo the polynomial */
if ( len & 1 )
crc = gf2_multiply ( crc , power , polynomial ) ;
len > > = 1 ;
if ( ! len )
break ;
/* Square power, advancing to x^(2^(i+1)) */
power = gf2_multiply ( power , power , polynomial ) ;
}
return crc ;
}
u32 __attribute_const__ crc32_le_shift ( u32 crc , size_t len )
2013-10-30 14:50:49 +04:00
{
2018-07-17 19:05:37 +03:00
return crc32_generic_shift ( crc , len , CRC32_POLY_LE ) ;
2013-10-30 14:50:49 +04:00
}
2014-06-23 17:11:54 +04:00
u32 __attribute_const__ __crc32c_le_shift ( u32 crc , size_t len )
2013-10-30 14:50:49 +04:00
{
2014-06-23 17:11:54 +04:00
return crc32_generic_shift ( crc , len , CRC32C_POLY_LE ) ;
2013-10-30 14:50:49 +04:00
}
2014-06-23 17:11:54 +04:00
EXPORT_SYMBOL ( crc32_le_shift ) ;
EXPORT_SYMBOL ( __crc32c_le_shift ) ;
2005-04-17 02:20:36 +04:00
2006-06-25 16:48:59 +04:00
/**
2013-09-12 01:23:52 +04:00
* crc32_be_generic ( ) - Calculate bitwise big - endian Ethernet AUTODIN II CRC32
2006-06-25 16:48:59 +04:00
* @ crc : seed value for computation . ~ 0 for Ethernet , sometimes 0 for
* other uses , or the previous crc32 value if computing incrementally .
2013-09-12 01:23:52 +04:00
* @ p : pointer to buffer over which CRC32 is run
2006-06-25 16:48:59 +04:00
* @ len : length of buffer @ p
2013-09-12 01:23:52 +04:00
* @ tab : big - endian Ethernet table
* @ polynomial : CRC32 BE polynomial
2006-06-25 16:48:59 +04:00
*/
2012-03-24 02:02:25 +04:00
static inline u32 __pure crc32_be_generic ( u32 crc , unsigned char const * p ,
size_t len , const u32 ( * tab ) [ 256 ] ,
u32 polynomial )
2005-04-17 02:20:36 +04:00
{
2012-03-24 02:02:22 +04:00
# if CRC_BE_BITS == 1
2005-04-17 02:20:36 +04:00
int i ;
while ( len - - ) {
crc ^ = * p + + < < 24 ;
for ( i = 0 ; i < 8 ; i + + )
crc =
2012-03-24 02:02:25 +04:00
( crc < < 1 ) ^ ( ( crc & 0x80000000 ) ? polynomial :
2005-04-17 02:20:36 +04:00
0 ) ;
}
2012-03-24 02:02:22 +04:00
# elif CRC_BE_BITS == 2
2005-04-17 02:20:36 +04:00
while ( len - - ) {
crc ^ = * p + + < < 24 ;
2012-03-24 02:02:25 +04:00
crc = ( crc < < 2 ) ^ tab [ 0 ] [ crc > > 30 ] ;
crc = ( crc < < 2 ) ^ tab [ 0 ] [ crc > > 30 ] ;
crc = ( crc < < 2 ) ^ tab [ 0 ] [ crc > > 30 ] ;
crc = ( crc < < 2 ) ^ tab [ 0 ] [ crc > > 30 ] ;
2005-04-17 02:20:36 +04:00
}
2012-03-24 02:02:22 +04:00
# elif CRC_BE_BITS == 4
2005-04-17 02:20:36 +04:00
while ( len - - ) {
crc ^ = * p + + < < 24 ;
2012-03-24 02:02:25 +04:00
crc = ( crc < < 4 ) ^ tab [ 0 ] [ crc > > 28 ] ;
crc = ( crc < < 4 ) ^ tab [ 0 ] [ crc > > 28 ] ;
2005-04-17 02:20:36 +04:00
}
2012-03-24 02:02:22 +04:00
# elif CRC_BE_BITS == 8
2012-03-24 02:02:23 +04:00
while ( len - - ) {
crc ^ = * p + + < < 24 ;
2012-03-24 02:02:25 +04:00
crc = ( crc < < 8 ) ^ tab [ 0 ] [ crc > > 24 ] ;
2012-03-24 02:02:23 +04:00
}
# else
2012-03-24 02:02:23 +04:00
crc = ( __force u32 ) __cpu_to_be32 ( crc ) ;
2012-03-24 02:02:22 +04:00
crc = crc32_body ( crc , p , len , tab ) ;
2012-03-24 02:02:23 +04:00
crc = __be32_to_cpu ( ( __force __be32 ) crc ) ;
2005-04-17 02:20:36 +04:00
# endif
2012-03-24 02:02:22 +04:00
return crc ;
2005-04-17 02:20:36 +04:00
}
2012-03-24 02:02:25 +04:00
# if CRC_LE_BITS == 1
u32 __pure crc32_be ( u32 crc , unsigned char const * p , size_t len )
{
2018-07-17 19:05:37 +03:00
return crc32_be_generic ( crc , p , len , NULL , CRC32_POLY_BE ) ;
2012-03-24 02:02:25 +04:00
}
# else
u32 __pure crc32_be ( u32 crc , unsigned char const * p , size_t len )
{
2012-10-05 04:12:15 +04:00
return crc32_be_generic ( crc , p , len ,
2018-07-17 19:05:37 +03:00
( const u32 ( * ) [ 256 ] ) crc32table_be , CRC32_POLY_BE ) ;
2012-03-24 02:02:25 +04:00
}
# endif
2005-04-17 02:20:36 +04:00
EXPORT_SYMBOL ( crc32_be ) ;