Museum

Home

Lab Overview

Retrotechnology Articles

Online Manuals

⇒ fd(4) — NEWS-os 3.3

Media Vault

Software Library

Restoration Projects

Artifacts Sought

Related Articles

format(8)

newfs(8)

mkfs(8)

tar(1)

FD(4)  —  UNIX Programmer’s Manual

名称

fd − NEWS フロッピーディスクインタフェース

形式

controller fc0 at iop0   priority 7 (NWS-800/900/1800/1900)
controller fc0 at hb0 csr 0x2000    priority 20 (NWS-1700 / PWS-1500)
disk fd0 at fc0 drive 0
disk fd1 at fc0 drive 1 (NWS-1700/PWS-1500のみ)
disk fd2 at fc0 drive 2 (NWS-1700/PWS-1500のみ)
disk fd3 at fc0 drive 3 (NWS-1700/PWS-1500のみ)

解説

fd デバイスドライバを用いて、 NEWS内蔵 3.5インチマイクロフロッピーディスク装置を使うことができます。 このドライブは、両面倍密度倍トラック(2DD)、 両面高密度倍トラック(2HD)のソフトセクタフロッピーディスクを使用できます。 マイナーデバイス番号を変えることで、 フロッピーにアクセスするフォーマットを変化させます。

NWS-1700/PWS-1500シリーズでは、内蔵ドライブに加えて、 NEC PC-9800シリーズの外部フロッピーディスク装置を接続することが可能で、 これに対応してデバイスドライバの機能も拡張されています。

拡張部分は主として複数のフォーマットを扱えるようになった点です。 1ユニットにつき8種類のマイナー番号を割り当ててあるため、 デバイスファイル名を変えるだけで、 同時に8種類のフォーマットを使うことができます。
また、ioctl を発行することでフォーマットを決定する 各種のパラメータを変更することができます。
そうして指定した任意のフォーマットで、メディアの初期化、 リード、ライト、IDリード等が行なえます。

その他セクタの ID部を読みだしたり、指定したデバイスファイルの 現在のフォーマットパラメータを調べる ioctl 等も用意されています。

NEWS内蔵の 3.5インチドライブは、 ハードウェア的には両面倍密度フロッピー(2D)の読み出しは可能ですが、 書き込みは保証していません。 また、2HDフォーマットの時の内蔵3.5インチドライブの スピンドルモーターの回転数は、300rpmとなります。 360rpmのドライブ (例 : NEC製3.5インチ拡張ドライブ) とは、 データー読み書きの互換性はないので注意してください。

read/write 開始点に関する制限

lseek(2) で read/write 開始点が指定できますが、機種ごとにいくつかの制限があります。

< NWS-800/900/1800/1900シリーズ >

 rawデバイスにI/Oリクエストを出すときは、 セクタ境界(512byte)から read/write を始めてください。 block デバイスでは制限なく正常に動作します。

< NWS-1700/PWS-1500シリーズ >

 ∗ セクタ長を 512byte より短く設定した場合

 rawデバイスに対するI/Oリクエストに限って、 read/write 開始点を 512byte 境界に合わせることが必要です。 従って例えばセクタ長が 256byte の場合、 奇数セクタから read/write を始めることはできません。

 block デバイスでは制限なく正常に動作します。 ただし、トラックによってフォーマットが異なるディスクの場合 注意が必要です(後述)。

 ∗ セクタ長を 512byte より長く設定した場合

 rawデバイスに対するリクエストでは、read/write 開始点をセクタ長 ( > 512byte) 境界に合わせれば、正常に動作します。

 block デバイスに対する I/O リクエストは、正常に動作しません。

NOTES

ドライバは block I/O と raw I/O の両方をサポートします。 FD の block デバイスと raw デバイスのメジャー番号は、 それぞれ 1 と 5 になります。

NWS-800/900/1800/1900シリーズ fd デバイスドライバ

2DD/2HDの2種類のフォーマットタイプが使えます。

タイプbytess#h#c#形式容量記録
2DD5129280E/I720KBMFM
2HD51218280E/I1440KBMFM

(bytes…セクタ長, s#…セクタ数, h#…ヘッド(サイド)数, c#…シリンダ数, E/I…ECMA/ISO)

< マイナー番号−ファイル名−フォーマットタイプ >

マイナー番号によってディスクのフォーマットタイプを識別しています。

minor#ファイル名(raw/block) タイプ
0rfh0a/fh02HD (両面高密度倍トラック)
8rfd0a/fd02DD (両面倍密度倍トラック)

NWS-1700/PWS-1500シリーズ fd デバイスドライバ

< 定義済みフォーマットタイプ >

ディスクのフォーマットは、あらかじめドライバ内に設定されている、 以下の 13種類のフォーマットタイプの中から選んで指定することができます。

type#typebytess#h#c#形式容量記録drSW
0FD2DD5129280E/I720KBMFMS/N640KB
1FD2HD51218280E/I1440KBMFMSONY
2FD2HD102410248277IBM1232KB MFM NEC 1MB
3FD2DDMS95129280IBM720KBMFMS/N 640KB
4FD2DDMS85128280IBM640KBMFMS/N 640KB
5FD2DMS95129240IBM360KBMFMS/N640KB
6FD2DMS85128240IBM320KBMFMS/N640KB
7FD2HDPS51218280IBM1440KBMFMSONY
8FD2HCAT51215280IBM1200KBMFMNEC 1MB
9FD2DDOA10245277IBM770KBMFM S/N 640KB
10FD2DDOA025616277IBM616KBMFMS/N 640KB
11FD1S12812826177IBM250KBFMNEC1MB
12FD2D25625626277IBM1001KBMFMNEC 1MB

(dr…推奨ドライブ, S/N…SONY/NEC)

推奨ドライブが存在するのは、前に述べた回転数の違いによるものです。

NECのドライブを使用する際に、 背面の密度切り替えスイッチを SW にしたがってセットしてください。 またドライブ番号切り替えスイッチは 3/4 にセットしてください。

< マイナー番号−ファイル名−フォーマットタイプ >

マイナー番号の使い方、デバイスファイル名のつけかたは以下のようになっています。

∗ マイナー番号

    bit(b7 - b0)
UUFFFPPP
     UU…ユニット#   FF…フォーマットスロット#  PPP…パーティション#
    FFF をフォーマット識別に用いています。
    各フォーマットスロットに任意のフォーマットを指定できるので、
  同時に 8 種類のフォーマットをデバイスファイル名を変えるだけで使用できます。
    また各スロットには後述するフォーマットが初期設定されています。

∗ デバイスファイル名(raw/block)

    rfdxya/fdxya
     x…ユニット#   y…フォーマットスロット#  a…パーティションa

MAKEDEV を用いて作られるデバイスファイルについて、 マイナー番号(minor#)とスペシャルファイル名の対応、 それぞれのファイル(フォーマットスロット)に 初期設定されているフォーマットタイプ(type#)は、 以下のようになります。

minor#ファイル名(raw/block)タイプtype# 備考
0rfd00a/fd00aFD2HD1rfh0a/fh0も可
8rfd01a/fd01aFD2DD0rfd0a/fd0も可
16rfd02a/fd02aFD2DDMS93
24rfd03a/fd03aFD2DDMS84
32rfd04a/fd04aFD2DMS95
40rfd05a/fd05aFD2DMS86
48rfd06a/fd06aFD2HDPS7
56rfd07a/fd07aFD2HCAT8
 128rfd20a/fd20aFD2HD10242
136rfd21a/fd21aFD2DDOA9
144rfd22a/fd22aFD2DDMS93
152rfd23a/fd23aFD2DDMS84
160rfd24a/fd24aFD2DMS95
168rfd25a/fd25aFD2DMS86
176rfd26a/fd26aFD1S12811
184rfd27a/fd27aFD2D25612
 192rfd30a/fd30aFD2HD10242
200rfd31a/fd31aFD2DDOA9
208rfd32a/fd32aFD2DDMS93
216rfd33a/fd33aFD2DDMS84
224rfd34a/fd34aFD2DMS95
232rfd35a/fd35aFD2DMS86
240rfd36a/fd36aFD1S12811
248rfd37a/fd37aFD2D25612

特殊なフォーマットのディスクについて

フォーマットが、トラックによって変わるディスクを取り扱う場合、 適切に lseek を行なうように注意してください。

アクセスしたいターゲットブロックのフォーマットにあわせて FDC の パラメータを設定し、 全ディスクがそのフォーマットであると仮定して lseek を行います。 lseek ではスキップする部分はディスクのヘッドをシークするだけで、 実際に読みはしないので、この方法が使えます。

ところがコマンドによっては、例えば dd コマンドのように 指定した skip 値の分だけ実際に読み捨てを行なうものもあるので注意してください。 読み捨てる部分のフォーマットが違っていると、その箇所でリードエラーになり、 ターゲットブロックも読めません。

また、ブロックデバイスとしてディスクをアクセスする場合も注意が必要です。 セクタ長を 512 byte 以下の長さに設定した場合、 ブロックデバイスを用いると read/write 開始点を自由に取ることができます。 これはカーネルの中で、 自動的に 2 Kbyte 単位のバッファリングを行なっているためであり、 ブロックデバイスでは read/write 開始点も長さも 2 Kbyte の倍数となります。
一方IBMフォーマット8インチの FD2D256 等のディスクの track#0 は、 128 byte/sector の 26 セクタから構成され、 1トラックあたり 3328 byte となり 2 Kbyte の倍数になりません。 このため2回目に 2 Kbyte 分アクセスしようとしたときに、 途中から track#1 になるため、フォーマットが変わってエラーとなります。
従ってこのような場合は raw デバイスとして open して、 read/write 開始点を 512 byte 境界に合わせてアクセスを行なってください。

一例として、IBMフォーマット 8インチ FD2D256 の場合のアクセス法を示します。

Cyl#Track#sect#デバイスフォーマット他
001−26rawFD1S128(lseek(0byte),read(3328byte))
011−6rawFD2D256(lseek(6656byte),read(1536byte))
017−raw/blkFD2D256(lseek(8192byte))

track#1 の sect#1−6 のアクセスで 6656 byte の lseek を行うのは、 track#0 も FD2D256 フォーマットと考えて 256(byte/sect)x26(sect) の lseek が必要とされるからです。

IOCTL

ioctl のコマンドについて解説します。なおヘッダファイルは、

#include <news800iop/fdreg.h> ..... NWS-800/900シリーズ
#include <news1800iop/fdreg.h> ..... NWS-1800/1900シリーズ
#include <newshbdev/fdc.h> ..... NWS-1700/PWS-1500シリーズ

をインクルードしてください。

IOCTL(NWS-800/900/1800/1900/1700/PWS-1500共通)

FDIOCFORMAT

指定したトラックのフォーマットを行います。 NWS-800/900/1800/1900 シリーズで唯一使うことのできる ioctl です。

usage:
int track;
ioctl(fd, FDIOCFORMAT, &track);

IOCTL(NWS-1700/PWS-1500専用)

以下の ioctl は NWS-1700/PWS-1500 シリーズでのみ使うことができます。

FDIOCSET

FDC のパラメータのマニュアルセットを行います。

sx2 フラグは、1 にすると 1 cylinder 置きにシークが行なわれます。 5/3.5 インチの 2D のディスクのように、 シリンダ間隔が 2DD/2HD の2倍になるものは、このフラグを 1 にセットします。

フラグを 1 にセットしておいて、例えばシリンダ #17 へシークすると、 2DD/2HD フォーマットのシリンダ #34 に相当する位置まで、 ヘッドのシークが行われます。

なお一般的に、2DD/2HD 対応のドライブ (大容量ドライブと呼ぶ) で 2D のメディアを取り扱う場合、 2D専用ドライブで書き込んだデータは大容量ドライブで読めますが、 その逆は保証されません。

大容量ドライブ同士のデータ交換ではこのような問題はおこりません。

注意1) NEWS内蔵のユニット(ユニット番号0)に対して EXT_VFO モードは指定できません。
注意2) 8インチのドライブユニットに対して、 77 以上のシリンダ数を指定しないでください。

usage:
FDCparam fdcp;
ioctl(fd, FDIOCSET, &fdcp);
typedef struct FDCparam {
intnsect;/∗ # sectors/track ∗/
intntrak;/∗ # tracks/cylinder ∗/
intncyl;/∗ # cylinders ∗/
intnbytes;/∗ # bytes/sector(fd_length) ∗/
 intn;/∗ sector length code(fd_n) ∗/
intgsl;/∗ GSL ∗/
intgpl;/∗ GPL ∗/
intmf;/∗ mfm mode(1=MFM,0=FM) ∗/
 intninterl;/∗ interleave(fd_interleave) ∗/
 inttrspd;/∗ transfer speed ∗/
intfomt;/∗ format(ECMA_ISO, IBM) ∗/
intvfomode;/∗ VFO mode(ext=1/int=0) ∗/
 intsrt;/∗ SRT ∗/
inthut;/∗ HUT ∗/
inthlt;/∗ HLT ∗/
intsx2;/∗ seek doublly flag ∗/
int  widd;/∗ write-id data ∗/
} FDCparam;
 #define MFM 1
#define FM 0
 #define IBM 0
#define ECMA_ISO 1
 #define EXT_VFO 1
#define INT_VFO 0

FDIOCSELECT

フロッピーのタイプを選んで、FDC のパラメータをセットします。

usage:
int type;
ioctl(fd, FDIOCSELECT, &type);

type にはフォーマットタイプを指定します。 前述の<定義済みフォーマットタイプ>の表の、1桁目の数字を指定してください。

FDIOCREADID

FDC の READID コマンドとほぼ同等です。

まず指定シリンダまでシークを行なってから、READID を実行します。 シークは、sx2 フラグとは無関係に、 通常のステップ (2DD/2HDのステップ) で行なわれます。

シーク先のシリンダで、最初に読めたセクタの c,h,r,n の値が、 結果としてセットされます。 リターン値としては、読めた場合 0、読めなかった場合負の値が返されます。

上述のようにシークが通常ステップで行なわれるため、 0 以外の偶数シリンダを読んでみた結果から、2DD か 2D かを判別できます。 指定した cylinder とリターン値のの res_c の間には、 それぞれ以下のような関係が成り立ちます。

2DDcylinder == res_c
2Dcylinder == res_c ∗ 2

usage:
FDCid fdcid;
ioctl(fd, FDIOCREADID, &fdcid);
 typedef struct FDCid {
intcylinder;/∗ physical cylinder # ∗/
int head;/∗ head ∗/
intres_c;/∗ result: cylinder ∗/
intres_h;/∗ result: head ∗/
intres_r;/∗ result: sector ∗/
intres_n;/∗ result: rec length code ∗/
} FDCid;

FDIOCRESTORETYPE

フロッピーのフォーマットを初期設定値に戻します。

usage:
ioctl(fd, FDIOCRESTORETYPE, 0);

FDIOCGET

現在のフロッピーのパラメータの値を問い合わせます。

usage:
FDCparam fdcp;
ioctl(fd, FDIOCGET, &fdcp);

ERRORS

システムコールがエラーで終了した場合、 大域変数 errno に次の値がセットされますので、 エラーの内容の大まかな確認は可能です。

#include <sys/errno.h>
extern int errno;

ENXIO

原因

open システムコールの、ユニット番号がおかしい (ユニット番号 1 を指定した)。

EIO

原因

open システムコール, FDIOCFORMAT, FDIOCREADID において、 モーターを ON できなかった(drive not ready)。

なお、openシステムコール時にドライブにメディアが入ってないと、 このエラーが発生します。

EACCES

原因

ライトプロテクトされているメディアをライトオープンしようとした。

EINVAL

原因

指定したデバイスのフォーマットパラメータがセットされてない。

ioctl の引数の値が不適当である。

EFAULT

原因

FDIOCFORMAT, FDIOCREADID において、 シークに失敗したか、もしくは ID が読めなかった。

なお、EFAULT、EACCES および EIO は Read/Write/Format などの 実行時に発生した場合、 コンソールにエラーメッセージを出力します。

関連ファイル

/dev/fh0/dev/rfh0a
/dev/fd0/dev/rfd0a
/dev/fd[0−3][0−7]a/dev/rfd[0−3][0−7]a

関連事項

format(8), newfs(8), mkfs(8), tar(1)

バグ

マウントしてあるフロッピーを取り出すときは、必ず umount(8) コマンドを実行した後で行なってください。

NEWS-OSRelease 3.3

Typewritten Software • bear@typewritten.org • Edmonds, WA 98026