我从硬件合作伙伴处收到了用C语言编写的CRC功能。他的设备发送的消息使用此代码进行签名。任何人都可以帮我翻译成Java吗?
int8 crc8(int8*buf, int8 data_byte)
{
int8 crc=0x00;
int8 data_bit=0x80;
while(data_byte>0)
{
if(((crc&0x01)!=0)!=((buf[data_byte]&data_bit)!=0))
{
crc>>=1;
crc^=0xCD;
}
else
crc>>=1;
data_bit>>=1;
if(!data_bit)
{
data_bit=0x80;
data_byte--;
}
}
return(crc);
}
我尝试将其转换为Java,但结果并非我期望。
public static byte crc8(byte [] buf, byte data_byte)
{
byte crc = 0x00;
byte data_bit = (byte)0x80;
while(data_byte>0)
{
if(((crc&0x01)!=0)!=((buf[data_byte]&data_bit)!=0))
{
crc>>=1;
crc^=0xCD;
}
else
{
crc>>=1;
}
data_bit>>=1;
if(data_bit == 0)
{
data_bit= (byte)0x80;
data_byte--;
}
}
return crc;
}
我认为这是错误:if(data_bit != 0)
编辑:
我在转换方法中将代码更改为byte。我从套接字接收数据并将其转换为String,我从中获取byteArray。
输入示例为16,0,1,-15,43,6,1,6,8,0,111,0,0,49 最后一个字段(49)应该是校验和
我也尝试过Durandals版本,但我的结果仍无效。
这是我阅读数据的方式
BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(socket.getInputStream()));
char[] buffer = new char[14];
int count= bufferedReader.read(buffer, 0, 14);
String msg = new String(buffer, 0, count);
byte[] content = msg.getBytes();
答案 0 :(得分:2)
if(!data_bit)
转换为
if(data_bit == 0)
你真的需要使用字节而不是短路。要解决使用字节的问题,请使用此
byte data_bit = (byte)0x80;
另外,正如马克所说,你需要使用>>>而不是>>。
答案 1 :(得分:0)
翻译代码1:1,特别注意对字节进行的所有操作以解释java的隐式转换为int(例如(byte>>>> 1)绝对没有价值,因为字节首先是extendet到int ,转移然后再回头,无论如何都使其成为有效的签名班次。
因此,局部变量最好声明为int,并且从掩码的bytearray加载以产生无符号扩展:int x = byte [i]& 0xFF的;因为在唯一完成数据的位置已经被掩盖到一个位(在if中),所以没有什么特别的事情要做。
应用C代码产生:
int crc8(byte[] buf, int dataCount) {
int crc = 0;
int data_bit = 0x80;
while(dataCount > 0) {
if ( ((crc & 0x01)!=0) != ((buf[dataCount] & data_bit)!=0)) {
crc >>= 1;
crc ^= 0xCD;
} else {
crc >>= 1;
}
data_bit >>= 1;
if (data_bit == 0) {
data_bit = 0x80;
dataCount--;
}
}
return crc;
}
也就是说,代码效率不高(它逐位处理输入,有更快的实现处理整个字节,使用表添加每个可能的字节,但你可能不关心这个用例)
另外,请注意当您将此方法的crc与一个字节进行比较时,必须使用0xFF正确地屏蔽该字节,否则对于值> = 0x80将无法进行比较:
(int) crc == (byte) crc & 0xFF
编辑:
担心我甚至关于原始代码的问题,data_byte显然是为了指定长度,首先它以相反的顺序计算,并且还会访问另外一个之后的字节指定的数字(data_byte在循环之前没有递减)。我怀疑原来是(已经)破解的代码,或者对它的调用非常混乱。