2013年9月1日日曜日

MCU Gear のプログラム:その2 mbed FRDM KL25Z 編

MCU Gear ® を使ったプログラムの説明などを書いています

MCUGear® のサンプルプログラムを参考に簡単な動作説明をします。
多少説明が間違っているかもしれません、その場合予告なく修正する可能性がありますのでご容赦ください。
かなり詳しく説明したつもりです。パッと見、分量が多い様ですが当たり前のことも多く書いています。気長に読んでみてください。
また、ここにも細かな注意点が書いてあります。

まずはスイッチを読んでLEDを光らせるというところをやりたいと思います。

目標は動画のような雰囲気です。
KL25Zはベースボードの下のマイコンボードに取り付けます。動画はイメージです


回路のイメージは以下のような雰囲気です。青い小さな四角は抵抗です。LEDに+3.3Vか+5V(ユニバーサルモジュールは5Vトレラント入力対応です)をかけて抵抗は220Ω、スイッチに1KΩ使ってます。LEDの種類によっては変化しますので適宜計算してみてください。

この回路を実現するための再配線をしてみましょう。




まず設定の確認をしましょう。
mbedのwebコンパイラはデバイスを選択できるようにコンパイラ画面右上にデバイス選択ボタンが用意されています。それを押してKL25Zを選んでください。

次にMCUGearライブラリのcommon.hを使いたいデバイスと合わせてください。
//select your mbed--------------------------------------------
//#define LPC1768_mbed
#define FS_KL25Z


最も基本的なユニバーサルモジュール2だけを使ってみましょう。
KL25Zのサンプルコードのmain.c を順番に見ていきましょう。

#include "MCUGearBase.h"

#include "MCUGear.h"
#include "common.h"
MCUGearのライブラリがあることを確認して、プログラムをインクルードしています。

MCUGear Uni2M(PTE0, PTE1, N_VDD_VDD_VDD,8);
これはMCUGearのモジュールを定義する部分です
MUCGear クラス(色々と設定情報などの塊と考えておいてください。)をUni2M という名前で定義して生成します。
かっこ内は
PTE0, PTE1 : I2Cの端子(専用のマイコンボードを使う限りはこのままです。)
N_VDD_VDD_VDD : はモジュールの下の設定したアドレスのを入れます。AD2 AD1 AD0 の順番に書き込んでください。VDD = +3V3、 VSS = GND と定義されているので覚えておいてください。また「N_」は コントロール用のI2CデバイスPCA9674、「A_」は  コントロール用のI2CデバイスPCA9674Aを表しています。
※A_VDD_VSS_VSSはベースボードのアドレスとかぶってしまうので設定できません。
8 :これはこのモジュールで使用するピン数を指定します。今回の回路では8ピン必要ですので8と入れてます。




DigitalOut Dout(PTA13);

DigitalOut Dout1(PTA1);
DigitalOut Dout2(PTA2);
DigitalOut Dout3(PTD4);
DigitalOut Dout4(PTA12);
DigitalOut Dout5(PTA4);
DigitalIn Din1(PTB0);
DigitalIn Din2(PTB1);
ここではKL25Z本来の端子の設定を行っています。

void IOUni2M(MCUGear *mcugear);    
プロトタイプ宣言 「こんな関数がここでは用意されてますよ」とあらかじめ宣言して浸透させておくというイメージで考えてください。

initBase(); //initialize Baseboard
これはベースボードの初期化をするところです。興味のある方は中身をのぞいてみてください。とりあえずおまじないだと思って通り過ぎてください。

IOUni2M(&Uni2M);
ここでは、先ほど生成したUni2M のIOの設定をしています。
では、IOUni2M 関数内部を見てみましょう。

void IOUni2M(MCUGear *mcugear){

    uint8_t fio[12];

    // detect SHM
    mcugear->detect_module(fio);
    
    //PTA1, PTA2, PTD4, PTA12, PTA4, PTA5, PTC8
    mcugear->savePinSetting(0, IO_MBED_PTB0, IO_REG_IN_DIR, fio[0]);
    mcugear->savePinSetting(1, IO_MBED_PTB1, IO_REG_IN_DIR, fio[1]);
    mcugear->savePinSetting(2, IO_MBED_PTA13, IO_REG_OUT_DIR, fio[2]);
    mcugear->savePinSetting(3, IO_MBED_PTA1, IO_REG_OUT_DIR, fio[3]);
    mcugear->savePinSetting(4, IO_MBED_PTA2, IO_REG_OUT_DIR, fio[4]);
    mcugear->savePinSetting(5, IO_MBED_PTD4, IO_REG_OUT_DIR, fio[5]);
    mcugear->savePinSetting(6, IO_MBED_PTA12, IO_REG_OUT_DIR, fio[6]);
    mcugear->savePinSetting(7, IO_MBED_PTA4, IO_REG_OUT_DIR, fio[7]);

#ifdef BOOST_MODE
    mcugear->makeCircuit();
#endif

}


オリジナルの設定を作るときは、以下の手順を順番に行ってください。

1、mcugear->detect_module(fio); を使ってモジュールの位置を把握し登録します。配列は8bit のuint8_t 12個の配列を使います。

2、mcugear->savePinSetting(0, IO_MBED_PTB0, IO_REG_IN_DIR, fio[0]);  //input
   ・・・
     mcugear->savePinSetting(2, IO_MBED_PTB1, IO_REG_OUT_DIR, fio[2]);
   ・・・
 は指定したモジュールの0番ピンにKL25Zのどの端子番号を割り振ったかを入れます。最後の IO_REG_OUT_DIR はどの出力ピンを割り振りますという意味です。これが入力ピンであれば IO_REG_IN_DIR と記載してください。
ここでは0と1番にinput 残りはoutputに設定しています。

3、
 #ifdef BOOST_MODE
    mcugear->makeCircuit();
#endif

オーバーヘッドを極力減らし自動化したモードです。(慣れてきてから試してみてください)
MCUGearにはバンクというレイヤーのようなものが存在しています。これは再配線する祭に、あらかじめ決まった配線をベースボードに登録しておき、レイヤーの切り替え命令だけで高速に配線を切り替えるためのものです。Bankは0~7まで設定できます。KL25Zのサンプルプログラムでは自動的に動作させることができますが、多くのモジュールを使うとバンクが足りなくなるので通常モードのモジュールそして動作します。
common.h
#define BOOST_MODE //if you want use BANK System, define this.
を定義すると動きます。
また、バンク部分のプログラムを作り替えるときは、複雑な動きをするので上級者向けです。(「マイコン端子の分岐は出来ない」ということを考えながら使ってください。)



int SW1,SW2;
タクトスイッチの入力信号を一旦保存するための変数です。

while(1){
次にmain関数のループ部分に入ります。
まずモジュールに接続前にIOの状態をどうしたいのかを常に考えましょう。
そのまま接続すると、仮に別のモジュールで同じピンを使っていたら、そのままデバイスに伝えてしまうことになります。事前にIOの状態はHighにしたいので以下のように記述しておきます。

       Dout = 1;
       Dout1 = 1;
       Dout2 = 1;
       Dout3 = 1;
       Dout4 = 1;
       Dout5 = 1;

次にモジュールと接続してみましょう。


 Uni2M.connectModule();
モジュールとマイコンを配線する関数です。先ほどのUni2Mと定義したものを使います。
この処理が終わるとすでにマイコンとユニバーサルモジュールの接続が確立されています。
通常のデジタル回路だと考えてください。

       SW1 = Din1.read();
       SW2 = Din2.read();

まずは0番、1番ピンにスイッチを押すとグランドに落ちるような回路ををブレッドボードにつないでください。GNDで落とすときは適当な抵抗を挟みましょう。

ここでは、0番にP9 と 1番にP10がつながっていて、結果をwhile(1)の前で定義したSW1 とSW2に保存しています。

出力確認のLEDは+3.3Vから抵抗とLEDを取り付け、最後にIOにつなげます。IOがLowになると光る仕組みです。





スイッチ0がGNDに落ちるとLEDが光ります。



       if(SW1 == 1){
            Dout = 1;
            Dout2 = 1;
            Dout3 = 1;
       }else{
            Dout = 0;
            Dout2 = 0;
            Dout3 = 0;
       }


       if(SW2 == 1){
            Dout1 = 1;
            Dout4 = 1;
            Dout5 = 1;
       }else{
            Dout1 = 0;
            Dout4 = 0;
            Dout5 = 0;
       }

wait(1000);等を途中途中に入れると処理の様子をじっくり見れます。


Uni2M.disconnectModule();
最後にモジュールのゲートを閉じる処理をします。


後は同様に
Uni2M.connectModule();

従来のデジタル回路の処理

Uni2M.disconnectModule();





という動きを繰り返すだけです。

0 件のコメント:

コメントを投稿