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()上記の関数を 2 番目のファイルの最後に追加してみてください(setup()およびloop()関数が定義された後)。main() を一番上に置きたい場合は、関数を定義する前に、関数プロトタイプを使用して関数を宣言する必要があります。または、後者のコード サンプルを独自のファイルに移動し、ヘッダーを付けることをお勧めします。

main.c

#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_プレフィックスは便利です。他の OO 言語に精通している場合、これは名前空間またはクラス プレフィックスの概念に似ています。setup()loop()

まばたき.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 に答える