内蔵RC発振器でArduinoを動かす…optiboot編
ATMega328P搭載Arduinoを内蔵RC発振器(8MHz)で動作させる、optiboot編です。
ここではArduino IDE Ver1.0以上を対象にしています。
注:IDE Ver1.6で確認したところ、コンパイラの最適化が異なるようで512バイト以下に収まりませんでした。optibootをコンパイルする場合はVer1.0.5をダウンロードし、そこでこのページに従ってコンパイルすれば大丈夫のようです。
変更するところ
変更点としては以下のふたつです。
- ヒューズビットで、クロック元の選択をする。
- 8MHz対応のブートローダー に書き換える。
このoptiboot編では、一度準備しておけばあとはAVR Studio等を使わず、Arduino IDEから変更できるようにしてみました。
ブートローダーの準備
8MHz用のブートローダー(optiboot)を準備します。以下はMacを使った例です。Windowsの場合は適宜ディレクトリ構成等を読み替えて下さい。
Arduinoアプリの中身を開き(アプリケーションアイコンを右クリックして「パッケージの内容を表示」を選択)、Contents→Resources→Java→hardware→arduino→bootloaders→optibootと開きます。その中にあるMakefileをテキストエディタで開き、atmega328_int8という定義を追加します。ほとんどはatmega328用の定義と同じですが、クロック周波数とヒューズビットの設定が異なります。
(前略) atmega328: TARGET = atmega328 atmega328: MCU_TARGET = atmega328p atmega328: CFLAGS += '-DLED_START_FLASHES=3' '-DBAUD_RATE=115200' atmega328: AVR_FREQ = 16000000L atmega328: LDSECTIONS = -Wl,--section-start=.text=0x7e00 -Wl,--section-start=.version=0x7ffe atmega328: $(PROGRAM)_atmega328.hex atmega328: $(PROGRAM)_atmega328.lst atmega328_isp: atmega328 atmega328_isp: TARGET = atmega328 atmega328_isp: MCU_TARGET = atmega328p # 512 byte boot, SPIEN atmega328_isp: HFUSE = DE # Low power xtal (16MHz) 16KCK/14CK+65ms atmega328_isp: LFUSE = FF # 2.7V brownout atmega328_isp: EFUSE = 05 atmega328_isp: isp // このあたりに以下を追加 atmega328_int8: TARGET = atmega328_int8 atmega328_int8: MCU_TARGET = atmega328p atmega328_int8: CFLAGS += '-DLED_START_FLASHES=3' '-DBAUD_RATE=115200' atmega328_int8: AVR_FREQ = 8000000L atmega328_int8: LDSECTIONS = -Wl,--section-start=.text=0x7e00 -Wl,--section-start=.version=0x7ffe atmega328_int8: $(PROGRAM)_atmega328_8m.hex atmega328_int8: $(PROGRAM)_atmega328_8m.lst atmega328_isp_int8: atmega328_int8 atmega328_isp_int8: TARGET = atmega328 atmega328_isp_int8: MCU_TARGET = atmega328p # 512 byte boot, SPIEN atmega328_isp_int8: HFUSE = DE # Int RC OSC 8MHz 16KCK/14CK+65ms atmega328_isp_int8: LFUSE = E2 # 2.7V brownout atmega328_isp_int8: EFUSE = FD atmega328_isp_int8: isp (以下略)
あとはこれをMakeします。赤文字がコマンド入力部分。まずはコンパイラのパスを環境変数に登録しておいて、Makeするだけです。以下はArduionoアプリケーションをシステム標準であるApplicationsフォルダ(日本語環境なら「アプリケーション」)に入れてる場合です。
$PATH=$PATH:/Applications/Arduino.app/Contents/Resources/Java/hardware/tools/avr/bin/ $cd /Applications/Arduino.app/Contents/Resources/Java/hardware/arduino/bootloaders/optiboot/ $make atmega328_int8 make atmega328_int8 avr-gcc -g -Wall -Os -fno-inline-small-functions -fno-split-wide-types -mshort-calls -mmcu=atmega328p -DF_CPU=8000000L '-DLED_START_FLASHES=3' '-DBAUD_RATE=115200' -c -o optiboot.o optiboot.c avr-gcc -g -Wall -Os -fno-inline-small-functions -fno-split-wide-types -mshort-calls -mmcu=atmega328p -DF_CPU=8000000L '-DLED_START_FLASHES=3' '-DBAUD_RATE=115200' -Wl,--section-start=.text=0x7e00 -Wl,--section-start=.version=0x7ffe -Wl,--relax -Wl,--gc-sections -nostartfiles -nostdlib -o optiboot_atmega328_8m.elf optiboot.o avr-size optiboot_atmega328_8m.elf text data bss dec hex filename 500 0 0 500 1f4 optiboot_atmega328_8m.elf avr-objcopy -j .text -j .data -j .version --set-section-flags .version=alloc,load -O ihex optiboot_atmega328_8m.elf optiboot_atmega328_8m.hex avr-objdump -h -S optiboot_atmega328_8m.elf > optiboot_atmega328_8m.lst rm optiboot.o optiboot_atmega328_8m.elf $
これで、「optiboot_atmega328_8m.hex」というファイルが作成されます。
ボードの定義を書き換え
次にボードの定義に8MHz版の基板を追加します。定義は「uno8」としました。Contents→Resources→Java→hardware→arduinoの中にある「board.txt」に、以下を追加します。ほとんどはUNOの定義と同じですが、ヒューズビットの定義、ブートローダーのファイル名、CPUのクロック数が異なります。
uno8.name=Arduino Uno Int 8MHz uno8.upload.protocol=arduino uno8.upload.maximum_size=32256 uno8.upload.speed=115200 uno8.bootloader.low_fuses=0xe2 uno8.bootloader.high_fuses=0xde uno8.bootloader.extended_fuses=0x05 uno8.bootloader.path=optiboot uno8.bootloader.file=optiboot_atmega328_8m.hex uno8.bootloader.unlock_bits=0x3F uno8.bootloader.lock_bits=0x0F uno8.build.mcu=atmega328p uno8.build.f_cpu=8000000L uno8.build.core=arduino uno8.build.variant=standard
これを保存後にArduino IDEを立ち上げると、ToolsメニューのBoardに「Arduino Uno Int 8MHz」が追加されます。それを選択し、AVRISP mk2等のプログラマを接続し、IDEからブートローダーの書き込みを行えば、内蔵RCを使った8MHzのArduinoとして動作します。