サードパーティの.NET Coreアプリケーション(VS Code拡張で使用されるバイナリ展開)を使用していますが、残念ながらアプリケーションで診断ログが有効になっていますが、これを無効にする明確な方法はありません(作成者にこれを少し報告しました)。 。無効にする以外の理想的な解決策は、特定のプログラムについて何も記録しないようにsystemdに割り当てることができますが、これを行う方法を見つけることができない場合です。これまでに試したことはすべて次のとおりです。
私が試した最初のことは、次にstdout
リダイレクトすることでした。これにより通常の出力が無効になりますが、診断ログはまだsystemdログに記録されます。stderr
/dev/null
dotnet-app > /dev/null 2>&1
アプリケーションに診断ロギングを無効にするコマンドラインパラメータがあることを願っています。これには長いパラメータがありますが、実験結果は診断ログではなく通常の出力にのみ影響するようです。
. への呼び出しを使用strace
して検索すると、connect
アプリケーションが/dev/log
。に直接診断ログを記録することを発見しました。
パスは/dev/log
へのシンボリックリンク/run/systemd/journal/dev-log
なので、結果を確認するためにシンボリックリンクを指すように変更しました/dev/null
。これにより、診断ログはsystemdログに表示されません。
誰かが私に接続しようとした後、LD_PRELOAD
標準を私のバージョンに置き換えるライブラリを作成しました。これは私のテストプログラムではうまく機能しましたが、.NET Coreアプリでは失敗しました。引数を標準関数に直接渡しても、同じエラーで失敗します。connect
/dev/log
connect ENOENT /tmp/CoreFxPipe_1ddf2df2725f40a68990c92cb4d1ff1e
connect
次に、.NET Coreアプリケーションのみを指す/dev/log
ようにLinuxネームスペースを使用して実装しました。テストプログラムでは再び動作しますが、同じエラーが原因で失敗します。ただ使用してもエラーが発生して失敗します。/dev/null
unshare --map-root-user --mount sh -c "mount --bind /dev/null /dev/log; dotnet-app $@"
unshare --map-root-user --mount dotnet-app "$@"
次に、アプリケーションの実行中にファイル記述子を閉じてみましたgdb
。/dev/log
これは機能しますが、しばらくすると再びオンになります。また、を指すようにファイル記述子を変更してみましたが、やはり動作しましたが、しばらくしてから/dev/null
。/dev/log
私の最後の試みは、.NET Coreアプリケーションで書かれたすべてをフィルタリングする独自のUNIXソケットを書くことでした。これはうまくいきますが、PIDはUNIXソケットに書き込まれたものと一緒に送信されるため、systemdログに渡されたすべてのエントリはUNIXソケットをサポートするプログラムでPIDを報告することに気づきました。
現在、このソリューションは私のシステムではほとんど使用されていないため、受け入れ可能ですが、/dev/log
より良いソリューションを歓迎します。私のような何かがUNIXソケットのルートになるようにだまされることがわかりました。しかし、これに関する追加情報が見つかりません。
または、単純なCテストプログラムが正しく実行されている間に.NET Coreアプリで失敗する理由LD_PRELOAD
と、何が失敗する可能性があるかについての洞察を持っている人がいますか?unshare
/dev/log
答え1
つまり、オーバーライドしてLD_PRELOAD
ライブラリをロードします。システムログ(3)接続する代わりに(3)。
Unix/dev/log
ソケットは syslog(3) glibc 関数によって連結され、データを書き込むために使用されます。 glibc 内の syslog(3) 実装が connect(2) を実行するため、 connect(3) オーバーライドが機能しないことがあります。システムコールライブラリ関数ではないLD_PRELOAD
フックはsyslog(3)内で呼び出しをキャプチャしません。
strace
システムコールの表示とLD_PRELOAD
オーバーライド可能なライブラリ関数(この場合はglibcの関数)の間で接続が失われました。接続(3)別のglibc関数があります接続(2)システムコールもこれらの混乱を解決するのに役立ちます。 (syslog(3)への呼び出しを表示したい場合は、代わりにusingを使用するとltrace
便利です。)
明示的に接続するのではなく、テストプログラムがsyslog(3)を直接呼び出すことで、connect(3)をオーバーライドした内容がLD_PRELOAD
syslog(3)で機能しないことを確認できます/dev/log
。これは、.NET Coreアプリケーションの実行方法と考えられます。
syslog(3) に接続する方が便利かもしれません。スタックの上位にある場合は、そのフックを使用して、選択的に転送などの決定を下すことができるためです。一部システムログに送信されたメッセージ。 (glibcを使用してsyslog関数をロードし、その関数dlsym(RTLD_NEXT, "syslog")
ポインタを使用してsyslog(3)を呼び出して、実際にフックから渡したいメッセージを取得できます。)
/dev/log
toをシンボリックリンクに置き換える方法は、connect(2)操作(open(2)などのファイル操作のみ)を許可しない/dev/null
ため、欠陥があります。/dev/null
したがって、syslog(3)は接続を試み、何らかの方法でエラーが発生します。とにかく、副作用がある可能性があるものを処理するか、呼び出し元に返します。
LD_PRELOAD
syslog(3)を使用したオーバーライドがあなたの要件を満たすことができることを願っています。