web-dev-qa-db-ja.com

コンソールのログイン画面で上矢印を押すと^ [[Aが表示される理由はありますか?

コンソールログインにいるときはいつでも、 up 以前に入力したコマンドを表示するために、意図的に矢印を付けます。しかし、私はこれを見ます^[[A

しかし、私が押すと CtrlAltPrint ScreenScroll LockPause BreakPage UpPage DownWin キーは文字をエコーし​​ません。

背後にある理由は何でしょうか?

します^[[A文字の種類は何かを意味しますか?

enter image description here

32
Ruban Savvy

キーボードはコンピューターにイベントを送信します。イベントは、「scan code nnn down」または「scan code nnn up」と言います。チェーンの反対側では、端末で実行されているアプリケーションは、文字のシーケンスの形式での入力を想定しています。 (Xサーバーのようにrawアクセスを要求していない限り)。 A、キーボードは「スキャンコード38ダウン」という情報を送信します。コンソールドライバーは keymap を検索し、これを「文字a」に変換します(修飾キーが押されていない場合)。

文字にならないキーまたはキーの組み合わせを押す場合、情報は文字でエンコードする必要があります。いくつかのキーとキーの組み合わせには、対応する制御文字があります。 Ctrl+A 文字(バイト値1)を送信し、 Return 文字(Ctrl + M、バイト値13)などを送信します。ほとんどのファンクションキーには対応する文字がなく、代わりに(エスケープ、バイト値27)文字。たとえば、キー Up エスケープシーケンス␛[Aに変換されます(3文字:エスケープ、開き角かっこ、大文字A)。

コンソールのユーザー名プロンプトは馬鹿げており、ほとんどのエスケープシーケンスを理解できません。使い慣れたラインエディションと履歴機能はありません。これらはシェルによって提供され、ログインするまでシェルはありません。したがって、エスケープシーケンスを表示するだけです。 文字にはグリフがないため、^[と表示されます。 ^記号は、伝統的に制御文字の接頭辞として使用され、エスケープは、そのバイト値のために^[です。これは、[のバイト値から64を引いたものです。

押すと Up シェルプロンプトで、これは同じ3文字のシーケンスをシェルに送信します。シェルはこれをコマンドシーケンスとして解釈します(通常、前の履歴アイテムを呼び出すため)。押すと Ctrl+V その後 Up シェルプロンプトでは、プロンプトにエスケープシーケンスを挿入します。 Ctrl+V 次の文字をコマンドとして解釈するのではなく、文字どおりに挿入するコマンドであるため、文字はエスケープシーケンスの開始として解釈されません。

一部のキーは修飾子のみであり、端末アプリケーションには送信されません。たとえば、 Shift、この情報は端末ドライバに残り、次にを押すと考慮されます Aなので、ドライバーはAではなくaをアプリケーションに送信します。

さらに、一部のファンクションキーがコンソールにマッピングされていない場合があります。

GUIの同様のビューについては、 bashのメタキーとは何ですか? を参照してください。

これは、キーボードが端末に送信したUpキーの生のキーコードを端末が表す方法です。基本的に、シェルは通常キープレスをインターセプトしますが、ログインプロンプトでそれを行うことは何もありません。入力した文字は、他の文字(または数字など)と同じようにコンソールに出力されます。

20
strugee

キーが「ターミナル」(つまり、ターミナルエミュレーターアプリケーション)によってどのように表されるかについてではありません。表示されているのは、1行上に移動するためのANSIコード( ANSIエスケープシーケンス )ですが、印刷可能な形式に変換されています。

  1. キーボードハードウェアは「スキャンコード」を送信しますが、それらは変換され、コマンドラインレベルのアプリケーションに文字として表示されます。キー A 1バイトになります。Shiftキーが押されている場合(またはShift Lockが押されている場合)A、それ以外の場合はa

  2. ANSI準拠の端末では、矢印キーは1文字を送信しません(ASCII文字セット)に矢印のコードはありません)が、3文字の「エスケープシーケンス」: escape-[-A。他の3つの矢印キーはescape-[-B, C, Dです。

  3. 同じ物理シーケンスが古い物理ANSI端末に送信(エコー)された場合、カーソルは1行上に移動します。ターミナルエミュレータを含む多くのプログラムは、これらの文字シーケンスを認識し、適切な処理を行います。ターミナルエミュレータはカーソルを上に移動します(これによりcursesライブラリがカーソルを移動します)が、bashはインターセプトします代わりに履歴をスクロールします。

  4. 画面内でカーソルを移動する必要のないプログラム内のすべての場所でカーソルが終了することを回避するために、キーボード入力でESCが印刷可能なシーケンス^[として表示されることがよくあります(エスケープはcontrol-[に対応するため)。これは実際には端末デバイスのインターフェースによって処理されます。 stty(1) を参照してください。その結果、上矢印は^[[Aとして表示されます。 catと入力してReturnキーを押し、矢印キーを押すと、コマンドラインからこれが表示されます。これは、コンソールのログイン画面にも表示されたものです。

最後に: Control、 Alt、およびあなたが言及した他のキーは文字シーケンスにマップされません。これらは、別のキープレス(上記のa/Aの例のように)によって送信された文字に影響するか、単にテキストへのマッピングがありません。このようなキー操作は、キーボードイベントをリッスンするプログラムでのみ検出できます。それらは、標準入力から読み取って見ることはできません(またはファイルに書き込むことはできません)。

5
alexis

この行動は、シェルごとに異なります。ほとんどのシェルは、readlineというライブラリを使用して、プロンプトの行を編集します。 ここ はこのライブラリの完全なコマンドリファレンスであるため、アプリケーションがreadlineを使用している場合は、このコマンドを使用して行を編集およびナビゲートできます。

垂直矢印キーは、コマンド履歴をナビゲートするためにreadlineで構成されます。また、ログインプロンプトにはコマンド履歴はありません。そのため、文字^[[Aおよび^[[Bが画面に表示されます。だから何を^[[A意味ですか?

BashのマニュアルページはPROMPTINGの下にあります:

\[     begin a sequence of non-printing characters, which could be used to embed
       a terminal control sequence into the Prompt

ANSIの矢印キーの エスケープシーケンス は次のとおりです。

  • [ValueA上カーソル(Valueは空にすることができます)

  • [ValueB下カーソル(Valueは空にすることができます)

3
chaos

TLDR

上矢印キーを押したときに生成される生のキーコードを出力するshを実行している可能性があります。

bashのようなより高度なシェルは、これらのキーコードをインターセプトして、何かを行います。例えば。履歴の最後のコマンドを表示します。

1
Snowcrash

それらは ANSIエスケープコード です。 ^[は、シェルがESCバイト(ASCIIバイト27)を表示するために使用する表記です。したがって、例はESCバイトの後にテキスト[Aが続きます。ウィキペディアの記事を見るとわかるように、^[[ESCの後に[)はControl Sequence IntroducerまたはCSI。 CSI Aは、カーソルを1列上に移動することを意味します。

端末でエスケープコードを表示するには、CTRL + Vを押してから、別のキーシーケンスを入力します。たとえば、CTRL + Vに続いて上矢印を押すと、^[[Aが表示されます。

0
yellowantphil

コマンドシェル、たとえばBashは、上向きの矢印をアクション「前のコマンドを取得する」に変換するプログラムです。コマンドシェルを実行していません。

0
Enzo