2011-02-28 64 views
5

¿Alguien puede ayudarme con la implementación Delphi de CRC-CCITT (0xFFFF)?CRC-CCITT (0xFFFF) función?

ya tiene la versión de Java, pero confuso sobre cómo portarlo a Delphi

public static int CRC16CCITT(byte[] bytes) { 
    int crc = 0xFFFF;   // initial value 
    int polynomial = 0x1021; // 0001 0000 0010 0001 (0, 5, 12) 

    for (byte b : bytes) { 
     for (int i = 0; i < 8; i++) { 
      boolean bit = ((b >> (7-i) & 1) == 1); 
      boolean c15 = ((crc >> 15 & 1) == 1); 
      crc <<= 1; 
      if (c15^bit) crc ^= polynomial; 
     } 
    } 

    crc &= 0xffff; 
    //System.out.println("CRC16-CCITT = " + Integer.toHexString(crc)); 
    return crc; 
} 

y para la implementación en PHP

<?php 
function crc16($data) 
{ 
    $crc = 0xFFFF; 
    for ($i = 0; $i < strlen($data); $i++) 
    { 
    $x = (($crc >> 8)^ord($data[$i])) & 0xFF; 
    $x ^= $x >> 4; 
    $crc = (($crc << 8)^($x << 12)^($x << 5)^$x) & 0xFFFF; 
    } 
    return $crc; 
} 

Respuesta

4

He encontrado un código que funciona:

function crc16(Buffer:String;Polynom,Initial:Cardinal):Cardinal; 
var 
    i,j: Integer; 
begin 
Result:=Initial; 
for i:=1 to Length(Buffer) do begin 
    Result:=Result xor (ord(buffer[i]) shl 8); 
    for j:=0 to 7 do begin 
    if (Result and $8000)<>0 then Result:=(Result shl 1) xor Polynom 
    else Result:=Result shl 1; 
    end; 
    end; 
Result:=Result and $ffff; 
end; 

fuente: http://www.miscel.dk/MiscEl/CRCcalculations.html

12
  • 0xFFFF se traduce en $FFFF
  • & se traduce en and
  • ^ traduce en xor
  • << traduce en shl
  • >> traduce en shr
  • x ^= y se traduce en x := x xor y, similar para &=, <<=, etc.

Estos operadores generalmente tienen mayor precedencia en Delphi tan por lo general, necesitan tener sus argumentos entre paréntesis.

Estoy seguro de que hay muchas otras implementaciones de CRC16, etc. para Delphi, consulte p. Ej. Improve speed on Crc16 calculation

9
function CRC16CCITT(bytes: TBytes): Word; 
const 
    polynomial = $1021; // 0001 0000 0010 0001 (0, 5, 12) 
var 
    crc: Word; 
    I, J: Integer; 
    b: Byte; 
    bit, c15: Boolean; 
begin 
    crc := $FFFF; // initial value 
    for I := 0 to High(bytes) do 
    begin 
    b := bytes[I]; 
    for J =: 0 to 7 do 
    begin 
     bit := (((b shr (7-J)) and 1) = 1); 
     c15 := (((crc shr 15) and 1) = 1); 
     crc := crc shl 1; 
     if ((c15 xor bit) <> 0) then crc := crc xor polynomial; 
    end; 
    end; 
    Result := crc and $ffff; 
end; 
+0

su código no funcionaba, pero gracias (algo con operando): bit: = (((b shr (7-I)) y 1) = 1); c15: = (((crc shr 15) y 1) = 1); – Dels

+0

el resultado para un único carácter como '9' es como otro convertidor en línea, pero cuando paso una cadena como 'helloworld' el resultado es diferente. ¿Cómo puede ser posible? –

1
unit CRC16CCITT; 

interface 

    function ComputeCRC16CCITT(crc: word; const data: PByte; len:integer) : word; 

implementation 

const 
    crc16_table: array [0..$FF] of word = (0,4489,8978,12955,17956,22445,25910,29887,35912,40385,44890,48851,51820,56293,59774, 
    63735,4225,264,13203,8730,22181,18220,30135,25662,40137,36160,49115,44626,56045,52068,63999, 
    59510,8450,12427,528,5017,26406,30383,17460,21949,44362,48323,36440,40913,60270,64231,51324, 
    55797,12675,8202,4753,792,30631,26158,21685,17724,48587,44098,40665,36688,64495,60006,55549, 
    51572,16900,21389,24854,28831,1056,5545,10034,14011,52812,57285,60766,64727,34920,39393,43898, 
    47859,21125,17164,29079,24606,5281,1320,14259,9786,57037,53060,64991,60502,39145,35168,48123, 
    43634,25350,29327,16404,20893,9506,13483,1584,6073,61262,65223,52316,56789,43370,47331,35448, 
    39921,29575,25102,20629,16668,13731,9258,5809,1848,65487,60998,56541,52564,47595,43106,39673, 
    35696,33800,38273,42778,46739,49708,54181,57662,61623,2112,6601,11090,15067,20068,24557,28022, 
    31999,38025,34048,47003,42514,53933,49956,61887,57398,6337,2376,15315,10842,24293,20332,32247, 
    27774,42250,46211,34328,38801,58158,62119,49212,53685,10562,14539,2640,7129,28518,32495,19572, 
    24061,46475,41986,38553,34576,62383,57894,53437,49460,14787,10314,6865,2904,32743,28270,23797, 
    19836,50700,55173,58654,62615,32808,37281,41786,45747,19012,23501,26966,30943,3168,7657,12146, 
    16123,54925,50948,62879,58390,37033,33056,46011,41522,23237,19276,31191,26718,7393,3432,16371, 
    11898,59150,63111,50204,54677,41258,45219,33336,37809,27462,31439,18516,23005,11618,15595,3696, 
    8185,63375,58886,54429,50452,45483,40994,37561,33584,31687,27214,22741,18780,15843,11370,7921, 
    3960); 

    function ComputeCRC16CCITT(crc: word; const data: PByte; len:integer) : word; 
    var 
    i : integer; 
    begin 
    for i := 0 to len-1 do 
     crc := (crc shr 8) xor crc16_table[(crc xor data[i]) and $ff]; 
    result := crc; 
    end; 

end. 
Cuestiones relacionadas