...

Visual C++によるPPI入門書

by user

on
Category: Documents
19

views

Report

Comments

Transcript

Visual C++によるPPI入門書
チュートリアル
Visual C++によるPPI入門書
www.interface.co.jp
商標/登録商標
本ドキュメントに掲載されている会社名,製品名は、それぞれ各社の商標または登録商標です。
保障の内容と制限
弊社はドキュメント内の情報の正確さに万全を期しています。万一、誤記または誤植等があった
場合、弊社は予告なく改訂する場合があります。ドキュメントまたはドキュメント内の情報に起
因するいかなる損害に対しても弊社は責任を負いません。
製品に含まれるバグ、あるいは製品の供給(納期遅延),性能、もしくは使用に起因する付帯的損害
もしくは間接的損害に対して、弊社に全面的に責がある場合でも、弊社はその製品に対する改良
(正常に動作する)、代品交換までとし、金銭面での賠償の責任は一切負わないものとしますので、
予めご了承ください。
ドキュメント内の図や表は説明のためであり、ユーザ個別の応用事例により変化する場合があり
ます。
著作権,知的所有権
弊社は本製品に含まれるおよび本製品に対する権利や知的所有権を保持しています。
本製品はコンピュータ ソフトウェア(プログラム),図,文章,写真等を含んでいます。
複製の禁止
弊社の許可なく、本製品(ドキュメント含む)の全て、または一部に関わらず、複製,改変等を行う
ことはできません。
責任の制限
弊社は、弊社または再販売者の予見の有無に関わらず、発生したいかなる特別損害,偶発的損害,
間接的な損害,重大な損害について、責任を負いません。
補償の内容
本ドキュメントで使用している弊社製品の補償については、各製品のマニュアルを参照してくだ
さい。
本書の内容の一部または全部を、無断で転載することを禁止します。
本書の内容は、将来予告なく変更することがありますので、予めご了承ください。
© 2001, 2007 Interface Corporation. All rights reserved.
www.interface.co.jp
TUT-0034
改訂履歴
年 月
Ver.
1.1
2007年5月
1.0
2001年3月
改 訂 内 容
●対象型式追加。
●製品紹介削除。
●インストール説明更新。
●技術資料一覧追加。
●フォーマット変更。
新規作成
本チュートリアルをご使用の際は、必ず各製品型式の最新のドキュメント(USER'S
MANUAL,Help)を併せて参照してください。また、最新のドライバソフトウェアをご使用くださ
い。
USER'S MANUAL,ドライバソフトウェアは弊社Web site(www.interface.co.jp)からダウンロードで
きます。(Helpはドライバソフトウェアに含まれています)
-1-
Interface Corporation
TUT-0034
目 次
第1章
1.1
1.2
1.3
第2章
PPI概要
6
ポート ............................................................................................................................................. 6
グループ制御................................................................................................................................. 7
動作モード ..................................................................................................................................... 7
PPI製品のインストール
8
2.1
コンピュータへの設置方法......................................................................................................... 8
2.1.1 デバイスドライバのインストール.................................................................................. 9
■Windows Vistaをご使用の場合 ......................................................................................... 9
■Windows XP Embedded,Windows XP,Windows Server 2003 をご使用の場合............ 12
■Windows 2000 をご使用の場合....................................................................................... 14
2.2 サンプルプログラム,Help,ヘッダファイル,インポートライブラリ,最新情報ドキュメン
トファイルのインストール................................................................................................................ 16
第3章
3.1
3.2
3.3
第4章
Visual C++によるPPI制御
17
ピンアサインメント................................................................................................................... 18
DLLプロシージャ呼び出しによるプログラミング(概要).................................................... 20
PPI製品制御概略 ......................................................................................................................... 20
チュートリアル
21
4.1
モード 0 入力/出力...................................................................................................................... 23
Step1.メインウィンドウ作成...................................................................................................... 24
Step2.DLL関数宣言 ...................................................................................................................... 25
Step3.初期化処理と終了処理...................................................................................................... 28
Step4.モード 0 入出力 .................................................................................................................. 32
4.2 モード1入力............................................................................................................................... 38
Step1.プロジェクトの作成(モード 1 入力側)........................................................................... 40
Step2.モード 1 入力 ...................................................................................................................... 40
Step3.プロジェクトの作成(モード 0 出力側)........................................................................... 46
Step4.モード 0 出力 ...................................................................................................................... 47
4.3 モード1出力............................................................................................................................... 50
Step1.プロジェクトの作成(モード 1 出力側)........................................................................... 53
Step2.モード1出力 ...................................................................................................................... 53
Step3.プロジェクトの作成(モード 0 入力側)........................................................................... 55
Step4.モード 0 入力 ...................................................................................................................... 55
4.4 モード 2 入力............................................................................................................................... 60
Step1.プロジェクトの作成(モード2入力側)........................................................................... 62
Step2.モード 2 入力 ...................................................................................................................... 62
Step3.プロジェクトの作成(モード0出力側)........................................................................... 66
Step4.モード 0 出力 .................................................................................................................... 67
Interface Corporation
-2-
TUT-0034
4.5
モード 2 出力............................................................................................................................... 69
Step1.プロジェクトの作成(モード 2 出力側)........................................................................... 69
Step2.モード 2 出力 ...................................................................................................................... 70
Step3.プロジェクトの作成(モード 0 入力側)........................................................................... 72
Step4.モード 0 入力 ...................................................................................................................... 72
4.6 割り込み処理............................................................................................................................... 77
Step1.プロジェクト作成 .............................................................................................................. 81
Step2.モード1出力(割り込み処理) ........................................................................................... 81
第5章
FbiPpi.DLLリファレンス
87
PpiOpen .......................................................................................................................................... 88
PpiClose .......................................................................................................................................... 88
PpiControl....................................................................................................................................... 88
PpiInputPort.................................................................................................................................... 89
PpiOutputPort ................................................................................................................................. 89
PpiSetEventMask............................................................................................................................ 90
PpiGetEventMask........................................................................................................................... 90
PpiSetEventConfig ......................................................................................................................... 91
PpiGetEventConfig......................................................................................................................... 92
PpiSetTimerConfig......................................................................................................................... 93
PpiGetTimerConfig ........................................................................................................................ 94
PpiGetTimerCount ......................................................................................................................... 95
PpiGetResetInStatus ....................................................................................................................... 95
PpiEventRequestPending ............................................................................................................... 96
PpiCommonGetPciDeviceInfo....................................................................................................... 97
エラーコード一覧 ........................................................................................................................ 98
第6章
6.1
6.2
6.3
8255 PPIコントローラ説明
99
ポートA,B,C................................................................................................................................. 99
グループA制御,グループB制御 ............................................................................................. 99
各ビットの対応......................................................................................................................... 100
技術資料紹介
110
-3-
Interface Corporation
TUT-0034
はじめに
平素は格別のご高配を賜り、厚く御礼申し上げます。本冊子は、初めて弊社PPI製品を利用し、Visual
C++にて制御プログラムの作成を行われる方を対象に、製品の導入からプログラム作成までに関
し説明したものです。プログラム初心者の方が弊社製品をご利用頂き、またVisual C++にてプログ
ラムの開発を行われる際の手助けになればと考えております。
記述する内容に関しましては、基本的なことにとどまっております。
また、弊社Web site(www.interface.co.jp)ではFAQ,製品マニュアル,および本チュートリアル記載の
サンプルプログラムのソース(BPC-0810)の公開を行っておりますので、こちらも併せてご覧頂け
ますと、より一層ご理解を深めて頂けるものと思います。
注意事項
本冊子では、使用する環境をWindows Vista/XP/XP Embedded/Server 2003/2000+Visual C++を想定
し記載しております。
Windows NT/Me/98/95をご利用の場合、I/Oモジュールのインストール方法が本冊子に記載した内
容とは異なりますのでご注意ください。こちらに関しましては、弊社製品マニュアルをご確認く
ださい。
対応OSはI/Oモジュール型式によって異なりますので、対応ソフトウェア(GPC-2746C)のReadme
もしくはHelpでご確認ください。
対象環境
本チュートリアルは以下の制約事項があります。
PCI-2746C
PCI-2747A
対象型式
(PCI)
CPZ-2746
対象型式
(CPZ)
CTP-2746
対象型式
(CTP)
対象ユーザ 制御用電子機器および、コンピュータ等に関して基本的な知識を有している方。
※ 本冊子は上記の弊社製品型式のみに対応しています。
製品の詳細は弊社Web siteを参照してください。
Interface Corporation
-4-
TUT-0034
本チュートリアルを行うにあたり、別途以下の製品が必要となります。
<CTP-2746,PCI-2746Cを使用する場合>
・TNS-9601×1台: 垂直96ピンネジ変換端子台
・ECO-66xx×1本: 96ピンハーフピッチケーブル
<CPZ-2746を使用する場合>
・TBZ-960x×1台: 垂直96ピン変換端子台
・WRZ-66xx×1本: 96ピンハーフピッチコネクタ接続ケーブル
<PCI-2747Aを使用する場合>
SET-LP01(PCI-2747A,TRM-2601*1,CAB-9816ME*2 各一点のセット)が2点必要です。
※1
TRM-2601×2台: 30点スモールタップ端子台
※2
CAB-9816ME×2本: 34ピンフラットコネクタ両端コネクタケーブル(1.6m)
尚、PCI-2747Aは2枚必要になります。
-5-
Interface Corporation
TUT-0034
第1章 PPI概要
PPIとはProgrammable Peripheral Interfaceの略で、コンピュータ(CPU)と周辺機器間の制御とデータ
転送を行うための8255という型番のICのことです。8255は、パラレルI/Oインタフェースデバイス
で、8ビット単位で入出力が行えるポートが3つあり、プログラムによる制御でデータ入力,データ
出力,ステータス信号入力,コントロール信号出力に使用することができます。
Intel 8255(相当品)
(NEC:μPD8255AC-5)
8255は、8ビット単位のデータをパラレル方式で転送できるデバイスで、単なる入出力,単方向の
ハンドシェーク入出力,双方向のハンドシェーク入出力の3つの動作が行えます。そのため、セン
トロニクス・インタフェースといったような、パラレル方式の通信製品として使用することもで
きます。
8255には8ビットの入出力ポートが3個あり、それらのポートの性質をうまく使うことで、通常の
デジタル入出力製品よりもきめ細かなハンドシェーク入出力が行えます。また、先程説明したよ
うに、単なるデジタル入出力としても使用することができます。
その3つの入出力ポート,制御方法,動作について詳しく説明していきます。
1.1 ポート
8255には8ビットの入出力ポートが3個あり、それぞれをポートA,ポートB,ポートCと呼びます。ま
た各ポートごとに独特の性質を持っていますので、ポートの選択によって8255の適応性が生かさ
れます。
ポートA
ポートB
ポートC
入力時 ラッチ入力あるいはバッファ入力動作
出力時 ラッチ出力動作
入力時 ラッチ入力あるいはバッファ入力動作
出力時 ラッチ出力動作
入力時 バッファ入力動作(ラッチされません)
出力時 ラッチ出力動作
ポートCはモードによって2つの4ビットポートに分割して使用することができま
す。また、ポートA,Bのコントロール信号の出力ポート、あるいはステータス信
号の入力ポートとして用いることができます。
ラッチ:変化する入出力信号を特定の時点で、その状態を保持すること。
バッファ:入出力信号を一時的に蓄積すること。
Interface Corporation
-6-
TUT-0034
1.2 グループ制御
8255を使用するにあたっては、入出力ポートをA,B,Cの3つに分けると同時に、ポートAとポートC
の半分、ポートBとポートCの半分といった、2つのグループに分けて考えることもできます。
このとき、それぞれをグループA,グループBと呼びます。
8255
ポート C
ポート A
上位 4 ビット
下位 4 ビット
ポート B
グループ B 制御
グループ A 制御
1.3 動作モード
8255はその使用方法によって次の3つのモードより動作を選択することができます。
モード0 基本的な入出力ポート
モード1 コントロール信号,ステータス信号による制御を伴う入出力ポート
モード2 双方向データを扱う入出力ポート
ポートA
ポートC
ポートC
上位4ビット
下位4ビット
モード0
8255
OR
入力
ポートB
モード1
モード2
8255
8255
OR
出力
入力
出力
制御信号
入出力
制御信号
また、使用する目的に合わせて、各グループごとにモードを設定することができます。可能なモー
ドの組み合わせは次の6通りです。
グループA
(1)
モード0
(2)
モード0
(3)
モード1
(4)
モード1
(5)
モード2
(6)
モード2
グループB
モード0
モード1
モード0
モード1
モード0
モード1
-7-
Interface Corporation
TUT-0034
第2章 PPI製品のインストール
作成するアプリケーションからアナログ入力制御を行う場合、当然のことながらアプリケーショ
ンを実行するコンピュータにPPI製品が組み込まれていなければなりません。
ここではWindowsVista/XP/Server 2003/2000+Ver. 5.0またはVer. 6.0環境における、弊社PPI製品のイ
ンストール方法を記載します。Windows NT/Me/98/95ではインストール方法がここに記載する内容
とは異なります。こちらに関しては、製品マニュアルまたはオンラインドキュメントをご確認く
ださい。
2.1 コンピュータへの設置方法
※ 写真は実物と異なる場合があります。
①コンピュータ本体の電源が“OFF”であることを確認し、電源ケーブルをACコンセントから外しま
す。その後、外装カバー,スロットカバーを外します。
②拡張用スロットへI/Oモジュールを差し込みます。
<例>
PCI コネクタ
ビス留め
I/O モジュール
金メッキ端子がコネクタに隠れていることを確認する。
コンピュータ
基板の左右の端に力を入れ、カツンとショックがある
まで押し込む。
! 注意
製品は正しい向きに実装してください。間違った向きに実装した場合、コンピュータ,I/Oモジ
ュールを破損する恐れがあります。
③パネルをコンピュータ本体とビス留めしてください。
④本体へ外装カバーを元通り取り付け、電源ケーブルをACコンセントに接続します。その後、コ
ンピュータを起動します。
以上でI/Oモジュールの設置は完了です。次にドライバのインストールを行います。
Interface Corporation
-8-
TUT-0034
2.1.1 デバイスドライバのインストール
■Windows Vistaをご使用の場合
Administratorsのグループに所属しているユーザが、インストールを行ってください。
※ 「続行するにはあなたの許可が必要です」と警告が表示されることがあります。その場合、
「続行」をクリックしてください。
①Windows Vistaが起動すると、「新しいハードウェアが見つかりました」が表示されます。
②「ドライバソフトウェアを検索してインストールします(推奨)」をクリックします。
③「オンラインで検索しません」をクリックします。
-9-
Interface Corporation
TUT-0034
④「ディスクはありません。他の方法を試します」をクリックします。
⑤「コンピュータを参照してドライバソフトウェアを検索します(上級)」をクリックします。
⑥ドライバ保存先の「¥Win2000」フォルダを指定し、「次へ」をクリックします。
Interface Corporation
- 10 -
TUT-0034
⑦ファイルのコピーが始まります。
※ 「ドライバソフトウェアの発行元を検証できません」と表示された場合、「このドライバ
ソフトウェアをインストールします」をクリックします。
⑧インストールが完了した旨のダイアログボックスが表示されるので、「閉じる」ボタンをクリッ
クします。
以上で、Windows Vista用のドライバインストールは完了です。
- 11 -
Interface Corporation
TUT-0034
■Windows XP Embedded,Windows XP,Windows Server 2003をご使用の場合
Administratorsのグループに所属しているユーザが、インストールを行ってください。
※ Windows XP Embeddedは、Windows XPと同様の手順で、ドライバのインストールができます。
(ただし、OSイメージにデバイスの検出に必要なコンポーネントが含まれている必要がありま
す。)
①Windows XP Embedded,Windows XP,Windows Server 2003が起動すると、
「新しいハードウェアの
検出ウィザード」が表示されます。
②「一覧または特定の場所からインストールする(詳細)」が選択されていることを確認し、「次へ」
をクリックします。
③「次の場所で最適のドライバを検索する」を選択し、「次の場所を含める」にチェックをつけ、
ドライバ保存先の「¥Win2000」フォルダを指定し、「次へ」をクリックします。
ドライバ保存先の「¥Win2000」フォルダを
指定します。
④ファイルのコピーが始まります。
Interface Corporation
- 12 -
TUT-0034
⑤インストールが完了した旨のダイアログボックスが表示されるので、「完了」ボタンをクリッ
クします。
以上で、Windows XP Embedded,Windows XP,Windows Server 2003用のデバイスドライバのインス
トールは完了です。デバイスドライバのインストール完了後以降は、システム起動時に上記②の
ように「新しいハードウェアの検索ウィザード」が起動することはありません。
• Windows XP Embedded 用ハードウェア情報ファイルのインポートをする場合
・ドライバダウンロード方法
①弊社Web siteよりGPC-2746CのDriver Disk [Windows Vista,XPe,XP,2003,2000]をダウン
ロードします。
②ダウンロードしたプログラムを実行すると、「Win2000」フォルダが作成されます。
・ドライバインストール方法
①Windows XP Embedded 開発環境の Component Database Manager を起動します。
②弊社製品のハードウェア情報ファイルをインポートします。作成した「Win2000」フォ
ルダ内の拡張子がSLDのファイルを、画面の指示に従ってインポートしてください。
③以上で、ハードウェア情報のインポートは完了です。
- 13 -
Interface Corporation
TUT-0034
■Windows 2000をご使用の場合
Administratorsのグループに所属しているユーザが、インストールを行ってください。
①Windows 2000が起動すると、「新しいハードウェアの検出ウィザード」が表示されるので、「次
へ」ボタンをクリックします。
②「デバイスドライバに最適なドライバを検索する(推奨)」を選択し、「次へ」ボタンをクリック
します。
③「検索場所のオプション」で「場所を指定」を選択し、「次へ」ボタンをクリックします。
④「参照」ボタンをクリックし、「製造元のファイルのコピー元」にドライバ保存先の「¥Win2000」
フォルダを指定します。その後、「OK」ボタンをクリックします。
Interface Corporation
- 14 -
TUT-0034
⑤デバイスドライバが見つかった旨のダイアログボックスが表示されるので、「次へ」ボタンを
クリックします。
⑥ファイルのコピーが始まります。
⑦インストールが完了した旨のダイアログボックスが表示されるので、「完了」ボタンをクリッ
クします。
以上で、Windows 2000用のデバイスドライバのインストールは完了です。
デバイスドライバのインストール完了後以降は、システム起動時に上記②のように「新しいハー
ドウェアの検索ウィザード」が起動することはありません。
インストールを完了したら、リソース(I/Oアドレス,割り込みレベル)の設定,競合の有無の確認を行
ってください。
ドライバのインストールが正常に行われると、システムプロパティのデバイスマネージャに表示
されます。
ここに I/O モジュールが追加
されます。
- 15 -
Interface Corporation
TUT-0034
2.2
サンプルプログラム,Help,ヘッダファイル,インポートライブラリ,最新情報ドキュメントファイル
のインストール
1. 弊社Web siteよりGPC-2746CのUtility Diskをダウンロードします。
2. ダウンロードしたプログラムを実行すると、「SETUP」フォルダが作成されます。
3.「SETUP」フォルダ内のSETUP.EXEを実行して下さい。プログラムが起動しインストールが開
始されます。
インストールが完了すると、「スタート」メニューの「プログラム」に、「Interface GPC-2746C」
が追加されます。
Interface Corporation
- 16 -
TUT-0034
第3章 Visual C++によるPPI制御
Visual C++より、PPI製品を制御するには、DLLを利用します。Windowsアプリケーションプログ
ラムおいては直接I/Oやメモリにアクセスすることは禁止されています。従って、PPI製品に対し
て直接制御を行うことができません。そこで、Visual C++ではI/Oモジュールに対して制御を行う
プログラム(DLL)から必要なプロシージャ(関数)を呼び出し、このDLLを介してI/Oモジュールの制
御を行います。
Visual C++
アプリケーション
ダイナミックリンクライブラリ
(DLL)
Win32 API
仮想デバイスドライバ
(CP2746Cxx.sys)
入力
PPI製品
出力
- 17 -
Interface Corporation
TUT-0034
3.1 ピンアサインメント
PPI製品への信号入力、またはPPI製品からの信号出力は、I/Oモジュールのコネクタ部分より行わ
れますが、使用する製品型式によって、各ピンに割り当てられた役割が異なります。配線時には、
これらピンアサインメントをよく確認の上、配線してください。
以下、弊社PCI-2746Cのピンアサインメントを一例として記載します。
CN1:96ピンハーフピッチコネクタ(オス)
(PCR-E96LMDC(本多通信工業製)(相当品))
−COM1
−COM1
1PA0
1PA1
1PA2
1PA3
1PA4
1PA5
1PA6
1PA7
1PB0
1PB1
1PB2
1PB3
1PB4
1PB5
1PB6
1PB7
+COM1
+COM1
−FCOM
NC
IR.IN1
NC
NC
+FCOM
−RCOM1
RSTOUT/P.OUT
−COM2
−COM2
1PC0
1PC1
1PC2
1PC3
1PC4
1PC5
1PC6
1PC7
NC
NC
NC
NC
NC
NC
NC
NC
+COM2
+COM2
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
NC: 本製品内部で未接続
Interface Corporation
- 18 -
−COM3
−COM3
2PA0
2PA1
2PA2
2PA3
2PA4
2PA5
2PA6
2PA7
2PB0
2PB1
2PB2
2PB3
2PB4
2PB5
2PB6
2PB7
+COM3
+COM3
−FCOM
NC
NC
NC
IR.IN2
+FCOM
−RCOM2
RSTIN
−COM4
−COM4
2PC0
2PC1
2PC2
2PC3
2PC4
2PC5
2PC6
2PC7
NC
NC
NC
NC
NC
NC
NC
NC
+COM4
+COM4
TUT-0034
●コネクタの+COM1∼4,+FCOM端子からPCIバスの+5V電源が出力されています。
●入出力信号はそれぞれ対応したCOMをご使用ください。
<COMの対応>
信 号
1PA0∼1PA7
1PB0∼1PB7
1PC0∼1PC7
2PA0∼2PA7
2PB0∼2PB7
2PC0∼2PC7
IR.IN1,IR.IN2
RSTOUT/P.OUT
RSTIN
COM
−COM1,+COM1
−COM2,+COM2
−COM3,+COM3
−COM4,+COM4
−FCOM,+FCOM
−RCOM1
−RCOM2
PCI-2747A,CTP-2746,CPZ-2746に関しましては、製品マニュアルまたは弊社製品カタログを参照し
てください。
- 19 -
Interface Corporation
TUT-0034
3.2 DLLプロシージャ呼び出しによるプログラミング(概要)
Visual C++よりDLLプロシージャ呼び出しプログラミングを行うには、弊社PPI制御用ソフトウェ
ア(FBIPPI.DLL)をダイナミックリンクし、使用します。DLLとはダイナミックリンクライブラリ
(Dynamic Link Library)の略でアプリケーションの実行時に動的にリンクして利用できる関数のラ
イブラリです。関数とは実行時に1つの単位として処理されるコードの集まりを意味します。
Visual C++にてDLL関数を利用するには、FBIPPI.LIBファイルをリンクしてDLL関数のアドレスを
指定します。(リンクの方法は後で記載しています)
3.3 PPI製品制御概略
PPI製品への制御を行う場合、基本的に下記の制御シーケンス(順番)で行います。
1
I/Oモジュール初期化
プログラム起動
2
I/Oモジュール設定
8255の設定
3
各種処理
データの入出力
4
終了処理
プログラム終了
①I/Oモジュールの初期化
Visual C++で作成されたアプリケーションがPPI製品への操作を行う場合、まずアプリケーショ
ンは、PPI製品を利用可能な状態にする必要があります。
この処理がI/Oモジュールの初期化です。I/Oモジュールの初期化を行うと、プログラムはPPI製
品へのアクセスが可能となります。本処理が行われないとPPI製品へのアクセスは行えません。
②I/Oモジュールの設定
I/Oモジュールに搭載された8255の各ポートに対し、モードの設定や各ポートをコンピュータか
ら見て入力/出力のどちらで使うかを設定します。
③各種処理
データ・ポートより信号の入力または出力を行います。
④終了
I/Oモジュールの使用終了を行うための手続きです。プログラム終了時には必ず必要です。
Interface Corporation
- 20 -
TUT-0034
第4章 チュートリアル
ここでは、実際に弊社PPI製品を用いて、I/Oモジュールへの信号入力およびI/Oモジュールからの
信号出力を行います。本チュートリアルを行うにあたっては、ご使用になるI/Oモジュールにより
以下の準備を行ってください。
CTP-2746,PCI-2746Cをご使用の場合
CTP-2746,PCI-2746Cにてチュートリアルを行う場合、以下の製品が必要になります。
CTP-2746,PCI-2746C
1枚:PPI製品
TNS-9601
1台:垂直96ピンネジ変換端子台
ECO-66xx
1本:96ピンハーフピッチコネクタ両端ケーブル
コンピュータにPPI製品(CTP-2746,PCI-2746C)を実装し、ケーブル(ECO-66xx)を用いて端子台
(TNS-9601)に接続してください。
CPZ-2746をご使用の場合
CPZ-2746にてチュートリアルを行う場合、以下の製品が必要になります。
CPZ-2746
1枚:PPI製品
TBZ-960x
1台:垂直96ピン変換端子台
WRZ-64xx,WRZ-66xx
1本:96ピンハーフピッチケーブル
コンピュータにPPI製品(CPZ-2746)を実装し、ケーブル(WRZ-66xx)を用いて端子台(TBZ-960x)に接
続してください。
INPUT/OUTPUT
端子台
PPI製品
- 21 -
Interface Corporation
TUT-0034
PCI-2747Aをご使用の場合
PCI-2747Aにてチュートリアルを行う場合、以下の製品が必要になります。
SET-LP01(工業高校向けラーニングパック)×2点
PCI-2747A
PPI製品×2枚
TRM-2601
30点端子台×2台
CAB-9816ME
34ピンフラットコネクタ両端ケーブル×2本
コンピュータにPPI製品(PCI-2747A)を2枚実装し、それぞれケーブル(CAB-9816ME)を用いて端子
台(TRM-2601)に接続してください。
端子台
INPUT/OUTPUT
PPI製品
Interface Corporation
- 22 -
TUT-0034
4.1 モード0入力/出力
PCI-2746Cには8255が2個実装されています。ここでは、その2個の8255のうち一方をモード0の出
力に、もう一方をモード0の入力に設定し、簡単な通信を行うプログラムを作成します。
8255①
通信
8255②
PCI-2747Aを使用する場合は、一方の製品から、もう一方のボートに対し通信を行います。
本チュートリアルでは便宜上製品に実装された8255をそれぞれ「8255①」,「8255②」と表記して
います。
では、使用する製品型式に応じて、下図のように対応するピンを接続してください。
<PCI-2746Cを使用する場合>
8255①側(入力)
信号
ピン
1PA0
3
1PA1
4
8255②側(出力)
信号
ピン
2PA0
51
2PA1
52
・
・
・
・
・
・
・
・
・
・
・
・
1PA7
10
2PA7
58
-COM1
-COM2
1
29
-COM3
-COM4
49
77
+COM1
+COM2
19
47
+COM3
+COM4
67
95
※ ピン番号はTNS-9601のものです。
<PCI-2747Aを2枚使用する場合>
8255①側(入力)
信号
ピン
1PA0
3
1PA1
4
8255②側(出力)
信号
ピン
2PA0
51
2PA1
52
・
・
・
・
・
・
・
・
・
・
・
・
1PA7
10
2PA7
58
-COM1
-COM2
1
29
-COM3
-COM4
49
77
+COM1
+COM2
19
47
+COM3
+COM4
67
95
※ ピン番号はTRM-2601のものです。2台のTRM-2601を接続するように配線してください。
※ 製品番号「0」のPCI-2747Aを8255(1)の端子台に、製品番号「1」のPCI-2747Aを8255(2)の端子
台に接続してください。
- 23 -
Interface Corporation
TUT-0034
Step1.メインウィンドウ作成
ここでは、これから作成するプログラムの画面作成を行います。
Visual C++を起動し、新しいプロジェクトを作成します。
1. 「ファイル」メニューより「新規作成」を選択します。
2. 新規作成ダイアログが表示されますので、「プロジェクト」タブを選択します。
・MFC AppWizard(exe)を選択し、「プロジェクト名」に“PpiMode0_InOut”と記入します。
・「位置」には作業するフォルダを指定してください。その後「OK」をクリックします。
プロジェクト名を書き込みます
MFC AppWizard (exe)
を選択します
作業するフォルダを指定します
3. 作成するアプリケーションの種類は「ダイアログベース」、リソースで使用する言語の指定は
「日本語」を選択し、「次へ」をクリックします。
ダイアログベースを
選択します
4. ステップ2,ステップ3では「次へ」をクリックし、ステップ4で「終了」をクリックします。
Interface Corporation
- 24 -
TUT-0034
5. 新規プロジェクト情報というダイアログが表示されますので「OK」をクリックします。
ここまでで、新規プロジェクトの作成は完了です。
Step2.DLL関数宣言
DLL関数を利用するには、FBIPPI.LIBファイルを使って関数の位置を指定し、関数の呼び出しに
使う引数の識別を行わなければなりません。
ここで一度宣言したDLL関数は、Visual C++の関数と同じようにコードで呼び出すことが可能とな
ります。
1. プロジェクトにFBIPPI.LIB, FBIPPI.Hのパス設定を行います。
・「ツール」→「オプション」を選択し、「ディレクトリ」タブを選択します。
- 25 -
Interface Corporation
TUT-0034
・表示するディレクトリを「インクルードファイル」にします。
・空白の部分をダブルクリックします。
ダブルクリックします
インクルードファイルにします
クリックします
・ディレクトリの追加を行います。ディレクトリ先を
<ProgramFiles>¥Interface¥Gpc2746C¥includeに設定して「OK」をクリックします。
include を選択します
Interface Corporation
- 26 -
TUT-0034
・下図のようにディレクトリが追加されます
追加されたディレクトリ
・次に、表示するディレクトリを「ライブラリファイル」にします。
・ディレクトリの追加を行います。ディレクトリ先を
<Program Files>¥Interface¥Gpc2746C¥libと設定して「OK」をクリックします。
lib を選択します
・下図のようにディレクトリが追加されます。
追加されたディレクトリ
- 27 -
Interface Corporation
TUT-0034
2.プロジェクトにFBIPPI.LIBファイルをリンクします。
・「プロジェクト」→「設定」を選択し、「リンク」タブを選択します。
・設定の対象を「全ての構成」に設定し、「オブジェクト/ライブラリモジュール」に“fbippi.lib”
と書き込み「OK」をクリックします
すべての構成にします
fbippi.lib をリンクします
“FBIPPI.LIB”,“FBIPPI.H”は、Setupでインストールされる<インストール先>¥lib.
<インストール先>¥includeにあります。(インストール先:<Program Files>¥Interface¥Gpc2746C)
Step3.初期化処理と終了処理
ここでは、実際のプログラム作成を行う前に、PPI製品の初期化処理と終了処理に関して、知って
おかなければならないこと、および制約事項について記載します。
PPI製品の制御を行うには、まず製品の初期化を行わなければなりません。製品の初期化は以下の
コードにより行います。
(List 1-1:製品の初期化)
//製品の初期化を行います。(1 軸目の初期化)
HANDLE
hDeviceHandle;
//デバイスハンドル
hDeviceHandle = PpiOpen(“FBIPPI1”, FBIPPI_FLAG_SHARE);
この時、FBIPPI1に設定する値は、使用する製品のデバイス名を指定します。デバイス名は、「コ
ントロールパネル」より「システム」を選択し「システムのプロパティ」の「デバイスマネージ
ャ」タブを選択すると確認できます。
ここにデバイス名が表示されます。
Interface Corporation
- 28 -
TUT-0034
製品の初期化はPpiOpen関数により行います。
「使用例」
使用する製品のデバイス名を指定します。
HANDLE hDeviceHandle;
hDeviceHandle = PpiOpen(“FBIPPI1”, PPI_FLAG_SHARE);
デバイスハンドルを格納する
HANDLE型の変数を指定します。
同じデバイスを重複(共有)してオープ
ンすることを許可するフラグです。
また、アプリケーションの終了時、もしくは処理の終了時に、オープンした軸に対して必ず終了
処理を行わなければなりません。
製品の終了処理は以下のコードにより行います。
(List 1-2:製品の終了処理)
//終了処理
INT
nRet;
//関数の実行結果
nRet = PpiClose(hDeviceHandle);
製品の終了処理はPpiClose関数より行います。ここで、注意しなければならないのは、設定する
引数のhDeviceHandleです。hDeviceHandle には製品の初期化の際に取得した、PpiOpen関数の戻り
値を指定します。PpiOpen 関数実行時、その戻り値であるhDeviceHandleには有効なハンドル(番
号)が格納されています(上記List参照)。ハンドルとは使用するデバイスの接続に関する情報が格納
されたメモリ領域を、識別するための値を示します。
プログラム作成時、終了処理を行うデバイスのhDeviceHandleの値が、PpiOpen実行時に取得され
た値となるように、PpiOpenとPpiCloseは必ず組になるよう注意してください。
ハンドル
PpiOpen
「使用例」
製品のオープン時に取得
したデバイスハンドルを
指定します。
nRet = PpiClose(hDeviceHandle);
関数が失敗するとエラーコードが
格納されます。
PpiClose
- 29 -
Interface Corporation
TUT-0034
では実際に製品の初期化と終了を行うプログラムを作成します。
1. 表示メニューからClassWizardを起動します。
2. 「メッセージマップ」タブを選択し、以下のように設定します。
プロジェクト
Ppi_Mode0_InOut
クラス名
CPpi_Mode0_InOutDlg
オブジェクト
CPpi_Mode0_InOutDlg
メッセージ
WM_CREATE
PpiMode0_InOut を指定します
CPpiMode0_InOutDlg を指定します
WM_CREATE を指定します
関数の追加をクリックします
CPpiMode0_InOut を指定します
3. 「関数の追加」をクリックします。
4. 同様にメッセージに「WM_DESTROY」を選択し、「関数の追加」をクリックします。
5. 「OK」をクリックし、ClassWizardを終了します
6. ワークスペースの「FileView」タブをクリックし、「Source Files」フォルダを展開します。
「PpiMode0_InOutDlg.cpp」をダブルクリックしてファイルを開き、(List1-3)の網掛け部分を記
述します。
(List 1-3:PpiMode0_InOutDlg.cpp の変更コード)
// PpiMode0_InOutDlg.cpp : インプリメンテーション ファイル
//
#include "stdafx.h"
#include "PpiMode0_InOut.h"
#include "PpiMode0_InOutDlg.h"
#include "fbippi.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
HANDLE ghDeviceHandle1;
//☆PCI-2747A 使用時のみ追加します
//HANDLE ghDeviceHandle2;
Interface Corporation
- 30 -
TUT-0034
7. ワークスペースの「ClassView」タブをクリックし、「CPpiMode0_InOutDlg」フォルダを展開
します。
8. フォルダの下の「OnCreate」をダブルクリックし、OnCreate関数に(List 1-4)を記述します。
(List 1-4:CppiMode0_InOutDlg クラスの OnCreate 関数のコード)
int CPpiMode0_InOutDlg::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (CDialog::OnCreate(lpCreateStruct) == -1)
return -1;
// TODO: この位置に固有の作成用コードを追加してください
//PCI-2746C(PCI-2747A 使用時は 1 枚目)の製品をオープンします
ghDeviceHandle1 = PpiOpen( "FBIPPI1", FBIPPI_FLAG_SHARE);
if (ghDeviceHandle1 == INVALID_HANDLE_VALUE) {
MessageBox("製品 1 のオープンに失敗しました");
exit(0);
}
//☆PCI-2747A を使用する場合の追加コード
//PCI-2747A の 2 枚目の製品をオープンします
//ghDeviceHandle2 = PpiOpen( "FBIPPI2", FBIPPI_FLAG_SHARE);
//if (ghDeviceHandle2 == INVALID_HANDLE_VALUE) {
//
MessageBox("製品 2 のオープンに失敗しました");
//
exit(0);
//}
return 0;
}
9. 同様に、「OnDestroy」をダブルクリックし、OnDestroy関数に(List 1-5)を記述します。
(List 1-5:CppiMode0_InOutDlg クラスの OnDestory 関数のコード)
void CPpiMode0_InOutDlg::OnDestroy()
{
CDialog::OnDestroy();
// TODO: この位置にメッセージ ハンドラ用のコードを追加してください
INT nRet;
//関数の実行結果
//PCI-2746C(PCI-2747A 使用時は 1 枚目)の製品をクローズします
nRet = PpiClose(ghDeviceHandle1);
if(nRet != FBIPPI_ERROR_SUCCESS) {
MessageBox("製品 1 のクローズに失敗しました");
exit(0);
}
//☆PCI-2747A を使用する場合の追加コード
//PCI-2747A の 2 枚目の製品をクローズします
//nRet = PpiClose(ghDeviceHandle2);
//if(nRet != FBIPPI_ERROR_SUCCESS) {
//
MessageBox("製品 2 のクローズに失敗しました");
//
exit(0);
//}
}
プログラムの入力が終わったら、保存した後、プログラムを実行してみてください。何もエラー
が表示されなければ、製品の初期化および終了処理部分のプログラムは完成です。
- 31 -
Interface Corporation
TUT-0034
Step4.モード0入出力
では、実際に通信プログラムの作成を行います。ここでは8255②のポートAから出力したデータ
を8255①のポートAより入力します。
※ PCI-2747Aを2枚使用する場合は1枚目の8255のポートAから出力したデータを2枚目の8255の
ポートAより入力します。
1. まず8255①と8255②に対して入力,出力の設定を行います。OnCreate関数に(List 1-6)の網掛け部
分のコードを追加してください。
(List 1-6:CppiMode0_InOutDlg クラスの OnCreate 関数の追加コード)
int CPpiMode0_InOutDlg::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
if (CDialog::OnCreate(lpCreateStruct) == -1)
return -1;
// TODO: この位置に固有の作成用コードを追加してください
INT nRet;
//関数の実行結果
//PCI-2746C(PCI-2747A 使用時は 1 枚目)の製品をオープンします
ghDeviceHandle1 = PpiOpen( "FBIPPI1", FBIPPI_FLAG_SHARE);
if (ghDeviceHandle1 == INVALID_HANDLE_VALUE) {
MessageBox("製品 1 のオープンに失敗しました");
exit(0);
}
//☆PCI-2747A を使用する場合の追加コード
//PCI-2747A の 2 枚目の製品をオープンします
//ghDeviceHandle2 = PpiOpen( "FBIPPI2", FBIPPI_FLAG_SHARE);
//if (ghDeviceHandle2 == INVALID_HANDLE_VALUE) {
//
MessageBox("製品 2 のオープンに失敗しました");
//
exit(0);
//}
//8255①をモード 0 全点入力に設定
nRet = PpiControl(ghDeviceHandle1, FBIPPI_8255_CONTROLLER1,0x9b);
if (nRet != FBIPPI_ERROR_SUCCESS) {
MessageBox("8255①のモード設定に失敗しました");
PpiClose(ghDeviceHandle1);
exit(0);
}
//8255②をモード 0 全点出力に設定
//PCI-2747A を使用する場合は ghDeviceHandle2,FBIPPI_8255_CONTROLLER1 に変更してください
nRet = PpiControl(ghDeviceHandle1, FBIPPI_8255_CONTROLLER2,0x80);
if (nRet != FBIPPI_ERROR_SUCCESS) {
MessageBox("8255②のモード設定に失敗しました");
PpiClose(ghDeviceHandle1);
exit(0);
}
return 0;
}
2. ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE0_INOUT_DIALOGをダブ
ルクリックします。
Interface Corporation
- 32 -
TUT-0034
ダブルクリックします
3. ダイアログボックスの必要のないボタン,スタティックテキストを削除します。
「OK」ボタン,「キャンセル」ボタン,「TODO:ダイアログのコントロールをここに配置」とい
うスタティックテキストをそれぞれ選択し、Deleteキーを押してください。
それぞれ選択して Delete キーで削除します
4. ダイアログ上に、①出力データを書き込むエディットボックスと②入出力を行うボタンと③
入力データを表示するエディットボックスを配置します。それぞれのオブジェクトにマウス
カーソルをあわせ、右クリック→「プロパティ」で以下のように設定してください。
①出力データを書き込むエディットボックス
ID
IDC_OUTDATA_WINDOW
「スタイル」タブを選択し複数行にチェック
②入出力を行うボタン
ID
IDC_INOUT
キャプション モード0入出力
③入力データを表示するエディットボックス
ID
IDC_INDATA_WINDOW
「スタイル」タブを選択し、複数行にチェック
①
出力データを書き込
むエディットボック
スを配置します
②
入出力を行うボタン
を配置します
③
入力データを表示す
るエディットボック
スを配置します
- 33 -
Interface Corporation
TUT-0034
5. ①出力データを書き込むエディットボックスにデータを格納するメンバ変数の追加設定を行
います。
・エディットボックス①にマウスカーソルをあわせ右クリックし、「ClassWizard」を選択して「メ
ンバ変数」タブを表示します。
・次のように設定し、「変数の追加」をクリックします。
プロジェクト名
PpiMode0_InOut
クラス名
PpiMode0_InOut
コントロール
IDC_OUTDATA_WINDOW
・さらに以下のように設定し、「OK」をクリックします。
メンバ変数
m_szOutData
カテゴリ
値
変数のタイプ
Cstring
6. ③同様に入力データを表示するエディットボックスにデータを格納するメンバ変数の追加
を行います。以下のように設定します。
プロジェクト名
PpiMode0_InOut
クラス名
CPpiMode0_InOut
コントロール
IDC_INDATA_WINDOW
メンバ変数
m_szInData
カテゴリ
値
変数のタイプ
CString
以下のようにメンバ変数が追加されます。
追加したメンバ変数
7. 先程作成した「モード0入出力」ボタンにマウスカーソルをあわせ、右クリックし
「ClassWizard」を選択します。「メッセージマップ」を選択し、以下のように設定した後、
「関数の追加」をクリックします。
プロジェクト
PpiMode0_InOut
クラス名
CPpiMode0_InOut
オブジェクト
IDC_INOUT
メッセージ
BN_CLICKED
Interface Corporation
- 34 -
TUT-0034
関数の追加をクリックします
・メンバ関数名を決定するダイアログが表示されますので、”OnInOut”となっていることを確認し、
「OK」をクリックします。その後ClassWizardを終了します。
・OnInOut関数を記述します(ワークスペースのClassViewを表示し、CInOutDlgクラスを展開して
OnInOut()をダブルクリックすると、OnInOut関数が編集できる位置にカーソルがジャンプして
くれます)。プログラムリストの説明については後述します。
(List 1-7:CPpiMode0_InOutDlg クラスの OnInOut 関数のコード)
void CPpiMode0_InOutDlg::OnInOut()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT nRet;
//関数の実行結果
INT SendNum;
//出力回数
INT nLen;
//出力文字数
BYTE bSend;
//出力データ
char SendBuf[32];
//出力バッファ
BYTE bRecv[32];
//入力データ
UpdateData(TRUE);
strcpy(SendBuf,m_szOutData);
nLen = strlen(SendBuf);
for(SendNum = 0; SendNum < nLen; SendNum++){
bSend = (BYTE)SendBuf[SendNum];
//8255②のポートAからデータ(1 文字)を出力します。
//PCI-2747A を使用する場合は ghDeviceHandle2,FBIPPI_8255_CONTROLLER1 に変更してください
nRet = PpiOutputPort(ghDeviceHandle1,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_A ,bSend);
if(nRet != FBIPPI_ERROR_SUCCESS) {
MessageBox("8255②ポート A の出力に失敗しました");
PpiClose(ghDeviceHandle1);
exit(0);
}
//8255①のポートAからデータ(1 文字)を入力します。
nRet = PpiInputPort(ghDeviceHandle1,FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_A,&bRecv[SendNum]);
if(nRet != FBIPPI_ERROR_SUCCESS) {
MessageBox("8255②ポート A の出力に失敗しました");
PpiClose(ghDeviceHandle1);
exit(0);
}
}
bRecv[SendNum] = NULL;
m_szInData.Format("%s", bRecv);
UpdateData(FALSE);
}
以上で、プログラムの作成は完了です。
では、保存した後実行してください。
- 35 -
Interface Corporation
TUT-0034
プログラムを実行し出力データを書き込むエディットボックスに「HELLO」と入力し、「モード
0入出力」ボタンをクリックしてください。
入力データを表示するエディットボックスに「HELLO」と表示されます。
8255②より出力されたデータが、端子台を介し8255①に入力され、その入力されたデータが表示
されています。
端子台
HELLO
HELLO
PPI 製品
サンプルプログラムでは半角32文字以下のメッセージが入出力できます。
では、(List 1-6)の処理を読み取ってみましょう。製品の初期化処理後プログラムは8255の設定を
行っています。8255の設定にはPpiControl関数を使用します。
「使用例」
8255に設定するコマン
ドです。
設定する8255を指定します。
nRet = PpiControl(ghDeviceHandle1, FBIPPI_8255_CONTROLLER1, 0x9B);
関数が失敗するとエラー
コードが格納されます。
Interface Corporation
製品のオープン時に取得したデバイスハン
ドルを指定します。
- 36 -
TUT-0034
第3引数に設定する8255 PPIコントローラ制御レジスタへの制御データですが、下図のように決め
られています。
制御レジスタ
D7
D6
D5
D4
D3
D2
D1
D0
グループB
ポートC下位
1=入力
0=出力
ポートB
1=入力
0=出力
ここでは、8255①をモード0の全点入
力に、8255②をモード0の全点出力に
設定しますので、それぞれの制御レ
ジスタには「10011011」と「10000000」
を設定します。
プログラム中ではこれらを16進数表
記にしていますので「0x9B」と「0x80」
を設定しています。
モード選択
1=モード1
0=モード0
グループA
ポートC上位
1=入力
0=出力
ポートA
1=入力
0=出力
モード選択
00=モード0
01=モード1
1X=モード2
機能制御
1=モード選択
0=ビットセット/リセット
次に、(List 1-7)ではデータの出力を行うわけですが、Forループにて出力文字列を1文字(1バイト)
ずつアスキーコードに変換し順に8255②のポートAより出力しています。データの出力には
PpiOutputPort関数を使用します。
「使用例」
設定する 8255 を指定します。
nRet = PpiOutputPort(ghDeviceHandle1, FBIPPI_8255_CONTROLLER2,
FBIPPI_PORT_A, bSend);
関数が失敗するとエラー
コードが格納されます。
出力する 1 バイトのデータを
指定します。
出力するポートを指定します。
製品のオープン時に取得したデ
バイスハンドルを指定します。
データを8255②のポートAより出力した直後、今度はそのデータを8255①のポートAより入力して
います。データの入力にはPpiInputPort関数を使用します。
「使用例」
設定する 8255 を指定します。
nRet = PpiInputPort(ghDeviceHandle1, FBIPPI_8255_CONTROLLER1,
FBIPPI_PORT_A, &bRecv[SendNum]);
関数が失敗すると
エラーコードが格
納されます。
製品のオープン時に取
得したデバイスハンド
ルを指定します。
入力する 1 バイトのデータ
を格納する変数へのポイ
ンタを指定します。
入力するポートを指定し
ます。
最後に製品の終了処理を行ってプログラムは終了します。
- 37 -
Interface Corporation
TUT-0034
4.2 モード1入力
ここでは、PPI製品の8255①をモード1入力に設定し、8255②より出力されるデータを入力する制
御信号を用いた簡単な通信プログラムの作成を行います。
では、まずこの制御信号について見てみます。
8255は設定されたモードにより、定められた動作をします。この定められた動作を示しているタ
イミングチャートを下図に記載します。タイミングチャートとは信号線に与える信号の手順を示
す図のことです。
H
L
STB
IBF
REIをセットしなければ、INTは
Hレベルのままです。
L
H
INT
L
H
RD
外部からの
データ
H
L
ラッチされたデータ
時間の経過
制御信号線は必ず5Vか0Vのどちらかの状態になります。それぞれをH(High)レベル,L(Low)レベル
といいます。コンピュータ上のデータとしては「1」と「0」に相当します※2。各制御信号の名称
に関しては『99ページ 第6章 8255 PPIコントローラ説明』を参照してください。
では、このタイミングチャートを解読してみましょう。
まず、入力ポートには外部の接続機器からデータが入力されているとします。この時、接続され
た外部機器よりSTBをLレベル,Hレベルの順に変化させると、入力データがラッチされ、同時にINT
信号がHレベルに変化します※3。また、STBをLレベルにした際にはIBFがHレベルに変化していま
す。
そして、ラッチされたデータを読み込む(RD)とIBFがHレベルからLレベルに変化します。
※2 PPI製品は正論理で動作しています。
※3 INT信号を有効にするためには、ビット操作命令でREIに「1」をセットします。
以上のことから、以下のハンドシェ−ク通信が可能であると考えられます。またここでは、便宜
上通信の終了時には出力側が入力側に通信終了コードを送信するものとします。
入力側
出力側
①INT信号がHレベルになるまで待機する
②データを読み込む
③通信終了コードが送られてくるまで①から
繰り返す
Interface Corporation
- 38 -
①データを出力する
②入力側のSTBをLレベル,Hレベルの順に
変化させる
③入力側のIBF信号を確認しLレベルになるま
で待機する
④次のデータがある場合は①から繰り返す
TUT-0034
これらのことをフローチャートにまとめると下図のようになります。
入力側(8255①)
出力側(8255②)
開始
開始
データ出力
INT は
H レベル?
入力側の STB を L レベル,
H レベルの順に変化させる
NO
YES
データ読み込み
入力側の IBF は
L レベル?
NO
NO
YES
通信終了コード
を受信した?
YES
NO
通信終了
コード?
YES
終了
終了
では、下図のように対応するピンを接続してください。
<PCI-2746Cを使用する場合>
8255①側(入力)
信号
ピン
1PA0
3
1PA1
4
・
・
・
・
・
・
1PA7
8255②側(出力)
信号
ピン
2PA0
51
2PA1
52
・
・
・
・
・
・
・
・
・
10
2PA7
58
1PC5(IBF)
1PC4(IBF)
1PC3(INT)
36
35
34
2PB7
2PC2
66
81
1PB7
18
-COM1
-COM2
1
29
-COM3
-COM4
49
77
+COM1
+COM2
19
47
+COM3
+COM4
67
95
※ ピン番号はTNS-9601のものです
<PCI-2747Aを2枚使用する場合>
8255①側(入力)
信号
ピン
PA0
3
PA1
4
・
・
・
・
・
・
PA7
8255②側(出力)
信号
ピン
PA0
51
PA1
52
・
・
・
・
・
・
・
・
・
10
PA7
58
PC5(IBF)
PC4(IBF)
PC3(INT)
28
27
26
PB7
PC2
20
25
1PB7
20
-COM1
11
-COM
11
-COM2
1
-COM
1
※ ピン番号はTRM-2601のものです。2台のTRM-2601を接続するように配線してください。
※ 製品番号「0」のPCI-2747Aを8255(1)の端子台に、製品番号「1」のPCI-2747Aを8255(2)の端子
台に接続してください。
- 39 -
Interface Corporation
TUT-0034
Step1.プロジェクトの作成(モード1入力側)
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode1_Recv)を作成します。を作
成します。(『23ページ 4.1 モード0入力/出力』でのStep1のメインウィンドウの作成を参照し
てください。)
2. プロジェクトにFbiPpi.Libファイル,FbiPpi.Hファイルのパス設定を行い、ライブラリファイ
ル”FpiPpi.lib”をリンクさせます。(『23ページ 4.1 モード0入力/出力』でのStep2のDLL関数宣
言を参照してください。)
3. 初期化処理と終了処理を行う関数を追加します。(『23ページ 4.1 モード0入力/出力』での
Step3の初期化処理と終了処理を参照してください。)
・“FbiPpi.H”ファイルのインクルード,デバイスハンドルの変数宣言を行います。
『23ページ 4.1
モード0入力/出力』における(List1-3)と同様にコードの追加を行います。(ただし、
PCI-2746C,PCI-2747Aにおける使用製品に対応したデバイスハンドル変数の区別を行う必要
はありません。)
「MFC ClassWizard」で以下のように設定し、メッセージ「WM_CREATE」,「WM_DESTROY」に
対する関数に初期化,終了コードをそれぞれ実装します。(モード0入力/出力の(List 1-4,List1-5)
を参照してください。ただし、使用製品に対応したコード変更,追加を行う必要はありません。)
プロジェクト
PpiMode1_Recv
クラス名
CPpiMode1_RecvDlg
オブジェクト
CPpiMode1_RecvDlg
Step2.モード1入力
次に、モード1で入力を行うためのプログラムの作成を行います。
1. データ入力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE1_RECV_DIALOG」をダブ
ルクリックします。
・表示されたダイアログボックスから、必要のないボタン、スタティックテキストを削除します。
「OK」ボタン,「キャンセル」ボタン,「TODO:ダイアログのコントロールをここに配置」という
スタティックテキストをそれぞれ選択し、Deleteキーを押してください。
それぞれ選択して Delete キーで削除します
Interface Corporation
- 40 -
TUT-0034
・コントロールから「ボタン」と「エディットボックス」を選択し、ダイアログに貼り付けます。
ボタンとエディットボッ
クスを貼り付けます
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDRECV
PPIモード1 入力
IDC_CMDRECV にします
「PPI モード 1 入力」にします
・同様にして、エディットボックスにカーソルを合わせ、右クリック→「プロパティ」を選択し
て以下のように設定します。
ID
IDC_TXTMON
IDC_TXTMON にします
・「スタイル」タブを選択し、「複数行」と「改行を許可」のチェックボックスにチェックを入
れます。
「複数行」と「改行を許可」にチェックを入れます
- 41 -
Interface Corporation
TUT-0034
2. 受信データを表示するためのメンバ変数“m_TxtMon”を作成します。
・先程作成した「エディットボックス」にカーソルを合わせ、右クリック→「Class Wizard」を選
択します。「メンバ変数」タブを選択し、以下のように設定した後、「変数の追加」をクリッ
クします。
PpiMode1_Recv
CPpiMode1_RecvDlg
IDC_TXTMON
プロジェクト
クラス名
コントロールID
それぞれの値を設定します
変数の追加をクリックします
・メンバ変数を決定するダイアログが表示されますので、以下のように設定し、「OK」をクリッ
クします。これでメンバ変数“m_TxtMon”が追加されました。
メンバ変数
m_TxtMon
カテゴリ
値
変数のタイプ
CString
それぞれの値を設定します
OK をクリックします
Interface Corporation
- 42 -
TUT-0034
3. データ受信のポーリングを行うためにTimer関数を作成します。
再びClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数
の追加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode1_Recv
CPpiMode1_RecvDlg
CPpiMode1_RecvDlg
WM_TIMER
それぞれの値を設定します
関数の追加をクリックします
・CPpiMode1_RecvDlgにタイマ識別変数の追加を行います。ワークスペースの「FileView」を表示
し、「PpiMode1_Recv ファイル」下の「Resource Files」フォルダを展開します。
“CPpiMode1_RecvDlg.c”をダブルクリックしてを開き、(List 2-1)の網掛けの部分の記述を追加し
ます。
(List 2-1 CPpiMode1_RecvDlg.c のコード)
// PpiMode1_RecvDlg.cpp : インプリメンテーション ファイル
//
#include
#include
#include
#include
"stdafx.h"
"PpiMode1_Recv.h"
"PpiMode1_RecvDlg.h"
"fbippi.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
HANDLE
UINT
ghDeviceHandle;
timerID = 0;
// デバイスハンドル
// タイマ ID
- 43 -
Interface Corporation
TUT-0034
4. データ入力処理を開始するためのメンバ関数“OnCmdRecv”の作成を行います。
・ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の
追加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode1_Recv
CPpiMode1_RecvDlg
IDC_CMDRECV
WM_CLICKED
それぞれの値を設定します
変数の追加をクリックします
・メンバ変数名を決定するダイアログが表示されますので、“OnCmdRecv”となっていることを確
認し、「OK」をクリックします。
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 2-2)のコードを記述します。
(List 2-2 CPpiMode1_RecvDlg クラスの OnCmdRecv 関数のコード)
void CPpiMode1InDlg::OnCmdRecv()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
// 8255①の設定を行います
// グループ A = Mode1 入力
// グループ B = Mode0 入力
// [制御データ = 10111011]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,0xbb);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// INT 信号を有効にするため、8255①グループ A の RIE に 1 をセットします
// [制御データ = 00001001]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,0x09);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のビットセットに失敗しました","制御データ設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// もし Timer が作成されていなければ Timer を作成して受信を開始する
if(timerID==0){
timerID=SetTimer(1, 10, NULL);
if(timerID==0){
MessageBox("タイマの作成に失敗しました","Timer 設定エラー", MB_ICONERROR);
}
}
}
Interface Corporation
- 44 -
TUT-0034
5. ポーリング処理をTimer関数に追加します。
ワークスペースの「ClassView」を表示し、CPpiMode1_RecvDlgクラスを展開します。「OnTimer()」
をダブルクリックしてソースコードを開き、“OnTimer”関数に(List 2-3)のコードを記述します。
(List 2-3 CPpiMode1_RecvDlg クラスの OnTimer 関数のコード)
void CPpiMode1_RecvDlg::OnTimer(UINT nIDEvent)
{
// TODO: この位置にメッセージ ハンドラ用のコードを追加するか
またはデフォルトの処理を呼び出してください
INT
nRet;
// 関数の実行結果
BYTE
bRecv;
// 受信データ
BOOL
fReadOk;
// 制御信号監視用フラグ
// タイマ処理
if(nIDEvent==timerID){
// 1PB7 の状態を監視し High になるまで待機します
fReadOk = false;
while(fReadOk == false){
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_B,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート A の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x80){
fReadOk = true;
}
}
// 8255①ポート A よりデータ(1 文字)を入力します
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_A,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート A の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 入力されたデータをエディットボックスに表示します
m_TxtMon.Format("%d", bRecv);
UpdateData(FALSE);
// 受信が終了していればタイマを破棄して受信を終了する
if(bRecv == 255){
KillTimer(timerID); // タイマの破棄
timerID=0;
// timerID を初期化する
}
}
CDialog::OnTimer(nIDEvent);
}
- 45 -
Interface Corporation
TUT-0034
・次に、Timer関数の終了処理を記述します。「ClassView」で「OnDestroy」関数をダブルクリッ
クして表示し、(List 2-4)の網掛け部分を追加します。
(List 2-4 OnTimer 関数の終了処理のコード)
void CPpiMode1_RecvDlg::OnDestroy()
{
CDialog::OnDestroy();
// TODO: この位置にメッセージ ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
// タイマが作成されていれば、破棄を行う
if(timerID!=0)
KillTimer(timerID);
// 製品クローズ
nRet = PpiClose(ghDeviceHandle);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("FBIPPI1 のクローズに失敗しました","製品クローズエラー", MB_ICONERROR);
}
}
以上でモード1データ入力のプログラムは完成です。
Step3.プロジェクトの作成(モード0出力側)
モード1での入力確認用にモード0でのデータ出力プログラムの作成を行います。
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode0_Send)を作成します。
2. プロジェクトにFBIPPI.LIBファイル,FBIPPI.Hファイルのパス設定を行い、ライブラリファイル
“Fbippi.lib”をリンクさせます。
3. 作成したプログラムに、PPI製品の初期化と終了処理を行う関数を追加します。
(ここまでの手順は『23ページ 4.1 モード0入力/出力』のStep1∼Step3と同様になりますので、
そちらを参照してください。ただし、PCI-2747Aを使用する場合はデバイス名を2枚目の製品のも
のに変更し、コントローラの番号を1(FBIPPI_8255_CONTROLLER1)に変更してください。)
Interface Corporation
- 46 -
TUT-0034
Step4.モード0出力
1. データ出力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE0_SEND_DIALOG」をダブ
ルクリックします。
・表示されたダイアログボックスから、必要のないボタン,スタティックテキストを削除します。
「OK」ボタン,「キャンセル」ボタン,「TODO:ダイアログのコントロールをここに配置」とい
うスタティックテキストをそれぞれ選択し、Deleteキーを押してください。
・コントロールから「ボタン」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDSEND
PPIモード0 出力
IDC_CMDSEND にします
「PPI モード 0 出力」にします
2. データ出力処理を開始するためのメンバ関数“OnCmdSend”の作成を行います。
・ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の
追加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode0_Send
CPpiMode0_SendDlg
IDC_CMDSEND
WM_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、“OnCmdSend”となっていることを
確認し、「OK」をクリックします。
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表
示し、(List 2-5)のコードを記述します。
- 47 -
Interface Corporation
TUT-0034
(List 2-5 CPpiMode0_SendDlg クラスの OnCmdSend 関数のコード)
void CPpimode0_SendDlg::OnCmdSend()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
INT
nLoop;
// for ループ用
BYTE
bRecv;
// 受信データ
BYTE
bSend;
// 送信データ
BOOL
fNextSend;
// 制御信号監視用フラグ
// 8255②の設定を行います
// Mode = 0
// PortA = OUT
// PortB = IN
// PortC = OUT
// [制御データ = 10000010]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,0x82);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
}
// 8255②より 0∼255 の数値データを出力します
for(nLoop=0;nLoop<=255;nLoop++){
bSend = nLoop;
// 8255②のポート A からデータを出力します
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_A,bSend);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート A の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②の STB に Low パルスを送信します
// 8255②の 2PC2 を Low にセットし入力側のデータをラッチします
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_C,0xfb);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②の 2PC2 を High にセットし入力側のデータラッチを終了します
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_C,0xff);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②の 2PB7 の状態を監視し、Low になるまで待機します
fNextSend = false;
while(fNextSend == false){
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_B,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート B の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x00){
fNextSend = true;
}
}
}
MessageBox("送信完了","データ送信確認", MB_ICONINFORMATION);
}
以上でモード0データ出力のプログラムは完成です。
Interface Corporation
- 48 -
TUT-0034
プログラムの入力が終わったら、保存した後、入力側/出力側のプログラムをそれぞれ実行してく
ださい。まず入力側の「PPI モード1入力」ボタンをクリックしてください。まだ、なにもおきま
せん。今度は出力側の「データ出力」ボタンをクリックしてください。入力側のテキストボック
ス(txtMon)に下図のよう表示されます。
1∼255 まで表示され、255 が表示されると
通信が終了します。
これは、入力側/出力側、それぞれのプログラムが特定の条件を満たさない限りデータの入力/出力
を行わないようにしているためです。
また、このことによりデータの取りこぼし等を防ぎ、安定した通信を行うことが可能になります。
D0~D7
8255
STB
IBF
INT
- 49 -
Interface Corporation
TUT-0034
4.3 モード1出力
ここでは、モード1出力に設定した8255(1)からデータを出力し、8255(2)よりデータを入力する
『38ページ 4.2 モード1入力』とは逆の動作をする、制御信号を用いた簡単な通信プログラム
の作成を行います。
下図にモード1出力設定時のタイミングチャートを示します。
WR
OBF
INTR
WEI をセットしなければ、
INTR は H レベルのままです。
ACK
H
L
H
L
H
L
H
L
外部への
出力データ
出力される新しいデータ
時間の経過
では、このタイミングチャートを解読してみましょう。
まず、INTR信号がHレベルのとき出力データの書き込み(WR)を行うと、INTR信号がHレベルから
Lレベルに変化します※。データの書き込みが完了すると、接続された外部機器にデータが出力さ
れ、OBF信号がHレベルからLレベルに変化します。この後、接続された外部機器よりACK信号を
Lレベル,Hレベルの順に変化させると、OBF信号,INTR信号がもとの状態(Hレベル)に変化します。
※ INTR信号を有効にするためには、ビット操作命令でWEIに「1」をセットします。
以上のことから、以下のハンドシェーク通信が可能であると考えられます。またここでは、便宜
上通信の終了時には出力側が入力側に通信終了コードを送信するものとします。
「出力側」
(1)データを出力する
(2)INTRを確認しHレベルになるまで待機する
(3)次のデータがある場合は(1)から繰り返す
「入力側」
(1)出力側のOBF信号がLレベルになるまで待機する
(2)データを読み込む
(3)出力側のACKをLレベル,Hレベルの順に変化させる
(4)通信終了コードが送られてくるまで(1)から繰り返す
Interface Corporation
- 50 -
TUT-0034
これらのことをフローチャートにまとめると下図のようになります。
出力側(8255(1))
出力側(8255(2))
開始
出力側のOBF
はLレベル?
Yes
データ入力
出力側のACKを
Lレベル,Hレベル
の順に変化させる
通信終了
コード?
Yes
終了
では、端子台上で下図のように対応するピンを接続してください。
-COM1~ -COM4はI/Oモジュール内で接続されていますので、接続は不要です。
ただし、外部回路との接続時は、必ず接続してください。
<PCI-2746C,CTP-2746を使用する場合>
8255(1) 側
信号
ピン
1PA0
3
1PA1
4
・
・
・
・
・
・
1PA7
10
1PC7(IBF)
1PC6(STB)
1PC3(INT)
38
37
34
1PB7
18
・
・
・
8255(2) 側
信号
ピン
2PA0
51
2PA1
52
・
・
・
・
・
・
2PA7
58
2PB7
2PC2
66
81
※ ピン番号はTNS-9601のものです。
- 51 -
Interface Corporation
TUT-0034
<PCI-2747Aを2枚使用する場合>
8255(1)
信号
PA0
PA1
・
・
・
PA7
側
ピン
CNA2
CNA3
・
・
・
CNA9
PC7(IBF)
PC6(STB)
PC3(INT)
CNC9
CNC8
CNC5
PB7
CNB9
・
・
・
8255(2)
信号
PA0
PA1
・
・
・
PA7
PB7
PC2
側
ピン
CNA2
CNA3
・
・
・
CNA9
CNB9
CNC4
※ ピン番号はTRM-2601のものです。2台のTRM-2601を接続するように配線してください。
※ 製品番号「0」のPCI-2747Aと製品番号「1」のPCI-2747Aを接続してください。
CPZ-2746を使用する場合
8255(1) 側
信号
ピン
1PA0
46
1PA1
45
・
・
・
・
・
・
1PA7
39
1PC7(IBF)
1PC6(STB)
1PC3(INT)
11
12
15
1PB7
31
・
・
・
8255(2) 側
信号
ピン
2PA0
94
2PA1
93
・
・
・
・
・
・
2PA7
87
2PB7
2PC2
79
64
※ ピン番号はTBZ-960xのものです。
これより、プログラムの作成を行います。まず、出力側のプログラムから作成します。
Interface Corporation
- 52 -
TUT-0034
Step1.プロジェクトの作成(モード1出力側)
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode1_Send)を作成します。
2. プロジェクトにFBIPPI.LIBファイル,FBIPPI.Hファイルのパス設定を行い、ライブラリファイル
“Fbippi.lib”をリンクさせます。
3. 作成したプログラムに、PPI製品の初期化と終了処理を行う関数を追加します。
(ここまでの手順は『23ページ 4.1 モード0入力/出力』のStep1∼Step3と同様となりますので、
そちらを参照してください。ただし、このプログラムでは出力側の処理のみを行いますので、
PCI-2747Aを使用する場合でも初期化と終了処理は一度だけ行います。)
Step2.モード1出力
1. データ出力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE1_SEND_DIALOG」をダブ
ルクリックします。
・表示されたダイアログボックスから、必要のないボタン,スタティックテキストを削除します。
「OK」ボタン,「キャンセル」ボタン,「TODO:ダイアログのコントロールをここに配置」とい
うスタティックテキストをそれぞれ選択し、Deleteキーを押してください。
・コントロールから「ボタン」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDSEND
PPIモード1 出力
2. データ出力処理を開始するためのメンバ関数“OnCmdSend”の作成を行います。
ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の追
加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode1_Send
CPpiMode1_SendDlg
IDC_CMDSEND
WM_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、“OnCmdSend”となっていることを確
認し、「OK」をクリックします。
- 53 -
Interface Corporation
TUT-0034
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 3-1)のコードを記述します。
(List 3-1 CPpiMode1_SendDlg クラスの OnCmdSend 関数のコード)
void CPpiMode1_SendDlg::OnCmdSend()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
INT
nLoop;
// for ループ用
BYTE
bRecv;
// 受信データ
BYTE
bSend;
// 送信データ
BOOL
fNextSend;
// 制御信号監視用フラグ
// 8255①の設定を行います
// グループ A = Mode1 出力
// グループ B = Mode0 入力
// [制御データ = 10100011]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,0xa3);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
}
// INT 信号を有効にするため、8255①グループ A の WIE に 1 をセットします
// [制御データ = 00001101]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,0x0d);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のビットセットに失敗しました","制御データ設定エラー", MB_ICONERROR);
}
for(nLoop=0;nLoop<=255;nLoop++){
bSend = nLoop;
// 8255①のポート A からデータを出力します
nRet = PpiOutputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_A,bSend);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート A の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255①の 1PB7 の状態を監視し、High になるまで待機します
fNextSend = false;
while(fNextSend == false){
nRet = PpiInputPort(ghDeviceHandle,
FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_B,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート B の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x80){
fNextSend = true;
}
}
}
MessageBox("送信完了","データ送信確認", MB_ICONINFORMATION);
}
以上で、モード1データ出力のプログラムは完成です。
Interface Corporation
- 54 -
TUT-0034
Step3.プロジェクトの作成(モード0入力側)
モード1での出力確認用にモード0でのデータ入力プログラムの作成を行います。
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode0_Recv)を作成します。
2. プロジェクトにFBIPPI.LIBファイル,FBIPPI.Hファイルのパス設定を行い、ライブラリファイル
“Fbippi.lib”をリンクさせます。
3. 作成したプログラムに、PPI製品の初期化と終了処理を行う関数を追加します。
(ここまでの手順は『23ページ 4.1 モード0入力/出力』のStep1∼Step3と同様になりますので、
そちらを参照してください。ただし、PCI-2747Aを使用する場合はデバイス名を2枚目の製品の
ものに変更し、コントローラの番号を1(FBIPPI_8255_CONTROLLER1)に変更してください。)
Step4.モード0入力
1. データ入力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE0_RECV_DIALOG」をダブ
ルクリックします。
・表示されたダイアログボックスから、必要のないボタン,スタティックテキストを削除します。
「OK」ボタン,「キャンセル」ボタン,「TODO:ダイアログのコントロールをここに配置」とい
うスタティックテキストをそれぞれ選択し、Deleteキーを押してください。
・コントロールから「ボタン」と「エディットボックス」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDRECV
PPIモード0 入力
・同様にして、エディットボックスにカーソルを合わせ、右クリック→「プロパティ」を選択し
て以下のように設定します。
ID
IDC_TXTMON
・「スタイル」タブを選択し、「複数行」と「改行を許可」のチェックボックスにチェックを入
れます。(ダイアログボックスへのコントロールの配置は『38ページ 4.2 モード1入力』の
モード1入力を参照してください)
- 55 -
Interface Corporation
TUT-0034
2. 受信データを表示するためのメンバ変数“m_TxtMon”を作成します。
・先程作成した「エディットボックス」にカーソルを合わせ、右クリック→「Class Wizard」を選
択します。「メンバ変数」タブを選択し、以下のように設定した後、「変数の追加」をクリッ
クします。
プロジェクト
クラス名
コントロールID
PpiMode0_Recv
CPpiMode0_RecvDlg
IDC_TXTMON
・メンバ変数を決定するダイアログが表示されますので、以下のように設定し、「OK」をクリッ
クします。これでメンバ変数“m_TxtMon”が追加されました。
メンバ変数
m_TxtMon
カテゴリ
値
変数のタイプ
Cstring
3. データ受信のポーリングを行うためにTimer関数を作成します。
再びClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数
の追加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode0_Recv
CPpiMode0_RecvDlg
CPpiMode0_RecvDlg
WM_TIMER
・CPpiMode0_RecvDlgにタイマ識別変数の追加を行います。ワークスペースの「FileView」を表示
し、「PpiMode0_Recv ファイル」下の「Resource Files」フォルダを展開します。
“CPpiMode0_RecvDlg.c”をダブルクリックしてを開き、(List 3-2)の網掛けの部分の記述を追加し
ます。
(List 3-2 CPpiMode0_RecvDlg.c のコード)
// PpiMode0_RecvDlg.cpp : インプリメンテーション ファイル
//
#include
#include
#include
#include
"stdafx.h"
"PpiMode1_Recv.h"
"PpiMode1_RecvDlg.h"
"Fbippi.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
HANDLE
UINT
ghDeviceHandle;
timerID = 0;
Interface Corporation
// デバイスハンドル
// タイマ ID
- 56 -
TUT-0034
4. データ入力処理を開始するためのメンバ関数“OnCmdRecv”の作成を行います。
ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の追
加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode0_Recv
CPpiMode0_RecvDlg
IDC_CMDRECV
WM_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、“OnCmdRecv”となっていることを確
認し、「OK」をクリックします。
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 3-3)のコードを記述します。
(List 3-3 CPpiMode0_RecvDlg クラスの OnCmdRecv 関数のコード)
void CPpiMode0_RecvDlg::OnCmdRecv()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
// 8255②の設定を行います
// Mode = 0
// PortA = OUT
// PortB = IN
// PortC = OUT
// [制御データ = 10010010]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,0x92);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②のポート C からデータを出力します
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_C,0xff);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポートの出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// もし Timer が作成されていなければ Timer を作成して受信を開始する
if(timerID==0){
timerID=SetTimer(1, 10, NULL);
if(timerID==0){
MessageBox("タイマの作成に失敗しました","Timer 設定エラー", MB_ICONERROR);
}
}
}
- 57 -
Interface Corporation
TUT-0034
5. ポーリング処理をTimer関数に追加します。
・ワークスペースの「ClassView」を表示し、CPpiMode0_RecvDlgクラスを展開します。「OnTimer()」
をダブルクリックしてソースコードを開き、“OnTimer”関数に(List 3-4)のコードを記述します。
(List 3-4 CPpiMode0_RecvDlg クラスの OnTimer 関数のコード)
void CPpiMode0_RecvDlg::OnTimer(UINT nIDEvent)
{
// TODO: この位置にメッセージ ハンドラ用のコードを追加するか
//
またはデフォルトの処理を呼び出してください
INT
nRet;
// 関数の実行結果
BYTE
bRecv;
// 受信データ
BOOL
fReadOk;
// 制御信号監視用フラグ
// タイマ処理
if(nIDEvent==timerID){
// 1BP7 の状態を監視し High になるまで待機します
fReadOk = false;
while(fReadOk == false){
nRet = PpiInputPort(ghDeviceHandle,
FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_B,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート A の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x00){
fReadOk = true;
}
}
// 8255②ポート A よりデータ(1 文字)を入力します
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_A,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート A の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255①に DAK の Low パルスを送信します
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_C,0xfb);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
}
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_C,0xff);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
}
// 入力されたデータをエディットボックスに表示します
m_TxtMon.Format("%d", bRecv);
UpdateData(FALSE);
// 受信が終了していればタイマを破棄して受信を終了する
if(bRecv == 255){
KillTimer(timerID); // タイマの破棄
timerID=0;
// timerID を初期化する
}
}
CDialog::OnTimer(nIDEvent);
}
・次に、Timer関数の終了処理を記述します。「ClassView」で「OnDestroy」関数をダブルクリッ
クして表示し、(List 3-5)の網掛け部分を追加します。
Interface Corporation
- 58 -
TUT-0034
(List 3-5 OnTimer 関数の終了処理のコード)
void CPpiMode0_RecvDlg::OnDestroy()
{
CDialog::OnDestroy();
// TODO: この位置にメッセージ ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
// タイマが作成されていれば、破棄を行う
if(timerID!=0)
KillTimer(timerID);
// 製品クローズ
nRet = PpiClose(ghDeviceHandle);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("FBIPPI1 のクローズに失敗しました","製品クローズエラー", MB_ICONERROR);
}
}
以上で、モード0データ入力のプログラムは完成です。
プログラムの入力が終わったら、保存した後、入力側/出力側のプログラムをそれぞれ実行してく
ださい。まず出力側の「PPI モード1出力」ボタンをクリックしてください。まだ、なにもおきま
せん。今度は入力側の「データ入力」ボタンをクリックしてください。入力側のテキストボック
ス(txtMon)に下図のように表示されます。
※ 1∼255まで表示され、255が表示されると通信が終了します。
これも、入力側/出力側、それぞれのプログラムが特定の条件を満たさない限りデータの入力/出力
を行わないようにしているためです。
D0~D7
8255
ACK
OBF
INTR
以上が、モード1による制御信号を用いた簡単な通信プログラムです。
- 59 -
Interface Corporation
TUT-0034
4.4 モード2入力
ここでは、PPI製品の8255(1)をモード2に設定し、8255(2)より出力されるデータを入力する制御信
号を用いた簡単な通信プログラムの作成を行います。
下図にモード2設定時のタイミングチャートを示します。
H
L
H
L
H
L
H
L
H
L
H
L
WR
OBF
INTR
ACK
STB
IBF
データ
出力データ
入力データ
H
L
RD
タイミングチャートを見る限りでは、データ・ポートが双方向であること以外、入出力時におけ
る制御信号の変化は、モード1の入力,モード1の出力時におけるそれと変わりはありません。
そこで、通信プログラムは『38ページ 4.2 モード1入力』で使用したものを流用し、端子台の
結線を変更することで、動作の検証を行ってみます。
では、下図のように対応するピンを接続してください。
-COM1~ -COM4はI/Oモジュール内で接続されていますので、接続は不要です。
ただし、外部回路との接続時は、必ず接続してください。
<PCI-2746C,CTP-2746を使用する場合>
8255(1) 側
信号
ピン
1PA0
3
1PA1
4
・
・
・
・
・
・
1PA7
10
1PC7(OBF)
1PC6(ACK)
1PC5(IBF)
1PC4(STB)
1PC3(INT)
38
37
36
35
34
1PB7
18
・
・
・
8255(2) 側
信号
ピン
2PA0
51
2PA1
52
・
・
・
・
・
・
2PA7
58
2PB7
2PC2
2PB6
2PC3
※ ピン番号はTNS-9601のものです。
Interface Corporation
- 60 -
66
81
65
82
TUT-0034
<PCI-2747Aを2枚使用する場合>
8255(1)
信号
PA0
PA1
・
・
・
PA7
側
ピン
CHA2
CHA3
CHA9
PC7(OBF)
PC6(ACK)
PC5(IBF)
PC4(STB)
PC3(INT)
CHC9
CHC8
CHC7
CHC6
CHC5
PB7
CNB9
・
・
・
8255(2)
信号
PA0
PA1
・
・
・
PA7
側
ピン
CHA2
CHA3
PB7
PC2
PB6
PC3
CHA9
CNB9
CHC4
CNB8
CHC5
※ ピン番号はTRM-2601のものです。2台のTRM-2601を接続するように配線してください。
※ I/Oモジュール番号「0」のPCI-2747Aを8255(1)の端子台に、I/Oモジュール番号「1」のPCI-2747A
を8255(2)の端子台に接続してください。
<CPZ-2746を使用する場合>
8255(1) 側
信号
ピン
1PA0
46
1PA1
45
・
・
・
・
・
・
1PA7
39
1PC7(OBF)
1PC6(ACK)
1PC5(IBF)
1PC4(STB)
1PC3(INT)
11
12
13
14
15
1PB7
31
・
・
・
8255(2) 側
信号
ピン
2PA0
94
2PA1
93
・
・
・
・
・
・
2PA7
87
2PB7
2PC2
2PB6
2PC3
79
64
80
63
※ ピン番号はTBZ-960xのものです。
これより、プログラムの作成を行います。まず、入力側のプログラムから作成します。
- 61 -
Interface Corporation
TUT-0034
Step1.プロジェクトの作成(モード2入力側)
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode2_Recv)を作成します。
『モー
(
ド0入力/出力』でのStep1のメインウィンドウの作成を参照してください。)
2. プロジェクトにFbiPpi.Libファイル,FbiPpi.Hファイルのパス設定を行い、ライブラリファイ
ル”FpiPpi.lib”をリンクさせます。(『23ページ 4.1 モード0入力/出力』でのStep2のDLL関数
宣言を参照してください。)
3. 初期化処理と終了処理を行う関数を追加します。
『23ページ
(
4.1 モード0入力/出力』
でのStep3
の初期化処理と終了処理を参照してください。)
・“FbiPpi.H”ファイルのインクルード,デバイスハンドルの変数宣言を行います。『モード0入力/
出力』における(List 1-3)と同様にコードの追加を行います。(ただし、PCI-2746C,PCI-2747Aにお
ける使用製品に対応したデバイスハンドル変数の区別を行う必要はありません。)
・「MFC ClassWizard」で以下のように設定し、メッセージ「WM_CREATE」,「WM_DESTROY」に対
する関数に初期化,終了コードをそれぞれ実装します。(『23ページ 4.1 モード0入力/出力』の
List1-4,List1-5を参照してください。ただし、使用製品に対応したコード変更,追加を行う必要は
ありません。)
プロジェクト
クラス名
オブジェクト
PpiMode2_Recv
CPpiMode2_RecvDlg
CPpiMode2_RecvDlg
Step2.モード2入力
これよりモード2入力部分のプログラムを作成するわけですが、実際は『38ページ 4.2 モード
1入力』のプログラムコードを流用して行きます。
1. データ入力を行うダイアログボックスの設定を行います。『38ページ 4.2 モード1入力』の
Step2の1を参照してください。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE2_RECV_DIALOG」をダブ
ルクリックします。表示されたダイアログボックスから、必要のないボタン,スタティックテキ
ストを削除します。
・コントロールから「ボタン」と「エディットボックス」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDRECV
PPIモード2入力
・同様にして、エディットボックスにカーソルを合わせ、右クリック→「プロパティ」を選択し
て以下のように設定します。
ID
IDC_TXTMON
・「スタイル」タブを選択し、テキストの配置を「右端」に変更し、「複数行」にチェックを入
れます。
Interface Corporation
- 62 -
TUT-0034
2. 受信データを表示するためのメンバ変数"m_TxtBox"を作成します。『38ページ 4.2 モード1
入力』のStep2の2を参照してください。
・先程作成した「エディットボックス」にカーソルを合わせ、右クリック→「Class Wizard」を選
択します。「メンバ変数」タブを選択し、以下のように設定した後、「変数の追加」をクリッ
クします。
プロジェクト
クラス名
コントロールID
PpiMode2_Recv
CPpiMode2_RecvDlg
IDC_TXTBOX
・メンバ変数を決定するダイアログが表示されますので、以下のように設定し、「OK」をクリッ
クします。これでメンバ変数"m_TxtBox"が追加されました。
3. Timer関数を作成します。『38ページ 4.2 モード1入力』のStep2の3を参照してください。
再びClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数
の追加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode2_Recv
CPpiMode2_RecvDlg
CPpiMode2_RecvDlg
WM_TIMER
・CPpiMode2_RecvDlgにタイマ識別変数の追加を行います。"CPpiMode2_RecvDlg.Cpp"ファイルを
開き、(List 4-1)の網掛けの部分の記述を追加します。
(List 4-1:PpiMode2_RecvDlg.cpp の変更コード)
// PpiMode2_RecvDlg.cpp : インプリメンテーション ファイル
//
#include "stdafx.h"
#include "PpiMode2_Recv.h"
#include "PpiMode2_RecvDlg.h"
#include "fbippi.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
HANDLE ghDeviceHandle;
UINT
m_timerID = 0;
//デバイスハンドル
//タイマ ID
- 63 -
Interface Corporation
TUT-0034
4. データ入力処理を開始するためのメンバ関数"OnCmdRecv"の作成を行います。『38ページ 4.2
モード1入力』のStep2の4を参照してください。
ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の追
加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode2_Recv
CPpiMode2_RecvDlg
IDC_CMDRECV
BM_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、"OnCmdRecv"となっていることを確
認し、「OK」をクリックします。
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 4-2)のように記述します。
(List 4-2:CPpiMode2_RecvDlg クラスの OnCmdrecv 関数のコード
void CPpiMode2_RecvDlg::OnCmdrecv()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
// 8255①の設定を行います
// グループ A = Mode2 入力
この部分が変更箇所です。
// グループ B = Mode0 入力
// [制御データ = 11000011]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,0xC3);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// INT 信号を有効にするため、8255①グループ A の RIE に 1 をセットします
// [制御データ = 00001001]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,0x09);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のビットセットに失敗しました","制御データ設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// もし Timer が作成されていなければ Timer を作成して受信を開始する
if(m_timerID==0){
m_timerID=SetTimer(1, 10, NULL);
if(m_timerID==0){
MessageBox("タイマの作成に失敗しました","Timer 設定エラー", MB_ICONERROR);
}
}
}
Interface Corporation
- 64 -
TUT-0034
5. ポーリング処理をTimer関数に追加します。『38ページ 4.2 モード1入力』のStep2の5を参
照してください。
・ワークスペースの「ClassView」を表示し、CPpiMode1_RecvDlgクラスを展開します。「OnTimer()」
をダブルクリックしてソースコードを開き、"OnTimer"関数に(List 4-3)のコードを記述します。
(List 4-3:CPpiMode2_RecvDlg クラスの OnTimer 関数のコード
void CPpiMode1InDlg::OnTimer(UINT nIDEvent)
{
// TODO: この位置にメッセージ ハンドラ用のコードを追加するか
//
またはデフォルトの処理を呼び出してください
INT
nRet;
// 関数の実行結果
BYTE
bRecv;
// 受信データ
BOOL
fReadOk;
// 制御信号監視用フラグ
// タイマ処理
if(nIDEvent==m_timerID){
// 1BP7 の状態を監視し High になるまで待機します
fReadOk = false;
while(fReadOk == false){
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_B,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート A の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x80){
fReadOk = true;
}
}
// 8255①ポート A よりデータ(1 文字)を入力します
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_A,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート A の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 入力されたデータをエディットボックスに表示します
m_TxtBox.Format("%d", bRecv);
UpdateData(FALSE);
// 受信が終了していればタイマを破棄して受信を終了する
if(bRecv == 255){
KillTimer(m_timerID); // タイマの破棄
m_timerID=0;
// m_timerID を初期化する
}
}
}
- 65 -
Interface Corporation
TUT-0034
・次に、Timer関数の終了処理を記述します。「Class View」で「OnDestroy」関数をダブルクリックし
て表示し、(List4-4)の網掛け部分を追加します。
(List 4-4 OnTimer 関数の終了処理のコード)
void CPpiMode2_RecvDlg::OnDestroy()
{
CDialog::OnDestroy();
// TODO: この位置にメッセージ ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
// タイマが作成されていれば、破棄を行う
if(m_timerID!=0)
KillTimer(m_timerID);
// ボードクローズ
nRet = PpiClose(ghDeviceHandle);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("FBIPPI1 のクローズに失敗しました","製品クローズエラー", MB_ICONERROR);
}
}
以上で、モード2データ入力のプログラムは完成です。
Step3.プロジェクトの作成(モード0出力側)
モード2での入力確認用にモード0でのデータ出力プログラムの作成を行います。
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名)を作成します。(プロジェクト
名:PpiMode0_Send )を作成します。(『23ページ 4.1 モード0入力/出力』でのStep1のメインウ
ィンドウの作成を参照してください)
2. プロジェクトにFbiPpi.Libファイル,FbiPpi.Hファイルのパス設定を行い、ライブラリファイ
ル”FpiPpi.lib”をリンクさせます。(『23ページ 4.1 モード0入力/出力』でのStep2のDLL関数
宣言を参照してください)
3. 初期化処理と終了処理を行う関数を追加します。(『23ページ 4.1 モード0入力/出力』での
Step3の初期化処理と終了処理を参照してください)
・“FbiPpi.H”ファイルのインクルード,デバイスハンドルの変数宣言を行います。『23ページ 4.1
モード0入力/出力』と同様にコードの追加を行います。(ただし、PCI-2746C,PCI-2747Aにおける
使用製品に対応したデバイスハンドル変数の区別を行う必要はありません。)
・「MFC ClassWizard」で以下のようにプロジェクト,クラス名,オブジェクトを設定し、メッセージ
「WM_CREATE」,「WM_DESTROY」に対する関数に初期化,終了コードをそれぞれ実装します。
(ただしPCI-2747Aは2枚使用するためOpen処理の場合、モード2出力で使用する製品とモード0
入力で使用する製品をデバイス名で区別する必要があります。)
プロジェクト
PpiMode0_Send
クラス名
CPpiMode0_SendDlg
オブジェクト
CPpiMode0_SendDlg
Interface Corporation
- 66 -
TUT-0034
Step4.モード0出力
これよりモード0出力部分のプログラムを作成するわけですが、実際は『38ページ 4.2 モード
1入力』で作成した「モード0出力」のプログラムを流用して行きます。
1. データ出力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE0_SEND_DIALOG」をダブ
ルクリックします。表示されたダイアログボックスから、必要のないボタン,スタティックテキ
ストを削除します。「コントロールから「ボタン」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDSEND
PPIモード0出力
2. データ出力処理を開始するためのメンバ関数"OnCmdSend"の作成を行います。
ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の追
加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode0_Send
CPpiMode0_SendDlg
IDC_CMDSEND
BM_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、"OnCmdSend"となっていることを確
認し、「OK」をクリックします。
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 4-5)のコードを記述します。網掛けの部分が変更箇所です。
(List 4-5:CPpiMode0_SendDlg クラスの OnCmdsend 関数のコード
void CPpiMode0_SendDlg::OnCmdsend()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
INT
nLoop;
// for ループ用
BYTE
bRecv;
// 受信データ
BYTE
bSend;
// 送信データ
BOOL
fNextSend;
// 制御信号監視用フラグ
//
//
//
//
PCI-2746C の場合は" FBIPPI_8255_CONTROLLER2 "
PCI-2747A の場合は" FBIPPI_8255_CONTROLLER1 "
で設定してください。
以下からのコードは PCI-2746C で設定しています
// 8255②の設定を行います
// Mode = 0
// PortA = OUT
// PortB = IN
// PortC = OUT
// [制御データ = 10000010]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,0x82);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②より 0∼255 の数値データを出力します
for(nLoop=0;nLoop<=255;nLoop++){
bSend = nLoop;
- 67 -
Interface Corporation
TUT-0034
// 8255②のポート A からデータを出力します
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_A,bSend);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート A の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②の STB に Low パルスを送信します
// 8255②の 2PC3 を Low にセットし入力側のデータをラッチします
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_C,0xf7);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②の 2PC3 を High にセットし入力側のデータラッチを終了します
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_C,0xff);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②の 2PB6 の状態を監視し、Low になるまで待機します
fNextSend = false;
while(fNextSend == false){
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_B,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート B の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x40)==0x00){
fNextSend = true;
}
}
}
MessageBox("送信完了","データ送信確認", MB_ICONINFORMATION);
}
プログラムの入力が終わったら、保存し、入力側/出力側のプログラムをそれぞれ実行してくださ
い。『38ページ 4.2 モード1入力』と同一の結果が得られることが確認できます。
Interface Corporation
- 68 -
TUT-0034
4.5 モード2出力
ここでは、モード2に設定した8255(1)からデータを出力し、8255(2)よりデータを入力する『60ペー
ジ 4.4 モード2入力』とは逆の動作をする、制御信号を用いた簡単な通信プログラムの作成を
行います。
配線は、端子台上で対応するピンをビニール被覆線で接続します。
では、出力側のプログラムから作成します。
Step1.プロジェクトの作成(モード2出力側)
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode2_Send)を作成します。
(『23ページ 4.1 モード0入力/出力』でのStep1のメインウィンドウの作成を参照してくださ
い。)
2. プロジェクトにFbiPpi.Libファイル,FbiPpi.Hファイルのパス設定を行い、ライブラリファイ
ル”FpiPpi.lib”をリンクさせます。(『23ページ 4.1 モード0入力/出力』でのStep2のDLL関数宣
言を参照してください。)
3. 初期化処理と終了処理を行う関数を追加します。(『23ページ 4.1 モード0入力/出力』での
Step3の 初期化処理と終了処理を参照してください。)
・“FbiPpi.H”ファイルのインクルード,デバイスハンドルの変数宣言を行います。『23ページ 4.1
モード0入力/出力』におけるプログラム作成と同様にコードの追加を行います。(ただし、
PCI-2746C,PCI-2747Aにおける使用製品に対応したデバイスハンドル変数の区別を行う必要は
ありません。)
・「MFC ClassWizard」で以下のようにプロジェクト,クラス名,オブジェクトを設定し、メッセージ
「WM_CREATE」,「WM_DESTROY」に対する関数に初期化,終了コードをそれぞれ実装します。
プロジェクト
PpiMode2_Send
クラス名
CPpiMode2_SendDlg
オブジェクト
CPpiMode2_SendDlg
- 69 -
Interface Corporation
TUT-0034
Step2.モード2出力
これよりモード0出力部分のプログラムを作成するわけですが、実際は『69ページ 4.5 モード2
出力』に作成した『69ページ 4.5 モード2出力』のプログラムを流用して行きます。
1. データ出力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE2_SEND_DIALOG」をダブ
ルクリックします。表示されたダイアログボックスから、必要のないボタン,スタティックテキ
ストを削除します。「コントロールから「ボタン」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDSEND
PPIモード2出力
2. データ出力処理を開始するためのメンバ関数"OnCmdSend"の作成を行います。
・ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の
追加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode2_Send
CPpiMode2_SendDlg
IDC_CMDSEND
BM_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、"OnCmdSend"となっていることを確
認し、「OK」をクリックします。
Interface Corporation
- 70 -
TUT-0034
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 5-1)のコードを記述します。網掛けの部分が変更箇所です。
(List 5-1:CPpiMode2_SendDlg クラスの OnCmdsend 関数のコード
void CPpiMode2_SendDlg::OnCmdsend()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
INT
nLoop;
// for ループ用
BYTE
bRecv;
// 受信データ
BYTE
bSend;
// 送信データ
BOOL
fNextSend;
// 制御信号監視用フラグ
// 8255①の設定を行います
// グループ A=Mode2
// グループ B=Mode0 入力
// [制御データ = 11xxx011]
nRet = PpiControl(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, 0xC3);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// INT 信号を有効にするために 8255①グループ A の WIE に 1 をセットします
// [制御データ = 00001101]
nRet = PpiControl(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, 0x0d);
// 8255①より 0∼255 の数値データを出力します
for(nLoop=0;nLoop<=255;nLoop++){
bSend = nLoop;
// 8255①のポート A からデータを出力します
nRet = PpiOutputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,FBIPPI_PORT_A,bSend);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート A の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255①の 1PB7 の状態を監視し High になるまで待機します
fNextSend = false;
while(fNextSend == false){
nRet = PpiInputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, FBIPPI_PORT_B, &bRecv);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート B の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x80){
fNextSend = true;
}
}
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート A の出力に失敗しました","データ送信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
}
MessageBox("送信完了","データ送信確認", MB_ICONINFORMATION);
}
- 71 -
Interface Corporation
TUT-0034
Step3.プロジェクトの作成(モード0入力側)
モード2での出力確認用にモード0でのデータ入力プログラムの作成を行います。
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode0_Recv)を作成します。
(『モード0入力/出力』でのStep1のメインウィンドウの作成を参照してください)
2. プロジェクトにFbiPpi.Libファイル,FbiPpi.Hファイルのパス設定を行い、ライブラリファイ
ル”FpiPpi.lib”をリンクさせます。(『23ページ 4.1 モード0入力/出力』でのStep2のDLL関数宣
言を参照してください)
3. 初期化処理と終了処理を行う関数を追加します。(『23ページ 4.1 モード0入力/出力』での
Step3の 初期化処理と終了処理を参照しながら追加してください)
・“FbiPpi.H”ファイルのインクルード,デバイスハンドルの変数宣言を行います。『23ページ 4.1
モード0入力/出力』におけるプログラム作成と同様にコードの追加を行います。
(ただし、PCI-2746C,PCI-2747Aにおける使用製品に対応したデバイスハンドル変数の区別を行
う必要はありません。)
・「MFC ClassWizard」で以下のように設定し、メッセージ「WM_CREATE」,「WM_DESTROY」に対
する関数に初期化,終了コードをそれぞれ実装します。(ただし、PCI-2747Aは2枚使用するため
Open処理の場合、モード2出力で使用する製品とモード0入力で使用する製品をデバイス名で区
別する必要があります。)
プロジェクト
クラス名
オブジェクト
PpiMode0_Recv
CPpiMode0_RecvDlg
CPpiMode0_RecvDlg
Step4.モード0入力
これよりモード0入力部分のプログラムを作成するわけですが、実際は『50ページ 4.3 モード
1出力』のモード0入力のプログラムを流用して行きます。
1. データ入力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIMODE0_RECV_DIALOG」をダブ
ルクリックします。表示されたダイアログボックスから、必要のないボタン,スタティックテキ
ストを削除します。
・コントロールから「ボタン」と「エディットボックス」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
キャプション
IDC_CMDRECV
PPIモード0入力
・同様にして、エディットボックスにカーソルを合わせ、右クリック→「プロパティ」を選択し
て以下のように設定します。
ID
IDC_TXTBOX
・「スタイル」タブを選択し、テキストの配置を「右端」に変更し、「複数行」にチェックを入
れます。
Interface Corporation
- 72 -
TUT-0034
2. 受信データを表示するためのメンバ変数"m_TxtBox"を作成します。
先程作成した「エディットボックス」にカーソルを合わせ、右クリック→「Class Wizard」を選
択します。「メンバ変数」タブを選択し、以下のように設定した後、「変数の追加」をクリッ
クします。
プロジェクト
クラス名
コントロールID
PpiMode0_Recv
CPpiMode0_RecvDlg
IDC_TXTBOX
・メンバ変数を決定するダイアログが表示されますので、以下のように設定し、「OK」をクリッ
クします。これでメンバ変数"m_TxtBox"が追加されました。
3. データ受信のポーリングを行うためにTimer関数を作成します。
・再びClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数
の追加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode0_Recv
CPpiMode0_RecvDlg
CPpiMode0_RecvDlg
WM_TIMER
・CPpiMode1_RecvDlgにタイマ識別変数の追加を行います。"CPpiMode0_RecvDlg.Cpp"ファイルを
開き、(List5-2)の網掛けの部分の記述を追加します。
(List 5-2:PpiMode0_RecvDlg.cpp の変更コード)
// PpiMode0_RecvDlg.cpp : インプリメンテーション ファイル
//
#include
#include
#include
#include
"stdafx.h"
"PpiMode0_Recv.h"
"PpiMode0_RecvDlg.h"
"FbiPpi.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
HANDLE ghDeviceHandle;
UINT m_timerID;
4. データ入力処理を開始するためのメンバ関数"OnCmdRecv"の作成を行います。
・ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の追
加」をクリックします。
プロジェクト
クラス名
オブジェクト
メッセージ
PpiMode0_Recv
CPpiMode0_RecvDlg
IDC_CMDRECV
BM_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、"OnCmdRecv"となっていることを確
認し、「OK」をクリックします。
- 73 -
Interface Corporation
TUT-0034
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 5-3)のコードを記述します。
(List 5-3:PpiMode0_RecvDlg クラス OnCmdrecv 関数のコード)
void CPpiMode0_RecvDlg::OnCmdrecv()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
//
//
//
//
PCI-2746C の場合は" FBIPPI_8255_CONTROLLER2 "
PCI-2747A の場合は" FBIPPI_8255_CONTROLLER1 "
で設定してください。
以下からのコードは PCI-2746C で設定しています
// 8255②の設定を行います
// Mode = 0
// PortA = IN
// PortB = IN
// PortC = OUT
// [制御データ = 10010010]
nRet = PpiControl(ghDeviceHandle,FBIPPI_8255_CONTROLLER2,0x92);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255②のモード設定に失敗しました","制御データ設定エラー", MB_ICONERROR);
}
// 8255②のポート C からデータを出力します
nRet = PpiOutputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, FBIPPI_PORT_C, 0xff);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポートの出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// もし Timer が作成されていなければ Timer を作成して受信を開始する
if(m_timerID==0){
m_timerID=SetTimer(1, 10, NULL);
if(m_timerID==0){
MessageBox("タイマの作成に失敗しました","Timer 設定エラー", MB_ICONERROR);
}
}
}
Interface Corporation
- 74 -
TUT-0034
5. ポーリング処理をTimer関数に追加します。
・ワークスペースの「ClassView」を表示し、CPpiMode0_RecvDlgクラスを展開します。「OnTimer()」
をダブルクリックしてソースコードを開き、"OnTimer"関数に(List 5-4)のコードを記述します。
(List 5-4:PpiMode0_RecvDlg クラスの OnTimer 関数のコード)
void CPpiMode0_RecvDlg::OnTimer(UINT nIDEvent)
{
// TODO: この位置にメッセージ ハンドラ用のコードを追加するか
//
またはデフォルトの処理を呼び出してください
INT
nRet;
// 関数の実行結果
BYTE
bRecv;
// 受信データ
BOOL
fReadOk;
// 制御信号監視用フラグ
// タイマ処理
if(nIDEvent == m_timerID){
// 2PB7 の状態を監視し High になるまで待機します(OBF のポーリング)
fReadOk = false;
while(fReadOk == false){
nRet = PpiInputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, FBIPPI_PORT_B, &bRecv);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート A の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x00){
fReadOk = true;
}
}
// 8255②に DAK の Low パルスを送信します
nRet = PpiOutputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, FBIPPI_PORT_C, 0xfb);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 8255②ポート A よりデータ(1 文字)を入力します
nRet = PpiInputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, FBIPPI_PORT_A, &bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート A の入力に失敗しました", "データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// 入力されたデータをエディットボックスに表示します
m_TxtBox.Format("%d", bRecv);
UpdateData(FALSE);
// 8255②に DAK の High パルスを送信します
nRet = PpiOutputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER2, FBIPPI_PORT_C, 0xff);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255②ポート C の出力に失敗しました","データ送信設定エラー", MB_ICONERROR);
}
// 受信が終了していればタイマを破棄して受信を終了する
if(bRecv == 255){
KillTimer(m_timerID); // タイマの破棄
timerID=0;
// m_timerID を初期化する
}
}
CDialog::OnTimer(nIDEvent);
}
- 75 -
Interface Corporation
TUT-0034
・次に、Timer関数の終了処理を記述します。「ClassView」で「OnDestroy」関数をダブルクリックし
て表示し、(List5-5)の網掛け部分を追加します。
(List 5-5 OnTimer 関数の終了処理のコード)
void CPpiMode0_RecvDlg::OnDestroy()
{
CDialog::OnDestroy();
// TODO: この位置にメッセージ ハンドラ用のコードを追加してください
INT
nRet;
// 関数の実行結果
// タイマが作成されていれば、破棄を行う
if(m_timerID!=0)
KillTimer(m_timerID);
// 製品クローズ
nRet = PpiClose(ghDeviceHandle);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("FBIPPI1 のクローズに失敗しました","製品クローズエラー", MB_ICONERROR);
}
}
以上でモード2データ入力のプログラムは完成です。
※ モード2ではDAK信号がLレベルの時のみデータの出力がされます。
プログラムの入力が終わったら、保存した後、入力側/出力側のプログラムをそれぞれ実行してく
ださい。『50ページ 4.3 モード1出力』と同一の結果が得られることが確認できます。
Interface Corporation
- 76 -
TUT-0034
4.6 割り込み処理
ここでは、割り込み処理の方法に関し、記載します。
PPIの割り込みは、
・8255①のポートC接点3(ピン名:1PC3)
・8255①のポートC接点0(ピン名:1PC0)
・8255②のポートC接点3(ピン名:1PC3)
・8255②のポートC接点0(ピン名:1PC0)
の4つの割り込みを設定することができます。今回は、『50ページ 4.3 モード1出力』(List3-1)
を例にしてみます。つまり、上記の1番目にある“8255①のポートC接点3(ピン名:1PC3)”の割り込
みを使用します。
List 3-1の中に以下のコードがあります。
// 8255①の 1PB7 の状態を監視し、High になるまで待機します
fNextSend = false;
while(fNextSend == false){
nRet = PpiInputPort(ghDeviceHandle,FBIPPI_8255_CONTROLLER1,FBIPPI_PORT_B,&bRecv);
if(nRet!=FBIPPI_ERROR_SUCCESS){
MessageBox("8255①ポート B の入力に失敗しました","データ受信エラー", MB_ICONERROR);
nRet = PpiClose(ghDeviceHandle);
exit(0);
}
// ビット判定
if((bRecv & 0x80)==0x80){
fNextSend = true;
}
}
この処理は、8255①のINT信号の出力をポートBより入力し、INT信号が上がる(Hレベル)のをwhile
文によるループ処理で待っています。いわゆるINT信号のポーリングを行っているわけです。
ところで、このINT信号はPCIの割り込み信号線に対しても出力されています。つまり、内部的に
コンピュータ上で検出できるわけです。『50ページ 4.3 モード1出力』では割り込み信号入力
用に1PB7を利用し、接続された1PC3のINT信号の変化を検知していたわけですが、Win32APIを利
用した割り込み処理を使うことでこの結線は不要となります。
- 77 -
Interface Corporation
TUT-0034
「モード 1 出力」(『モード 1 出力』参照)
① データを出力する
② INT 信号を確認し H レベルになるまで待機する
③次のデータがある場合は①から繰り返す
「割り込みを使用しない」(List 3-1)
8255①の INT 信号が H レベルになるのを、while 文によ
るループ処理を行って待つ。
「割り込みを使用する」(List 6-1)
8255①の INT 信号が H レベルになるのを、Win32API の
割り込み処理を使って待つ。
WR
H
L
H
L
H
L
OBF
INT
WEI をセットしなければ、INT は
H レベルのままです。
ACK
外部への
出力データ
H
L
出力される新しいデータ
時間の経過
INTR 信号が H になる割り込み
処理で待ちます
Interface Corporation
- 78 -
TUT-0034
接続を下図のように変更します。
<PCI-2746C,CTP-2746を使用の場合>
8255(1) 側
信号
ピン
1PA0
3
1PA1
4
・
・
・
・
・
・
1PA7
10
1PC7(OBF)
1PC6(ACK)
・
・
・
38
37
8255(2) 側
信号
ピン
2PA0
51
2PA1
52
・
・
・
・
・
・
2PA7
58
2PB7
2PC2
66
81
※ ピン番号はTNS-9601のものです。
<PCI-2747Aを2枚使用の場合>
8255(1) 側
信号
ピン
PA0
CNA2
PA1
CNA3
・
・
・
PA7
CNA9
PC7(OBF)
PC6(ACK)
・
・
・
CNC9
CNC8
8255(2)
信号
PA0
PA1
・
・
・
PA7
側
ピン
CNA2
CNA3
PB7
PC2
CNA9
CNB9
CNC4
※ ピン番号はTRM-2601のものです。2台のTRM-2601を接続するように配線してください。
※ 製品番号「0」のPCI-2747Aを8255(1)の端子台に、製品番号「1」のPCI-2747Aを8255(2)の端子
台に接続してください。
<CPZ-2746を使用の場合>
8255(1) 側
信号
ピン
1PA0
46
1PA1
45
・
・
・
・
・
・
1PA7
39
1PC7(OBF)
1PC6(ACK)
・
・
・
11
12
8255(2) 側
信号
ピン
2PA0
94
2PA1
93
・
・
・
・
・
・
2PA7
87
2PB7
2PC2
79
64
※ ピン番号はTBZ-960xのものです。
- 79 -
Interface Corporation
TUT-0034
次に『50ページ 4.3 モード1出力』のモード1での出力プログラムを割り込み信号を利用した
ものに書き換えてみます。
割り込み処理における非同期I/O処理を実現するために、ここではWin32 APIに定義される以下の
関数、および構造体を使用しています。
・CreateEvent関数
イベントオブジェクトの作成を行います。
・Overlapped構造体
非同期I/O制御に必要な構造体です。
・WaitForSingleObject関数
オブジェクトがシグナル状態になるまで待機します
・CloseHandle関数
オブジェクトハンドルのクローズを行います。
各関数および構造体の詳細はMicrosoft社提供のWin32 APIリファレンスか、もしくはその他専門書
籍を参照してください。
Interface Corporation
- 80 -
TUT-0034
Step1.プロジェクト作成
1. Visual C++を起動し、新しいプロジェクト(プロジェクト名:PpiMode1_Send)を作成します。
2. プロジェクトにFBIPPI.LIBファイル,FBIPPI.Hファイルのパス設定を行い、ライブラリファイル
“Fbippi.lib”をリンクさせます。
3. 作成したプログラムに、PPI製品の初期化と終了処理を行う関数を追加します。
(ここまでの手順は『23ページ 4.1 モード0入力/出力』のStep1∼Step3と同様となりますので、
そちらを参照してください。ただし、このプログラムでは出力側の処理のみを行いますので、
PCI-2747Aを使用する場合でも初期化と終了処理は一度だけ行います。)
Step2.モード1出力(割り込み処理)
基本的には、モード1出力とプログラム作成手順は同じです。
1. 初期化処理処理で記述したPpiIntr_SendDlg.cppファイルの“HANDLE ghDeviceHandle”の後に、
“OVERLAPPED glpOverlapped “というコードを付け加えます。
2. 終了処理にイベントオブジェクト終了のコードを追加します。(下記の網掛け部分)
(List 6-1 CPpiIntr_SendDlg クラスの OnDestroy 関数のコード)
void CPpiIntr_SendDlg::OnDestroy()
{
CDialog::OnDestroy();
// TODO: この位置にメッセージ ハンドラ用のコードを追加してください
INT nRet;
//関数の実行結果
//PCI-2746C(PCI-2747A 使用時は 1 枚目)の製品をクローズします
nRet = PpiClose(ghDeviceHandle);
if(nRet != FBIPPI_ERROR_SUCCESS) {
MessageBox("製品 1 のクローズに失敗しました");
exit(0);
}
// 作成したイベントを終了します
CloseHandle(glpOverlapped.hEvent);
}
3. データ出力を行うダイアログボックスの設定を行います。
・ResourceViewを表示し、Dialogフォルダを展開して「IDD_PPIINTR_SEND_DIALOG」をダブル
クリックします。
・表示されたダイアログボックスから、必要のないボタン,スタティックテキストを削除します。
「OK」ボタン,「キャンセル」ボタン,「TODO:ダイアログのコントロールをここに配置」とい
うスタティックテキストをそれぞれ選択し、Deleteキーを押してください。
・コントロールから「ボタン」を選択し、ダイアログに貼り付けます。
・配置したボタンにカーソルを合わせ、右クリック→「プロパティ」を選択して以下のように設
定します。
ID
IDC_CMD_SEND
キャプション
PPIモード1 出力
- 81 -
Interface Corporation
TUT-0034
4. データ出力処理を開始するためのメンバ関数“OnCmdSend”の作成を行います。
ClassWizardを表示し、「メッセージマップ」タブを選択し、以下のように設定して「関数の追
加」をクリックします。
プロジェクト
PpiIntr_Send
クラス名
CPpiIntr_SendDlg
オブジェクト
IDC_CMD_SEND
メッセージ
BN_CLICKED
・メンバ変数名を決定するダイアログが表示されますので、“OnCmdSend”となっていることを確
認し、「OK」をクリックします。
・次に、そのままClassWizardで「コード編集」ボタンをクリックして関数のソースコードを表示
し、(List 6-2)のコードを記述します。
プログラムの流れは、『50ページ 4.3 モード1出力』の(List 3-1)と同じです。変更点は、割り込み
処理に関する部分(下記List)の網掛け部分になります。
(List 6-2 CPpiIntr_SendDlg クラスの OnCmdSend 関数のコード)
void CppiIntr_SendDlg::OnCmdSend()
{
// TODO: この位置にコントロール通知ハンドラ用のコードを追加してください
INT
nRet;
// 関数の戻り値
DWORD
dwEventBuf;
// イベント内容を格納する変数
BYTE
bySend;
// 送信データ
// 8255①のモード設定を行う
// グループ A :モード 1、ポート A とポート C の上位 = 出力
// グループ B :モード 0、ポート B とポート C の下位 = 入力
nRet = PpiControl(ghDeviceHandle, FBIPPI_8255_CONTROLLER1, 0xa3);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のモード設定に失敗しました", "実行エラー", MB_ICONERROR);
PpiClose(ghDeviceHandle1);
exit(0);
}
// INT 信号を有効にするために、8255①のグループ A の WIE に"1"をセットします
// ポート C をコントロール信号の出力、ステータス信号の入力として使用する(bit7 = 0)
// 制御データ = 0x00001101
nRet = PpiControl(ghDeviceHandle, FBIPPI_8255_CONTROLLER1, 0x0d);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①の W ビットセットに失敗しました", "実行エラー", MB_ICONERROR);
PpiClose(ghDeviceHandle);
exit(0);
}
// 8255①の割り込み要因の割り当て、割り込み発生論理を設定する
// 設定値(0x11) = 1PC3 入力信号が L → H を設定
nRet = PpiSetEventConfig(ghDeviceHandle, 0xf0);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①の割り込み設定に失敗しました", "実行エラー", MB_ICONERROR);
PpiClose(ghDeviceHandle1);
exit(0);
}
// 8255①の割り込みマスク状態を設定する
// 1PC3 の入力による割り込みだじぇ検知する
nRet = PpiSetEventMask(ghDeviceHandle, 0x01);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①の割り込みマスク設定に失敗しました", "実行エラー", MB_ICONERROR);
PpiClose(ghDeviceHandle1);
exit(0);
}
Interface Corporation
- 82 -
TUT-0034
// 8255①より 0∼255 の数値データを出力する
for(int count = 0; count <= 255; count++){
bySend = count;
// 8255①のポート A からデータを出力
nRet = PpiOutputPort(ghDeviceHandle, FBIPPI_8255_CONTROLLER1,
FBIPPI_PORT_A, bySend);
if(nRet != FBIPPI_ERROR_SUCCESS){
MessageBox("8255①のポート A からのデータ出力に失敗しました",
"実行エラー", MB_ICONERROR);
break;
}
// イベントオブジェクトの作成
glpOverlapped.hEvent = CreateEvent(NULL, TRUE, FALSE, NULL);
// 製品のイベント要求を待つ
nRet = PpiEventRequestPending(ghDeviceHandle, 0x01, &dwEventBuf, &glpOverlapped);
if(nRet != FBIPPI_ERROR_IO_PENDING){
MessageBox("割り込みイベント待ち開始に失敗しました", "実行エラー", MB_ICONERROR);
break;
}
// 割り込みがあるまで待機
nRet = WaitForSingleObject(glpOverlapped.hEvent, 10000);
// 10 秒でタイムアウト
if(nRet != WAIT_OBJECT_0){
MessageBox("タイムアウト(送信停止)", "実行エラー", MB_ICONERROR);
break; // データ出力停止(キャンセル)
}
}
if(count == 256) MessageBox("送信完了", "完了", MB_ICONERROR);
}
以上でモード1データ出力のプログラムは完成です。
入力側のプログラムは『55ページ Step4.モード0入力』(List 3-2)と同じものを使用します。
プログラムの入力が終わったら、保存した後、入力側(プロジェクト名:PpiMode0_Recv),出力側(プ
ロジェクト名:PpiIntr_Send)のプログラムをそれぞれ実行してください。中で行われている処理が、
while文での待機か割り込み処理での待機かの違いであって、『53ページ Step2.モード1出力』
と同一の結果が得られることが確認できます。
では、ここより、使用したFbiPpi.DLLの関数について記載します。
(List 6-2)ではINT(1PC3)がLレベルからHレベルに変化した時のみ割り込みイベントが発生し、Hレ
ベルからLレベルに変化しても割り込みイベントは発生しません。これは、どういった信号を割り
込みとして扱うか、製品に設定しているからです。割り込み要因の設定にはPpiSetEventConfig関
数を使用します。
「使用例」
割り込み要因の論理を設定します。
関数が失敗するとエラーコード
が格納されます。
nRet = PpiSetEventConfig(ghDeviceHandle, 0xf0);
製品のオープン時に取得したデバ
イスハンドルを指定します。
- 83 -
Interface Corporation
TUT-0034
割り込み要因の論理の設定ですが、設定される数値データは2進数変換時、各ビットにおいて以下
の意味をもっています。
Bit7
Bit6
Bit5
Bit4
EDS4 EDS3 EDS3 EDS1
SIG1∼SIG4の各々がどういった条件の
時、割り込みとするかを設定します。
Bit3
SIG4
Bit2
SIG3
Bit1
SIG2
Bit0
SIG1
各ビットを割り込み接点にアタッチ
します。
割り込み発生論理設定状態
EDS1
SIG1の割り込み発生論理の設定
EDS2
SIG2の割り込み発生論理の設定
EDS3
SIG3の割り込み発生論理の設定
EDS4
SIG4の割り込み発生論理の設定
値
意味
0
High → Lowの遷移で割り込み発生
1
Low → Highの遷移で割り込み発生
SIG1[割り込み要因割り当て]
値
意味
0
8255①のポートC接点3(ピン名:1PC3)入力信号
SIG2[割り込み要因割り当て]
値
意味
0
8255①のポートC接点0(ピン名:1PC0)入力信号
1
IR.IN1
※ PCI-2747AはIR.IN1信号を持ちません。
SIG3[割り込み要因割り当て]
値
意味
0
8255②のポートC接点3(ピン名:2PC3)入力信号
※ PCI-2747Aは8255②を持ちません。
SIG4[割り込み要因割り当て]
値
意味
0
8255②のポートC接点0(ピン名:2PC0)入力信号
1
IR.IN2
※ PCI-2747Aは8255②、IR.IN2信号を持ちません。
※ 電源投入時,PCIバスリセット時,外部リセット信号入力時は全て設定値が0となっています。
(List 6-2)においては、0xf0(16進数でf0)が設定されています。つまり、Bit7∼Bit0までが「11110000」
と設定され、その意味は「1PC3,1PC0,2PC3,2PC0のうちどれかが、LレベルÆHレベルに変化した
時それを割り込み入力とする」と定義しているわけです。
Interface Corporation
- 84 -
TUT-0034
しかし、今回割り込みとして使用したい信号は1PC3のINTのみですので、他の信号の変化は無視
するように設定をする必要があります。
この処理のことをマスク処理といいます。
割り込み入力のマスク処理にはPpiSetEventMask関数を
使用します。
「使用方法」
関数が失敗するとエラーコードが
格納されます。
割り込み要因のマスク/アンマスクを
設定します。
nRet = PpiSetEventMask(ghDeviceHandle, 0x01);
製品のオープン時に取得したデバイスハンドルを指定します。
割り込み要因のマスクの設定ですが、設定される数値データは2進数変換時、各ビットにおいて以
下の意味をもっています。0の時その接点はマスクされます。
Bit7
未使用
Bit6
未使用
Bit5
SIGR
Bit4
SIGT
Bit3
SIG4
Bit2
SIG3
Bit1
SIG2
Bit0
SIG1
PpioSetEventConfig関数で設定した
各接点に対応します。
SIGR=外部割り込み
SIGT=タイマ割り込み
値
0
1
意味
マスクする
マスクしない
(List 6-2)では0x01(16進数で1)が設定されています。つまりBit7∼Bit0までが「00000001」と設定さ
れ、1PC3以外の入力信号はマスク処理されているので、1PC3以外の状態の変化は割込み信号とし
て処理されません。
最後に、実際の監視処理の開始ですが、PpiEventRequestPending関数が呼び出されて初めて処理
が開始(割り込み待機状態)されます。
関数が失敗するとエラーコー
ドが格納されます。
「使用方法」
許可するイベントをビットア
サインで設定します。
nRet = PpiEventRequestPending(hDeviceHandle, 0x01, &EventBuf, &lpOverlapped);
製品のオープン時に取得したデバイスハン
ドルを指定します。
通知されたイベント内
容が格納されます。
OVERLAPPEDデータ構造体へのポインタを指定します。
- 85 -
Interface Corporation
TUT-0034
許可するイベントですが、設定される数値データは2進数変換時、各ビットにおいて以下の意味を
もっています。‘1’の時そのイベントは有効となります。(List 6-2)ではBit5∼Bit0までが「000001」
と設定され、1PC3で入力信号を検知すると割り込みイベントとして認識するよう定義しています。
Bit0
8255①のポートC接点3(ピン名:1PC3)入力信号
Bit1
8255①のポートC接点0(ピン名:1PC0)入力信号
または、IR.IN1(外部割り込み入力信号)からの入力信号
※ PCI-2747AはIR.IN1信号を持ちません。
Bit2
8255②のポートC接点3(ピン名:2PC3)入力信号
※ PCI-2747Aは8255②を持ちません。
Bit3
8255②のポートC接点0(ピン名:2PC0)入力信号
または、IR.IN2(外部割り込み入力信号)からの入力信号
※ PCI-2747Aは8255②、IR.IN2信号を持ちません。
Bit4
インターバルタイマ
Bit5
外部リセット入力(RSTIN)割り込み
ここまでが、Win32APIを用いた割り込み処理のプログラム例です。割り込みを多用するとプログ
ラムが複雑になることがありますが、柔軟なシステム作成において、この割り込み処理は有効な
手段となります。
Interface Corporation
- 86 -
TUT-0034
第5章 FbiPpi.DLLリファレンス
DLL関数一覧
No.
1. PpiOpen
関数名
内 容
PPI製品のオープンを行います。以後の製品へのアクセスを
行えるようにします。
PPI製品のクローズを行います。各種リソースの解放を行い、
以後の製品へのアクセスを禁止します。
8255制御レジスタの制御を行います。
2.
PpiClose
3.
PpiControl
4.
PpiInputPort
5.
6.
7.
PpiOutputPort
PpiSetEventMask
PpiGetEventMask
8.
PpiSetEventConfig
9.
PpiGetEventConfig
10.
PpiSetTimerConfig
割り込みイベント要因割り当ておよび割り込みイベント発
生論理の設定を行います。
割り込みイベント要因割り当ておよび割り込みイベント発
生論理の設定状態を取得します。
インターバルタイマの設定を行います。
11.
PpiGetTimerConfig
インターバルタイマの設定情報を取得します。
12.
PpiGetTimerCount
インターバルタイマのカウント値を取得します。
13.
14.
PpiGetResetInStatus
PpiEventRequestPending
外部リセット入力信号端子(RSTIN)の状態を取得します。
イベント要求を待ちます。
15.
PpiCommonGetPciDeviceInfo デバイスID,リソース情報,製品ID(RSW1)等の情報を取得し
ます。
任意の8255コントローラのポートからデータを読み込みま
す。
任意の8255コントローラのポートへデータを出力します。
割り込みイベントのマスク/アンマスクの設定を行います。
割り込みイベントのマスク状態を取得します。
- 87 -
Interface Corporation
TUT-0034
PpiOpen
指定されたデバイス名の製品のオープンを行い、以後の製品へのアクセスを行えるようにします。
宣言
HANDLE PpiOpen(LPCTSTR lpszName, DWORD fdwFlags);
パラメータ
lpszName
fdwFlags
オープンするデバイス名を指定します。
オープン時のフラグを指定します。
値
FBIDIO_FLAG_SHARE
意味
同じデバイスを重複(共有)してオープンすることを許可します。
戻り値
関数が成功すると有効なデバイスハンドルが返されます。
関数が失敗するとINVALID_HANDLE_VALUEが返されます。INVALID_HANDLE_VALUEの値は、FFFFFFFFh(-1)です。
解説
Windows95では、「コントロールパネル」の「デバイス」に「FbiPciPpi」が追加され認識された当社デジタル入出力製品が一覧
表示されます。一覧の製品型式の横に製品上のロータリスイッチの値とデバイス名が表示されます。自己診断プログラムでも確
認できます。
WindowsNTでは、自己診断プログラムにて割り当てられたデバイス名をご確認ください。
デバイス名は製品上のロータリスイッチ(RSW1)の値で決定されるわけではありません。
使用する製品枚数やスロット位置の変更等でシステム構成が変化すると割り当てられる名前が変化する場合があります。システ
ム構成が変化する環境でご使用になる場合は、デバイス名の指定が変更できるようにアプリケーションを作成ください。製品上
に実装されたRSW1(製品ID設定)の値を取得し、アプリケーションで目的の製品であるかを判断することができます。詳しくは、
PpiCommonGetPciDeviceInfo関数 の説明をご参照してください。
PpiClose
製品のクローズを行い、製品アクセスのために使用されていた各種リソースの解放し、以後の製品へのアクセスを禁止します。
宣言
INT PpiClose(HANDLE hDeviceHandle);
パラメータ
hDeviceHandle
有効なデバイスハンドルを指定します
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
PpiControl
8255 PPIコントローラ制御レジスタを制御します。
宣言
INT PpiContrl(HANDLE hDeviceHandle, DWORD dwController, BYTE bControlData);
パラメータ
hDeviceHandle
dwController
bControlData
有効なデバイスハンドルを指定します
搭載された2つの8255のうちどちらを制御するかを指定します。
値
意味
8255コントローラ①
FBIPPI_8255_CONTROLLER1
8255コントローラ②
FBIPPI_8255_CONTROLLER2
※ PCI-2747AではFBIPPI_8255_CONTROLLER2は指定できません。
制御データを指定します。8255のモード設定,入出力設定の設定データは『99ページ
8255 PPIコントローラ説明』を参照してください。
第6章
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
Interface Corporation
- 88 -
TUT-0034
PpiInputPort
8255コントローラのポートからデータを読み込みます。引数にて、コントローラとポートを指定します。
宣言
INT PpiInputPort(HANDLE hDeviceHandle, DWORD dwController, DWORD dwPort, PBYTE pbValue);
パラメータ
hDeviceHandle
dwController
dwPort
pbValue
有効なデバイスハンドルを指定します
搭載された2つの8255のうちどちらを制御するかを指定します。
値
意味
8255コントローラ①
FBIPPI_8255_CONTROLLER1
8255コントローラ②
FBIPPI_8255_CONTROLLER2
※ PCI-2747AではFBIPPI_8255_CONTROLLER2は指定できません。
入力を行うポートを指定します。
値
FBIPPI_PORT_A
FBIPPI_PORT_B
FBIPPI_PORT_C
意味
ポートA
ポートB
ポートC
バッファへのポインタを指定します。このバッファに指定されたポートより取得した状態が
格納されます。
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
PpiOutputPort
8255コントローラのポートへデータを出力します。引数にて、コントローラとポートを指定します。
宣言
INT PpiOutputPort(HANDLE hDeviceHandle, DWORD dwController, DWORD dwPort, BYTE bValue);
パラメータ
hDeviceHandle
dwController
有効なデバイスハンドルを指定します
搭載された2つの8255のうちどちらを制御するかを指定します。
値
意味
8255コントローラ①
FBIPPI_8255_CONTROLLER1
8255コントローラ②
FBIPPI_8255_CONTROLLER2
※ PCI-2747AではFBIPPI_8255_CONTROLLER2は指定できません。
dwPort
入力を行うポートを指定します。
値
意味
FBIPPI_PORT_A
ポートA
FBIPPI_PORT_B
ポートB
FBIPPI_PORT_C
ポートC
pbValue
バッファへのポインタを指定します。このバッファに格納した値が指定されたポートより出
力されます。
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
- 89 -
Interface Corporation
TUT-0034
PpiSetEventMask
割り込みマスク状態を設定します。
宣言
INT PpiSetEventMask(HANDLE hDeviceHandle, BYTE bEventMask);
パラメータ
hDeviceHandle
bEventMask
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファに設定された値により,
割り込み要因のマスク/アンマスクの設定が行われます。設定は下記のビットの組み合わせで行
います。
Bit7
Bit1
Bit0
−
−
SIGR
SIGT
SIG4
SIG3
SIG2
SIGR=外部割り込み
SIGT=タイマ割り込み
SIG1∼4は、PpiSetEventConfig関数にて設定される割り込み要因
Bit6
Bit5
Bit4
Bit3
Bit2
SIG1
値
意味
0
マスク
1
アンマスク
電源投入時は全てマスク状態(0)です。
PCIバスリセット時、外部リセット入力時はSIGR以外がマスク状態(0)になります。SIGRのマ
スク/アンマスク状態は変更しません。
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
PpiGetEventMask
割り込みマスク状態を取得します。
宣言
INT PpiGetEventMask(HANDLE hDeviceHandle, PBYTE pbEventMask);
パラメータ
hDeviceHandle
pbEventMask
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファに製品に設定された割り込み要因のマスク/
アンマスクの状態が格納されます。
Bit7
Bit1
Bit0
−
−
SIGR
SIGT
SIG4
SIG3
SIG2
SIGR=外部割り込み
SIGT=タイマ割り込み
SIG1∼4は、PpiSetEventConfig関数にて設定される割り込み要因
Bit6
Bit5
Bit4
Bit3
Bit2
SIG1
値
意味
0
マスク
1
アンマスク
電源投入時は全てマスク状態(0)です。
PCIバスリセット時、外部リセット入力時はSIGR以外がマスク状態(0)になります。SIGRのマス
ク/アンマスク状態は変更しません。
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
Interface Corporation
- 90 -
TUT-0034
PpiSetEventConfig
割り込み要因の割り当て,割り込み発生論理を設定します。
宣言
INT PpiSetEventConfig(HANDLE hDeviceHandle, BYTE bEventConfig);
パラメータ
hDeviceHandle
bEventConfig
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファに割り込み要因の割り当て,割り込み発生論
理の設定データを設定します。
Bit7
Bit6
Bit5
Bit4
Bit3
Bit2
Bit1
Bit0
EDS4
EDS3
EDS3
EDS1
SIG4
SIG3
SIG2
SIG1
割り込み発生論理設定状態
EDS1
SIG1の割り込み発生論理の設定
EDS2
SIG2の割り込み発生論理の設定
EDS3
SIG3の割り込み発生論理の設定
EDS4
SIG4の割り込み発生論理の設定
値
意味
0
High → Low
1
Low → High
SIG1[割り込み要因割り当て]
値
意味
0
8255①のポートC接点3(ピン名:1PC3)入力信号
SIG2[割り込み要因割り当て]
値
意味
0
8255①のポートC接点0(ピン名:1PC0)入力信号
1
IR.IN1
※ PCI-2747AはIR.IN1信号を持ちません。
SIG3[割り込み要因割り当て]
値
意味
0
8255②のポートC接点3(ピン名:2PC3)入力信号
※ PCI-2747Aは8255※を持ちません。
SIG4[割り込み要因割り当て]
値
意味
0
8255②のポートC接点0(ピン名:2PC0)入力信号
1
IR.IN2
※ PCI-2747Aは8255※、IR.IN2信号を持ちません。
※ 電源投入時,PCIバスリセット時、外部リセット信号入力時は全て設定値が0となっています。
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
- 91 -
Interface Corporation
TUT-0034
PpiGetEventConfig
割り込み要因の割り当て,割り込み発生論理の設定状態を取得します。
宣言
INT PpiGetEventConfig(HANDLE hDeviceHandle, PBYTE pbEventConfig);
パラメータ
hDeviceHandle
bEventConfig
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。割り込み要因の割り当て,割り込み発生論理の状態が格納
されます。
Bit7
Bit6
Bit5
Bit4
Bit3
Bit2
Bit1
Bit0
EDS4
EDS3
EDS3
EDS1
SIG4
SIG3
SIG2
SIG1
割り込み発生論理設定状態
EDS1
SIG1の割り込み発生論理の設定
EDS2
SIG2の割り込み発生論理の設定
EDS3
SIG3の割り込み発生論理の設定
EDS4
SIG4の割り込み発生論理の設定
値
意味
0
High → Low
1
Low → High
SIG1[割り込み要因割り当て]
値
意味
0
8255①のポートC接点3(ピン名:1PC3)入力信号
SIG2[割り込み要因割り当て]
値
意味
0
8255①のポートC接点0(ピン名:1PC0)入力信号
1
IR.IN1
SIG3[割り込み要因割り当て]
値
意味
0
8255②のポートC接点3(ピン名:2PC3)入力信号
SIG4[割り込み要因割り当て]
値
意味
0
8255②のポートC接点0(ピン名:2PC0)入力信号
1
IR.IN2
※ 電源投入時,PCIバスリセット時、外部リセット信号入力時は全て設定値が0となっています。
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
Interface Corporation
- 92 -
TUT-0034
PpiSetTimerConfig
インターバルタイマの設定を行います。
宣言
INT PpiSetTimerConfig(HANDLE hDeviceHandle,BYTE bTimerConfigValue);
パラメータ
hDeviceHandle
bTimerConfigValue
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファにインターバルタイマの設定を以下のビット
構成で設定します。
Bit7
Bit6
Bit5
Bit4
Bit3
Bit2
Bit1
Bit0
−
CTL7
CTL6
CTL5
CTL4
CTL3
CTL2
CTL1
タイマ周期はCTL5∼7で設定した基準周期と、CTL1∼4で設定した分周比の積となります。
(周期=基準周期×分周比)
CTL4
CTL3
CTL2
CTL1
タイマ停止
0
0
0
0
1分周
0
0
0
1
2分周
0
0
1
0
3分周
0
0
1
1
4分周
0
1
0
0
5分周
0
1
0
1
6分周
0
1
1
0
7分周
0
1
1
1
8分周
1
0
0
0
9分周
1
0
0
1
10分周
1
0
1
0
11分周
1
0
1
1
12分周
1
1
0
0
13分周
1
1
0
1
14分周
1
1
1
0
15分周
1
1
1
1
CTL5∼7基準周期設定
10μs
100μs
1ms
10ms
100ms
CTL7
0
0
0
0
1
CTL6
0
0
1
1
0
CTL5
0
1
0
1
0
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
- 93 -
Interface Corporation
TUT-0034
PpiGetTimerConfig
インターバルタイマの設定情報を取得します。
宣言
INT PpiGetTimerConfig(HANDLE hDeviceHandle, PBYTE pbTimerConfigValue);
パラメータ
hDeviceHandle
pbTimerConfigValue
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファにインターバルタイマの設定が以下のビット
構成で格納されます。
Bit7
Bit6
Bit5
Bit4
Bit3
Bit2
Bit1
Bit0
−
CTL7
CTL6
CTL5
CTL4
CTL3
CTL2
CTL1
タイマ周期はCTL5∼7で設定した基準周期と、CTL1∼4で設定した分周比の積となります。
(周期=基準周期×分周比)
CTL4
CTL3
CTL2
CTL1
タイマ停止
0
0
0
0
1分周
0
0
0
1
2分周
0
0
1
0
3分周
0
0
1
1
4分周
0
1
0
0
5分周
0
1
0
1
6分周
0
1
1
0
7分周
0
1
1
1
8分周
1
0
0
0
9分周
1
0
0
1
10分周
1
0
1
0
11分周
1
0
1
1
12分周
1
1
0
0
13分周
1
1
0
1
14分周
1
1
1
0
15分周
1
1
1
1
CTL5∼7基準周期設定
CTL7
CTL6
CTL5
10μs
0
0
0
100μs
0
0
1
1ms
0
1
0
10ms
0
1
1
100ms
1
0
0
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
Interface Corporation
- 94 -
TUT-0034
PpiGetTimerCount
インターバルタイマのカウント値を取得します。
宣言
INT PpiGetTimerCount(HANDLE hDeviceHandle, PBYTE pbTimerCount);
パラメータ
hDeviceHandle
pbTimerCount
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファにインターバルタイマの現在のカウンタ値が
以下のビット構成で格納されます。
Bit7
Bit6
Bit5
Bit4
Bit3
Bit2
Bit1
Bit0
−
−
−
−
CTL4
CTL3
CTL2
CTL1
PpiSetTimerConfig関数より設定した周期における、現在の状態値を4bitカウンタで取得します。
0カウント
1カウント
2カウント
2カウント
4カウント
5カウント
6カウント
7カウント
8カウント
9カウント
10カウント
11カウント
12カウント
13カウント
14カウント
15カウント
CTL4
0
0
0
0
0
0
0
0
1
1
1
1
1
1
1
1
CTL3
0
0
0
0
1
1
1
1
0
0
0
0
1
1
1
1
CTL2
0
0
1
1
0
0
1
1
0
0
1
1
0
0
1
1
CTL1
0
1
0
1
0
1
0
1
0
1
0
1
0
1
0
1
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
PpiGetResetInStatus
外部リセット入力信号の状態を取得します。
宣言
INT PpiGetResetInStatus(HANDLE hDeviceHandle, PBYTE pbResetInStatus);
パラメータ
hDeviceHandle
pbResetInStatus
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファに外部リセット入力信号の状態が格納されます。
値
0
1
意味
リセット入力無効
リセット入力有効
戻り値
関数が成功するとFBIPPI_ERROR_SUCCESSが返されます。
関数が失敗するとFBIPPI_ERROR_SUCCESS以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラー
コード一覧』を参照してください。
解説
外部リセット信号が有効の間(pbResetInStatus = 1)は、出力、および割り込みマスク、要因等の設定をすることができません。外
部リセット信号入力でリセットされた場合、PpiGetResetInStatusでリセット入力信号が無効になったことを確認してから製品の再
設定を行ってください。
- 95 -
Interface Corporation
TUT-0034
PpiEventRequestPending
割り込みイベント要求を待ちます。
宣言
INT PpiEventRequestPending(HANDLE hDeviceHandle, DWORD dwEventEnableMask, PDWORD pdwEventBuf, LPOVERLAPPED
pOverlapped);
パラメータ
hDeviceHandle
dwEventEnableMask
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファに許可するイベントを以下のビットアサイン
で指定します。該当ビットが1の時有効です。
Bit0
Bit1
Bit2
Bit3
Bit4
Bit5
pdwEventBuf
バッファへのポインタを指定します。このバッファに通知されたイベントが以下のビットアサイ
ンで格納されます。該当ビットが1の時有効です。
Bit0
Bit1
Bit2
Bit3
Bit4
Bit5
lpOverlapped
8255 のポートC接点3(ピン名:1PC3)入力信号
8255 のポートC接点0(ピン名:1PC0)入力信号または、IR.IN1(外部割り込み入力信号)から
の入力信号
※ PCI-2747AはIR.IN1信号を持ちません。
8255 のポートC接点3(ピン名:2PC3)入力信号
※ PCI-2747Aは8255 を持ちません。
8255 のポートC接点0(ピン名:2PC0)入力信号または、IR.IN2(外部割り込み入力信号)から
の入力信号
※ PCI-2747Aは8255 、IR.IN2信号を持ちません。
インターバルタイマ
外部リセット入力(RSTIN)割り込み
8255 のポートC接点3(ピン名:1PC3)入力信号
8255 のポートC接点0(ピン名:1PC0)入力信号または、IR.IN1(外部割り込み入力信号)から
の入力信号
※ PCI-2747AはIR.IN1信号を持ちません。
8255 のポートC接点3(ピン名:2PC3)入力信号
※ PCI-2747Aは8255 を持ちません。
8255 のポートC接点0(ピン名:2PC0)入力信号または、IR.IN2(外部割り込み入力信号)から
の入力信号
※ PCI-2747Aは8255 、IR.IN2信号を持ちません。
インターバルタイマ
外部リセット入力(RSTIN)割り込み
OVERLAPPEDデータ構造体へのポインタを指定します。
戻り値
関数が成功すると0が返されます。
関数が失敗すると0以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラーコード一覧』を参照して
ください。
解説
オーバーラップ構造体(lpOverlapped)を指定した非同期コールの場合、FBIPPI_ERROR_IO_PENDINGを返し非同期での動作となり
ます。PpiSetEventMask、PpiSetEventConfig関数により必要な割り込みイベントの設定、マスク解除を事前に行う必要があります。
Interface Corporation
- 96 -
TUT-0034
PpiCommonGetPciDeviceInfo
デバイスID,リソース情報,製品ID(RSW1)等の情報を取得します。
宣言
INT PpiCommonGetPciDeviceInfo(HANDLE hDeviceHandle, PDWORD pdwDeviceID, PDWORD pdwVenderID, PDWORD
pdwClassCode, PDWORD pdwRevisionID, PDWORD pdwBaseAddress0, PDWORD pdwBaseAddress1, PDWORD pdwBaseAddress2,
PDWORD pdwBaseAddress3, PDWORD pdwBaseAddress5, PDWORD pdwSubsystemID, PDWORD pdwSubsystemVenderID, PDWORD
pdwInterruptLine, PDWORD pdwBoardID);
パラメータ
hDeviceHandle
pdwDeviceID
pdwVenderID
pdwClassCode
pdwRevisionID
pdwBaseAddress0
pdwBaseAddress1
pdwBaseAddress2
pdwBaseAddress2
pdwBaseAddress4
pdwBaseAddress5
pdwSubsystemID
pdwSubsystemVenderID
pdwInterruptLine
pdwBoardID
有効なデバイスハンドルを指定します。
バッファへのポインタを指定します。このバッファにデバイスIDデータが格納されます。弊社
PCIバス用PPI製品は、製品型式の数字部分4桁が適用されます。PCI-2746Cならば2746(16進数で
はABAh)、PCI-2747Aならば2747(16進数ではABBh)です。
バッファへのポインタを指定します。このバッファにベンダIDデータが格納されます。弊社の
ベンダIDは、1147h(16進数)です。
バッファへのポインタを指定します。このバッファにクラスコードデータが格納されます。
バッファへのポインタを指定します。このバッファにリビジョンIDデータが格納されます。
バッファへのポインタを指定します。このバッファにリソース0データが格納されます。弊社PCI
バス用PPI製品は、ここに占有するI/O領域が格納されます。取得した値をFFFChでマスクした値
が占有するI/O領域のベースアドレスです。
バッファへのポインタを指定します。このバッファにリソース1データが格納されます。弊社PCI
バス用PPI製品では、使用しません。
バッファへのポインタを指定します。このバッファにリソース2データが格納されます。弊社PCI
バス用PPI製品では、使用しません。
バッファへのポインタを指定します。このバッファにリソース3データが格納されます。弊社PCI
バス用PPI製品では、使用しません。
バッファへのポインタを指定します。このバッファにリソース4データが格納されます。弊社PCI
バス用PPI製品では、使用しません。
バッファへのポインタを指定します。このバッファにリソース5データが格納されます。弊社PCI
バス用PPI製品では、使用しません。
バッファへのポインタを指定します。このバッファにサブシステムIDデータが格納されます。
バッファへのポインタを指定します。このバッファにデバイスIDデータが格納されます。
バッファへのポインタを指定します。このバッファに割込みラインデータが格納されます。
バッファへのポインタを指定します。このバッファに製品IDデータが格納されます。
戻り値
関数が成功すると0が返されます。
関数が失敗すると0以外の値が返ります。関数が失敗した場合の戻り値については『98ページ エラーコード一覧』を参照して
ください。
- 97 -
Interface Corporation
TUT-0034
エラーコード一覧
定数
FBIPPI_ERROR_SUCCESS
FBIPPI_ERROR_NOT_DEVICE
FBIPPI_ERROR_NOT_OPEN
FBIPPI_ERROR_INVALID_HANDLE
FBIPPI_ERROR_ALREADY_OPEN
FBIPPI_ERROR_HANDLE_EOF
FBIPPI_ERROR_MORE_DATA
FBIPPI_ERROR_INSUFFICIENT_BUFFER
FBIPPI_ERROR_IO_PENDING
FBIPPI_ERROR_NOT_SUPPORTED
FBIPPI_ERROR_MEMORY_NOTALLOCATED
FBIPPI_ERROR_PARAMETER
FBIPPI_ERROR_INVALID_CALL
FBIPPI_ERROR_DRVCAL
FBIPPI_ERROR_NULL_POINTER
Interface Corporation
値
0
0xC0000001
0xC0000002
0xC0000003
0xC0000004
0xC0000005
0xC0000006
0xC0000007
0xC0000008
0xC0000009
0xC0001000
0xC0001001
0xC0001002
0xC0001003
0xC0001004
内容
正常終了
指定されたデバイスがありません
システムがデバイスをオープンできません
デバイスハンドルが正しくありません
すでにOPENしているデバイスをOPENしようとしました
EOFに達しました
さらに多くのデータが利用可能です
システムコールに渡されたデータ領域が小さすぎます
非同期I/O操作が進行中です
サポートされていない機能です
作業用メモリの確保に失敗しました
引数パラメータの値が不正です
不正なファンクション呼び出しです
ドライバ が 呼び出せません。
ドライバ,DLL間でNULLポインタが渡されました
- 98 -
TUT-0034
第6章 8255 PPIコントローラ説明
8255は、プログラマブル汎用I/Oデバイスです。3組(8ビット)の入出力ポートがあり、プログラム
による制御でデータ入力,データ出力,ステータス信号入力,コントロール信号出力に使用すること
ができます。
6.1 ポートA,B,C
8255は8ビットの入出力ポートが3個あり、それぞれをポートA,ポートB,ポートCと呼びます。
各ポートごとに独特の性質を持っていますので、ポートの選択によって8255の適応性が生かされ
ます。
ポートA
ポートB
ポートC
入力時 ラッチ入力あるいはバッファ入力動作
出力時 ラッチ出力動作
入力時 ラッチ入力あるいはバッファ入力動作
出力時 ラッチ出力動作
入力時 バッファ入力動作(ラッチされません)
出力時 ラッチ出力動作
ポートCはモードによって2つの4ビットポートに分割して使用することが
できます。
また、ポートA,Bのコントロール信号の出力ポート、あるいはステータス信
号の入力ポートとして用いることができます。
各ポートと信号名は次の表のように対応しています。
PA0∼PA7
PB0∼PB7
PC0∼PC7
ポートA
ポートB
ポートC
6.2 グループA制御,グループB制御
8255を使用するにあたって、ポートA,ポートB,ポートCを2つに分けグループA,グループBとしま
す。
モード0
モード1
モード2
基本的な入出力ポート
コントロール信号,ステータス信号による制御を伴う入出力ポート
双方向データを扱う入出力ポート
使用する目的に合わせて、各グループごとにモードを設定します。可能なモードの組み合わせは
次の6通りです。
・グループA:モード0, グループB:モード0
・グループA:モード0, グループB:モード1
・グループA:モード1, グループB:モード0
・グループA:モード1, グループB:モード1
・グループA:モード2, グループB:モード0
・グループA:モード2, グループB:モード1
- 99 -
Interface Corporation
TUT-0034
モードの選択はPpiControl関数にて行います。指定する制御データ下記のフォーマットとなりま
す。
制御データ(8ビットのバイトデータ)
D7
D6
D5
D4
D0
グループB
D3
ポートC下位
D1
ポートB
D2
モード選択
D3
グループA
ポートC上位
D4
ポートA
D5,
モード選択
D6
D7
機能制御
D2
D1
D0
0
出力
1
入力
0
出力
1
入力
0
モード0
1
モード1
0
出力
1
入力
0
出力
1
入力
00
モード0
01
モード1
1X
モード2
0
ビットセット,リセット
1
モード選択
ポートCをコントロール信号の出力,ステータス信号の入力として使用する場合、PpiControl関数に
てビットセット/リセットすることができます。
この操作を行うことによって割り込み許可,割り込み禁止等の設定をします。
コントロール信号のビットセット/リセットを行う場合の制御データ
0(D7)
X
X
X
D3
D2
D1
D0
6.3 各ビットの対応
D0
D1
D2
D3
D7
セット/
リセット
ポートC
ビット選択
機能制御
0
リセット
1
セット
0
1
2
3
4
ビット
D1
0
1
0
1
0
D2
0
0
1
1
0
D3
0
0
0
0
1
0を指定しビットセット,リセット機能選択
5
1
0
1
6
0
1
1
7
1
1
1
備考:I/Oモジュールがリセットされた時、あるいはモードを選択した時、自動的に全ビットは
リセットされます。
Interface Corporation
- 100 -
TUT-0034
(1)モード0
このモードでは基本的な入出力ポートとして動作をします。この場合、モード0になっている
各ポートはバッファ入力,ラッチ出力動作をします。
出力ポートに指定されたポートは、出力値をラッチし、常に端子から出力します。モード設定直
後はLowレベルを出力します。
また出力ポートに指定されているポートを読み出せば、出力している値が得られます。
PpiContorol関数にて下記の制御データを指定することによりポートA,ポートB,ポートC(上位),
ポートC(下位)それぞれを独立に入力あるいは出力ポートに設定します。
モード0を設定する場合の制御データ
1(D7)
D0
0(D6)
グループB
D1
D2
D3
0(D5)
D4
D3
ポートC下位
PC0∼PC3
(PC0∼PC2) ※
ポートB
D4
モード選択
ポートC上位
PC4∼PC7
ポートA
D5,D6
モード選択
D7
グループA
機能制御
0(D2)
0
1
D1
D0
出力
入力
0
出力
1
入力
0を指定しグループBをモード0を指定
0
出力
1
入力
0
出力
1
入力
00(D6,D5)を指定し
モード0を指定
1を指定しモード選択機能を選択
※ グループAがモード0以外の場合にはグループBが使えるポートCのビットはPC0∼PC2の3ビッ
トになります。
- 101 -
Interface Corporation
TUT-0034
(2)モード1
データの入出力制御にコントロール信号,ステータス信号を用いるモードです。モード1では、グ
ループA,グループBを単位として使用し、グループAはデータ・ポートにポートA(PA0∼PA7),コン
トロール/ステータス・ポートにポートC上位ビット(PC3∼PC7),グループBはデータ・ポートに
ポートB(PB0∼PB7),コントロール/ステータス・ポートにポートC下位3ビット(PC0∼PC2)によって
構成します。
モード1では、ポートCへの書き込みはビットセット/リセット機能で行います。
モード1を設定する場合の制御データ
1(D7)
0(D6)
1(D5)
D0
グループB
D1
D2
D3
グループA
D4
D5,D6
D7
D4
D3
ポートC
PC3※
ポートB
モード選択
ポートC
・ポートA入力時 PC6,PC7
・ポートA出力時 PC4,PC5
ポートA
モード選択
機能制御
1(D2)
D1
D0
0 出力
1 入力
0 出力
1 入力
1を指定しモード1を指定
0 出力
1 入力
0 出力
1 入力
01(D6,D5)を指定しモード1を指
定
1を指定しモード選択機能を選
択
※ グループAがモード0の時のみポートCのPC3を使用できます。それ以外ではPC3はグループA
に属します。
モード1でのポートCの機能
ビット
PC0
グループB
グループA
データ入力ポート時
INTR(INTerrupt Request)
データ出力ポート時
INTR(INTerrupt Request)
PC1
IBF(Input Buffer Full F/F)
OBF (Output Buffer Full F/F)
PC2
STB (STroBe input)
RIE(Read Interrupt Enable
flag)
入出力
INTR(INTerrupt Request)
DAC (Data Acknowledge input)
WIE(Write Interrupt Enable flag)
PC3※
PC3
PC4
PC5
PC6
PC7
入出力
INTR(INTerrupt Request)
入出力
STB (STroBe input)
RIE(Read Interrupt Enable
flag)
IBF(Input Buffer Full F/F)
入出力
ACK(Data Acknowledge input)
入出力
WIE(Write Interrupt Enable flag)
入出力
OBF (Output Buffer Full F/F)
※ グループAがモード0の時のみ使用できます。それ以外ではPC3はグループAに属します。
Interface Corporation
- 102 -
TUT-0034
<データ・ポートを入力に指定した時の動作>
データ・ポート(グループAならポートA、グループBならポートB)を入力ポートに指定すると、
データ・ポートは入力ポートとなり、コントロール/ステータス・ポート(ポートC)は次のように定
義されます。(説明中では信号名の上線を省略しています。)
STB(Strobe Input)・・・・入力
この入力をLowレベルにすると、外部接続機器からデータ・ポートに送られている信号をデータ・
ポートがラッチします。
IBF(Input Buffer Full F/F)・・・・出力
この出力がHighレベルの時は入力バッファが満たされていることを意味し、外部接続機器に対し
てデータの転送の禁止を知らせます。この信号はSTBの立ち下がりでHighレベルとなりデータ読
み出し終了時でLowレベルになります。モード設定直後の初期値はLowレベルです。
INTR(Interrupt Request)・・・・出力
この出力は外部接続機器からのデータが入力ポートにラッチされたときにHighレベルとなり、コ
ンピュータに対するデータ読み出し要求割り込み信号として働きます。
なお、RIEにより割り込み許可を行っていない場合、出力はHighレベルのままとなります。
RIE(Read Interrupt Enable flag)
コンピュータに対するデータ読み出し要求割り込みの許可フラグで、このビットをビット操作命
令で1にすることによって割り込み許可、0にすることによって割り込み禁止にします。RIEを書き
換えても同じビットに割り当てられているSTBの機能には影響を与えません。
IBF信号がLowレベルになる前にSTBがLowレベルになるとポート内ラッチデータが変化してしま
います。
STBはIBFがLowレベルになるまではHighレベルに保たなければなりません。
モード1の入力ポート指定状態でポートCを読み出せばIBF,INT,RIEのステータスが得られます。
●モード1(グループA)入力
- 103 -
Interface Corporation
TUT-0034
●モード1(グループB)入力
※印の場合、8255内部のラッチが変化してしまいますので、IBF=”0”になるまでSTBを”1”に保つ
ようにする必要があります。
●モード1入力タイミング
t ST
ST B
t S IB
IB F
tPH
tP S
外部バス
RD
t S IT
IN T
Interface Corporation
- 104 -
TUT-0034
<データ・ポートを出力に指定した時の動作>
データ・ポート(グループAならポートA、グループBならポートB)を出力ポートに指定すると、デー
タ・ポートは出力ポート(モード設定直後はLowレベルを出力)となり、コントロール/ステータス・
ポート(ポートC)は次のように定義されます。(説明中では信号名の上線を省略しています。)
OBF (Output Buffer Full F/F)・・・・出力
この信号はコンピュータからのデータを受け出力ポートにラッチされた時にLowレベルとなり、
外部接続機器に対してのデータ受け取り要求として働きます。
OBFはACK=1のときのデータ書き込み終了時でLowレベルになり外部接続機器がデータを受け取
った時のACKの立ち下がりでHighレベルになります。
モード設定直後の初期値はHighレベルです。
ACK(Data Acknowledge input)・・・・入力
この入力は外部接続機器が出力ポートのデータを受け取ったということを知らせる信号です。
データを受け取った時にLowレベルの信号を出すように外部接続機器を設計します。
INTR (Input Request)・・・・出力
この出力は外部接続機器がデータを受け取った時にHighレベルとなり、コンピュータに対する次
のデータの書き込み要求割り込み信号として働きます。
なお、WIEにて割り込み許可を行っていない場合、Highレベルのままとなります。
WIE (Write Interrupt Enable Flag)
コンピュータに対するデータ書き込み要求割り込みの許可フラグで、このビットをビット操作命
令で1にすることによって割り込み許可、0にすることによって割り込み禁止にします。
WIEを書き換えても同じビットに割り当てられているACKの機能には影響を与えません。
OBF信号がHighレベルになる前にデータの書き込みを行うとポート出力が変化してしまいますの
で、OBF信号がLowレベルの間は書き込みは避けてください。
モード1の出力ポート指定状態でポートCを読み出せば、OBF,NT,WIEのステータスが得られます。
- 105 -
Interface Corporation
TUT-0034
●モード1(グループA)出力
●モード1(グループB)出力
●モード1出力タイミング
WR
IN T
tAO B
OBF
t A IT
ACK
t AK
外部バス
Interface Corporation
- 106 -
TUT-0034
(3)モード2
このモードはグループAのみが可能で、ポートAがコントロール/ステータス信号(ポートC上位5ビ
ット)の制御によって入力,出力の双方向の8ビット・データ・ポートとして使用され、モード1の入
力ポート動作,出力ポート動作を合わせたような動作をします。
グループA・モード2でのポートCの機能
ビット
PC3
PC4
PC5
PC6
PC7
INTR(INTerrupt Request)
STB(STroBe input)
RIE(Read Interrupt Enable flag)
IBF(Input Buffer Full F/F)
DAC(Data Acknowledge input)
WIE(Write Interrupt Enable flag)
OBF(Output Buffer Full F/F)
DAKとSTBの信号でポート0の入力状態,出力状態を切り換えながら、データを双方向へ送ること
ができます。モード2ではポートCへの書き込みはビット操作命令で行います。各信号の動作,機能
はモード1の説明を参照してください。
モード2においてポートCを読み出せば、OBF,IBF,INTR,WIE,RIEのステータスが得られます。
備考:モード1と入力動作は同じです。出力動作は次の点が違います。
・ACK信号がLowレベルの時のみ、出力データがポートAより出力される。
・出力ポートの出力データは読み出せない。
- 107 -
Interface Corporation
TUT-0034
モード2入出力タイミング
8255 → PC I バ ス
データ書き込み
WR
IN T
8255 → PC I バ ス
データ読み出し
RD
tAK
ACK
tST
ST B
tAO B
OBF
t S IB
IB F
tP S
tP H
tAD
tKD
外部バス
外 部 バ ス → 8255
8255 → 外 部 バ ス
(4)特殊なモードの組み合わせについて
ポートCの全てのビットがコントロール/ステータス信号として用いられるわけではありません。
グループA,グループBともにユーザがデータの入出力に利用できるビットがあります。これらのビ
ットを持つモードの組み合わせによって次のような機能を持ちます。
入力動作としてプログラムした時
全ての入力ラインをポートCの読み出し中にアクセスできます。
出力動作としてプログラムした時
ポートC上位4ビット(PC4∼PC7)とポートC下位4ビット(PC0∼PC3)は、それぞれビット操作命令を
用いて個別に書き込みができます。ポートC下位3ビット(PC0∼PC2)は3ビット単位でも書き込み
ができます。
Interface Corporation
- 108 -
TUT-0034
モード1でのPC6,PC7またはPC4,PC5のデータの入出力のセットは、モード選択時の制御データの
ビット3(ポートC(上位))で、PC3はビット0(ポートC(下位))で行います。
“1”で入力,“0”で出力ポートにセットします。
入力ポートにセットしたビットのデータは、ポートCの読み出し動作でシステム・バスに読み出せ
ます。一方出力ポートにセットしたビットにデータを書き込むためには、ビット操作命令を実行
してください。1度のビット操作命令で出力できるのは1ビットのON/OFFのみです。例えば
PC6,PC7と2ビットのデータを書き込むためにはビット操作命令を2回実行してください。
1回目:PC6への書き込み
2回目:PC7への書き込み
ポートCに8ビット単位でデータを書き込めるのは、モード0でポートCの上位,下位ビットともに出
力ポートと指定した時だけです。
- 109 -
Interface Corporation
TUT-0034
技術資料紹介
弊社では下記の技術資料を提供しております。
詳しくは、弊社Web site(www.interface.co.jp)、または弊社窓口までお問い合わせください。
カタログ
PRM-0061
PRM-0062
PRM-0063
CPZカタログ(日本語版)
PCIカタログ(日本語版)
CSIカタログ(日本語版)
チュートリアル
TUT-0058
TUT-0056
TUT-0055
TUT-0054
TUT-0053
TUT-0050
TUT-0048
TUT-0044
TUT-0043
TUT-0041
TUT-0040
TUT-0039
TUT-0038
TUT-0037
TUT-0036
TUT-0034
TUT-0033
TUT-0032
TUT-0031
TUT-0030
TUT-0029
TUT-0028
TUT-0027
TUT-0026
TUT-0025
TUT-0024
TUT-0023
TUT-0022
TUT-0021
TUT-0020
TUT-0019
TUT-0018
TUT-0017
TUT-0016
TUT-0015
TUT-0014
TUT-0008
TUT-0007
TUT-0006
TUT-0005
TUT-0004
TUT-0003
TUT-0002
TUT-0001
チュートリアル CPZ拡張ユニット 入門編
チュートリアル XP Embedded OS構築編
チュートリアル 画像入力I/Oモジュール
CANチュートリアル
モーションコントロールチュートリアル
RTLinuxによるモーションコントローラI/Oモジュール制御プログラミング チュートリアル(GPG-7400用)
RTLinuxによるメモリンクI/Oモジュール制御プログラミング チュートリアル
RTLinuxによるメモリ共有インタフェースI/Oモジュール制御プログラミング チュートリアル
RTLinuxによる調歩同期シリアル通信I/Oモジュール制御プログラミング チュートリアル
RTLinuxによるGP-IBI/Oモジュール制御プログラミング チュートリアル
RTLinuxによるDAI/Oモジュール制御プログラミング チュートリアル
RTLinuxによるADI/Oモジュール制御プログラミング チュートリアル
RTLinuxによるDIOI/Oモジュール制御プログラミング チュートリアル
RTLinuxによるHDLCI/Oモジュール制御プログラミング チュートリアル
RTLinuxによるPCI/CompactPCI/CardBus制御入門書(導入編)
Visual C++によるPPI入門書
Visual Basicによるメモリ共有インタフェース入門書
Visual C++によるメモリ共有インタフェース入門書
Visual Basicによるメモリンク入門書
Visual C++によるメモリンク入門書
Visual BasicによるHDLC入門書
Visual C++によるHDLC入門書
Visual BasicによるGP-IB入門書
Visual C++によるGP-IB入門書
Visual BasicによるDIO入門書
Visual C++によるDIO入門書
Visual BasicによるDA入門書
Visual C++によるDA入門書
Visual BasicによるAD入門書
Visual C++によるAD入門書
Visual Basicによるモーションコントローラ入門書
Visual C++によるモーションコントローラ入門書
メモリンクを使用した負荷分散システム事例チュートリアル
Visual BasicによるPPI入門書
モーションコントロールチュートリアル
Microsoft Visual Studio .NET移行ガイド
拡張ユニット チュートリアル(問題解決編)
拡張ユニットチュートリアル(入門編)
C(98)/ISA製品からPCI/CompactPCI製品への移行チュートリアル(DOS編)
DOSによるLAP-B入門書
DOSによるAD入門書
LinuxによるPCI/CompactPCI/CardBus制御 入門書
PCI-ISAバスブリッジチュートリアル
PCI-Cバスブリッジチュートリアル
技術情報資料
初めてのCANインタフェース
Linux, リアルタイムLinux移植(SH-4)経験談及び当社の今後の取り組みについて
LinuxからPCI/CompactPCII/Oモジュールを制御する方法
ActiveXコントロールによるシステム組み込み技術
CompactPCIへの置き換え+システム構築/移行ガイド
MS-DOSからPCI/CompactPCII/Oモジュールを制御する方法
Interface Corporation
- 110 -
TUT-0034
参考文献
著 者
題 名
里 和政/神崎 康宏/斎藤 健司
トランジスタ技術SPECIAL №9「パラレル・インタフェー
ス用LSIの使い方」(CQ出版社:1988年)
Intel
IntelR82C55A CHMOS PROGRAMMABLE PERIPHERAL
INTERFACE Datasheets(Intel:October 1995)
マイクロソフト株式会社 監修, Microsoft Visual C++/Visual C++ Win32 API オフィシャル
アスキー書籍編集部 編
リファレンス 改訂版(株式会社アスキー:1997年)
[ISBN4-7561-1106-8]
! 警告
本ドキュメントの一部または全てを弊社の許可なく、複写,複製,転載,電子化することを禁じま
す。
- 111 -
Interface Corporation
TUT-0034
2007年 5月 Ver. 1.1 発行
発行所
〒732-0828
広島県広島市南区京橋町10-21
TEL 082-262-7777
FAX 082-262-5066
定価 ¥2,000
本書の内容の一部または全部を、無断で転載することを禁止します。
本書の内容は、将来予告なく変更することがありますので、予めご了承ください。
© 2001, 2007 Interface Corporation. All rights reserved.
サポート体制
本製品についてのお問い合わせは、カスタマーサポートセンタで承ります。弊社Web siteのオ
ンラインQA(「サポート」→「お客様相談センタ」をクリック)、E-mailまたはフリーダイヤルをご
利用ください。
お問い合わせ先
<カスタマーサポートセンタ>
0120-447213
FAX
0120-458257
TEL
(祝日および弊社休業日を除く月~金 AM9:00~PM5:00迄)
E-mail [email protected]
TUT-0034 Ver. 1.1 Vol. 1/1
www.interface.co.jp
Visual C++によるPPI入門書
TUT-0034 Ver. 1.1
www.interface.co.jp
Fly UP