简体   繁体   中英

Converting C to Java for [CRC16 /IBM-SDLC ]

This example program is written in C language. It is used to generate a 16-bit FCS number based on CRC-16/IBM-SDLC. I'm trying to write the same in JAVA. Can someone help me with this or provide some idea on this? I don't know the C language.

Example I/O from C language: Key:10530237 16-Bit FCS Number: 9588 The I/O is two bytes and hexadecimal form.

Input Output
1234 DEC1
1111 8206
4143 2066
C language code:
unsigned short crcgen (data, length)
    char *data; /* address of the key */ 
    int length; /* key length   */
{
    unsigned char crcbytel, crcbyte2, r1; 
    char *ptr;
    int i;
    union byte_to_word
    {
        char bytes[2]; 
        unsigned short  ret;
    } return_val;
    ptr = data; 
    crcbyte1 = 0xFF 
    crcbyte2 = 0xFF
    for (i=0; i<length; i++)
    {
        r1 = *ptr++ ^ crcbyte2; 
        r1 = (r1 << 4) ^ r1;
        crcbyte2 = (r1 << 4) | (r1 >> 4); 
        crcbyte2 = (crcbyte2 & 0x0F ) ^ crcbyte1; 
        crcbyte1 = r1;
        r1 = (r1 << 3) | (r1 >> 5);
        crcbyte2 = crcbyte2 ^ (r1 & 0xF8);
         
        crcbyte1 = crcbyte1 ^ (r1 & 0x07);
    }
        
    return_val.bytes[0] = ˜crcbyte2; 
    return_val.bytes[1] = ˜crcbyte1; 
    return(return_val.ret);
}

I have looked at some answers but it did not help and not able to get that output. Convert C CRC16 to Java CRC16 and https://www.source-code.biz/snippets/java/crc16/

The Code that I tried:

  private static final int POLYNOMIAL   = 0x8408;
private static final int PRESET_VALUE = 0xFFFF;
public static void main(String[] args) throws IOException {
    // FileRead.read();
    int crc = 0xFFFF;          // initial value
    int polynomial = 0x1021;   // 0001 0000 0010 0001  (0, 5, 12)

    // byte[] testBytes = "123456789".getBytes("ASCII");

    byte[] buffer = "10530237".getBytes("ASCII");

    System.out.println(FileRead.crc16(buffer));
}

public static int crc16(byte[] data)
{
    int current_crc_value = PRESET_VALUE;
    for (int i = 0; i < data.length; i++ )
    {
        current_crc_value ^= data[i] & 0xFF;
        for (int j = 0; j < 8; j++)
        {
            if ((current_crc_value & 1) != 0)
            {
                current_crc_value = (current_crc_value >>> 1) ^ POLYNOMIAL;
            }
            else
            {
                current_crc_value = current_crc_value >>> 1;
            }
        }
    }
    current_crc_value = ~current_crc_value;

    return current_crc_value & 0xFFFF;
}

It returns 34134 instead of 9588.

There's nothing wrong with your translation. It's because you didn't pass the correct "two bytes and hexadecimal form" parameter. Change buffer to

byte[] buffer = {0x10, 0x53, 0x02, 0x37 };

BTW, this may help you deal with the string input.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM