2012.4.27
前へ
次へ
ホームページトップへ戻る

復活!CP/M ワンボードマイコンでCP/Mを!
CP/MがTK−80互換のワンボードマイコンの上で復活します
ND80ZVとMYCPU80の上でCP/Mが走ります

[第104回]


●大きなランダムファイルの作られ方について

CP/Mのランダムファイルについて、何回かにわたって説明をしてきました。
前回は、ランダムファイルでは、どのようにしてレコードbゥらブロック、セクタbノ変換されるのか、という仕組みについて説明をしました。

前回は、下のようなレコード番号データを読み込んで、そのレコード番号がその下に示すFCB上のレコード番号テーブル(キー配列表と呼ぶことにします)のどこにあるかを調べて、その位置にブロックb記入する、という仕組みについて説明をしました。

[テスト用に作成したレコード番号データ]
26 0F 22 27 29 0E 11 12 16 03 0D FF
38 15 34 39 41 14 17 18 22  3 13
02 03 04 02 05 03 06 06 07 08 03

[レコード番号テーブル(キー配列表)]
 0
 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
08 00  00 03 06 07 00 00 04 02 05 00 00 00 00 00

実は、前回までの説明ではちょっとごまかしていたところがあります。
そこで使ったレコード番号データは、うまく説明ができるように都合良くアレンジしたものでした。
上のレコード番号テーブル(キー配列表)には、0から63までのレコード番号しかありません。
それよりも大きなレコード番号を指定したらどうなるのでしょうか?

そこのところについて、前回までの説明では、はっきりと説明はしていませんでした。
はっきりは書いていませんでしたが、次のようなことを書きました。

このテストで使っている仮RAMディスクの容量はAドライブもBドライブもわずか6KBです。
1セクタは128バイトですから、セクタの総数は48しかありません。
実際はそこから少なくともディレクトリエリアの4セクタは除外しなければなりません。
するとランダムファイルのデータエリアとして使えるのは最大でも44セクタになります。
ですから、この場合にはレコード番号を0〜43までの範囲にしないとファイル容量が限界を超えてしまう可能性があります。

以上のような説明は、間違いではないのですが、しかしちょっと誤解を招き易い説明でもあります。
そこで問題です。
上のテストデータでは、最大のレコード番号が43以内におさまるようにしてありました(最大のレコード番号は41)。
それでは、もしもそれを超える番号、たとえばレコードbU3を指定したら、そのレコードは作成されるでしょうか、それとも作成されないでしょうか?

これは簡単に試してみることができます。
63は16進数では3Fです。
レコード番号表データの最後に3Fを追加しました。

>cm 830b
830B FF-3F
830C EB-ff
830D D2-

>dm 8300,830f
8300 26 0F 22 27 29 0E 11 12-16 03 0D 3F FF D2 CA FF  S..')......?.メハ.
>

再テストをするため、もう一度FILLE5.BINを実行してRAMディスクをクリアしました。
そのあと、FTST20.BINをロードしてCP/Mを起動しました。

>/ld fille5.bin,8100
loading FILLE5.BIN ...0010(16)bytes loaded,from 8100 to 810F
>jp 8100
>/ld ftst20.bin,8100
loading FTST20.BIN ...00a5(165)bytes loaded,from 8100 to 81A4
>jp d233

a>dir
No file
a>save 1 ftst20.com

そのあと、AドライブにFTST20.COMをセーブしました。
これで再テストのスタンバイOKです。

FTST20.COMを実行しました。
そのあと、結果を確認するために、CP/Mを終了してZB3BASICに戻り、
DM 8800,887F[Enter]
を実行して、ディレクトリエリアのメモリダンプを行ないました。

>jp d233

a>dir
A: FTST20   COM
a>ftst20 test.raf
done

a>dir
A: FTST20   COM : TEST     RAF
a>^D
end of CP/M
>dm 8800,887f
8800  00 46 54 53 54 32 30 20-20 43 4F 4D 00 00 00 02  .FTST20  COM....
8810  01 00 00 00 00 00 00 00-00 00 00 00 00 00 00 00  ................
8820  00 54 45 53 54 20 20 20-20 52 41 46 00 00 00 40  .TEST    RAF...@
8830  08 00 00 03 06 07 00 00-04 02 05 00 00 00 00 09  ................
8840  E5 E5 E5 E5 E5 E5 E5 E5-E5 E5 E5 E5 E5 E5 E5 E5  ................
8850  E5 E5 E5 E5 E5 E5 E5 E5-E5 E5 E5 E5 E5 E5 E5 E5  ................
8860  E5 E5 E5 E5 E5 E5 E5 E5-E5 E5 E5 E5 E5 E5 E5 E5  ................
8870  E5 E5 E5 E5 E5 E5 E5 E5-E5 E5 E5 E5 E5 E5 E5 E5  ................

TEST.RAFのブロックアローケーションエリア8830−883Fの最後のところには09と書かれています。
この場所は上の方でお見せしたレコード番号テーブル(キー配列表)で、レコードbU0〜63が置かれていたところです。
前回のテストで使われたブロックは08まででした。
今回はその次のブロック09が、レコードbU3を書き込むのに使われたことを示しています。

Aドライブのブロック09はアドレス9A00〜9BFFになります。
前回[第103回]のダンプリストではブロック08までをダンプしています。
ブロック08の最後のアドレスは99FFでした。

レコード番号テーブル(キー配列表)で、レコードbU3は、上から4番目に置かれていますから、ブロック09の最後のセクタに書き込まれることになります。
そのアドレスは、9B80〜9BFFです。
実際にそのアドレスにデータが書き込まれたかどうかDMコマンドで確認をしてみました。

>dm 9b80,9bff
9B80  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????
9B90  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????
9BA0  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????
9BB0  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????
9BC0  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????
9BD0  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????
9BE0  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????
9BF0  3F 3F 3F 3F 3F 3F 3F 3F-3F 3F 3F 3F 3F 3F 3F 3F  ????????????????

そのエリアには3FH(63)が書き込まれていることが確認できました。

これはちょっと危険なテストでした。
ディスクの存在しないエリアに書き込んでしまうかもしれません。
実はまだBIOSも完全なものにはなっていませんから、仮RAMディスクに対しては範囲外をアクセスしないためのガードができていないのです。

ただ、CP/Mのランダムファイルの仕組みをしっかり理解できれば、そのようなことを回避することができます。
上のテストで重要なポイントは、レコードbフ大きさではなくて、そのレコードを書き込むことになるブロックbノ注意することです。
前回と今回のテストの結果から、ランダムファイルでもシーケンシャルファイルと同じように、使用されるブロックbヘ前から順番に消費されていくことがわかります。
AドライブとBドライブに分割した仮RAMディスクのサイズは、ともに6KBです。
1ブロックは4セクタ0.5KBですから、12ブロックあることになります。
つまり使用できるブロックは00〜0Bの12ブロックです。
今回のテストではブロック09が使われました。
まだ0Aと0Bの2ブロックは未使用のまま残っていることがわかります。

ところで、まだ今回の最初の疑問には答えていませんでした。
それは、
レコードbU3よりも大きいレコードを指定したら、どうなるでしょうか?
という疑問でした。

それも試してみることにしましたが、実は意外な結果になってしまいました。
本日は時間がなくなってしまいましたので、そのことにつきましては次回に説明することにいたします。

ワンボードマイコンでCP/Mを![第104回]
2012.4.27upload

前へ
次へ
ホームページトップへ戻る