メインページ | 構成 | ファイル一覧 | 構成メンバ | ファイルメンバ | 関連ページ

dkcCRC.c

説明を見る。
00001 
00008 #define DKUTIL_C_CRC_C
00009 #include "dkcCRC.h"
00010 
00011 typedef ULONG value_type;
00012 typedef USHORT value_type16;
00013 
00014 /*size_t a = (0x00000001 << Bits);
00015 size_t b = (0xFFFFFFFF >> 32 - Bits);
00016 size_t result = a & b;
00017 (0x00000001 << Bits) & (0xFFFFFFFF >> 32 - Bits)
00018 */
00019 static DKC_INLINE value_type mask_value( size_t Bits){
00020     //return (~(0x80000000 >> (Bits )) << 1) + 1;
00021     //size_t a = (0x00000001 << Bits);
00022     size_t b = (0xFFFFFFFF >> (32 - Bits));
00023     //size_t result = a & b;
00024     return b;
00025 
00026     //return (0x00000001 << Bits) & (0xFFFFFFFF >> (32 - Bits));
00027 }
00028 
00029 
00031 static  unsigned char  index( value_type rem, unsigned char x ,size_t Bits,BOOL DoReflect)
00032 {
00033     return (BYTE)(x ^ ( rem >> (DoReflect ? 0u : Bits - CHAR_BIT) ));
00034 }
00035 
00037 static  value_type  shift( value_type rem ,BOOL DoReflect)
00038 {
00039     return DoReflect ? rem >> CHAR_BIT : rem << CHAR_BIT; 
00040 }
00041 /*
00042 static  value_type  shift( value_type rem )
00043 { 
00044     return rem << CHAR_BIT; 
00045 }
00046 
00047 static  unsigned char  index( value_type rem, unsigned char x ,size_t Bits)
00048 { 
00049     return (unsigned char)(x ^ ( rem >> (Bits - CHAR_BIT) )); 
00050 }
00051 */
00052 static value_type reflector(size_t Bits,value_type x){
00053     value_type        reflection = 0;
00054   value_type const  one = 1;
00055     size_t i;
00056 
00057   for ( i = 0 ; i < Bits ; ++i, x >>= 1 )
00058   {
00059       if ( x & one )
00060       {
00061           reflection |= ( one << (Bits - 1u - i) );
00062       }
00063   }
00064 
00065 
00066   //return reflection;
00067     //return reflection & (~(0x80000000 >> (Bits )) << 1) + 1;
00068     
00069     return reflection & mask_value(Bits);
00070 }
00071 
00072 static value_type reflection(BOOL DoReflect,size_t Bits,value_type x){
00073     return DoReflect ? reflector( Bits,x ) : x;
00074     
00075 }
00076 
00078 static int makecrctable32(ULONG *crctable,size_t Bits,ULONG TruncPoly,BOOL Reflect)
00079 {
00080 
00081   // factor-out constants to avoid recalculation
00082   const value_type     fast_hi_bit = 1ul << ( Bits - 1u );
00083   unsigned char const  byte_hi_bit = 1u << (CHAR_BIT - 1u);
00084 
00085   // loop over every possible dividend value
00086   unsigned char  dividend = 0;
00087     value_type  remainder ;
00088     unsigned char mask;
00089 
00090     if(Bits > 32){
00091         return edk_FAILED;
00092     }
00093 
00094   do
00095   {
00096         remainder = 0;
00097     
00098 
00099     // go through all the dividend's bits
00100     for ( mask = byte_hi_bit ; mask ; mask >>= 1 )
00101     {
00102       // check if divisor fits
00103       if ( dividend & mask )
00104       {
00105           remainder ^= fast_hi_bit;
00106       }
00107 
00108       // do polynominal division
00109       if ( remainder & fast_hi_bit )
00110       {
00111           remainder <<= 1;
00112           remainder ^= TruncPoly;
00113       }
00114       else
00115       {
00116           remainder <<= 1;
00117       }
00118     }
00119 
00120     //crctable[ crc_helper<CHAR_BIT, Reflect>::reflect(dividend) ]
00121     // = crc_helper<Bits, Reflect>::reflect( remainder );
00122         crctable[ reflection(Reflect,CHAR_BIT,dividend) ]
00123             = reflection(Reflect,Bits,remainder);
00124   }
00125   while ( ++dividend );
00126 
00127     return edk_SUCCEEDED;
00128 }
00129 
00131 static int makecrctable16(USHORT *crctable,size_t Bits,ULONG TruncPoly,BOOL Reflect)
00132 {
00133 
00134 
00135   // factor-out constants to avoid recalculation
00136   const value_type16     fast_hi_bit = (const value_type16)(1u << ( Bits - 1u ));
00137   unsigned char const  byte_hi_bit = 1u << (CHAR_BIT - 1u);
00138 
00139   // loop over every possible dividend value
00140   unsigned char  dividend = 0;
00141     value_type16  remainder ;
00142     unsigned char mask;
00143 
00144     if(Bits > 16){
00145         return edk_FAILED;
00146     }
00147 
00148   do
00149   {
00150         remainder = 0;
00151     
00152 
00153     // go through all the dividend's bits
00154     for ( mask = byte_hi_bit ; mask ; mask >>= 1 )
00155     {
00156       // check if divisor fits
00157       if ( dividend & mask )
00158       {
00159           remainder ^= fast_hi_bit;
00160       }
00161 
00162       // do polynominal division
00163       if ( remainder & fast_hi_bit )
00164       {
00165           remainder <<= 1;
00166           remainder ^= TruncPoly;
00167       }
00168       else
00169       {
00170           remainder <<= 1;
00171       }
00172     }
00173 
00174     //crctable[ crc_helper<CHAR_BIT, Reflect>::reflect(dividend) ]
00175     // = crc_helper<Bits, Reflect>::reflect( remainder );
00176         crctable[ reflection(Reflect,CHAR_BIT,dividend) ]
00177             = (USHORT)reflection(Reflect,Bits,remainder);
00178   }
00179   while ( ++dividend );
00180 
00181     return edk_SUCCEEDED;
00182 }
00183 /*
00184 static Loader32(DKC_CRC *p,const BYTE *pBuffer,size_t size){
00185 
00186 }
00187 static Loader16(DKC_CRC *p,const BYTE *pBuffer,size_t size){
00188 
00189 }*/
00190 
00191 /* 勝手にプール */
00192 
00193 static USHORT *get_crc16left(){
00194 
00195 }
00196 
00197 static USHORT *get_crc16right(){
00198 
00199 }
00200 static ULONG *get_crc32left(){
00201 
00202 }
00203 static ULONG *get_crc32right(){
00204 
00205 }
00206 
00207 static USHORT *get_crc_ccitt(){
00208 
00209 }
00210 static USHORT *get_crc_xmodem(){
00211 
00212 }
00213 
00214 size_t WINAPI dkcCRCGetUseTableSize(size_t Bits){
00215     //手抜き演算〜〜
00216     size_t t; 
00217     if(Bits <= 16){
00218         t = sizeof(USHORT) * 0x100;
00219     }else if(Bits <= 32){
00220         t = sizeof(ULONG) * 0x100;
00221     }else{
00222         t = 0;
00223     }
00224     return t;
00225 }
00226 
00227 DKC_CRC *WINAPI dkcAllocCRC( size_t Bits, ULONG TruncPoly,
00228            ULONG InitRem, ULONG FinalXor,
00229            dkctBOOL ReflectIn, dkctBOOL ReflectRem)
00230 {
00231     DKC_CRC *p = (DKC_CRC *)dkcAllocate(sizeof(DKC_CRC));
00232     void *pt;
00233 
00234     if(NULL==p){
00235         return NULL;
00236     }
00237     pt = dkcAllocate(dkcCRCGetUseTableSize(Bits));
00238     if(NULL==pt){
00239         goto Error;
00240     }
00241     dkcCRCInit(p,pt,Bits,TruncPoly,InitRem,FinalXor,ReflectIn,ReflectRem);
00242     
00243     return p;
00244 
00245 Error:
00246     dkcFree((void **)&p);
00247     return NULL;
00248 }
00249 
00250 DKC_CRC* WINAPI dkcAllocCRC_32left(){
00251     return dkcAllocCRC(32, 0xEDB88320, 0xFFFFFFFF, 0xFFFFFFFF, FALSE, FALSE);
00252 
00253 }
00254 
00255 DKC_CRC* WINAPI dkcAllocCRC_32right(){
00256     //バグ ... 値を治す
00257     return dkcAllocCRC(32, 0x04C11DB7, 0xFFFFFFFF, 0xFFFFFFFF, TRUE, TRUE);
00258 }
00259 DKC_CRC* WINAPI dkcAllocCRC_ansi16left(){
00260     return dkcAllocCRC(16, 0x8005, 0, 0, TRUE,TRUE);
00261 }
00262 
00263 DKC_CRC* WINAPI dkcAllocCRC_ansi16right(){
00264     return dkcAllocCRC(16, 0xa001, 0, 0, FALSE,FALSE);
00265 }
00266 
00267 DKC_CRC* WINAPI dkcAllocCRC_ccitt_left(){
00268     return dkcAllocCRC(16, 0x1021, 0xFFFF, 0, FALSE,FALSE);
00269 }
00270 DKC_CRC* WINAPI dkcAllocCRC_ccitt_right(){
00271     return dkcAllocCRC(16, 0x8005, 0xFFFF, 0, TRUE,TRUE);
00272 }
00273 DKC_CRC *WINAPI dkcAllocCRC_7left(){
00274     return dkcAllocCRC(16, 0x51, 0xFFFF, 0, FALSE,FALSE);
00275 }
00276 DKC_CRC *WINAPI dkcAllocCRC_7right(){
00277     return dkcAllocCRC(16, 0x8a, 0xFFFF, 0, TRUE,TRUE);
00278 }
00279 
00280 DKC_CRC* WINAPI dkcAllocCRC_xmodem(){
00281     return dkcAllocCRC(16, 0x8408, 0, 0, TRUE,TRUE);
00282 }
00283 /*
00284 bool CheckTable(DKC_CRC *p)
00285 {
00286     int i;
00287         //手抜き演算〜〜
00288     size_t t; 
00289     if(Bits <= 16){
00290         t = sizeof(USHORT) * 0x100;
00291     }else if(Bits <= 32){
00292         t = sizeof(ULONG) * 0x100;
00293     }else{
00294         t = 0;
00295     }
00296     dkcCRCGetUseTableSize(p->mBits)
00297     for(i=0;i<;i++){
00298         DKC_EXTERN DKC_CRC* WINAPI dkcAllocCRC_32left();
00299 
00300 DKC_EXTERN DKC_CRC* WINAPI dkcAllocCRC_32right();
00301 
00302 DKC_EXTERN DKC_CRC* WINAPI dkcAllocCRC_ansi16left();
00303 
00304 DKC_EXTERN DKC_CRC* WINAPI dkcAllocCRC_ansi16right();
00305 
00306 DKC_EXTERN DKC_CRC* WINAPI dkcAllocCRC_ccitt_left();
00307 
00308 DKC_EXTERN DKC_CRC* WINAPI dkcAllocCRC_ccitt_right();
00309 
00310 DKC_EXTERN DKC_CRC* WINAPI dkcAllocCRC_xmodem();    
00311 
00312     }
00313 
00314     dkcCRCFree(&p);
00315 }
00316 
00317 dkcCheckTable(HOGE){
00318     
00319 }
00320 
00321 DKC_CRC *WINAPI dkcAllocCRC_
00322 */
00323 
00324 int WINAPI dkcFreeCRC(DKC_CRC **pp){
00325     dkcFree((void **)&((*pp)->mTable));
00326     return dkcFree((void **)pp);
00327 }
00328 
00329 //int WINAPI dkcCRCInit(DKC_CRC *p,ULONG buffer[256],
00330 int WINAPI dkcCRCInit(DKC_CRC *p,void *buffer,
00331                      size_t Bits, ULONG TruncPoly,
00332            ULONG InitRem, ULONG FinalXor,
00333            dkctBOOL ReflectIn, dkctBOOL ReflectRem )
00334 {
00335     int r;
00336 
00337     //初期値
00338     p->mR = reflection(ReflectIn,Bits,InitRem);
00339     //処理結果
00340     p->mResult = 0;
00341     //テーブルへのポインタ
00342     p->mTable = buffer;
00343     
00344     p->mBits = Bits;
00345     p->mTruncPoly = TruncPoly;
00346     p->mInitRem = InitRem;
00347     p->mFinalXor = FinalXor;
00348     p->mReflectIn = ReflectIn;
00349     p->mReflectRem = ReflectRem;
00350 
00351 
00352 
00353     if(Bits <= 16){
00354         r = makecrctable16((USHORT *)buffer,Bits,TruncPoly,ReflectIn);
00355         //p->mLoader = Loader16;
00356     }else if(Bits <= 32){
00357         r = makecrctable32((ULONG *)buffer,Bits,TruncPoly,ReflectIn);
00358         //p->mLoader = Loader32;
00359     }else{
00360         r = edk_FAILED;
00361     }
00362     return r;
00363 
00364 }
00365 
00366 void WINAPI dkcCRCLoad(DKC_CRC *p,const BYTE *pBuffer,size_t size)
00367 {
00368     unsigned char const * const  b = (unsigned char const *)pBuffer;
00369     dkcCRCLoadBlock(p, b, b + size );
00370 
00371 }
00372 
00373 typedef union dkc_local_ptr_offset_union{
00374     ULONG *pt32;
00375     USHORT *pt16;
00376 }OFFSET_PTR_UNION;
00377 
00378 typedef union dkc_local_offset_union{
00379     ULONG t32;
00380     USHORT t16;
00381 }OFFSET_UNION;
00382 
00383 
00384 void WINAPI dkcCRCLoadBlock(DKC_CRC *pobj,const void *bytes_begin,const void *bytes_end)
00385 {
00386     unsigned char const * p = (unsigned char const *)bytes_begin;
00387 
00388   unsigned char byte_index;
00389     //for 32bit
00390     //ULONG *pTable32 = (ULONG *)pobj->mTable;
00391     //for 16bit
00392     //USHORT *pTable16 = (ULONG *)pobj->mTable;
00393 
00394 
00395 
00396     //general purpose
00397     size_t Bits = pobj->mBits;
00398     BOOL DoReflect = pobj->mReflectIn;
00399 
00400     USHORT *usp;
00401     ULONG *ulp;
00402     ULONG rem;
00403 
00404     ulp = (ULONG *)pobj->mTable;
00405     usp = (USHORT *)ulp;
00406 
00407     //もし、おかしな値になったらエンディアン系を疑ってネ^^;
00408     rem = pobj->mR;
00409 
00410 
00411     if(Bits <= 16)
00412     {//16bit filter
00413         // Recompute the CRC for each byte passed
00414         for (; p < (const BYTE *)bytes_end ; ++p )
00415         {
00416             // Compare the new byte with the remainder's higher bits to
00417             // get the new bits, shift out the remainder's current higher
00418             // bits, and update the remainder with the polynominal division
00419             // of the new bits.
00420             byte_index = index( rem, *p ,Bits,DoReflect);
00421             rem = (USHORT)shift( rem , DoReflect);
00422             rem ^= usp[ byte_index ];
00423         }
00424         
00425         pobj->mR = rem & mask_value(Bits);
00426 
00427     }else if(Bits <= 32)
00428     {//32bit filter
00429         for (; p < (const BYTE *)bytes_end ; ++p )
00430         {
00431 
00432             byte_index = index( rem, *p ,Bits,DoReflect);
00433             rem = shift( rem ,DoReflect);
00434             rem ^= ulp[ byte_index ];
00435         }
00436         pobj->mR = rem;
00437     }else{
00438         dkcmFORCE_NOT_ASSERT("dkcCRCLoadBlock中に32ビット以上の計算を要求された");
00439     }
00440     /*
00441     OFFSET_PTR_UNION uni;
00442     OFFSET_UNION rem;
00443 
00444     uni.pt32 = (ULONG *)pobj->mTable;
00445     //もし、おかしな値になったらエンディアン系を疑ってネ^^;
00446     rem.t32 = pobj->mR;
00447 
00448 
00449     if(Bits <= 16)
00450     {//16bit filter
00451         // Recompute the CRC for each byte passed
00452         for (; p < (const BYTE *)bytes_end ; ++p )
00453         {
00454             // Compare the new byte with the remainder's higher bits to
00455             // get the new bits, shift out the remainder's current higher
00456             // bits, and update the remainder with the polynominal division
00457             // of the new bits.
00458             byte_index = index( rem.t16, *p ,Bits,DoReflect);
00459             rem.t16 = (USHORT)shift( rem.t16 , DoReflect);
00460             rem.t16 ^= uni.pt16[ byte_index ];
00461         }
00462 
00463         pobj->mR = rem.t16;
00464 
00465     }else if(Bits <= 32)
00466     {//32bit filter
00467         for (; p < (const BYTE *)bytes_end ; ++p )
00468         {
00469 
00470             byte_index = index( rem.t32, *p ,Bits,DoReflect);
00471             rem.t32 = shift( rem.t32 ,DoReflect);
00472             rem.t32 ^= uni.pt32[ byte_index ];
00473         }
00474         pobj->mR = rem.t32;
00475     }else{
00476         dkcmFORCE_NOT_ASSERT("dkcCRCLoadBlock中に32ビット以上の計算を要求された");
00477     }
00478     */
00479 
00480     
00481     //  rem.t32 & mask_value(Bits);
00482 }
00483 
00484 static DKC_INLINE ULONG get_sigbit(size_t Bits)
00485 {
00486     return (( (BYTE)1u ) << ( Bits - 1u )) ;
00487     //return (~( ~( 0ul ) << Bits )) ;
00488     //return (~( ~(least( 0u )) << Bits ))
00489 }
00490 ULONG WINAPI dkcCRCFinal(DKC_CRC *p){
00491     BOOL b = (p->mReflectRem != p->mReflectIn);
00492     size_t Bits = p->mBits;
00493     ULONG ult = mask_value(Bits);
00494         //~(0x80000000 >> (Bits ));//( ( 1u ) << ( get_sigbit(Bits) - 1u ) );
00495     //変数の再利用・・・。本当はしたくないのだが・・・。
00496     Bits = ( reflection(b,Bits,p->mR) ^ p->mFinalXor ) & ult;
00497     
00498     p->mResult = Bits;
00499 
00500     return Bits;
00501     
00502     
00503     //reflect_out_type::reflect(rem_) ^ get_final_xor_value() )
00504   //   & masking_type::sig_bits_fast;
00505 }
00506 
00507 ULONG WINAPI dkcCRCResult(const DKC_CRC *p){
00508     return p->mResult;
00509 }

dkutil_cに対してTue Oct 19 03:34:55 2004に生成されました。 doxygen 1.3.6