1

我正在 Arduino 中进行寄存器级编程。目标是使用计时器编写我自己的延迟逻辑。这是代码:

#include<avr/io.h>

int main()
{
    DDRB = (1<<PORTB5);
    TCCR1B = (1<<CS12);
    while(1)
    {
        if(TCNT1 >= 31250)
        {
            PORTB ^= (1<<PORTB5);
            TCNT1 = 0;
        }
    }
    return 0;
}

上面的程序是让Arduino在不使用延迟功能的情况下引入延迟并且它工作正常。但是看看下面的代码。

#include<avr/io.h>

void setup()
{
    DDRB = (1<<PORTB5);
    TCCR1B = (1<<CS12);
}

void loop()
{
    if(TCNT1 >= 31250)
    {
        PORTB ^= (1<<PORTB5);
        TCNT1 = 0;
    }
}

当我这样写时,程序正在编译,但 Arduino 中没有闪烁。与上述代码类似的代码运行正常时可能会出现什么问题?

#include <util/delay.h>

void setup()
{
    DDRB = (1<<PORTB5);
}

void loop()
{
    PORTB ^= (1<<PORTB5);
    _delay_ms(500);
}
4

1 回答 1

2

这看起来像 C,尤其是#include <avr/io.h>在顶部和使用main()函数的情况下。你是用 avr-gcc/AVRstudio 编译它还是打算用 Arduino IDE 写一个草图?

假设您正在尝试编写 C,您的后一个文件是为 Arduino IDE 编写的,它隐含包含一个main()函数,该函数执行以下操作:

int main()
{
  setup();
  while(1) {
    loop();
  }
}

这似乎是您后面的代码示例所期望的环境。main()尝试在第二个文件的底部添加上述函数(在定义setup()andloop()函数之后)。如果您想在顶部使用 main(),则需要在定义函数之前使用函数原型声明函数。或者,更好的是,将后面的代码示例移动到它自己的文件中并给它一个标题:

主程序

#include "blink.h"

int main(void)
{
  blink_setup();
  while(1) {
    blink_loop();
  }
}

眨眼.h

#ifndef BLINK_H  // Include guards prevent this file from being duplicated
#define BLINK_H

void blink_setup(void);  // blink_ prefix allows other modules to use comm
void blink_loop(void);

#endif

#ifndef ... #define ... #endif 结构,称为包含保护,可以防止在编译中多次包含此文件时出现错误,如果其他.h文件引用它,则很容易发生这种情况。blink_前缀很有用,因为和setup()loop()通用名称,可能被其他模块使用。如果您熟悉其他 OO 语言,这将类似于命名空间或类前缀的概念。

眨眼.c

#include <avr/io.h>
#include "blink.h"

void setup()
{
   DDRB = ( 1 << PORTB5 );
   TCCR1B = ( 1 << CS12 );
}

void loop()
{
   if( TCNT1 >= 31250 )
   {
      PORTB ^= ( 1 << PORTB5 );
      TCNT1 = 0;
   }
}

请注意,我在此文件的顶部包含了 blink.h,使用"引号而不是括号,因为它是本地文件而不是系统文件。这会导致函数声明出现在文件的顶部,以便(例如)即使尚未定义它setup()也可以调用。loop()

除了那个环境问题,你的代码看起来应该可以工作。我更喜欢多一点的空白;我已经在我的代码示例中添加了它,但除此之外,一切看起来都很棒!

于 2012-07-12T16:55:49.197 回答