LoginSignup
1
0

mruby/cペリフェラルライブラリのSTM32マイコンへの実装 Chapter01: 準備編

Last updated at Posted at 2024-06-21

しまねソフト研究開発センター(略称 ITOC)にいます、東です。

今回から数回に分けて、STM32マイコン評価ボード Nucleo-F401REに、mruby, mruby/c共通ペリフェラルインターフェースガイドラインに沿ったライブラリを実装する作業をします。作業を進めるにあたり、どのように行ったのかを記事にしてみようと思います。

目標

最初にプロジェクト全体の目標を、以下のように決めました。

  • mruby, mruby/c共通ペリフェラルインターフェースガイドラインを、Nucleo-F401RE に実装する
  • ユーザーは、mrubyのバイトコードだけを転送するだけで使える環境を用意する

mruby/c プログラムを動作させるやり方はいくつかありますが、今回は、VMをあらかじめ書き込んだボードに mrubyバイトコードだけを転送し動かす方法を採用します。自由度は少ないので最終的なプロダクトには物足りないケースが多いかと思いますが、POCや教育現場など、ちょっと試してみたい場合にはとても便利に使う事ができます。

実現可能性調査、及び技術の選択

この目標を達成するために、どのような手段をとれば良いのかを決める必要があります。場合によっては、実現難易度などを考慮して、あきらめた方が良いと判断する部分がないかを検討します。
また、私の役割上、第3者が再現しやすい方法の採用が好ましく、そういったことも考慮の対象にしています。

開発ツール・環境

開発環境は、ST社製 STM32CubeIDE を使います。
Eclipseベースなので、動作が緩慢で嫌がる声も多く聞きます(個人の感想です)が、無料で利用できて多機能、かつメーカー純正という安心感から、こちらを選定します。

ピンアサインの自由度

CubeIDEのピンアサイン、コード自動生成機能は、とても便利に使える反面、今回のように上位層(mruby/c)からピンアサインの指示、変更の要求とは、折り合いがつけにくそうです。ですので今回は、各ペリフェラルが利用する物理ピンは固定にしようと思います。

ペリフェラルへのアクセス

ペリフェラルの使用方法は、現時点だと

  1. ST社製 HALライブラリを使う
  2. ST社製 LLライブラリを使う
  3. レジスタを直接アクセスして使う

この3つの方法が考えられます。それぞれメリットデメリットがあります。

移植性 良い 1 <---> 3 悪い
フットプリント 大きい 1 <---> 3 小さい
速度 遅い 1 <---> 3 速い
将来にわたって使えるか 若干不安 1 <---> 3 問題なし

ST社には非常に多くの STM32 シリーズがあります。今回のボードに使われている STM32F401RET6 は、Flashが512KBと大きく、また、他のマイコンにも容易に移植できる方がより良いだろうとの判断から、HALライブラリを使う事にしました。HALライブラリは、便利に使える分、抽象度も高いので、要求をフルスペックで満たしてくれることができないかもしれません。それは、今後進める上で都度判断します。

フラッシュメモリの自己書き換え

今回は、VMをあらかじめ書き込んだボードに mrubyバイトコードだけを転送し動かす方法を採用します。そのため、書き込みプログラムが動作中に転送したバイトコードをフラッシュメモリに書き込む方法が用意されている必要があります。
つまり、

  • Flash上でコードを実行中に、Flashに書き込むことができるか
     (できない場合は、書き込みプログラムをRAMに移してから実行させるなど、面倒な手順が必要になる)
  • Flashの一部領域のみ、消去、書き込みができるか
     (あらかじめ書き込まれたVMを消さないようにする)
  • 書き込んだ内容は、リニアなメモリとしてアクセスできるか
     (mruby/c VMがこれを要求)

等を検討します。
調査の結果、これもHALライブラリが用意してあるようなので、大丈夫そうです。

作業手順

では、実際の作業に入ります。

CubeIDEによるプロジェクトの作成

別記事「mruby/cをSTM32マイコンで動かす Chapter01: 環境構築」 に書いた方法と同様の手順でプロジェクトを作ります。併せて同記事連載全てで説明した通りの方法で、mruby/cポーティングを終えた状態からスタートさせます。

ペリフェラル及び利用するピンの割り付け

ガイドラインで定められたペリフェラルは、以下の通りです。

これら全てを、あらかじめ最初にアサインします。
基板上のシルクなどを参考にしながら、今回は以下のように決めました。

CN pin SILK GPIO Usage (PWM)
CN5 10 SCL/D15 PB8 I2C1_SCL
CN5 9 SDA/D14 PB9 I2C1_SDA
CN5 8 AVDD AVDD ---
CN5 7 GND GND ---
CN5 6 SCK/D13 PA5 (LED2)
CN5 5 MISO/D12 PA6 TIM3_CH1
CN5 4 PWM/MOSI/D11 PA7 TIM3_CH2
CN5 3 PWM/CS/D10 PB6 TIM4_CH1
CN5 2 PWM/D9 PC7 TIM3_CH2
CN5 1 D8 PA9 UART1_TX TIM1_CH2
CN pin SILK GPIO Usage (PWM)
CN9 8 D7 PA8 TIM1_CH1
CN9 7 PWM/D6 PB10 TIM2_CH3
CN9 6 PMW/D5 PB4 TIM3_CH1
CN9 5 D4 PB5 TIM3_CH2
CN9 4 PWM/D3 PB3 (SWO) TIM2_CH2
CN9 3 D2 PA10 UART1_RX TIM1_CH3
CN9 2 TX/D1 PA2 (UART2_TX)
CN9 1 RX/D0 PA3 (UART2_RX)
CN pin SILK GPIO Usage (PWM)
CN8 1 A0 PA0 AD0 TIM2_CH1
CN8 2 A1 PA1 AD1 TIM2_CH2
CN8 3 A2 PA4 AD4
CN8 4 A3 PB0 AD8 TIM3_CH3
CN8 5 A4 PC1 AD11
CN8 6 A5 PC0 AD10
CN pin SILK GPIO Usage (PWM)
CN10 14 PA11 UART6_TX TIM1_CH4
CN10 16 PA12 UART6_RX
CN7 1 PC10 SPI3_SCK
CN7 2 PC11 SPI3_MISO
CN7 3 PC12 SPI3_MOSI

ADCは、シルクに書かれているとおりに、CN8の6チャネルを使います。
UARTは、ボード設計で利用が決められた UART2のほか、UART1, UART6 の3つをアサインします。
I2C, SPI は、それぞれ1つずつ、アサインしておきます。

STM32mrbc01-スクリーンショット 2024-06-21 15.02.39.png

多少、コンフリクトしていると IDE が文句を言っていますが、後々問題が出たらそのときに対処します。

タイマーの設定

次にPWMに使用するタイマーです。
PWM出力でピンが固定されると、単なるGPIOの入力/出力をしたい場合と被ってしまって困りますので、IDEからの利用は無理かなと考えていたところ、IDEの設定に、「PWM Generation No Output」 という選択肢がありました。恐らく タイマーの多段接続に利用する内部的な設定項目だと思いますが、ちょうど良いのでこれを利用します。

タイマーは、先の表のPWM欄に示したユニット、チャネルを、PWM Generation No Output モードに設定します。

(例:TIM2)
STM32mrbc01-スクリーンショット 2024-06-21 16.13.57.png

テストビルド

ここまでで、IDEでのペリフェラル割り付けは一旦終了です。保存するとコードを自動生成するか聞いてくるので、Yesで自動生成させます。
プロジェクトをビルドし、エラー無く終了するか確認しておきます。

おわりに

ここまでで、準備は終了です。
次回から実際に、GPIOクラスを実装します。

1
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
0