今回は、使用する関数が多くなるので、これから作成するモーター制御プログラムの概念図を用意しました(画像4)。
この図からも分かるように、モーター制御といっていますが、実際にマイコンが制御しているのは、モータードライバICです。モータードライバICに対し、MTUからパルスを出し、スピードや正転逆転の指示を送ることでモーターを駆動させています。
モータードライバには、3つの関数を作ります。モーター励磁関数「drv_mtr_pw」では、モーターの励磁のON/OFFを行います。モーターを動かす前にON、停止させた後にOFFの指令を出します。
モータードライバ(左右)関数「drv_mtr」は2つの引数を持ち、左右のモーターの「停止」「前進」「後進」を指定します。また、MTUカウントの開始/停止も行っています。
左右のモーターのMTU周期を設定する関数「drv_mtu」は、MTUから出すパルスの周期を設定し、モーターのスピードを調整します。これら3つの関数は、コントローラ層にある関数から呼び出されます。
移動距離を制御するために、割り込み処理を使っています。MTUがパルスを出すたびに割り込みが発生し、割り込み処理の中で左右のモーターのステップ数をカウントしています。そのためのグローバル変数が用意されており、コントローラ層のモーター処理wait関数「ctrl_mtr_wait」がこのグローバル変数を読んで、指定されたステップ数に至るまで待ちます。その間、MTUはパルスを出し続け、マイクロマウスは指定された距離を走るのです。
| 参考記事: | |
|---|---|
| ⇒ | 階層構造を意識して、信頼性の高いプログラムを組もう! |
モーター制御プログラムのイメージがつかめたら、いつものようにプログラムを作成していきましょう。今回はソースコードが長くなるので、ヘッダーに記述するコードは掲載していません。本稿の最後に紹介するダウンロードファイルで確認してください。
まず、「init.c」にモーター関連のI/Oポートの初期化(ソースコード2)と、MTUの諸設定を追加します(ソースコード3)。
/************************************************/
/* I/Oポート初期化 (init_io) */
/************************************************/
/* ポートを初期化する */
/************************************************/
void init_io(void)
{
(…… 中略 ……)
//モーター励磁
PFC.PBIORL.BIT.B5 = 1; //PB5を出力に設定
//モータードライバ
PFC.PEIORL.BIT.B8 = 1; //PE8を出力に設定(右Clock)
PFC.PEIORL.BIT.B9 = 1; //PE9を出力に設定(右CWCCW)
PFC.PEIORL.BIT.B10 = 1; //PE10を出力に設定(左CWCCW)
PFC.PEIORL.BIT.B12 = 1; //PE12を出力に設定(左Clock)
//モーターMTU
PFC.PECRL3.BIT.PE8MD = 1; //MTU端子に設定
PFC.PECRL4.BIT.PE12MD = 1; //MTU端子に設定
//モーター励磁OFF
PB.DR.BIT.B5 = 1; //モーター励磁をOFFにする
}
/************************************************/
/* MTU初期化 (init_mtu) */
/************************************************/
/* MTUを初期設定する */
/* MTU22:ブザー用 */
/* MTU23:右モーター用 */
/* MTU24:左モーター用 */
/************************************************/
void init_mtu(void)
{
(…… 中略 ……)
//右モーター用MTU設定
MTU23.TCR.BIT.TPSC = 1; //MTU23の動作クロックは24/4=6MHz
MTU23.TCR.BIT.CCLR = 1; //TGRAコンペアマッチでカウンタクリア
MTU23.TIOR.BIT.IOB = 2; //初期出力0コンペアマッチ1出力
MTU23.TIOR.BIT.IOA = 1; //初期出力0コンペアマッチ0出力
MTU23.TGRA = 22000; //周期(MIN_SPEED(100)の周期)
MTU23.TGRC = 22000; //周期のバッファ
MTU23.TGRB = 50; //パルス幅
MTU23.TMDR.BIT.MD = 2; //PWMモード1に設定
MTU23.TMDR.BIT.BFA = 1; //TGRCをTGRAのバッファレジスタとして使用
MTU23.TIER.BIT.TGIEB = 1; //TGRAコンペアマッチでの割り込み許可
INTC.IPRE.BIT._MTU23G = 0xd; //割り込み優先度を設定
//左モーター用MTU設定
MTU24.TCR.BIT.TPSC = 1; //MTU24の動作クロックは24/4=6MHz
MTU24.TCR.BIT.CCLR = 1; //TGRAコンペアマッチでカウンタクリア
MTU24.TIOR.BIT.IOB = 2; //初期出力0コンペアマッチ1出力
MTU24.TIOR.BIT.IOA = 1; //初期出力0コンペアマッチ0出力
MTU24.TGRA = 22000; //周期(MIN_SPEED(100)の周期)
MTU24.TGRC = 22000; //周期のバッファ
MTU24.TGRB = 50; //パルス幅
MTU24.TMDR.BIT.MD = 2; //PWMモード1に設定
MTU24.TMDR.BIT.BFA = 1; //TGRCをTGRAのバッファレジスタとして使用
MTU24.TIER.BIT.TGIEB = 1; //TGRAコンペアマッチでの割り込み許可
INTC.IPRF.BIT._MTU24G = 0xc; //割り込み優先度を設定
//
MTU2.TOER.BYTE=0xff; //MTU出力端子を出力許可する
//
MTU2.TSTR.BIT.CST4 = 0; //タイマストップ
MTU2.TSTR.BIT.CST3 = 0; //タイマストップ
(…… 中略 ……)
}
続いて「Mouse2012.h」に、モーターを制御するのに必要なグローバル変数を“volatile”修飾子を付けて宣言します。volatile修飾子を付け忘れた状態でビルドすると、コンパイラがプログラムを最適化してしまい、その結果、思わぬエラーを引き起こすので注意してください(ソースコード4)。
//グローバル変数 volatile int G_TimerCount; //1msごとにカウントアップされる変数 volatile int G_StepCountR; //右モーター 1stepごとにカウントアップされる変数 volatile int G_StepCountL; //左モーター 1stepごとにカウントアップされる変数
モーターのMTU割り込みに必要な処理を「intrpt.h」と「intrpt.c」に追加します(ソースコード5)。
/************************************************/
/* 右モーターMTU割り込み処理 (int_mtr_r) */
/************************************************/
/* 右モーターが1ステップ進むごとの割り込み */
/************************************************/
void int_mtr_r(void)
{
//右モーターが1ステップ進むごとの割り込み
MTU_R_INT_F = 0; //フラグクリア
//
G_StepCountR++; //ステップ数をカウント
}
「intprg.c」に「intrpt.c」で作った関数を登録し、MTUの割り込み処理が呼び出されるようにします(ソースコード6)。
// 113 MTU2_3 TGIB3
//右モーターのMTU割り込み
//void INT_MTU2_3_TGIB3(void){/* sleep(); */} <= コメントアウト
extern void int_mtr_r(void);
void INT_MTU2_3_TGIB3(void){
int_mtr_r();
}
(…… 中略 ……)
// 121 MTU2_4 TGIB4
//void INT_MTU2_4_TGIB4(void){/* sleep(); */} <= コメントアウト
//左モーターのMTU割り込み
extern void int_mtr_l(void);
void INT_MTU2_4_TGIB4(void){
int_mtr_l();
}
プログラムの概念図があると、イメージがつかみやすいですね!
概要設計のときに、こうやって各モジュールの関係と役割を明確にしておくんだ。頭の中で考えているだけだと人に説明できないからね。特に、チームで開発するような場合は絶対に必要だよ。
なるほど〜。
じゃあ、ドライバとコントローラを作るよ。
はいっ!
Copyright © ITmedia, Inc. All Rights Reserved.
組み込み開発の記事ランキング
コーナーリンク