1. 概要

シェルプログラムの重要な機能は、ユーザーの以前のコマンドを履歴として保持することです。 この記事では、GNU Bashが提供する検索機能を研究し、端末とシェルの両方で使用される競合するキーシーケンス( Cs )についても学習します。

2. インクリメンタル検索

GNU Bashシェルは、Readlineライブラリを介してコマンドライン編集機能を提供します。 このライブラリには、Crにバインドされた2つの履歴検索機能reverse-history-searchforward-history-searchが含まれています。それぞれCsキーシーケンス。

これは、bashでbuiltinコマンドbindを使用して確認できます。

bind -q reverse-search-history;
# reverse-search-history can be invoked via "\C-r".
bind -q forward-search-history;
# forward-search-history can be invoked via "\C-s".

これらの検索機能を使用して、以前のコマンドをフェッチし、それを現在の行に復元できます。 また、各キャラクターの入力による即時フィードバックも備えています。 これは、インクリメンタル検索と呼ばれます。

bashでいくつかのシェル履歴データを作成し、簡単な検索エクスペリエンスを示しましょう。

unset HISTFILE # if variable HISTFILE is unset, then ~/.bash_history will not be modified.
history -c
: a;
: b;
: c;
: d;
: e;

それでは、履歴からコマンド’:e;‘を検索してみましょう。 これを行うには、キーシーケンス Cr を入力して検索機能を呼び出し、文字’e‘を入力します。

(reverse-i-search)`e': : e;

bashのインクリメンタルサーチには小さな落とし穴があります。これは履歴リストでの位置を維持し、検索が失敗した後は折り返されません。 この動作は、履歴リストの前の位置にいるときにコマンドを検索しようとしたときに観察できます。

(reverse-i-search)`d': : d;
(failed reverse-i-search)`e': : d;

:e;’を見つけるために 検索を完全に再開せずに、Csキーシーケンスを使用して関数forward-history-searchを呼び出す必要があります。 残念ながら、シェルがCを受信する前に、Cが傍受されて消費される可能性があります。

次のセクションでは、キーシーケンス Cs を使用する別のシステムについて学習しますが、今のところは、キーシーケンスCgを送信して検索を中止する必要があります。

2. ソフトウェア制御フロー(XOFF / XON)

歴史的に、CsCqは、2つのシステム間で制御コードXOFFXONを通信するために使用されていました。 端末ベースのシステム内で、これらの制御コードは、端末にデータを送信しているプロセスを一時停止するために使用されます。

シェルを開いて、CsCqを使用して、ループ本体が端末にデータを書き込むように要求するときに、ループ構造を停止/再開できることを確認しましょう。

for i in 1 2 3 4 5; do
    printf "%s\n" $i; sleep 1;
done;

幸い、キーシーケンス Csを制御コードXOFFの送信から解放し、キーシーケンスをシェルに正常に到達させることができます。 sttyユーティリティを使用して、入力設定 ixon を構成できます。これにより、 XOFF /XONフロー制御が有効になります。 ixon を無効にする前に、まず現在の設定を確認しましょう。

stty -a | grep "ixon"
# -ignbrk -brkint -ignpar -parmrk -inpck -istrip -inlcr -igncr icrnl ixon -ixoff
#                                                                    ^^^^
stty -ixon
stty -a | grep "ixon"
# -ignbrk -brkint -ignpar -parmrk -inpck -istrip -inlcr -igncr icrnl -ixon -ixoff
#                                                                    ^^^^^

キーシーケンスCsは、bashシェルのforward-search-history関数を正常に呼び出す必要があります。

(i-search)`':

ただし、これらの設定は保持されません。 新しいシェルセッションごとにそれらを構成する必要があります。 これらの設定を保持するには、シェルのスタートアップファイルにコマンド stty-ixonを含める必要があります。

3. 検索方向の切り替え

forward-search-history 関数を呼び出すと、検索は現在の位置から開始されます。これは、事実上、履歴リストの最後の位置です。 その結果、逆検索履歴機能を補完するものとしてフォワード検索履歴を使用する方が適切です。逆検索履歴機能は、検索時に検索位置を効果的に戻します

forward-search-history の一般的な使用法を示すために、コマンド履歴の新しいデータセットを作成しましょう。

unset HISTFILE # if variable HISTFILE is unset, then ~/.bash_history will not be modified.
history -c
: a; 
: b;
: x1;
: d;
: x2;
: e;

それでは、前に実行したコマンド’:x1;‘を検索してみましょう。 これを行うには、キーシーケンス Cr を入力して検索機能を呼び出し、文字’x1‘を入力します。

(reverse-i-search)`x1': : x1;

検索を続行したいが、後で実行されたコマンドを検索するとします。 キーシーケンスCsを入力して検索の方向を変更し、検索語を修正するだけです。

(i-search)`x2': : x2;

最後に、 ESCキーまたはキーシーケンスCjを送信することで、検索を終了し、検索結果を現在の行に挿入できます。

4. 結論

この記事では、GNUBashのインクリメンタルサーチメカニズムについて学習しました。 また、ターミナルライン設定 XON / OFFフロー制御を構成しました。これにより、キーシーケンスCsが事前にインターセプトされていました。