スクリプト内の「\033[6n」のように出力を入力(バッファ)に強制する

スクリプト内の「\033[6n」のように出力を入力(バッファ)に強制する

パイプとリダイレクトを使用して、(C プログラムまたはスクリプト) 出力を入力バッファに配置する方法を試みましたprintf "\033[6n"が、良い結果は得られませんでした。

これがどのように可能になるか知っている人はいますか:

  1. コマンドライン
  2. シェルスクリプトで
  3. Cコード

パイプ出力_cmd_ > /dev/stdinと C コードにはfprintf(stdin, "blah\n");測定可能な効果はありません。

注記:入力を別のコマンドに「パイプ」出力するのではなく、「キーボード バッファ」に文字を「注入」したいのです (いわば)。

編集:元々のユースケースは、サンドボックス化されたCLIアプリで、外部shellからsystemコマンドOS(Basなど)と対話するが、ないファイル記述子を処理します。

答え1

編集:短い答えだった /dev/uinput、今はTIOCSTI(投稿の最後を参照)


これまでの回答は以上です。コメントへの回答は次のとおりです。

ioctl_tty(2)私は持っていませんが、TIOCSTIカーネルソース(経由フリーエレクトロン) にtiocstiは、コンテキストを使用する「偽の入力文字」が表示されますtty_struct

問題のアプリケーションは常時対話的に実行されているため、パイプやリダイレクトは使用できません。shellスクリプトを実行することはできますが、他の多くの同様のアプリケーションとは異なり、結果のキャプチャは許可されておらず、通常どおりに実行することしかできませstdinん。stdout

当面の間、これを変更する可能性はありません。これは私のアプリケーションではないからです。ただし、コンテキストを使用する の&を"\033[6n"介してカーネルによってキーボード バッファーに挿入された の結果をカットすることはできました。tty_insert_flip_chartty_schedule_flipsrc/drivers/tty/tty_buffer.ctty_port

記憶が正しければ、FDファイル構造が変更される前、のみ4 つのファイル記述子があれば、これを実現できたかもしれません。現在では、/dev/stdinまたはに書き込むことはできますが/proc/self/fd/0、それらはに接続されており/dev/tty#、TTY デバイスに書き込まれたものはすべて画面に表示されます ( /dev/stdout)。カーネルは、TTY を使用する場合にファイル記述子ルートをバイパスしているようです。flip関数がそれを として参照していることに注意してください。ポート

xvkbdどのユーザーランド アプリも、これらのカーネル関数のいずれにもアクセスできません。X-Windows では、およびxdotoolまたはを使用できますxteが、このアプリは Linux (VT) コンソールで使用されています。


(ほぼ)本当の答え:

/dev/uinputユーザー権限はありませんが(ほとんどのシステムでは)、すべての引数が機能するsudoスクリプトです。printf

あるいは、キーボードイベントも機能します。すべてのユーザーがアクセスできますが、起動ごとおよびシステムごとに変わります (私の場合は通常 です/dev/input/event0が、常にではありません)。

さらに調査した結果、これらのアプローチはどちらも実用的ではないことがわかりました。特にスクリプトの場合はそうです。何をする必要があるのか​​を理解する必要があるのは、私たちが提示したいのは文章入力バッファ上で実行され、「キー押下をシミュレートする」 (上記のデバイスの動作方法) ではありません。


(最も実用的な)本当の答え:

オフサイトの質問は、2011年のstackexchangeの回答を参照しました(ここ) を使用します。PerlTIOCSTIの例をもう一度確認すると、アプリケーションが提供されていないスクリプトにも実用的である可能性があります。

perl -le 'require "sys/ioctl.ph";
      ioctl(STDIN, &TIOCSTI, $_) for split "", join " ", @ARGV
     ' `_cmds_`

ただし、画面にも表示されます。さらに何時間も調査と実験を行った結果、スクリプトまたはコマンド ラインでは次の方法が実用的であることがわかりました。

stty -echo; perl -le 'require "sys/ioctl.ph"; ioctl(STDIN, &TIOCSTI, $_) for split "", join " ", @ARGV ' `_cmds_` ;stty echo

注記:TIOCSTI取り消されたがオープンBSD6.2(2017年10月)、どうやらLinuxカーネル開発者は反対(これについては、OpenBSD ジャーナル)。

答え2

Debian Bullseyeの時点では、にconsole-tools吸収されました。kbdwritevtない含まれています。必要な場合は、この投稿の最後にある更新にソースへのリンクがあります。


writevt /dev/tty# text少なくともLinux、おそらくBSDとUnixでは、現在はconsole-toolsパッケージの一部です。ユーザーは書くVT の権限。具体的には、(編集: お使いの OS で利用可能な場合) OP に対する完全かつ正しい回答は次のとおりです。

writevt `tty` "`_cmds_`"

この質問は、StackExchangeコミュニティ全体の基本オペレーティングシステムに関する知識の深さの欠如を示しています。writevtこれは非常に古く、99%(編集:Debian Linux)システムにインストールされている基本コマンドです。2002年6月まで、Debianにはマニュアルページもメンテナーもありませんでした。それが、15年前のことですが、多くの人が知らない理由かもしれません。しかし、Kali Linux(すべて)ほとんどの場合、利用可能 コマンド最初から存在していたにもかかわらずです。


Debian では Busterwritevtはデフォルトでインストールされなくなり、一部の人によると、どのパッケージにも存在しない可能性があるとのことです (メンテナーの不足のためか、console-toolsパッケージの変更のためか?)

更新: 実際のところ、console-toolsDebian パッケージ検索 (私が最初に内容を確認した場所) では、バックポートさえも見つけられなくなりました。

元のパッケージ プロジェクトはここにあります:

http://lct.sourceforge.net/

パッチは必要ありません。Raspbian/RPiOS には、Debian ビルド (Wheezy から Buster) がここにあります:

http://raspbian.raspberrypi.org/raspbian/pool/main/c/console-tools/

ヤン・ディルソン氏の言葉:

私が現在取り組んでいる (公開) ソフトウェア プロジェクトは、1997 年からメンバーとなっている Debian GNU/Linux プロジェクトです。

http://ydirson.free.fr/en/software/

吸収を待つkbd- 2001

「Linux Console Tools」プロジェクトのパッケージは、RPiOS で引き続き利用可能です。これは、SourceForge にも存在する「Linux Console Project」プロジェクトのパッケージconsole-toolsとは異なります。linuxconsoletools

関連情報