2018-04-22 19:23:50 +03:00
// SPDX-License-Identifier: GPL-2.0
2005-11-07 14:15:37 +03:00
/*
2018-04-22 19:23:49 +03:00
* Generic Reed Solomon encoder / decoder library
2005-11-07 14:15:37 +03:00
*
2005-04-17 02:20:36 +04:00
* Copyright 2002 , Phil Karn , KA9Q
* May be used under the terms of the GNU General Public License ( GPL )
*
* Adaption to the kernel by Thomas Gleixner ( tglx @ linutronix . de )
*
2018-04-22 19:23:49 +03:00
* Generic data width independent code which is included by the wrappers .
2005-04-17 02:20:36 +04:00
*/
{
2018-04-22 19:23:53 +03:00
struct rs_codec * rs = rsc - > codec ;
2005-04-17 02:20:36 +04:00
int i , j , pad ;
int nn = rs - > nn ;
int nroots = rs - > nroots ;
uint16_t * alpha_to = rs - > alpha_to ;
uint16_t * index_of = rs - > index_of ;
uint16_t * genpoly = rs - > genpoly ;
uint16_t fb ;
uint16_t msk = ( uint16_t ) rs - > nn ;
/* Check length parameter for validity */
pad = nn - nroots - len ;
if ( pad < 0 | | pad > = nn )
return - ERANGE ;
for ( i = 0 ; i < len ; i + + ) {
fb = index_of [ ( ( ( ( uint16_t ) data [ i ] ) ^ invmsk ) & msk ) ^ par [ 0 ] ] ;
/* feedback term is non-zero */
2005-11-07 14:15:37 +03:00
if ( fb ! = nn ) {
2005-04-17 02:20:36 +04:00
for ( j = 1 ; j < nroots ; j + + ) {
2005-11-07 14:15:37 +03:00
par [ j ] ^ = alpha_to [ rs_modnn ( rs , fb +
2005-04-17 02:20:36 +04:00
genpoly [ nroots - j ] ) ] ;
}
}
/* Shift */
memmove ( & par [ 0 ] , & par [ 1 ] , sizeof ( uint16_t ) * ( nroots - 1 ) ) ;
if ( fb ! = nn ) {
2005-11-07 14:15:37 +03:00
par [ nroots - 1 ] = alpha_to [ rs_modnn ( rs ,
2005-04-17 02:20:36 +04:00
fb + genpoly [ 0 ] ) ] ;
} else {
par [ nroots - 1 ] = 0 ;
}
}
return 0 ;
}