AVR C中的位和字节解释

时间:2013-01-14 13:17:42

标签: c byte microcontroller bit avr-gcc

我知道这可能是错误的部分,但我的问题是微控制器编程特定(主要是AVR)!

我使用Uart在两个AVR atmega8之间发送字节,其中字节中的每个位代表某个东西,并且每个字节中只有一个位为1

因此,如果我想检查,例如,接收字节中的第5位,那么如果写入如下:

short byte=UDR;
if(byte&(1<<5))
{
// do stuff for bit 5
}

然后它总能正常工作

但是,如果我这样写:

short byte=UDR;
if(byte==0b00100000)

OR
short byte=UDR;
if(byte==0x20)

然后它将无法工作,如果我使用Switch-case而不是if-else也会失败 我无法理解这个问题,编译器是否将其解释为sign no和7th Bit作为符号? 或者是其他东西? 编译器是AVR studio 5的AVR-gnu

如果有人要求我在接收器上也有LED显示接收到的字节 所以我知道收到的字节是正确的但由于某种原因我无法比较它的条件!仍然会有一些噪音导致Uart误解了比特,从而改变了接收到的实际字节?

帮助!

了解每一个

这里的东西就像PARANORMAL

最后我走投无路的问题

我添加了8个LED来表示接收字节的位数,这是我发现的:

LED表示(1 <&lt; 5)为0b00100000,这与我发送的一样正常

但是

指定在接收0b00100000时发光的其他LED(不包括8)不会发光!

FTW MAN!

我确定收到的字节是正确的..但if-else和switch-case比较有问题

2 个答案:

答案 0 :(得分:3)

C没有二进制文字的语法,你不能输入0b00100000并让它编译。<​​/ p>

有点难以理解为什么它不适用于== 0x20案例,因为我们不知道特定于您的平台的UDR的价值。

如果UDR设置的位数超过1位,那么完全相等的检查当然会失败,而单位测试会成功。

您只能使用switch()为每个case准确的值,但在检查之前您当然可以屏蔽:

switch( byte & 0x20 )
{
  case 0:
   break;
  case 0x20:
   break;
}

答案 1 :(得分:3)

它不起作用,因为第二个公式改变了代码的含义,而不仅仅是掩码常量的拼写。要测试一下,必须按位和(&)应用常量,而不仅仅是将值与常量进行比较:

if (byte & 0b00100000)    /* note: 0b00100000 is a gcc extension */

或:

if (byte & 0x20)          /* or byte & 32, or byte & (1 << 5), etc. */