<HTML>

<HEAD>

<META NAME="GENERATOR" CONTENT="Internet Assistant for Microsoft Word 2.0j Beta">
</HEAD>

<BODY>

<H1>
<CENTER>
第４部 
</CENTER>
</H1>

<HR>

<H1>
<CENTER>
ソフト開発時の注意 
</CENTER>
</H1>

<P>

<CENTER>
<IMG SRC="dtd4.gif">
</CENTER>

<P>
　　　第１章　ディスクの環境
<OL>
<LI><A NAME="a411"></A>１　ディスクの有無と数を知る方法 
</OL>

<P>
　Ｈ．ＰＨＹ<FONT FACE="Century">DIO(FFA7H)</FONT>の内容が<FONT FACE="Century">C9H</FONT>であればディスクは接続されていません。ディスクから実行されていることが明らかなプログラムではこれを調べることは不必要かつ無意味です。　ディスクが存在する場合は、「ログインベクタの獲得」ファンクションコール<FONT FACE="Century">(18H)</FONT>で論理ドライブの数を知ることができます。
<OL>
<LI><A NAME="a412"></A>２　ハードディスクを見分ける方法 
</OL>

<P>
ある特定の論理ドライブがハードディスクなのか、それともフロッピーディスクなのかを知るには、次のようにします。
<BR>
　まず、「ディスクのフォーマット」ファンクションコール<FONT FACE="Century">(67H)</FONT>を<FONT FACE="Century">B</FONT>にドライブ番号、<FONT FACE="Century">A</FONT>に<FONT FACE="Century">0(</FONT>選択文字列を返す<FONT FACE="Century">)</FONT>をセットしてコールします。ここで返された、スロットとアドレスからの文字列を得ると、ハードディスクの場合は、文字列が<FONT FACE="Century">0</FONT>でターミネイトされた直後に、<FONT FACE="Century">&quot;SCSI7FFC&quot;</FONT>といった文字列が入っています。最初の<FONT FACE="Century">4</FONT>文字が<FONT FACE="Century">ID</FONT>で次の<FONT FACE="Century">4</FONT>文字が<FONT FACE="Century">I/O</FONT>アドレスを示しています。
<BR>
　この処理で、「ディスクのフォーマット」ファンクションコールをコールした時、そのドライブがハードディスクインターフェイスだと「このドライブはフォーマットできません」<FONT FACE="Century">(.IFORM
0F0H)</FONT>が帰りますが、その後の上記の操作は有効です。<BR>
　この方法は<FONT FACE="Century">DOS1</FONT>では使えません。
<OL>
<LI><A NAME="a413"></A>３　物理ドライブ 
</OL>

<P>
ソフトウェアから見た時に存在しているドライブを論理ドライブと言いますが、<FONT FACE="Century">2</FONT>ドライブシミュレーションによって仮想的に存在しているドライブである場合も含まれています。これにたいして、物理的に存在しているドライブを物理ドライブと言います。
<BR>
　物理ドライブの数や、どのドライブが物理ドライブであるかを知ることは通常できません<FONT FACE="Century">(</FONT>と<FONT FACE="Century">Datapack</FONT>には書いてあります<FONT FACE="Century">)</FONT>。が、<FONT FACE="Century">MSX</FONT>マガジンで裏技とでも言うべき方法が紹介されたことがあります。その方法を紹介します。
<BR>
　まず、<FONT FACE="Century">H.PROMPT(F24FH,3)</FONT>を書き換えます。ここは通常<FONT FACE="Century">RET</FONT>で、<FONT FACE="Century">RET</FONT>すると<FONT FACE="Century">2</FONT>ドライブシミュレーションのディスク入れ替えメッセージを出力してキー入力待ちをするルーチンがあります。書き換えたジャンプ先ではスタックを<FONT FACE="Century">1</FONT>レベル捨ててから<FONT FACE="Century">RET</FONT>命令を実行します。これで、<FONT FACE="Century">2</FONT>ドライブシミュレーションのメッセージは出力されません。
<BR>
　次に<FONT FACE="Century">H:</FONT>から<FONT FACE="Century">A:</FONT>の全てのドライブを逆順にアクセスしていきます。これによって、<FONT FACE="Century">2</FONT>ドライブシミュレーションによって物理ドライブと仮想ドライブが入れ替わっていたりする状態をリセットします。
<BR>
　ここで、<FONT FACE="Century">A:</FONT>から<FONT FACE="Century">H:</FONT>にむかって今度は順番にアクセスしていきます。このとき<FONT FACE="Century">H.PROMPT</FONT>がコールされたらそのドライブは仮想ドライブです。<FONT FACE="Century">H.PROMPT</FONT>からのジャンプ先ではコールされたことをワークエリアに記録して<FONT FACE="Century">RET</FONT>するようにします。プログラムはディスクアクセスから帰ってきた時にこのワークエリアの内容を調べることによって、そのドライブが仮想ドライブであることを知ることができます。もし、仮想ドライブだった時はもう一度その前のドライブをアクセスして<FONT FACE="Century">2</FONT>ドライブシミュレーションの状態を戻しておかないといけません。
<BR>
　ここまでのディスクアクセスで、ディスクがドライブにセットされているかどうかはわからないので<FONT FACE="Century">DISKVE</FONT>も書き換えて、ディスクエラーを回避しなければなりません。
<BR>
　物理ドライブを調べ終わったら<FONT FACE="Century">H.PROMPT</FONT>および<FONT FACE="Century">DISKVE</FONT>を元に戻しておいてください。
<OL>
<LI><A NAME="a414"></A>４　マスターカートリッジ 
</OL>

<P>
<FONT FACE="Century">MSX</FONT>には<FONT FACE="Century">DISK ROM</FONT>が最高<FONT FACE="Century">4</FONT>つまで接続される可能性があります。ただし、実際に主な処理を受け持つのはそのうち<FONT FACE="Century">1</FONT>つだけで、その<FONT FACE="Century">DISK
ROM</FONT>をマスターカートリッジといいます。そして、マスターカートリッジ以外の<FONT FACE="Century">DISK
ROM</FONT>をスレーブカートリッジといいます。<BR>
　マスターカートリッジのスロット番号は、<FONT FACE="Century">MASTERS(F348H)</FONT>に保存されています。
<P>
<A NAME="a415"></A>　　　　１．５　<FONT FACE="Century">DISK ROM</FONT><FONT SIZE=2>のスロットを知る方法</FONT>
<P>
<FONT FACE="Century">FB21H</FONT>〜<FONT FACE="Century">FB28H</FONT>のドライブテーブルという領域に、ディスクインターフェイスに関する情報が記録されています。各ディスクインターフェイスカートリッジ毎に<FONT FACE="Century">2</FONT>バイトが割り当てられており、そのカートリッジの論理ドライブ数とスロットアドレスが記録されています。ここで、<FONT FACE="Century">1</FONT>番目のカートリッジがマスターカートリッジとは限りません。混同しないようにして下さい。
<P>
<FONT FACE="Century">FB21H 1</FONT>番目のカートリッジの論理ドライブ数
<BR>
　<FONT FACE="Century">FB22H</FONT>　　　　　〃　　　　　<FONT FACE="Century">
</FONT>スロット番号<BR>
　<FONT FACE="Century">FB23H 2</FONT>番目のカートリッジの論理ドライブ数
<BR>
　<FONT FACE="Century">FB27H 4</FONT>番目のカートリッジの論理ドライブ数
<BR>
　<FONT FACE="Century">FB28H</FONT>　　　　　〃　　　　　<FONT FACE="Century">
</FONT>スロット番号
<OL>
<LI><A NAME="a416"></A>６　ディスクを使用しない方法 
</OL>

<P>
　ディスクを使用できる環境では、ディスクワークエリアの為にフリーエリアが減少してしまいます。そのためにディスクを使用しなくてもよいソフトがディスクワークエリアを確保しない環境で実行を行いたい場合は、システムを起動する際に<FONT FACE="Century">SHIFT</FONT>キーを押しながら立ち上げます<FONT FACE="Century">(SHIFT</FONT>キー立ち上げ<FONT FACE="Century">)</FONT>。このようにすると、<FONT FACE="Century">DISK
ROM</FONT>は初期化を行わず、ディスクワークエリアは設定されません。当然この状態ではディスクを使用することはできません。
<BR>
　<FONT FACE="Century">SHIFT</FONT>キーの押されていることを確認するとシステムは<FONT FACE="Century">BEEP</FONT>音で知らせます。つまり、
<BR>
<FONT FACE="Century">SHIFT</FONT>キーは<FONT FACE="Century">BEEP</FONT>音がなるまで押していれば良いことになります。
<P>
<A NAME="a417"></A>　　　　１．７　2ドライブシミュレーションを無効にする方法
<P>
　システム立ち上げ時に、BEEP音がなるまでCTRLキーを押していると2ドライブシミュレーション機能を無効にすることができます。システムが立ち上がってから2ドライブシミュレーションを無効にすることはできません。
<P>
<A NAME="a42"></A>　　　第２章　プログラム作成上の注意
<P>
<A NAME="a421"></A>　　　　２．１ TPA、フリーエリアの上限
<P>
ディスク上で実行されるプログラムの場合、ディスクのワークエリアがメモリ上のどこまでを占めるかはシステムによって異なります。ですからプログラムは実行の前にかならず使用可能なメモリの上限を調べてから実行しなければなりません。もし実行するのにメモリが足りない場合はメッセージを表示して実行を止めて下さい。
<BR>
　<FONT FACE="Century">DOS</FONT>環境の場合、使用できるエリアは<FONT FACE="Century">TPA</FONT>の範囲となりますが、<FONT FACE="Century">TPA</FONT>の上限は<FONT FACE="Century">0006H</FONT>に示されます。<FONT FACE="Century">(0006H)</FONT>からがシステムのある領域なので、<FONT FACE="Century">(0006H)-1</FONT>までを利用できます。
<BR>
　<FONT FACE="Century">BASIC</FONT>環境の場合フリーエリアの上限は<FONT FACE="Century">CLEAR</FONT>文を実行する前の<FONT FACE="Century">HIMEM(FC4AH)</FONT>の内容から知ることができます。<FONT FACE="Century">MSX</FONT>では<FONT FACE="Century">DE3FH</FONT>までのエリアを利用することが推奨されています。ただし、この範囲内でプログラムを書いたとしても、フリーエリアの確認は必ずするようにして下さい。
<P>
<A NAME="a422"></A>　　　　２．２　環境の確認
<P>
　プログラムの内容によっては、起動時に動作環境を確認しないと異常動作や暴走につながりますから、次のような項目の確認を怠らないようにしましょう。
<BR>
　<FONT FACE="Century">MSX</FONT>のバージョン。<FONT FACE="Century">MSX1</FONT>にない画面モードを使用する場合や、<FONT FACE="Century">MSX2</FONT>以降で追加された機能を使用する場合には<FONT FACE="Century">MSX</FONT>バージョンの確認が必要です。<FONT FACE="Century">MSX</FONT>のバージョンを確認するには<FONT FACE="Century">MAIN
ROM</FONT>の<FONT FACE="Century">002DH</FONT>番地の値を見れば判別できます。この際、この値がいくつならば動作するというプログラムではそれよりバージョンが新しい<FONT FACE="Century">MSX</FONT>で使用できなくなってしまいますから、かならずいくつ以上なら動作するというようにプログラムして下さい。
<BR>
　<FONT FACE="Century">MSX-DOS</FONT>のバージョン。<FONT FACE="Century">DOS2</FONT>のファンクションコールを使用するプログラムなどでは、<FONT FACE="Century">DOS</FONT>のバージョンを判別する必要があります。これも<FONT FACE="Century">MSX</FONT>のバージョンの場合と同様、そのバージョン以降ならば動作するというようなプログラムにしておくことが必要です。
<BR>
　画面モード。<FONT FACE="Century">ANK</FONT>モードか漢字モードかの判別が必要な場合があります。プログラムの実行に不適当なモードだった場合にはモードを変更する必要があります。また、スクリーンモード、表示色、表示桁数、ファンクションキー表示の有無なども確認する必要がある場合には確認します。
<P>
<A NAME="a423"></A>　　　　２．３　環境の保存
<P>
　プログラム実行のためにスクリーンモードなどMSXの動作環境を変更するプログラムでは、DOSのコマンドラインに戻る際にできる限りもとの環境を復元するべきです。
<BR>
　復元するべき環境とは、スクリーンモード、漢字モード、ファンクションキーの表示、表示色、表示文字数、キークリックの有無などです。
<P>
<A NAME="a424"></A>　　　　２．４　2ドライブシミュレーション
<P>
　2ドライブシミュレーションが機能している場合、仮想ドライブにアクセスしようとした時にディスク入れ替えのメッセージが表示されます。しかし、グラフィック画面を使用するプログラムや、画面のフォーマットを乱されては困るプログラムでは、入れ換えメッセージの出力が正常に行われなかったり、画面を乱すなどの問題が発生します。
<BR>
　このメッセージを変える必要のある時は次のようにします。<BR>
　2ドライブシミュレーションのメッセージを表示する前にH.PROMPT(F24FH)がコールされます。ここは通常RETになっていますが、ここにユーザーのディスク交換ルーチンへのジャンプ命令を書きます。
<BR>
　ディスク交換ルーチンが呼ばれた時、Aレジスタにドライブ名がキャラクタで入っています。また、スタックトップが標準のプロンプトルーチンへのリターンアドレス、スタックトップ+2がシステムへのリターンアドレスです。ですから、システムに戻る時はスタックを1レベル捨ててからリターンします。
<BR>
　ディスク交換ルーチンではレジスタを保存する必要はありません。またこのルーチンが呼ばれる時にはスロット切り換えは行われないので、ページ1に交換ルーチンを置くことはできません。交換ルーチンからユーザープログラムにジャンプしてはいけません。
<BR>
　プログラムが終了又はアボートする時、H.PROMPTの内容を元に戻す必要があります。
<P>
<A NAME="a425"></A>　　　　２．５　ブレーク処理
<P>
　ディスクエラー処理や2ドライブシミュレーションのためにフックを書き換えた場合、プログラムが強制的に中断された場合にもフックを正しく戻せるようにすることが必要です。フックを正しく戻していないと、DOSに戻ってからディスクエラーや2ドライブシミュレーションの処理が発生した時に暴走します。
<BR>
　ブレーク処理の方法は次のように行います。<BR>
　DOS1の場合<BR>
　WOOM BOOT(0001H,2)を処理ルーチンのアドレスに書き換えます。ブレーク処理ルーチンからシステムに戻ろうとする場合は、WOOM
BOOTの内容を元の状態に戻して下さい。さもないと、システムに戻ろうとした時、再びブレーク処理ルーチンに戻ってしまいます。
<BR>
　DOS2の場合<BR>
　「アボート終了ルーチンの定義」ファンクションコール(63H)を利用します。システムに戻ろうとする時は、「アボート終了ルーチンの定義」ファンクションコールを利用して、アボート終了ルーチンを解除して下さい。そうしないとシステムに戻るつもりが再びアボート終了ルーチンに帰ってきてしまいます。
<BR>
　DOS2のアボート終了ルーチンは、0000Hへのジャンプでシステムに戻ろうとした場合にはコールされません。DOS2ではプログラムの終了には「エラーコードを伴った終了」ファンクションコール(62H)を利用しなければなりません。
<P>
<A NAME="a426"></A>　　　　２．６　エラー発生時の処理
<P>
　ディスクアクセスで発生するエラーにはロジカルエラーとハードウェアエラーの2種類があります。
<BR>
　ロジカルエラーとは、ディスク容量が足りないとか、ファイルがオープンできないといったエラーで、ファンクションコールの戻り値で知ることができます。ユーザーはこの戻り値を見て適当な処理を行うことになります。
<BR>
　これに対して、ハードウェアエラーはディスクが入っていないとか、ライトプロテクトが掛かっているなどといったディスクドライバが返すエラーで、これらのエラーはファンクションコールからエラーコードとして返されることはありません。通常、ディスクドライバからこれらのエラーを受け取ると、DOSのエラーハンドラが"Abort
Retry Ignore?"などと問いかけて、その結果により処理を決定します。
<BR>
　問題になるのはハードウェアエラーです。DOSが正常に画面出力できる環境で動作するプログラムであれば、特にプログラムがそれを必要とする場合を除けば、エラー処理はDOSにまかせてもほとんど問題は発生しないのですが、グラフィック画面を使用しているためにDOSが文字を出力できない場合や、画面を乱されては困るようなプログラムでは独自にエラー処理を行う必要があります。
<BR>
　ハードウェアエラーの処理方法はDOS1とDOS2で異なります。DOS1のエラー処理を使用したプログラムを、DOS2で使用して問題が起こることはないと思いますが、DOS2専用のプログラムやDOS2での使用をあらかじめ考えて作成されるプログラムでは、DOS2上で実行された場合はDOS2でのエラー処理を採用して下さい。
<BR>
　次にDOS1、DOS2それぞれのエラー処理を説明します。<BR>
　DOS1でのエラー処理<BR>
　DOSのディスクエラーハンドラは、ハードウェアエラーが発生すると、DISKVE(F323H)の示すアドレスの内容が示すアドレスのエラー処理ルーチンを実行します。
<BR>
　エラー処理ルーチンを変更したい場合は、DISKVEの内容を書き換えて、ユーザーのエラー処理ルーチンに処理が渡るようにして下さい。
<BR>
　エラー処理ルーチンのエントリ条件は次のようになっています。<BR>
　　設定　A　エラーを起こしたドライブの番号(0:A 1:B・・・7:H)
<BR>
　　　　　C　エラーの種類<BR>
　　　　　　 b0　エラー時の状態<BR>
　　　　　　　　 0:読み込み時　1:書き込み時<BR>
　　　　　　 b1〜7　エラーの種類<BR>
　　　　　 b7 6 5 4 3 2 1<BR>
1 0 0 0 0 0 0　bad FAT<BR>
0 0 0 0 0 0 0　write protect<BR>
0 0 0 0 0 0 1　not ready<BR>
0 0 0 0 0 1 0　CRC error<BR>
0 0 0 0 0 1 1　seek error<BR>
0 0 0 0 1 0 0　record not found<BR>
0 0 0 0 1 0 1　unsupported media type(読み込み時)<BR>
0 0 0 0 1 0 1　write fault(書き込み時)<BR>
0 0 0 0 1 1 0　other error<BR>
　戻り値　C　0　ignore(エラーを無視して先へ進む)<BR>
　　　　　　 1　retry(入出力を再度試みる)<BR>
　　　　　　 2　abort(処理を中断)<BR>
　エラーが発生すると上記のようにAにドライブ番号Cにエラーの種類がセットされてエラー処理ルーチンがコールされます。エラー処理ルーチンが、エラーの表示と処理の確認のみ処理して、DOSの標準エラー処理に戻るならば、Cに処理を指定してリターンします。
<BR>
　ただし、エラーがbad FATとunsupported media typeだった場合には、ignoreを返すとディスクを破壊する場合があるので、必ずabortかretryを返すようにして下さい。
<BR>
　もし、DOSの標準エラー処理を使用せずに独自のエラー処理を行いたいならば、標準エラー処理に帰らずにユーザープログラムにジャンプすることもできます。この場合は、ファンクションコールを実行する前にスタックポインタを保存しておき、エラー処理ルーチンはスタックポインタを元に戻してから処理を続けて下さい。
<BR>
　エラー処理ルーチンの呼び出しの際、Disk BASICの環境ではDISK ROMがイネーブルされていて、スロット切り換えは行われませんのでページ1にはエラー処理ルーチンを置くことはできません。DOSの環境ではページ1のRAMがイネーブルされてから処理が渡ってきます。DOS1では、エラー処理ルーチンがDOSのエラー処理ルーチンに戻ろうとする場合は、エラー処理ルーチンの内部でファンクションコールを利用することはできません。
<BR>
　DISKVEを書き換えた状態でユーザープログラムを終了すると、次にディスクエラーが発生した時に正規のエラー処理ルーチンに処理が渡らずに暴走してしまいます。このためにプログラムを終了する際には必ずDISKVEを元の状態に戻すことが必要です。また、Ctrl-STOPでシステムに戻ってしまわないようにしておくことが必要です。これには0001Hと0002Hの内容(WOOM
BOOT)を書き換えます。<BR>
　DOS2でのエラー処理<BR>
　DOS2では「ディスクエラー処理ルーチンの定義」ファンクションコール(64H)があるので、これを利用します。(ファンクションコールの詳細を参照)
<BR>
　この場合、DOS1の場合とはエラー処理ルーチンの呼ばれた時のレジスタの内容と戻り値の内容がそれぞれ異なりますから注意して下さい。また、エラー処理ルーチンからユーザーのプログラムにジャンプできないことにも注意して下さい。ユーザーのプログラムにジャンプする方法は「ディスクエラー処理ルーチンの定義」ファンクションコールの説明を参照して下さい。DOS2でのエラー処理ルーチンの内部では、エラー処理ルーチンから安全に呼び出せるとされたファンクションコールを利用することができます。
<P>
<A NAME="a427"></A>　　　　２．７　コマンドラインでのスイッチ
<P>
　DOSのコマンドでスイッチはコマンドの機能を選択、指定するのに使われます。スイッチは"/"で始まりその後にアルファベット(通常1文字)を指定します。アルファベットの大文字小文字は通常区別しません。
<BR>
　スイッチの先頭の文字は"/"を使用するのが原則ですが、実際には"-"(マイナス符号)を使用できるものもあります。"-"を使用できるようにする場合は"/"と"-"の両方を使用できるようにしてください。
<BR>
　"-"文字はファイル名に使用することができるので、スイッチとファイル名を区別できなくなる可能性があります。ですから、オプションにファイル名を指定するコマンドでは"-"は使用できないようにするなど考慮が必要です。
<BR>
　また、できるだけ既存のものに準ずることが、使いやすさにつながります。DOSの標準コマンドがよく使用しているスイッチを参考までに以下に挙げます。
<BR>
/A (アスキーファイル)ファイルをASCIIファイルとして扱います<BR>
/B (バイナリファイル)ファイルをそのまま扱います<BR>
/H (不可視属性)不可視属性ファイルも対象にする<BR>
/P (ページモード)画面いっぱいになったら出力を一度止めてキー入力を待つ
<BR>
/V (ベリファイ)コマンド実行中ベリファイ機能を有効にします<BR>
/W (ワイド形式)DIRコマンドで複数のファイル名を一行に表示する<BR>
/X (無表示)メッセージを表示しない
<P>
<A NAME="a428"></A>　　　　２．８　バッチの停止
<P>
　DOSのバッチコマンドを実行中に、エラーの発生等の原因でバッチ処理を停止したい時は、(0006H)+13Hのアドレスに0を書き込んで下さい。以後バッチの実行を停止します。
<BR>
　この方法はDOS2上では使用できません。
<P>
<A NAME="a429"></A>　　　　２．９　COMMAND.COM
<P>
　DOSの外部プログラムをCOMMAND.COMという名前にしておけば、DOSの起動時に直接実行させることができます。この場合、スタックがシステムの内部にあるため、スタックを初期化しないと暴走することがあります。スタックをTPAの上限に設定するには
LD SP,(0006H) を実行すればいいことになります。
<P>
<A NAME="a4210"></A>　　　　２．10　DOS2利用上の注意
<P>
　DOS1上で動作するソフトはほとんどそのままDOS2上でも動作しますが、一部非互換の部分があるために正常動作をしないことがあります。
<BR>
　まず、ファイルアクセスの方式が少し違うために、DOS2で作成したファイルがDOS1で読めなくなるようなことがまれにあります。次に、COPY命令に互換性がありません。COPY命令や、ディスク-VRAM間直接転送を使っているソフトはDOSが変わると動作不良を起こすことがあります。これはBASICでも機械語でも同じです。それから、いくつかのファンクションの機能が若干変更になっているのでこれらのファンクションを使用しているソフトはDOS2で動かない可能性があります。詳しくは第３部第５章ファンクションコールの詳細を参照して下さい。
<BR>
　またDOS2のファンクションでは裏レジスタは保存されますがDOS1では保存されません。またDOS1では0080Hからに保存されるパラメータの最後が0DHでおわりますが、DOS2では00Hで終わるので注意が必要です。これ以外にも若干、小さなバグのような物がいくらかあるようです。
<P>
<A NAME="a4211"></A>　　　　２．11　スタック
<P>
　ディスクアクセスの際、スタックはどのページにあっても問題ありません。DOSのファンクションコールは、コールされるとスタックを内部のスタックに切り替えてからファンクションコールを処理します。
<P>
<A NAME="a43"></A>　　　第３章　ディスクアクセス
<P>
<A NAME="a431"></A>　　　　３．１　ディスクアクセスの方法
<P>
　ディスクアクセスには、Disk BASICを使う、システムコールを使う、PHYDIOを使うなどの方法があります。それらの特徴について説明します。
<P>
<A NAME="a4311"></A>　　　　　１　Disk BASICを使う
<P>
　特に説明の必要はないと思いますが、Disk BASICの命令を利用してディスクアクセスを行います。ファイルのアクセスやVer.2.0では階層ディレクトリの使用なども簡単に行えるようになっているので、Disk
BASIC上でディスクをアクセスするならばこの方法が最も簡単かつ合理的です。
<BR>
　この場合、通常はアクセスの途中でディスクエラーが発生するとBASICのエラーメッセージが表示してプログラムが中断します。ディスクの書き込みを伴うプログラムでは、プログラムが停止した場合やエラーが発生した場合にディスクに正しくデータが書き込まれるような処理を行うと安全です。注意しなければならないのは、ファイルをオープンして書き込みを行い、そのファイルがクローズされないうちにエラーやCTRL-STOPでプログラムが中断した場合です。この時は、まだディスクにバッファを書き出していないので、ファイルのクローズを伴う命令を実行しないうちにディスクを抜いてしまうと、ディスクの内容が破壊される可能性があります。
<BR>
　ファイルのクローズを伴う命令とは、CLOSE、CLEAR、CLOAD、END、LOAD、NEW、があります。また、プログラムの書き換えが発生するとファイルはクローズされます。
<P>
<A NAME="a4312"></A>　　　　　２　ファンクションコールを使う
<P>
　この方法はDOS上のプログラムではもっとも一般的です。マシン語を使用すればDisk
BASICの環境からでも利用できます。詳しくは第３部を参照して下さい。
<BR>
　この方法では、ファイルのアクセスはもとより、カレントドライブの変更など豊富なDOSの機能が利用できます。
<BR>
　エラーが起こった際の処理等がいくらか複雑になりますが、ディスクの書き込みを伴うソフトでは確実にエラー処理を行って下さい。
<P>
<A NAME="a4313"></A>　　　　　３　PHYDIOを使う
<P>
　PHYDIOとは、MAIN ROMのBIOSエントリに存在する未公開ルーチンです。ディスクをセクタ単位でアクセスしますが、ディスクドライバに一番近いルーチンなので、メディアIDを指定できたり、ディスクドライバからのエラーコードを得ることができたりということがあり、場合によっては有用です。未公開ルーチンですが、市販ソフトではプロテクトチェックのために一般的に使用されており、とくに問題はないようです。ただしDOS2では使用できません。
<BR>
　ただ、あくまでも未公開ですので、通常のアクセスでは使用しない方が良いでしょう。PHYDIOを使用することによるアクセス速度の改善はほとんどありません。
<BR>
PHYDIO(0144H/MAIN)(未公開)<BR>
　　　設定　A　物理ドライブ番号(0:A・・・7:H)<BR>
　　　　　　B　処理するセクターの数　　C　メディアID<BR>
　　　　　　DE　先頭のセクター 　　　　HL　転送アドレス<BR>
　　　　　　Cy　0:読み込み　1:書き込み<BR>
　　戻り値　Cy　0:成功　1:失敗<BR>
　　　　　　A　エラーコード(Cy=1の場合)<BR>
　　　　　　B　残りのセクタ数(Cy=1の場合)<BR>
　レジスタ　すべて<BR>
　Disk BASICの環境から使用するときは上記の0144Hをコールすればいいのですが、DOSの環境などではPHYDIOのジャンプ先であるFFA7H(H.PHYD)をコールすることも行われます。
<P>
<A NAME="a432"></A>　　　　３．２　ドライブを止める方法
<P>
　ディスクアクセスの後のドライブの停止をタイマ割り込みを使って行っているディスクドライバがあります。このようなドライバが接続されているシステムで、割り込みが禁止されたり、システムのタイマ割り込みルーチンを無効にしたりした場合に、ディスクドライブが止まらなくなる現象が発生します。
<BR>
　これを防ぐためには、ディスクアクセスの後にマスターカートリッジの4029Hをコールして下さい。ただし、古いDISK
ROMにはこのルーチンがない場合もありますので、コールする前にその存在を確認する必要があります。4029Hの内容が00Hだった場合はモーターを停止するルーチンは存在しません。よって、モーターを停止することはできません。
<P>
<A NAME="a433"></A>　　　　３．３　フォーマット
<P>
ディスクのフォーマットをする方法を説明します。DOS2の場合はシステムコールでサポートされていますので第３部第５章を参照して下さい。
<P>
4025H/マスタースロット<BR>
　　　設定　HL　フォーマット用ワークエリアの先頭アドレス<BR>
　　　　　　DE　フォーマット用ワークエリアの長さ<BR>
　　戻り値　Cy 0:成功　1:失敗<BR>
　　　　　　A　エラーコード(Cy=1の場合)<BR>
　このルーチンをコールするとBASICで_FORMATを実行したのと同じようにフォーマットのタイプを聞いてきます。ここでフォーマットのタイプを入力すると実際にフォーマットします。フォーマットの指定を入力することなしにフォーマットすることはできません。
<BR>
　フォーマット用ワークエリアは8KB以上あれば問題ありません。<BR>
　FORMAT(0147H/MAIN)やフックのFFACH(H.FORM)をコールしても同様にフォーマットすることができますが、こちらは未公開です。
<P>
<A NAME="a434"></A>　　　　３．４　turboRでのディスクアクセス
<P>
　turboRで、DOS1またはDisk BASICVer.1.0上で動いているプログラムが高速モードになっている場合にディスクアクセスをする際にはCPUをZ80に切り換えてからディスクアクセスをしなければなりません。なぜかというと、ディスクドライバはZ80上で動作することを考えて作られているので、R800を使っている時にディスクアクセスを行うとFDCとのタイミングが狂う可能性があるからです。DOS2上では、DOSカーネルがディスクアクセスを行う時にはZ80に切り換えているので問題は発生しません。
<P>
<A NAME="a435"></A>　　　　３．５ 効率のよいディスクアクセス
<P>
　ディスクアクセスのアルゴリズムを間違えると、必要以上にディスクアクセスに時間が掛かってしまい、使いにくいソフトになってしまいます。実用的なソフトでは、ファイルアクセスの方法もデータの構造や目的によりある程度制限があると思いますが、ゲーム等のソフトでは、ディスクアクセス待ちは短いほうが良いので、ディスクアクセスの方法を工夫すると良いでしょう。ディスクアクセスの効率を上げるためには次のような事を守って下さい。
<BR>
　まず、データの読み込みや書き込みはなるべく大きなまとまりを単位としてすることです。例えば、1セクタ(512バイト)づつ16回読み込みを行うよりも、1回で16セクタ(8KB)の読み込みを行ったほうが一般に早くなります。これは、ディスクの構造を考えればわかるのですが、1セクタを読む度にユーザーに処理を返していると、ユーザーが処理を行っている間にディスクは回転して次のセクタはヘッドの位置を通過してしまい、ディスクがもう一周してくるのを待つことになってしまいます。ディスクドライバの内部で処理しているぶんには、次のセクタがヘッドの位置にくるまでに次のセクタを読み込む処理に移れるので無駄がありません。この読み込み処理の時間はディスクドライバの性質によって大きく変わることがありますが、セクタ単位でアクセスすると最悪の場合で最高の場合の数倍程度の時間が掛かることがあります。
<P>
<A NAME="a44"></A>　　　第４章　プログラムのオートスタート
<P>
　ゲームソフト等で、自作のプログラムをオートスタートするようにしたいと考えることがあると思います。そのような場合に使える代表的な方法を説明します。
<P>
<A NAME="a441"></A>　　　　４．１　BASICの場合
<P>
　BASICのプログラムをオートスタートさせたい場合は実行させたいBASICプログラムを"AUTOEXEC.BAS"というファイル名でセーブしておくことです。こうしておけば、BASICが起動した直後にそのプログラムが読み込まれて実行されます。
<P>
<A NAME="a442"></A>　　　　４．２　DOSプログラム
<P>
　DOSの外部コマンドを自動的に実行させたい場合は"AUTOEXEC.BAT"という名前のバッチファイルで実行させたい外部コマンドを実行させます。
<BR>
　コマンドインタプリタに戻る必要がない場合は、外部コマンドを"COMMAND.COM"という名前にして置くことでMSXDOS.SYSによって読み込まれて実行されます。この場合スタックの初期化を忘れずに行うことが必要です。
<P>
<A NAME="a443"></A>　　　　４．３　ブートセクタからの起動
<P>
以上の方法を使うと、実行の前にBASICやDOSの起動メッセージが出てしまいますが、これを避けたい場合にはディスクのブートセクタに起動プログラムを書いておくことによりDOSなどの起動メッセージなしに自分のプログラムを自動実行させることができます。
<BR>
　ブートセクタから起動する場合にはブートセクタのC01EH番地からにプログラムを書いておきます。ブートセクタの先頭256バイトはシステムの起動時にC000Hに読み込まれ、2回コールされます。
<BR>
　1回目のコールではCyフラグをリセットしてコールされ、その時のスロットの状態はページ0がBIOS
ROM、ページ1がDISK ROM、ページ2と3はRAMになっています。この時Aが0ならシステムが起動した直後であることを表します。また、HLにはDISKVEのアドレスが入っています。
<BR>
　2回目のコールではCyフラグがセットされてコールされ、その時のスロットの状態はページ1がDISK
ROMで他のページはRAMになっています。この時も1回目のコールと同様にレジスタがセットされ、Aが0なら起動直後を表し、HLにDISKVEのアドレス、DEにページ1をRAMに切り換えるルーチンのアドレスがセットされています。
<BR>
　1回目のコールではページ1をRAMに切り換えることはできないのでユーザープログラムの起動には適当ではありません。
<BR>
CO1EHからのプログラムではまず"RET NC"で1回目のコールを無視した後、2回目のコールで実行するプログラム本体を読み込んで実行します。
<BR>
　ブートセクタの読み込みでは先頭の256バイトのみが読み込まれるのでブートプログラムはこの範囲で書く必要があります。
<BR>
<BR>

<HR>

<P>
※個人的以外の使用および無断転載を禁止します。
<P>
Copyright(C) 1996 by ASCAT All rights reserved.
<P>
<A HREF="../index.htm">ホームページに戻る</A> <A HREF="tgdindex.htm">目次に戻る</A>

<P>
<A NAME="a444"></A>
</BODY>

</HTML>
