H8CPUのビット入力の使用法
Copyright(C) 13May2002
coskx
はじめに
この文書はH8CPUでスイッチの状態(ONかOFFか)を入力するにはどうしたらよいかを解説しています。対象はH8CPUを使ったCPUボードのAKI-H8になっていますが,その他のCPU等でもその電流仕様を理解すれば使えるようになっているはずです。
【1】ビット入力
H8CPUで特定のポートにつながっているピンに0Vまたは5Vを接続し,そのポートを検査すると,あるビットが0または1になります。
例えばCPUの18番ピンに0Vまたは5Vを接続するとポート4の第0ビットから0または1を読み出すことが出来ます。
AKI-H8では,CPUの18番ピンに結線されているコネクタ1の31番ピンに0Vまたは5Vを接続するとよい。
このときの様子を表にすると表1.1のようになる。
図1.1 CPUの18番ピンに0Vまたは5Vを入力しているところ
表1.1 「コネクタのピン」および「CPUのピン」と「ポートのビット」の関係
コネクタ1の31番 | CPUの18番ピン | ポート番号とビット番号の表記 | Cプログラムでの表記例 |
0ボルトを与える | 0ボルト | ポート4の第0ビットに0が見える | if (P4.DR.BIT.B0==0) {.... |
5ボルトを与える | 5ボルト | ポート4の第0ビットに1が見える | if (P4.DR.BIT.B0==1) {.... |
注意:CPUの18番ピンは測定が難しいので測定しないこと
注意:測定にはオシロスコープあるいはディジタルテスタ等を用いること
補足:P4.DRはP4のデータレジスタであり8ビット構成である。.BIT.B0はその第0ビットを表す。
【2】ビット入力の方法
先の例のようなビット入力を行なうには,そのビットを入力用に初期化しプルアップ設定してからおこなう。
P4.DDRはデータディレクションレジスタ(方向レジスタ)と呼ばれ8ビット構成である。
P4の各ビットごとに方向を定めることが出来,出力にしたい場合は1を入力にしたい場合は0をプログラムの最初に設定する。
P4.DRR=0; /*P4の全ビット入力に設定,本当は第0ビットだけでよい 注意1 */
のように書き,その後で,プルアップ設定(ビットごとに0ならOFF,1ならONに設定される。詳細は後述)
P4.PCR=0xff; /*P4の全ビットプルアップ設定,本当は第0ビットだけでよい 注意2 */
を行ない,その後,
if (P4.DR.BIT.B0==0) {....
あるいは
if (P4.DR.BIT.B0==1) {....
と書いて入力を検査できる。
注意1 AKI-H8ではマザーボード上で,P4の上位4ビットがプッシュスイッチにつながっているため全ビット入力に設定した。
注意2 AKI-H8ではマザーボード上で,P4の上位4ビットがプッシュスイッチにつながっているため全ビットプルアップONに設定した。
【3】スイッチのON-OFF状態の取得の方法
スイッチのON-OFF状態を取得する回路として,まず考えるのは,図3.1のような回路である。この回路で入力したものをCPUでビット入力するとスイッチのON-OFF状態を取得出来そうであるが,これは出来ない。
図3.1 スイッチのON-OFF状態取得回路(これを作ってはいけない)
どうして出来ないかというと,CPUの入力ピンがL(0V),H(5V)を判断するには次のような基準があるからである。
図3.1左でスイッチがON状態では入力電圧は5V(3.5V以上)が保証されるが,OFF状態ではなにも信号がこない状態になり,1.0V以下が保証されない。図3.1右でスイッチがON状態では入力電圧は0Vが保証されるが,OFF状態ではなにも信号がこない状態になり,3.5V以上が保証されない。
表3.1 信号に要求される電圧
信号 |
電圧 |
H |
最低でも3.5V以上 |
L |
最大でも1.0Vまたは0.8V* |
*ポート1,2,3,4,5,6,7,9:1.0V, ポート8,B:0.8V
そこで図3.2のような回路が考えられる。これでも悪くないが,スイッチの切り替え時に入力が不安定になるのが気持ち悪い。
図3.2 三端子スイッチの利用
通常用いられるのは,図3.3の回路である。スイッチがOFFの時CPUの入力ピンには5Vが与えられ,スイッチがONの時CPUの入力ピンには0Vが与えられる。この用途で用いられている抵抗のことをプルアップ抵抗と呼んでいる。通常この抵抗値は10kΩから100kΩが用いられる。図3.4左はスイッチがOFFであるため,電流は流れず,抵抗で電圧降下が起こらないため,5Vが出力されているところを示している。図3.4右はスイッチがONであるため,電流が流れ,抵抗で電圧降下が起こり,0Vが出力されているところを示している。
図3.3 スイッチの通常用いられる接続
図3.4 スイッチにより0Vまたは5Vが出力される様子
図3.4の状態を,電池と抵抗とテスタ(電圧計)を使ってやってみよう。図3.5で抵抗を10kΩくらいのものを使うと,左図では電圧計はほぼ電池の電圧を指し,右図は電圧計は0Vを指す。(右図は直感的にわかるが,左図は実際に試して納得しよう。)
図3.5 電池,抵抗,テスタで確かめよう
【4】H8CPUにおけるスイッチのON-OFF状態の取得の方法
H8CPUのポート2,4,5では,スイッチのON-OFF状態の取得等に都合の良い仕掛けがある。図4.1に示すように,図3.3のプルアップ抵抗をCPUが内蔵しており,プルアップ抵抗を有効にするかどうかをソフトウェアで決めることができるようになっている。このプルアップ抵抗の有効無効を設定するのが,プルアップコントロールレジスタ(PCR)で,【2】のところで設定したP4.PCRである。
AKI-H8のマザーボードでは,ディップスイッチ(8ビットスイッチ)がポート2の8つのビットに,プッシュスイッチ(4つ)がポート4の上位4ビットにつながっており,P2.PCRとP4.PCRの対応するビットに1を書き込むことで,プルアップ抵抗を有効にして使用することができる。そのため,マザーボード上のこれらのスイッチにはプルアップ抵抗がついていない。
図4.1 H8CPUのプルアップコントロールの仕組み
ロボットなどの触覚として図4.2のようなリミットスイッチを使用し,H8CPUがリミットスイッチのON-OFF状態を読み込むためには,この機能を利用するとよい。しかし,リミットスイッチのポート割り当てが,P2,P4,P5以外になった場合は,この機能がないため,プルアップ抵抗をつけて接続しなければならない。また図4.3のような非接触で赤外線の反射の有無の検出を用いたフォトセンサ(反射面の存在の有無を検査する。物体の存在の有無を検査する)も同じように接続することが出来る。
図4.2 リミットスイッチ(オムロン)
図4.3 フォトセンサ
【5】AKI-H8におけるディップスイッチ(8ビットスイッチ)のON-OFF状態の取得プログラムの例
/**********************************************************
8ビットスイッチによってLEDのON-OFFを行う
**********************************************************/
#include "3048f.h"
void
initLed00(void)
{
P5.DDR =
0x3;
}
/*
------------------------------------------------- */
/* LET LED ON */
/*
------------------------------------------------- */
/*numberは0または1*/
void
turnOnLed00(short int number)
{
static const
unsigned char mask[]={1,2};
P5.DR.BYTE
|=mask[number];
}
/*
------------------------------------------------- */
/* LET LED OFF */
/*
------------------------------------------------- */
/*numberは0または1*/
void
turnOffLed00(short int number)
{
static const unsigned
char mask[]={0xfe,0xfd};
P5.DR.BYTE
&=mask[number];
}
void
init8BitSW00(void)
{
P2.DDR =
0x00;/*8bitSWのポートを入力に設定*/
P2.PCR.BYTE =
0xff;/*8bitSWのプルアップ設定*/
}
short int check8BitSW00(short int number)
/*8bitsw
0,1,2,3,4,5,6,7の状態を調べる number:0,1,2,3,4,5,6,or
7*/
/*ONなら1、そうでなかったら0を返す*/
{
short int
ret;
static const unsigned char
mask[]={1,2,4,8,0x10,0x20,0x40,0x80};
if
(P2.DR.BYTE&mask[number]) ret=0;
else
ret=1;
return
ret;
}
main()
{
initLed00();
init8BitSW00();/*8bitSWの初期化*/
while(1)
{
if (check8BitSW00(0)) {
/*8bitSWの1がONの時*/
turnOnLed00(0);
turnOnLed00(1);
} else if
(check8BitSW00(1)) {
/*8bitSWの2がONの時*/
turnOnLed00(0);
turnOffLed00(1);
} else if
(check8BitSW00(2)) {
/*8bitSWの3がONの時*/
turnOffLed00(0);
turnOnLed00(1);
} else
{
turnOffLed00(0);
turnOffLed00(1);
}
}
}