SOURCE.TXT
========================================================================

             master.lib 0.23 Sources に関するあれこれ

                                                       記述 恋塚昭彦
========================================================================

  master.libのソースファイルの要となるファイル

   Makefile     肝心要。nmake用。
   makeind.exe  Makefileから利用している作成補助プログラム。
   master.h     C言語のための宣言。
   master.pas   Pascalのための宣言と定義。


  master.libのソースを作成するときのルール

    ・ソースコード
        　OPTASMとTASMで共用することが前提であるため、MASM 5.0の文法のみ
        を利用する。
        　.MODEL SMALLは使えるが、,Cなどの高級言語インターフェイスは使用
        不可。proc の argやusesも使用不可。
        　EXTRNで使える型は、基本型だけ。構造体などは使えない。
        　CPU指定は、.186まで。できるだけ.8086(無指定)
        　.CODE, .DATA, .DATA?は利用可能。
        　.CONST は使用不可。 このセグメントを指定すると、Borland の古い
        リンカ(BC2.0程度まで)で異常なリンクがなされる。 .DATA で代用する
        こと。
        　.DATA? のなかには、 初期値を指定することは禁止。初期値は不定で
        あることを仮定すること。これは、アセンブラから直接リンクして使う
        場合には使えるのだが、 Cでは .DATA? はランタイムスタートアップ部
        分が奇麗に 0 で初期化してしまうし、Turbo Pascal はそもそもこの部
        分は obj から吸い取るときに中身を棄てて、しかも初期値不定となる。
        よって、初期値を定義することは実行形式を無駄に大きくするだけであ
        る。
        　OPTASM の仕様により、 外部参照の宣言文を記述する位置も決まる。
        データラベルの参照(EXTRN)は、.DATAの中で行うこと。
        　逆に、コードラベルのEXTRNは、セグメントに属さない場所、すなわち
        .MODEL文の後で、.CODEや.DATAに入る前の地点で行うこと。
        従来は.CODEを要求していたが、Turbo Pascal版のためにunitを分割した
        際にこの要請が生じた。.CODEの中でEXTRNすると、FAR labelでも tasm,
        optasmなどは push cs,call near文を生成してしまい、異なるセグメント
        に配置されたコードを呼ぶと誤動作していたため。
        　TASMの仕様により、ソースの末尾には END文を置くこと(笑)
        　jump文は、 short で届く範囲は条件ジャンプであろうと short 指定
        を付けること。 (ジャンプ最適化を殺し、マルチパスでなくとも無駄な
        NOPを挿入させないため)

    ・レジスタ,フラグの使用
        　自由に破壊してかまわないレジスタは、BX,CX,ES だけである。DS は、
        他の関数を呼び出す時やリターンする時には seg DGROUP を差している
        必要がある。
        　DSと同様な条件において、 dflagは 0 (CLD)である必要がある。ただ
        し、Pascal からの呼びだしにおいて、dflag は 0 とは限らないので、
        dflagを利用するとき(rep文を使う時)には、 必ず dflag を初期化して
        使うこと。
        　SI,DI,BP は、 リターンするときには呼びだし時点と同じ値であるこ
        と。
        　AX,DX は、関数の戻り値になる場合でなければ自由に破壊してかまわ
        ない。

    ・関数名
        　全て大文字。 理由は Pascal と C の共通で使える呼び出し規約であ
        る Pascal 呼び出し規約を利用するため。
    ・引数
        すべてスタック経由。引数は先頭から順に push される。
        long 値は、上位→下位の順に push される。
        これも Pascal 規約による。
    ・リターン
        リターンのときに、同時にスタックに積まれた引数を開放する。
        たとえば 2 wordの引数があった場合、
          ret 4
        でリターンする。
        これも Pascal 規約による。

    ・グローバル変数
        　グローバル変数は、プロシージャと同一のモジュールには置かずに、
        ひとかたまりのグローバル変数の定義専用のモジュールを用意する。こ
        れは、  グローバル変数を外部  obj  側で定義できないという  Turbo
        Pascal の仕様による。 つまり、グローバル変数専用モジュールという
        のは C言語側からしか利用せずに、 Pascal では Pascal 上で定義され
        たグローバル変数をアセンブラ側から参照する形になる。
        　この制約は、「ライブラリ内部でしか使わないが、複数モジュール間
        で共有するデータ」にも適用される。

    ・グローバル変数名
        　大文字/小文字混在は許されるが、区別されない。
        先頭に _(アンダーバー)は付けないで参照する。
        　C言語用のグローバル変数定義モジュールでは、同一データに _(アン
        ダーバー)のついた名前と付かない名前の両方で定義し、 公開する。こ
        れにより、 C側からは _(アンダーバー)の付いた名前によって同じ変数
        を参照することができるようになる。

    ・ローカル変数
        　特にラージモデルに於いて、スタック上のデータは常に SS:相対でア
        クセスすること。 ラージモデルのobjをTurbo Pascal版でも共用するた
        めと、そのTurbo Pascalでは常に DS != SS であるため。
                  ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~

    ・ファイルの読み込み用オープン処理
        　ファイルを読み込みのためにオープンする関数では、引数にもらった
        ファイル名のアドレスをそのまま DOS_ROPEN 関数に渡して呼び出す。 
        戻ってきたときに cy が立っていたら、 super.lib エラーコードが AX
        に入っている。cy=0 なら、ファイルハンドルが AX に入っている。
        　なぜこの関数を呼ぶかというと、 この関数は Pascal のときと C の
        ときで異なるモジュールが結合されるようになっており、 Pascal 版で
        はファイル名を Pascal 文字列で受け付けるようになっているため。こ
        うすることで、Pascal 版ではファイル名を C 文字列に変換せずに、直
        接 Pascal の普通の文字列で指定できるようになる。

    ・では、書き込みオープンなどはどうするか。
        　これは、DOS_ROPEN 同様に、DOS_AXDX という関数がある。
        　これは、 引数にAX,DXに入れるべき値をpushして呼び出すのだが、残
        りのレジスタはそのまま int 21hに渡されるようにできているため、こ
        れを利用することとする。
        　そして、この関数に渡す DX の値というのが「文字列のアドレス」を
        差すことになっており、 つまり Pascal  の場合は  Pascal  文字列を
        ASCIZ 文字列に変換する処理が自動的に呼び出されることになる。
        　なお、 DX の部分が文字列のアドレスである関係から、ラージデータ
        版のライブラリでは、セグメント値もここに渡すこととなることに注意。
        　この関数の戻り値は、 DOS_ROPEN と同様。つまり cy=1 なら、DOSの
        エラーコードの符号を反転した値、 すなわち super.lib エラーコード
        が AX に格納されている。 cy=0 なら int 21h の結果通り。ただし DX
        と他のフラグは破壊されている。


  インクルードファイル
    master.libでは、以下のインクルードファイルを利用している。
     func.inc     func マクロや _push, RETSIZE など、メモリモデル制御
     super.inc    super.lib エラーコードや BFNT 構造体などの定義
     clip.inc     直線のクリッピング用マクロ
     sio.inc      RS-232C 関連
     vgc.inc      VGA のレジスタ定義
     bgm.inc      BGM 演奏関連
     pf.inb       pf.lib関連

       func.incのマクロ

          ・モデルの呼び名
              small/medium/compact/large 各モデルに対し、 データポインタ
              の大きさをデータモデル、コードポインタの大きさをコードモデ
              ルとしてそれぞれの大きさで分類する。

                            small code       large code
              small data    [SMALL]          [MEDIUM]
              large data    [COMPACT]        [LARGE]

          ・func 名前 〜 endfunc
               func 名前 を実行すると、
                  public 名前
                  even
                  名前 proc CALLMODEL
               という文が生成される。 これにより、公開関数が簡単に作成で
               きる。 なお、 CALLMODEL は、master.lib メモリモデルにより
               FAR または NEAR が割り当てられる。
               そして、endfunc を記述すると、
                  名前 endp
               が生成される。

          ・_mov, _push, _lds, _lesなど
               _movは、large data modelのときにのみ mov文が生成され、
                       small dataのときは削除される。
               _push も _movと同様。

               _lds, _les は、 large data modelのときは lds, les文が生成
                              される。
                              small data modelのときは、 mov文となり、セ
                              グメントレジスタへのロードは行われない。

               s_ <文>   small dataのときのみ文が生成される。
               l_ <文>   large dataのときのみ文が生成される。

          ・_call
               _call は、 master.lib内にある別の関数を呼び出すときに用い
               る。これは、large code modelのときにも master.libの全関数
               が同一セグメントに配置される事を前提に、push cs/near call
               を行うものである。 これにより多少の高速化と実行形式の大き
               さの節約になる。

          ・RETSIZE
               large code modelなら 2, small code modelなら 1が定義される。
          ・DATASIZE
               large data modelなら 2, small dataなら 1。
          ・CALLMODEL
               large code modelなら FAR, small code なら NEAR。

   makeind.exe
     ソース作成時に呼び出す、makeindユーティリティの使い方。

       makeind ファイル名 objディレクトリ\ アセンブルオプション...

       ファイル名 には、アセンブルしたいソースファイル名を空白または
                  改行で区切って大量に並べたテキストファイルの名前を置く。
       objディレクトリ には、目的のソースをアセンブルした結果のobjを
                  出力するディレクトリ名を、後ろに'\' を付けて置く。
       アセンブルオプション には、アセンブラに渡すオプション文字列を
                  そのまま並べる。

        　このユーティリティは、 obj ディレクトリにある obj ファイルと間
        接ファイルによって指定されたソースファイルのタイムスタンプを比較
        し、obj より新しいか、obj が存在しないソースのみ、ファイル名とア
        センブルオプションをファイルあたり 1行の形式で標準出力に出力する。
        　この出力をテキストファイルにリダイレクトし、アセンブラの起動レ
        スポンスファイルとすることにより、一括して必要なモジュールのみア
        センブルすることができる。
          例:
             makeind asmlist obj\ /T /MX > temp
             tasm @temp

  ・ソースファイル命名規則
    一部例外はあるが、基本的に次のようになっている。

    grp*.asm     PC-9801V       16色グラフィック画面
    gc_*.asm     PC-9801V       16色グラフィック画面(gc_poly)
    egc*.asm     PC-9801        16色EGCグラフィック制御(gc_poly)
    gdc*.asm     PC-9801        16色GDCグラフィック制御(gc_poly)
    gj*.asm      PC-9801        外字処理
    cur*.asm     PC-9801V PC/AT 16色グラフィックカーソル処理
    csr*.asm                    グラフィックカーソルパターンデータ
    vg4*.asm             PC/AT  VGA16色制御
    vgc*.asm             PC/AT  VGA16色制御(gc_poly VGA)
    aj*.asm              PC/AT  joystick読み取り
    b30*.asm     PC-9801        30BIOS/TT制御
    b_*.asm      PC-9801 PC/AT  BEEP演奏、効果音(bgmlib)
    js*.asm      PC-9801        joystick読み取り
    dos*.asm                    DOS汎用一般
    fil*.asm                    ファイル処理(file_*())
    str*.asm                    文字列処理
    tx*.asm      PC-9801        テキスト画面処理
    vt*.asm              PC/AT  テキスト画面処理
    get*.asm                    システム情報取得
    set*.asm                    システム情報変更
    super*.asm   PC-9801V       16色 スーパーインポーズ表示(super.lib)
    over*.asm    PC-9801V       16色 上書き表示(super.lib)
    rep*.asm     PC-9801V       16色 復元描画(super.lib)
    slice*.asm   PC-9801V       16色 部分描画(super.lib)
    small*.asm   PC-9801V       16色 縮小描画(super.lib)
    vg4sp*.asm            VGA   16色 スーパーインポーズ表示(super.lib)
    vg4rp.asm             VGA   16色 復元描画(super.lib)
    vg4o*.asm             VGA   16色 上書き表示(super.lib)
    key*.asm     PC-9801        キーボード読み取り
    font*.asm    PC-9801        フォント読み書き
    fontat*.asm          PC/AT  フォント読み書き
    fep*.asm                    日本語FEP制御
    ems*.asm                    EMSアクセス
    xms*.asm                    XMSアクセス
    pal*.asm     PC-9801V       Palette制御
    dac*.asm              PC/AT VGA Palette制御
    mag*.asm                    MAGデータ処理
    mouse*.asm   PC-9801V       マウス処理
    mousex*.asm                 マウスドライバ呼出し
    perf*.asm    PC-9801        区間精密計測
    perfat.asm           PC/AT  区間精密計測
    pcm*.asm     PC-9801        BEEP PCM再生
    rand*.asm                   擬似乱数
    rsl*.asm                    RSL制御
    rsp*.asm     PC-9801V       常駐パレット制御
    sdi*.asm     PC-9801V       SDI制御
    sin*.asm                    三角関数データ
    sio*.asm     PC-9801        RS-232C
    smem*.asm                   スタック型メモリ管理
    hmem*.asm                   ヒープ型メモリ管理
    tim*.asm     PC-9801        タイマ割り込み
    wfont*.asm   PC-9801V       8x8dot/16x8dot font処理
    b*.asm                      バッファつきファイルアクセス(pf.lib)
    pf*.asm                     アーカイブファイルアクセス(pf.lib)

========================================================================
[END OF SOURCE.TXT]
