コンソール ハンドル

コンソール プロセスでは、ハンドルを使用して、コンソールの入力バッファーと画面バッファーにアクセスします。 プロセスでは、GetStdHandleCreateFile、または CreateConsoleScreenBuffer 関数を使用して、これらのハンドルのいずれかを開くことができます。

GetStdHandle 関数には、プロセスに関連付けられている標準入力 (STDIN)、標準出力 (STDOUT)、および標準エラー (STDERR) ハンドルを取得するためのメカニズムが用意されています。 コンソールの作成時に、システムによってこれらのハンドルが作成されます。 初めは、STDIN はコンソールの入力バッファーのハンドルであり、STDOUTSTDERR はコンソールのアクティブな画面バッファーのハンドルです。 ただし、SetStdHandle 関数を使用して、STDINSTDOUT、または STDERR に関連付けられているハンドルを変更することで、標準ハンドルをリダイレクトできます。 親の標準ハンドルは子プロセスに継承されるため、後続の GetStdHandle への呼び出しでは、リダイレクトされたハンドルが返されます。 したがって、GetStdHandle によって返されるハンドルでは、コンソール I/O 以外のものが参照される場合があります。 たとえば、子プロセスを作成する前に、親プロセスで SetStdHandle を使用して、パイプ ハンドルが子プロセスに継承される STDIN ハンドルになるように設定できます。 子プロセスで GetStdHandle を呼び出すと、パイプ ハンドルが取得されます。 これは、親プロセスによって子プロセスの標準ハンドルを制御できることを意味します。 SetStdHandle を使用して標準ハンドルに低いアクセス権を設定している場合を除いて、GetStdHandle によって返されるハンドルには GENERIC_READ | GENERIC_WRITE アクセス権があります。

GetStdHandle によって返されるハンドルの値は、0 でも 1 でも 2 でもないため、コンソール ハンドルを必要とする関数で Stdio.h の標準の定義済みストリーム定数 (STDINSTDOUT、および STDERR) を使用することはできません。

CreateFile 関数を使用すると、STDINSTDOUT がリダイレクトされている場合でも、プロセスでコンソールの入力バッファーとアクティブな画面バッファーのハンドルを取得できます。 コンソールの入力バッファーのハンドルを開くには、CreateFile の呼び出しで CONIN$ 値を指定します。 コンソールのアクティブな画面バッファーのハンドルを開くには、CreateFile の呼び出しで CONOUT$ 値を指定します。 CreateFile では、返されるハンドルの読み取り/書き込みアクセス権を指定できます。

CreateConsoleScreenBuffer 関数では、新しい画面バッファーが作成され、ハンドルが返されます。 コンソール出力のハンドルを受け入れる任意の関数で、このハンドルを使用できます。 新しい画面バッファーは、SetConsoleActiveScreenBuffer 関数の呼び出しでそのハンドルが指定されるまで、アクティブになりません (表示されません)。 アクティブな画面バッファーを変更しても、GetStdHandle によって返されるハンドルには影響しないことに注意してください。 同様に、SetStdHandle を使用して STDOUT ハンドルを変更しても、アクティブな画面バッファーには影響しません。

CreateFileCreateConsoleScreenBuffer によって返されるコンソール ハンドルは、コンソールの入力バッファーまたはコンソール画面バッファーのハンドルを必要とするすべてのコンソール関数で使用できます。 GetStdHandle によって返されるハンドルは、コンソールの I/O 以外のものを参照するようにリダイレクトされていなければ、コンソール関数で使用できます。 ただし、標準ハンドルがファイルまたはパイプを参照するようにリダイレクトされている場合は、ReadFile 関数と WriteFile 関数でのみ使用できます。 GetFileType は、ハンドルが参照するデバイスの種類を判断するのに役立ちます。 コンソール ハンドルは FILE_TYPE_CHAR として提示されます。

プロセスでは、DuplicateHandle 関数を使用して、元のハンドルとは異なるアクセス権や継承性を持つ重複するコンソール ハンドルを作成できます。 ただし、プロセスでは、自身が使用するためにのみ、重複するコンソール ハンドルを作成できることに注意してください。 これは、DuplicateHandle によって別のプロセスで有効な複製を作成できる他のハンドルの種類 (ファイル、パイプ、相互排除オブジェクトなど) とは異なります。 コンソールへのアクセスは、他のプロセスの作成中に共有する必要があります。または、AttachConsole メカニズムを使用して、他のプロセスから要求できます。

コンソール ハンドルを閉じるには、プロセスで CloseHandle 関数を使用できます。