⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 reedsol.c

📁 truefs for vxworks, make fs on flash or rom
💻 C
📖 第 1 页 / 共 2 页
字号:
  LTRarrayEightToTen(block, (unsigned short *)packed_symbol);					/* Calculate the parity value of the 512 */					/* bytes array, and store it in the 8 */					/* lsb of the 410'th 10-bit value: */  packed_symbol[410] |= (resolveParity(block, 512) & 0xFF);					/* Calculate the EDC code: */	register_division(reg, packed_symbol, K512);					/* Convert the EDC code from four */					/* 10-bit values, into five bytes: */  LTRtenToEight((unsigned short *)reg, code);					/* Store the parity byte in the last */					/* element of code[]: */  code[5] = (char)(packed_symbol[410] & 0xFF);}/*------------------------------------------------------------------------------*//* Function Name: flCalcEDCSyndrom                                              *//* Purpose......: Trys to detect errors.                                        *//*                block[] should contain 512 bytes of data.                     *//*                code[] should contain the EDC code as 5 bytes, and one        *//*                parity byte (identical to the output of EDCencode::resolve()).*//*                Upon returning errorSyndrom[] will contain the syndrom as     *//*                5 bytes and one       parity byte (identical to the input of  *//*                EDCdecode::resolve()).                                        *//* Returns......: The error status.                                             *//*                NOTE! If the error status is NO_EDC_ERROR upon return, ignore *//*                      the value of the arguments.                             *//*------------------------------------------------------------------------------*/EDCstatus flCalcEDCSyndrom(char FAR1 *block, char code[6], char errorSyndrom[6]){  short nonZero, i;  short residue[SYND_LEN];  short reg[SYND_LEN];         /* register for main division procedure */					/* Convert block[] into a 10-bit values */					/* array: */  LTRarrayEightToTen(block, (unsigned short *)packed_symbol);  packed_symbol[410] |= code[5] & 0xFF; /* Copy the parity value from code[] */					/* into the 8 lsb of the 410'th */					/* 10-bit value */					/* Copy the EDC code into the last four */					/* 10-bit values of packed_symbol: */  LTReightToTen(code, (unsigned short *)&packed_symbol[411]);					/* Calculate the syndrom (the result */					/* is in reg[]): */  register_division( reg, packed_symbol, N512 );  for(i=nonZero=0; i<SYND_LEN; i++)     /* Chack if reg[] is all zeroes */    if(reg[i])      nonZero++;  if(nonZero == 0)                      /* If reg[] is all zeroes, there is */  {                                     /* no error */    return NO_EDC_ERROR;                /* No error found */  }  for( i = 0; i < SYND_LEN; i++ )       /* reverse the order of reg[] */    residue[SYND_LEN-1-i] = reg[ i ];   /* into residue[] */					/* Convert the syndrom (in residue[]) */					/* from four 10-bit values into five */					/* bytes: */  RTLtenToEight((unsigned short *)residue, errorSyndrom);					/* Calculate the parity byte for the */					/* original 512 bytes plus the parity */					/* byte that was received in code[]: */  errorSyndrom[5] = resolveParity(block, 512) ^ (code[5] & 0xFF);  return EDC_ERROR;                     /* An error was detected */}#endif  /* EDC_IN_SOFTWARE *//*----------------------------------------------------------------------------*/static short convert_to_byte_patterns( short *locators, short *values,				short noferr, short *blocs, short *bvals ){  static short mask[] = { 0x0, 0x1, 0x3, 0x7, 0xf, 0x1f, 0x3f, 0x7f, 0xff };  short i,j,n, n0, n1, tmp;  short n_bit, n_byte, k_bit, nb;  for( i = 0, nb = 0; i< noferr; i++)  {    n = locators[i];    tmp = values[i];    n_bit = n *10 - 6 ;    n_byte = n_bit >> 3;    k_bit  = n_bit - (n_byte<<3);    n_byte++;    if( k_bit == 7 )    {      /* 3 corrupted bytes */      blocs[nb] = n_byte+1;      bvals[nb++] = tmp & 1 ? 0x80 : 0;      tmp >>= 1;      blocs[nb] = n_byte;      bvals[nb++] = tmp & 0xff;      tmp >>= 8;      bvals[nb++] = tmp & 0xff;    }    else    {      n0 = 8 - k_bit;      n1 = 10 - n0;      blocs[nb] = n_byte;      bvals[nb++] = (tmp & mask[n1]) << (8 - n1);      tmp >>= n1;      blocs[nb] = n_byte - 1;      bvals[nb++] = (tmp & mask[n0]);    }  }  for( i = 0, j = -1; i < nb; i++ )  {    if( bvals[i] == 0 ) continue;    if( (blocs[i] == blocs[j]) && ( j>= 0 ) )    {      bvals[j] |= bvals[i];    }    else    {      j++;      blocs[j] = blocs[i];      bvals[j] = bvals[i];    }  }  return j+1;}/*----------------------------------------------------------------------------*/static short deg512( short x ){  short i;  short l,m;  l = flog(x);  for( i=0;i<9;i++)  {    m = 0;    if( (l & 0x200) )      m = 1;    l =  ( ( l << 1 ) & 0x3FF  ) | m;  }  return alog(l);}/*----------------------------------------------------------------------------*/static short decoder_for_2_errors( short s[], short lerr[], short verr[] ){  /* decoder for correcting up to 2 errors */  short i,j,k,temp,delta;  short ind, x1, x2;  short r1, r2, r3, j1, j2;  short sigma1, sigma2;  short xu[10], ku[10];  short yd, yn;  ind = 0;  for(i=0;i<SYND_LEN;i++)    if( s[i] != 0 )      ind++;                /* ind = number of nonzero syndrom symbols */  if( ind == 0 ) return 0;  /* no errors */  if( ind < 4 )    goto two_or_more_errors;/* checking s1/s0 = s2/s1 = s3/s2 = alpha**j for some j */  r1 = gfdiv( s[1], s[0] );  r2 = gfdiv( s[2], s[1] );  r3 = gfdiv( s[3], s[2] );  if( r1 != r2 || r2 != r3)    goto two_or_more_errors;  j = flog(r1);  if( j > 414 )    goto two_or_more_errors;  lerr[0] = j;/*  pattern = (s0/s1)**(510+1) * s1	  or    pattern = (s0/s1)**(512 - 1 )  * s1 */  temp = gfi( r1 );  {    int i;    for (i = 0; i < 9; i++)      temp = gfmul( temp, temp );  /* deg = 512 */  }  verr[0] = gfmul( gfmul(temp, r1), s[1] );  return 1;    /* 1 error */two_or_more_errors:  delta = gfmul( s[0], s[2] ) ^ gfmul( s[1], s[1] );  if( delta == 0 )    return -1;  /* uncorrectable error */  temp = gfmul( s[1], s[3] ) ^ gfmul( s[2], s[2] );  if( temp == 0 )    return -1;  /* uncorrectable error */  sigma2 = gfdiv( temp, delta );  temp = gfmul( s[1], s[2] ) ^ gfmul( s[0], s[3] );  if( temp == 0 )    return -1;  /* uncorrectable error */  sigma1 = gfdiv( temp, delta );  k = gfdiv( sigma2, gfmul( sigma1, sigma1 ) );  unpack( k, 10, ku );  if( ku[2] != 0 )    return -1;  xu[4] = ku[9];  xu[5] = ku[0] ^ ku[1];  xu[6] = ku[6] ^ ku[9];  xu[3] = ku[4] ^ ku[9];  xu[1] = ku[3] ^ ku[4] ^ ku[6];  xu[0] = ku[0] ^ xu[1];  xu[8] = ku[8] ^ xu[0];  xu[7] = ku[7] ^ xu[3] ^ xu[8];  xu[2] = ku[5] ^ xu[7] ^ xu[5] ^ xu[0];  xu[9] = 0;  x1 = pack( xu, 10 );  x2 = x1 | 1;  x1 = gfmul( sigma1, x1 );  x2 = gfmul( sigma1, x2 );  j1 = flog(x1);  j2 = flog(x2);  if( (j1 > 414) || (j2 > 414) )    return -1;  r1 = x1 ^ x2;  r2 = deg512( x1 );  temp = gfmul( x1, x1 );  r2 = gfdiv( r2, temp );  yd = gfmul( r2, r1 );  if( yd == 0 )    return -1;  yn = gfmul( s[0], x2 ) ^ s[1];  if( yn == 0 )    return -1;  verr[0] = gfdiv( yn, yd );  r2 = deg512( x2 );  temp = gfmul( x2, x2 );  r2 = gfdiv( r2, temp );  yd = gfmul( r2, r1 );  if( yd == 0 )    return -1;  yn = gfmul( s[0], x1 ) ^ s[1];  if( yn == 0 )    return -1;  verr[1] = gfdiv( yn, yd );  if( j1 > j2 ) {    lerr[0] = j2;    lerr[1] = j1;    temp = verr[0];    verr[0] = verr[1];    verr[1] = temp;  }  else  {    lerr[0] = j1;    lerr[1] = j2;  }  return 2;}/*------------------------------------------------------------------------------*//* Function Name: flDecodeEDC                                                   *//* Purpose......: Trys to correct errors.                                       *//*                errorSyndrom[] should contain the syndrom as 5 bytes and one  *//*                parity byte. (identical to the output of calcEDCSyndrom()).   *//*                Upon returning, errorNum will contain the number of errors,   *//*                errorLocs[] will contain error locations, and                 *//*                errorVals[] will contain error values (to be XORed with the   *//*                data).                                                        *//*                Parity error is relevant only if there are other errors, and  *//*                the EDC code fails parity check.                              *//*                NOTE! Only the first errorNum indexes of the above two arrays *//*                      are relevant. The others contain garbage.               *//* Returns......: The error status.                                             *//*                NOTE! If the error status is NO_EDC_ERROR upon return, ignore *//*                      the value of the arguments.                             *//*------------------------------------------------------------------------------*/EDCstatus flDecodeEDC(char *errorSyndrom, char *errorsNum,		    short errorLocs[3*T],  short errorVals[3*T]){  short noferr;                         /* number of errors */  short dec_parity;                     /* parity byte of decoded word */  short rec_parity;                     /* parity byte of received word */  short realsynd[SYND_LEN];             /* real syndrom calculated from residue */  short locators[T],                    /* error locators */  values[T];                            /* error values */  short reg[SYND_LEN];                  /* register for main division procedure */  int i;  RTLeightToTen(errorSyndrom, (unsigned short *)reg);  rec_parity = errorSyndrom[5] & 0xFF;  /* The parity byte */  residue_to_syndrom(reg, realsynd);  noferr = decoder_for_2_errors(realsynd, locators, values);  if(noferr == 0)    return NO_EDC_ERROR;                /* No error found */  if(noferr < 0)                        /* If an uncorrectable error was found */    return UNCORRECTABLE_ERROR;  for (i=0;i<noferr;i++)    locators[i] = N512 - 1 - locators[i];  *errorsNum = (char)convert_to_byte_patterns(locators, values, noferr, errorLocs, errorVals);  for(dec_parity=i=0; i < *errorsNum; i++)/* Calculate the parity for all the */  {                                       /*   errors found: */    if(errorLocs[i] <= 512)      dec_parity ^= errorVals[i];  }  if(dec_parity != rec_parity)    return UNCORRECTABLE_ERROR;         /* Parity error */  else    return CORRECTABLE_ERROR;}/*------------------------------------------------------------------------------*//* Function Name: flCheckAndFixEDC                                              *//* Purpose......: Decodes the EDC syndrom and fixs the errors if possible.      *//*                block[] should contain 512 bytes of data.                     *//*                NOTE! Call this function only if errors where detected by     *//*                      syndCalc or by the ASIC module.                         *//* Returns......: The error status.                                             *//*------------------------------------------------------------------------------*/EDCstatus flCheckAndFixEDC(char FAR1 *block, char *syndrom, FLBoolean byteSwap){  char errorsNum;  short errorLocs[3*T];  short errorVals[3*T];  EDCstatus status;  status = flDecodeEDC(syndrom, &errorsNum, errorLocs, errorVals);  if(status == CORRECTABLE_ERROR)       /* Fix the errors if possible */  {    int i;    for (i=0; i < errorsNum; i++)      block[errorLocs[i] ^ byteSwap] ^= errorVals[i];    return NO_EDC_ERROR;                /* All errors are fixed */  }  else    return status;                      /* Uncorrectable error */}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -