bcm2835 ライブラリ(Ver:1.44)を使って、Raspberry Piで動作するSPI通信のプログラムを作成しました。SPIの設定は、InとOutを接続した簡単なものなので、特にSPIインタフェースを持つデデバイスを準備する必要はありません。実行したRaspberry Piのバージョンを次に示します。
Linux raspberrypi 3.18.0-trunk-rpi #1 REEMPT Debian 3.18.5-1~exp1+rpi16 (2015-03-28) armv6l GNU/Linux
Raspberry PiでのSPI通信の動作環境構築
初期の状態では、SPI通信がOFFになっているので、次のコマンドでSPIを有効にします。コマンドを入力すると選択画面が表示されるので、表示に従って選択していきます。
sudo raspi-config
その後、再起動します。
$ sudo reboot
再起動後、下のコマンドでspidev0.0、0.1が表示されているか確認します。
$ ls /dev/spi* /dev/spidev0.0 /dev/spidev0.1
なお、2014年までの Raspbian では、/etc/modprobe.d/raspi-blacklist.conf を使って SPI の有効/無効 を切り替えるようになっていましたが、2015-01-31 リリースからは、より汎用的な Device Tree という仕組みが導入されたのに伴い、SPI のペリフェラル機能の有効化方法が変わり、raspi-blacklist.confへの設定はなくなりました。
lsmodコマンドを用いて、SPI 関連のモジュール(spidev、spi_bcm2708)が組み込まれていることを確認します。
# lsmod Module Size Used by snd_bcm2835 18961 0 snd_pcm 76716 1 snd_bcm2835 snd_seq 56172 0 snd_seq_device 5605 1 snd_seq snd_timer 19204 2 snd_pcm,snd_seq snd 53596 5 snd_bcm2835,snd_timer,snd_pcm,snd_seq,snd_seq_device soundcore 5579 1 snd spidev 6533 0 spi_bcm2708 6578 0
SPIテストプログラムによる動作確認
プログラムを実行する前に、SPIのinとoutを接続してループ状態にします。bcm2835 ライブラリを用いたSPI通信では、SPIの設定用の関数群が提供されています。また実際の送受信には、bcm2835_spi_transfer関数を使用します。
SPIテストプログラム「spi.c」
#include <bcm2835.h> #include <stdio.h> int main(int argc, char **argv) { if (!bcm2835_init()) return 1; bcm2835_spi_begin(); bcm2835_spi_setBitOrder(BCM2835_SPI_BIT_ORDER_MSBFIRST); // The default bcm2835_spi_setDataMode(BCM2835_SPI_MODE0); // The default bcm2835_spi_setClockDivider(BCM2835_SPI_CLOCK_DIVIDER_65536); // The default bcm2835_spi_chipSelect(BCM2835_SPI_CS0); // The default bcm2835_spi_setChipSelectPolarity(BCM2835_SPI_CS0, LOW); // the default uint8_t send_data = 0x23; uint8_t read_data = bcm2835_spi_transfer(send_data); printf("Sent to SPI: 0x%02X. Read back from SPI: 0x%02X.\n", send_data, read_data); if (send_data != read_data) printf("Do you have the loopback from MOSI to MISO connected?\n"); bcm2835_spi_end(); bcm2835_close(); return 0; }
SPIプログラムのビルドは次のコマンドを使用します。
$ gcc -o spi spi.c -l bcm2835
SPIプログラムの実行は次のように行います。
$ sudo ./spi Sent to SPI: 0x23. Read back from SPI: 0x23.
試しに、ループ状態を解除すると次のメッセージが表示される。
$ sudo ./spi Sent to SPI: 0x23. Read back from SPI: 0x00. Do you have the loopback from MOSI to MISO connected?