162306a36Sopenharmony_ci========================================== 262306a36Sopenharmony_ciReed-Solomon Library Programming Interface 362306a36Sopenharmony_ci========================================== 462306a36Sopenharmony_ci 562306a36Sopenharmony_ci:Author: Thomas Gleixner 662306a36Sopenharmony_ci 762306a36Sopenharmony_ciIntroduction 862306a36Sopenharmony_ci============ 962306a36Sopenharmony_ci 1062306a36Sopenharmony_ciThe generic Reed-Solomon Library provides encoding, decoding and error 1162306a36Sopenharmony_cicorrection functions. 1262306a36Sopenharmony_ci 1362306a36Sopenharmony_ciReed-Solomon codes are used in communication and storage applications to 1462306a36Sopenharmony_ciensure data integrity. 1562306a36Sopenharmony_ci 1662306a36Sopenharmony_ciThis documentation is provided for developers who want to utilize the 1762306a36Sopenharmony_cifunctions provided by the library. 1862306a36Sopenharmony_ci 1962306a36Sopenharmony_ciKnown Bugs And Assumptions 2062306a36Sopenharmony_ci========================== 2162306a36Sopenharmony_ci 2262306a36Sopenharmony_ciNone. 2362306a36Sopenharmony_ci 2462306a36Sopenharmony_ciUsage 2562306a36Sopenharmony_ci===== 2662306a36Sopenharmony_ci 2762306a36Sopenharmony_ciThis chapter provides examples of how to use the library. 2862306a36Sopenharmony_ci 2962306a36Sopenharmony_ciInitializing 3062306a36Sopenharmony_ci------------ 3162306a36Sopenharmony_ci 3262306a36Sopenharmony_ciThe init function init_rs returns a pointer to an rs decoder structure, 3362306a36Sopenharmony_ciwhich holds the necessary information for encoding, decoding and error 3462306a36Sopenharmony_cicorrection with the given polynomial. It either uses an existing 3562306a36Sopenharmony_cimatching decoder or creates a new one. On creation all the lookup tables 3662306a36Sopenharmony_cifor fast en/decoding are created. The function may take a while, so make 3762306a36Sopenharmony_cisure not to call it in critical code paths. 3862306a36Sopenharmony_ci 3962306a36Sopenharmony_ci:: 4062306a36Sopenharmony_ci 4162306a36Sopenharmony_ci /* the Reed Solomon control structure */ 4262306a36Sopenharmony_ci static struct rs_control *rs_decoder; 4362306a36Sopenharmony_ci 4462306a36Sopenharmony_ci /* Symbolsize is 10 (bits) 4562306a36Sopenharmony_ci * Primitive polynomial is x^10+x^3+1 4662306a36Sopenharmony_ci * first consecutive root is 0 4762306a36Sopenharmony_ci * primitive element to generate roots = 1 4862306a36Sopenharmony_ci * generator polynomial degree (number of roots) = 6 4962306a36Sopenharmony_ci */ 5062306a36Sopenharmony_ci rs_decoder = init_rs (10, 0x409, 0, 1, 6); 5162306a36Sopenharmony_ci 5262306a36Sopenharmony_ci 5362306a36Sopenharmony_ciEncoding 5462306a36Sopenharmony_ci-------- 5562306a36Sopenharmony_ci 5662306a36Sopenharmony_ciThe encoder calculates the Reed-Solomon code over the given data length 5762306a36Sopenharmony_ciand stores the result in the parity buffer. Note that the parity buffer 5862306a36Sopenharmony_cimust be initialized before calling the encoder. 5962306a36Sopenharmony_ci 6062306a36Sopenharmony_ciThe expanded data can be inverted on the fly by providing a non-zero 6162306a36Sopenharmony_ciinversion mask. The expanded data is XOR'ed with the mask. This is used 6262306a36Sopenharmony_cie.g. for FLASH ECC, where the all 0xFF is inverted to an all 0x00. The 6362306a36Sopenharmony_ciReed-Solomon code for all 0x00 is all 0x00. The code is inverted before 6462306a36Sopenharmony_cistoring to FLASH so it is 0xFF too. This prevents that reading from an 6562306a36Sopenharmony_cierased FLASH results in ECC errors. 6662306a36Sopenharmony_ci 6762306a36Sopenharmony_ciThe databytes are expanded to the given symbol size on the fly. There is 6862306a36Sopenharmony_cino support for encoding continuous bitstreams with a symbol size != 8 at 6962306a36Sopenharmony_cithe moment. If it is necessary it should be not a big deal to implement 7062306a36Sopenharmony_cisuch functionality. 7162306a36Sopenharmony_ci 7262306a36Sopenharmony_ci:: 7362306a36Sopenharmony_ci 7462306a36Sopenharmony_ci /* Parity buffer. Size = number of roots */ 7562306a36Sopenharmony_ci uint16_t par[6]; 7662306a36Sopenharmony_ci /* Initialize the parity buffer */ 7762306a36Sopenharmony_ci memset(par, 0, sizeof(par)); 7862306a36Sopenharmony_ci /* Encode 512 byte in data8. Store parity in buffer par */ 7962306a36Sopenharmony_ci encode_rs8 (rs_decoder, data8, 512, par, 0); 8062306a36Sopenharmony_ci 8162306a36Sopenharmony_ci 8262306a36Sopenharmony_ciDecoding 8362306a36Sopenharmony_ci-------- 8462306a36Sopenharmony_ci 8562306a36Sopenharmony_ciThe decoder calculates the syndrome over the given data length and the 8662306a36Sopenharmony_cireceived parity symbols and corrects errors in the data. 8762306a36Sopenharmony_ci 8862306a36Sopenharmony_ciIf a syndrome is available from a hardware decoder then the syndrome 8962306a36Sopenharmony_cicalculation is skipped. 9062306a36Sopenharmony_ci 9162306a36Sopenharmony_ciThe correction of the data buffer can be suppressed by providing a 9262306a36Sopenharmony_cicorrection pattern buffer and an error location buffer to the decoder. 9362306a36Sopenharmony_ciThe decoder stores the calculated error location and the correction 9462306a36Sopenharmony_cibitmask in the given buffers. This is useful for hardware decoders which 9562306a36Sopenharmony_ciuse a weird bit ordering scheme. 9662306a36Sopenharmony_ci 9762306a36Sopenharmony_ciThe databytes are expanded to the given symbol size on the fly. There is 9862306a36Sopenharmony_cino support for decoding continuous bitstreams with a symbolsize != 8 at 9962306a36Sopenharmony_cithe moment. If it is necessary it should be not a big deal to implement 10062306a36Sopenharmony_cisuch functionality. 10162306a36Sopenharmony_ci 10262306a36Sopenharmony_ciDecoding with syndrome calculation, direct data correction 10362306a36Sopenharmony_ci~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 10462306a36Sopenharmony_ci 10562306a36Sopenharmony_ci:: 10662306a36Sopenharmony_ci 10762306a36Sopenharmony_ci /* Parity buffer. Size = number of roots */ 10862306a36Sopenharmony_ci uint16_t par[6]; 10962306a36Sopenharmony_ci uint8_t data[512]; 11062306a36Sopenharmony_ci int numerr; 11162306a36Sopenharmony_ci /* Receive data */ 11262306a36Sopenharmony_ci ..... 11362306a36Sopenharmony_ci /* Receive parity */ 11462306a36Sopenharmony_ci ..... 11562306a36Sopenharmony_ci /* Decode 512 byte in data8.*/ 11662306a36Sopenharmony_ci numerr = decode_rs8 (rs_decoder, data8, par, 512, NULL, 0, NULL, 0, NULL); 11762306a36Sopenharmony_ci 11862306a36Sopenharmony_ci 11962306a36Sopenharmony_ciDecoding with syndrome given by hardware decoder, direct data correction 12062306a36Sopenharmony_ci~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 12162306a36Sopenharmony_ci 12262306a36Sopenharmony_ci:: 12362306a36Sopenharmony_ci 12462306a36Sopenharmony_ci /* Parity buffer. Size = number of roots */ 12562306a36Sopenharmony_ci uint16_t par[6], syn[6]; 12662306a36Sopenharmony_ci uint8_t data[512]; 12762306a36Sopenharmony_ci int numerr; 12862306a36Sopenharmony_ci /* Receive data */ 12962306a36Sopenharmony_ci ..... 13062306a36Sopenharmony_ci /* Receive parity */ 13162306a36Sopenharmony_ci ..... 13262306a36Sopenharmony_ci /* Get syndrome from hardware decoder */ 13362306a36Sopenharmony_ci ..... 13462306a36Sopenharmony_ci /* Decode 512 byte in data8.*/ 13562306a36Sopenharmony_ci numerr = decode_rs8 (rs_decoder, data8, par, 512, syn, 0, NULL, 0, NULL); 13662306a36Sopenharmony_ci 13762306a36Sopenharmony_ci 13862306a36Sopenharmony_ciDecoding with syndrome given by hardware decoder, no direct data correction. 13962306a36Sopenharmony_ci~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 14062306a36Sopenharmony_ci 14162306a36Sopenharmony_ciNote: It's not necessary to give data and received parity to the 14262306a36Sopenharmony_cidecoder. 14362306a36Sopenharmony_ci 14462306a36Sopenharmony_ci:: 14562306a36Sopenharmony_ci 14662306a36Sopenharmony_ci /* Parity buffer. Size = number of roots */ 14762306a36Sopenharmony_ci uint16_t par[6], syn[6], corr[8]; 14862306a36Sopenharmony_ci uint8_t data[512]; 14962306a36Sopenharmony_ci int numerr, errpos[8]; 15062306a36Sopenharmony_ci /* Receive data */ 15162306a36Sopenharmony_ci ..... 15262306a36Sopenharmony_ci /* Receive parity */ 15362306a36Sopenharmony_ci ..... 15462306a36Sopenharmony_ci /* Get syndrome from hardware decoder */ 15562306a36Sopenharmony_ci ..... 15662306a36Sopenharmony_ci /* Decode 512 byte in data8.*/ 15762306a36Sopenharmony_ci numerr = decode_rs8 (rs_decoder, NULL, NULL, 512, syn, 0, errpos, 0, corr); 15862306a36Sopenharmony_ci for (i = 0; i < numerr; i++) { 15962306a36Sopenharmony_ci do_error_correction_in_your_buffer(errpos[i], corr[i]); 16062306a36Sopenharmony_ci } 16162306a36Sopenharmony_ci 16262306a36Sopenharmony_ci 16362306a36Sopenharmony_ciCleanup 16462306a36Sopenharmony_ci------- 16562306a36Sopenharmony_ci 16662306a36Sopenharmony_ciThe function free_rs frees the allocated resources, if the caller is 16762306a36Sopenharmony_cithe last user of the decoder. 16862306a36Sopenharmony_ci 16962306a36Sopenharmony_ci:: 17062306a36Sopenharmony_ci 17162306a36Sopenharmony_ci /* Release resources */ 17262306a36Sopenharmony_ci free_rs(rs_decoder); 17362306a36Sopenharmony_ci 17462306a36Sopenharmony_ci 17562306a36Sopenharmony_ciStructures 17662306a36Sopenharmony_ci========== 17762306a36Sopenharmony_ci 17862306a36Sopenharmony_ciThis chapter contains the autogenerated documentation of the structures 17962306a36Sopenharmony_ciwhich are used in the Reed-Solomon Library and are relevant for a 18062306a36Sopenharmony_cideveloper. 18162306a36Sopenharmony_ci 18262306a36Sopenharmony_ci.. kernel-doc:: include/linux/rslib.h 18362306a36Sopenharmony_ci :internal: 18462306a36Sopenharmony_ci 18562306a36Sopenharmony_ciPublic Functions Provided 18662306a36Sopenharmony_ci========================= 18762306a36Sopenharmony_ci 18862306a36Sopenharmony_ciThis chapter contains the autogenerated documentation of the 18962306a36Sopenharmony_ciReed-Solomon functions which are exported. 19062306a36Sopenharmony_ci 19162306a36Sopenharmony_ci.. kernel-doc:: lib/reed_solomon/reed_solomon.c 19262306a36Sopenharmony_ci :export: 19362306a36Sopenharmony_ci 19462306a36Sopenharmony_ciCredits 19562306a36Sopenharmony_ci======= 19662306a36Sopenharmony_ci 19762306a36Sopenharmony_ciThe library code for encoding and decoding was written by Phil Karn. 19862306a36Sopenharmony_ci 19962306a36Sopenharmony_ci:: 20062306a36Sopenharmony_ci 20162306a36Sopenharmony_ci Copyright 2002, Phil Karn, KA9Q 20262306a36Sopenharmony_ci May be used under the terms of the GNU General Public License (GPL) 20362306a36Sopenharmony_ci 20462306a36Sopenharmony_ci 20562306a36Sopenharmony_ciThe wrapper functions and interfaces are written by Thomas Gleixner. 20662306a36Sopenharmony_ci 20762306a36Sopenharmony_ciMany users have provided bugfixes, improvements and helping hands for 20862306a36Sopenharmony_citesting. Thanks a lot. 20962306a36Sopenharmony_ci 21062306a36Sopenharmony_ciThe following people have contributed to this document: 21162306a36Sopenharmony_ci 21262306a36Sopenharmony_ciThomas Gleixner\ tglx@linutronix.de 213