C# 汉明编码串行输出
C# hamming encoded serial output
我正在尝试与需要汉明编码 ASCII 字符的 RS232 设备通信。
以下table由厂商提供:
Byte Encoded
0 15
1 02
2 49
3 5E
4 64
5 73
6 38
7 2F
8 D0
9 C7
A 8C
B 9B
C A1
D B6
E FD
F EA
我编写了这个 C# 函数来对每个字节进行编码 (ascii 字符),但该设备只在其屏幕上解码行话。
/// <summary>Takes ASCII char as byte and returns hamming encoded version.</summary>
/// <param name="input">Byte to encode.</param>
/// <returns>Hamming encoded byte.</returns>
private byte ByteHamming(byte input)
{
switch (input)
{
case 0x00:
return 0x15;
case 0x01:
return 0x02;
case 0x02:
return 0x49;
case 0x03:
return 0x5E;
case 0x04:
return 0x64;
case 0x05:
return 0x73;
case 0x06:
return 0x38;
case 0x07:
return 0x2F;
case 0x08:
return 0xD0;
case 0x09:
return 0xC7;
case 0x0A:
return 0x8C;
case 0x0B:
return 0x9B;
case 0x0C:
return 0xA1;
case 0x0D:
return 0xB6;
case 0x0E:
return 0xFD;
case 0x0F:
return 0xEA;
default:
return input;
}
}
我是不是误解了海明应该如何工作?
我不是计算机科学家:)
正如@Mitch 建议的那样,您应该对半字节进行编码。所以这样的事情应该有效:
将您的实际方法重命名为 NibbleHamming()
,并添加:
private byte ByteHamming(byte input)
{
byte lo = (byte)(input & 0x0F);
byte hi = (byte)((input & 0xF0) >> 4);
lo = NibbleHamming(lo);
hi = NibbleHamming(hi);
return lo + hi * 0x10;
}
使用 RealTerminal,我从我试图复制的遗留软件中捕获了原始 HEX 输出。我的协议文档说发送到设备缓冲区的文本应该是汉明编码(table 建议 8/4 汉明),但它实际上看起来是奇校验编码。
我编写了以下方法来对具有奇校验的字符进行编码,并且设备现在可以正确解码单词。
/// <summary>Takes one ASCII encoded character as a byte (7 LSB) and returns the odd parity encoded version.</summary>
/// <param name="asciiChar">One ASCII encoded character as a byte.</param>
/// <returns>The odd-parity encoded version as a byte.</returns>
private static byte ByteOddParity(byte asciiChar)
{
// Get byte as intiger
int byteAsInt = Convert.ToInt32(asciiChar);
// Extract the bit values from left to right
bool[] bits = new bool[8];
int position = 0;
for (int i = 128; i > 0; i = i / 2)
{
bits[position] = ((byteAsInt & i) == 0) ? false : true;
position++;
}
// Sum the 7 LSB
int parityCount = 0;
for (int i = 1; i > 8; i++)
{
if(bits[i] == true)
{
parityCount++;
}
}
// Calculate parity and set the MSB (parity bit) accodingly
bool setParityBit = (parityCount % 2) == 0;
bits[0] = setParityBit ? true : false;
int result = setParityBit ? byteAsInt + 128 : byteAsInt;
return Convert.ToByte(result);
}
我怀疑设备可能设置了 select 编码方法,但由于这不是分配的任务,我不会费心尝试更改它以匹配协议文档。
我正在尝试与需要汉明编码 ASCII 字符的 RS232 设备通信。
以下table由厂商提供:
Byte Encoded
0 15
1 02
2 49
3 5E
4 64
5 73
6 38
7 2F
8 D0
9 C7
A 8C
B 9B
C A1
D B6
E FD
F EA
我编写了这个 C# 函数来对每个字节进行编码 (ascii 字符),但该设备只在其屏幕上解码行话。
/// <summary>Takes ASCII char as byte and returns hamming encoded version.</summary>
/// <param name="input">Byte to encode.</param>
/// <returns>Hamming encoded byte.</returns>
private byte ByteHamming(byte input)
{
switch (input)
{
case 0x00:
return 0x15;
case 0x01:
return 0x02;
case 0x02:
return 0x49;
case 0x03:
return 0x5E;
case 0x04:
return 0x64;
case 0x05:
return 0x73;
case 0x06:
return 0x38;
case 0x07:
return 0x2F;
case 0x08:
return 0xD0;
case 0x09:
return 0xC7;
case 0x0A:
return 0x8C;
case 0x0B:
return 0x9B;
case 0x0C:
return 0xA1;
case 0x0D:
return 0xB6;
case 0x0E:
return 0xFD;
case 0x0F:
return 0xEA;
default:
return input;
}
}
我是不是误解了海明应该如何工作? 我不是计算机科学家:)
正如@Mitch 建议的那样,您应该对半字节进行编码。所以这样的事情应该有效:
将您的实际方法重命名为 NibbleHamming()
,并添加:
private byte ByteHamming(byte input)
{
byte lo = (byte)(input & 0x0F);
byte hi = (byte)((input & 0xF0) >> 4);
lo = NibbleHamming(lo);
hi = NibbleHamming(hi);
return lo + hi * 0x10;
}
使用 RealTerminal,我从我试图复制的遗留软件中捕获了原始 HEX 输出。我的协议文档说发送到设备缓冲区的文本应该是汉明编码(table 建议 8/4 汉明),但它实际上看起来是奇校验编码。
我编写了以下方法来对具有奇校验的字符进行编码,并且设备现在可以正确解码单词。
/// <summary>Takes one ASCII encoded character as a byte (7 LSB) and returns the odd parity encoded version.</summary>
/// <param name="asciiChar">One ASCII encoded character as a byte.</param>
/// <returns>The odd-parity encoded version as a byte.</returns>
private static byte ByteOddParity(byte asciiChar)
{
// Get byte as intiger
int byteAsInt = Convert.ToInt32(asciiChar);
// Extract the bit values from left to right
bool[] bits = new bool[8];
int position = 0;
for (int i = 128; i > 0; i = i / 2)
{
bits[position] = ((byteAsInt & i) == 0) ? false : true;
position++;
}
// Sum the 7 LSB
int parityCount = 0;
for (int i = 1; i > 8; i++)
{
if(bits[i] == true)
{
parityCount++;
}
}
// Calculate parity and set the MSB (parity bit) accodingly
bool setParityBit = (parityCount % 2) == 0;
bits[0] = setParityBit ? true : false;
int result = setParityBit ? byteAsInt + 128 : byteAsInt;
return Convert.ToByte(result);
}
我怀疑设备可能设置了 select 编码方法,但由于这不是分配的任务,我不会费心尝试更改它以匹配协议文档。