プログラム セグメント プレフィックス( PSP ) は、 DOSシステムでプログラムの状態を保存するために使われるデータ構造です。これは、CP/Mオペレーティング システムのゼロ ページに似ています。PSP の構造は次のとおりです。
PSP は、 DOS プログラムのコマンド ライン引数を取得するために最もよく使用されます。たとえば、コマンド「FOO.EXE /A /F」は、引数「/A」と「/F」を使用して FOO.EXE を実行します。
コマンドラインの長さの PSP エントリがゼロ以外で、環境セグメントへのポインタが 0000h でも FFFFh でもない場合、プログラムはまず環境変数 %CMDLINE%からコマンドラインを取得してから、PSP からコマンドラインを抽出する必要があります。この方法により、126 文字を超えるコマンドラインをアプリケーションに渡すことができます。
PSPのセグメントアドレスは、プログラム実行時にDSレジスタに渡されます。また、後でInt 21h関数51hまたはInt 21h関数62hを使用して決定することもできます。どちらの関数も、レジスタBXにPSPアドレスを返します。[6]
あるいは、オフセットにロードされた.COM100hプログラムでは、上記のオフセットを使用するだけで PSP を直接アドレス指定できます。オフセットは000hPSP の先頭を指し、0FFh最後を指します。
たとえば、次のコードはコマンドライン引数を表示します。
org 100h ; .COM - ds を使用しない
; INT 21h サブファンクション 9 は文字列を終了するために '$' を必要とします
xor bx , bx mov bl ,[ 80h ] cmp bl , 7Eh ja exit ; オーバーフローを防止します
movバイト[ bx + 81h ], '$'
; 文字列を出力します
mov ah , 9 mov dx , 81h int 21h
終了:
mov ax , 4C00h ; サブ関数 4C int 21h
DOS 1.x では、プログラム終了時に CS (コード セグメント) レジスタに PSP と同じセグメントが含まれている必要があったため、標準的なプログラミング手法では、プログラム開始時に DS レジスタ (DS レジスタには PSP セグメントがロードされるため) とゼロ ワードをスタックに保存し、RETF 命令でプログラムを終了して、保存されたセグメント値をスタックからポップし、INT 20h 命令を含む PSP のアドレス 0 にジャンプしていました。
; 保存
プッシュds xor ax 、axプッシュax
; デフォルトのデータグループ (@data) に移動する
mov ax , @ data mov ds , ax
; mess1 にメッセージを出力 (21h サブファンクション 9)
mov dx , mess1 mov ah , 9 int 21h
retf
実行ファイルが.COMファイルの場合、この手順は不要であり、プログラムは単に直接INT 20h命令またはINT 21h関数0を呼び出すだけで終了できます。ただし、プログラマーは、プログラム終了時にCSレジスタにPSPのセグメントアドレスが含まれていることを確認する必要があります。したがって、
ジャンプスタート
mess1 db 'こんにちは世界!$'
開始:
mov dx , mess1 mov ah , 9 int 21h
20時間
DOS 2.x 以降では、プログラムの終了は INT 21h 関数 4Ch によって実行され、CS レジスタに PSP のセグメント値を格納する必要はありませんでした。
参照
- ゼロページ (CP/M)
- コール5(DOS)
- スタックフレーム(Unix)[7]
- プロセスディレクトリ(Multics)[7]
- プロセス識別子(PID)[7]
- これ(コンピュータプログラミング)
- 自己言及
参考文献
- ^ ab Taylor, Roger; Lemmons, Phil (1982 年 6 月). 「上方移行 - パート 1: トランスレータ - CP/M-86 プログラムを CP/M および MS-DOS に移行する」 [CP/M プログラムを CP/M-86 および MS-DOS に移行する変換プログラムの使用] (PDF) . BYTE . 第 7 巻、第 6 号。BYTE Publications Inc. pp. 321–322, 324, 326, 328, 330, 332, 334, 336, 338, 340, 342, 344 [342, 344]。ISSN 0360-5280。CODEN BYTEDJ。2020年1 月 16日のオリジナルから アーカイブ(PDF) 。2020-01-15取得。
[…]
CP/M-86
へのアクセス […] CP/M-86 にアクセスするには、機能コードを CL レジスタに配置し、バイト パラメータを DL レジスタに配置するか、ワード パラメータを DX レジスタに配置し、データ セグメントを DS レジスタに配置し (データ セグメントは通常、変換されたプログラムでは変更されません)、ソフトウェア割り込み
INT #224
を実行する必要があります。結果は、バイト値の場合は AL レジスタに返され、ワード値の場合は AX レジスタと BX レジスタの両方に返されます。ダブルワード値は、オフセットが BX レジスタに、セグメントが ES レジスタに返されます。したがって、プログラムを
CP/M-80から CP/M-86 に変換するには、位置 5 への呼び出しをソフトウェア割り込み INT #224 に置き換える必要があります。もう 1 つの必要な変更は、
ウォーム ブート
に関するものです
。 CP/M-80 では、位置 0 にジャンプするための機能コード 0 のシステム コールによってウォーム ブートにアクセスできます。ただし、CP/M-86 では位置 0 へのジャンプはサポートされていません。そのため、プログラムを正しく実行するには、変換されたプログラムでこのプログラム終了を変更する必要があります。位置 5 への呼び出しが INT #224 に置き換えられ、ウォーム ブートの変更が行われ、レジスタが正しくマップされていれば、変換されたプログラムが CP/M-86 システム機能にアクセスするのに問題はほとんどありません。[…]
MS-DOS
へのアクセスの取得[…] MS-DOS には、システムにアクセスするためのソフトウェア割り込み
INT #33
による「推奨」メカニズムがありますが、「既存の」プログラム用に、少なくとも 0 ~ 36 の範囲の機能については、CP/M-80 呼び出し規約と互換性のある追加のメカニズムが提供されています。許可された関数範囲内のシステム コールに関しては、プログラマーは、レジスタを正しくマップする以外に、翻訳されたプログラムを MS-DOS で実行するために何もする必要はありません。MS-DOS は、CP/M-80 のウォーム ブート機能もサポートしています。MS-DOS で位置 0 にジャンプすると、ソフトウェア割り込み
INT #32 が
実行されます。これは機能的にはプログラムの終了であり、プログラムを終了する通常の方法です。[…]
[1] [2][3][4][5][6][7][8][9][10][11][12][13][14] (13ページ)
- ^ Paul, Matthias R. (2002-10-07) [2000]. 「Re: COM ファイルを実行する」.ニュースグループ: alt.msdos.programmer. 2017-09-03 にオリジナルからアーカイブ。2017-09-03に取得。[15] (注:DOS COMプログラムの呼び出し規約の詳細が記載されています。)
- ^ Necasek, Michal (2011-09-13). 「とにかく、アドレスのラップアラウンドが必要なのは誰ですか?」OS/2 Museum。 2020-02-19 にオリジナルからアーカイブ。 2020-02-19に取得。
[…]
86-DOS
、そして
PC DOS
/
MS-DOS
では、巧妙なトリックが使用されていました。 PSP のオフセット 5 のバイトには、ファーコール オペコード (9Ah) が含まれていました。 PSP のオフセット 6 のワードには、プログラム セグメント サイズを示す適切な値と、ファーコールのオフセット部分が含まれていました。 ファーコールのセグメント部分として機能するオフセット 8 のワードは、オフセットと組み合わせるとラップアラウンドし (
8086
CPU のよく知られた機能)、割り込みベクター 30h を含むアドレス 0:C0h を指すように作成されました。 […]
CALL 5
インターフェイスは Windows NT および OS/2 の DOS エミュレーションでも動作しますが、これらのシステムは
A20 ライン
が無効になっている状態では動作しません。それでは、どのように動作するのでしょうか? […] アドレス ビットを切り捨てるのではなく、システムは 0:C0h の 5 バイトを 1000C0h にミラーリングします。同じ手法は、実際に DOS 5 以降で
DOS=HIGH
で動作しているときに使用されていました。その場合、DOS はリニア アドレス 1000C0h に適切なファー コールが含まれていることを確認します。 […]
- ^ ポール、マティアス R. (1997-07-01) [1994-01-01]。 MSDOSTIPs — MS-DOS 5.0-7 に関するヒント (ドイツ語)。 2017-08-22 のオリジナルからアーカイブ。2013 年 10 月 25 日に取得。
{{cite book}}:|work=無視されます (ヘルプ) (注: MSDOSTIP.TXT は MPDOSTIP.ZIP の一部であり、2001 年まで維持され、当時多くのサイトで配布されていました。提供されたリンクは、HTML に変換された古いバージョンの MSDOSTIP.TXT ファイルを指しています。) [16] - ^ ポール、マティアス R. (1997-05-01) [1995-03-01]. 「JPSofts 4DOS 5.5b/c、5.51、5.52a および NDOS に関するヒント」。MPDOSTIP (ドイツ語)。 2016-11-04 のオリジナルからアーカイブ。2015 年 5 月 8 日に取得。
4DOS5TIP.TXT(注:提供されたリンクは、コレクションの一部であるファイルのHTML変換バージョンを指していますMPDOSTIP.ZIP。)[17] - ^ 「INT 21h,62h - PSP アドレスを取得する (DOS 3.x)」。2012 年 2 月 7 日のオリジナルからアーカイブ。
- ^ abc シュルマン、アンドリュー;ブラウン、ラルフ D. ; マクシー、デビッド; ミシェルズ、レイモンド J.; カイル、ジム (1994) [1993 年 11 月]。Undocumented DOS: 予約済みの MS-DOS 関数とデータ構造のプログラマー向けガイド - MS-DOS 6 、Novell DOS、Windows 3.1 まで拡張(第 2 版)。マサチューセッツ州レディング: Addison Wesley。ISBN 0-201-63287-X。(xviii+856+viページ、3.5インチフロッピー) 訂正: [18][19]
さらに読む
- 86-DOS - 8086 用ディスク オペレーティング システム - プログラマーズ マニュアル(PDF)。バージョン 0.3 (暫定版)。米国ワシントン州シアトル: Seattle Computer Products, Inc. 1980。2019年 6 月 23 日にオリジナル(PDF)からアーカイブ。2011年 9 月 13 日に取得。(41ページ)
- 「プログラムセグメントプレフィックス(PSP)のフォーマット」。INTER61 。 2000年。2020年2月17日にオリジナルからアーカイブ。2019年12月19日に取得。
- シェパース、アルネ (1991)。 「Kapitel 5: EXEC im Detail - プログラム セグメント プレフィックス (PSP)」。DOS 5 for Programmierer: Die endgültige Referenz (ドイツ語) (第 1 版)。Addison Wesley (Deutschland) GmbH。 148–151、971–972ページ。ISBN 3-89319-350-2。(1123 ページ以上、折り込み、5.25 インチフロッピー)
外部リンク
- コマンドライン引数へのアクセス (Microsoft.com)
