在C ++中不工作的XOR校验和算法

时间:2014-12-02 23:28:37

标签: c++ arduino checksum xor

我搞砸了在cstring char数组上为电报计算的简单XOR校验和。

奇怪的是:校验和的解码有效。这是一个Arduino应用程序从一个Arduino发送电报到另一个。

这是要发送的电报,包括*:

之后的正确校验和
  

$ GPS,52.534015,3.9,13.496394,2.5,0.053,0,44.6,6.2 * 65

你看起来正确:它就像一条NEMEA信息。

所以这是校验和计算的代码

MessageStr.toCharArray(MessageBuffer, MessageStr.length()); //Arduino String Class
for (int x = 1; x < (sizeof(MessageBuffer)/sizeof(MessageBuffer[0])); x++)
{
    if (MessageBuffer[x] == '*')
    {
        Serial.println();
        break;
    }
    else
    {
        MesChecksum ^= MessageBuffer[x]; //XOR the Message data...
    }
}
MessageStr += MesChecksum;
Serial.println(MessageStr);

它甚至计算大校验和。

  • 102而不是62

  • 103而不是67

我使用这个在线工具检查了校验和: NEMEA checksum calc

另一方面,我使用了类似的代码来解析NEMEA消息:

boolean TelegramCheckChecksum(char* Message, int MessageLength)
{
    byte checksumReceived = 0, checksum = 0;
    for (int x = 1; x < MessageLength; x++)
    {
        if (Message[x] == '*') //Checksum starts with '*'
        {
            checksumReceived = strtol(&Message[x + 1], NULL, 16); //Parsing received checksum... |strtol parsing string to integer
            break; //Exit for and continue with next if
        }
        else
        {
            checksum ^= Message[x]; //XOR the received data...
        }
    }
    if (checksum == checksumReceived)
    {
        return true;
    }
    else
    {
        return false;
    }
}

我真的尝试了一切。甚至用手按位检查。没有任何成功。

1 个答案:

答案 0 :(得分:0)

您的代码在计算校验和时看起来是正确的,但是在将数字添加到消息时,您不会将数字转换为十六进制。 请注意,十进制的102是十六进制的62。

要使用标准库将数字转换为十六进制字符串,您可以使用stringstream

std::stringstream stream;
stream << std::hex << MesChecksum;
std::string result( stream.str() );

使用Arduino String类,你可以做这样的事情(我想 - 我不能测试它):

MessageStr += String(MesCheckSum, HEX);