
私は現在、高校のプロジェクトで RSA キーを研究し、理論的かつ実践的に理解を深めています。プロジェクトの一部は実験で構成されており、異なる長さの RSA キーを生成するときに CPU の作業負荷がどの程度になるかをテストして確認することにしました。また、結論を出す必要がある場合に備えて、時間をデータ ポイントとして保存したいと考えています。
マシンは Ubuntu 16.04 を実行しており、アプリケーションはデフォルトのリポジトリからダウンロードされます。
計画では、GnuPG を使用して異なる長さ (1024、2048、4096) の RSA キーを生成し、GNU Time を使用して CPU のワークロードとプロセスの実行時間を取得します。プロセスは Python スクリプトで自動化され、次のようになります。
長さが[1024, 2048, 4096]の場合:
1.1. X 回の場合:
1.1.1. Gnu PGコマンドを実行してシステムリソースを監視する
1.1.2. システムリソースの使用状況をファイルに書き込む
その後、私の仮説が正しいかどうかを確認するためにいくつかのグラフをプロットします。
しかし、GnuPG テストの実装に関していくつか質問がありました。実装方法については質問の後に説明します。質問は次のとおりです。
- この設定は私がやりたいことを実現するのでしょうか?
- 失効証明書の自動作成を無効にすることはできますか?
- 一部のキーの生成に時間がかかるのはなぜですか?
- GnuPG はなぜ、キーの作成にユーザー空間で 0 CPU 秒かかったという答えを返すのでしょうか? 別のプロセスで実行されるのですか?
- キーの作成に 1 秒未満 (ウォールクロック > 1) しかかからなかったのに、CPU ワークロード パラメータに値 (0 < CPU) のみが表示されるのはなぜですか?
マニュアルを読むと、キーを生成する最も簡単な方法は--batch
オプションをオンにすることのようです。私は、次の指示に従ってファイルでオプションを設定しました。
# Text syntax in this file
#%dry-run
%echo Generating RSA key...
# Don't ask after passphrase
%no-protection
Key-type: RSA
Key-Length: 1024
Name-Real: Real Name
Name-Email: [email protected]
Expire-Date: 0
# Generate RSA key
%commit
%echo Done!
このファイルを実行するコマンドには、Gnu Time 部分と GnuPG 部分の 2 つの部分があります。GNU Time コマンドは次のようになります。
$ time --format="Wall clock: %e[s], CPU (userspace): %U[s], CPU (workload): %P%"
GnuPG コマンドは次のとおりです。
$ gpg2 --gen-key --homedir=./rsa-keys --batch [filename]
私のシェル (重要な場合は fish シェル) で実行するコマンドは次のとおりです (GNU Time + GnuPG)。
$ time --format="Wall clock: %e[s], CPU (userspace): %U[s], CPU (workload): %P%" gpg2 --gen-key --homedir=./rsa-keys --batch [filename]
コマンドからの出力:
Wall clock: 36.83[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 0.04[s], CPU (userspace): 0.00[s], CPU (workload): 8%
Wall clock: 4.76[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 72.39[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 57.52[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 84.71[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 63.32[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 51.10[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 47.58[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 64.72[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 0.05[s], CPU (userspace): 0.00[s], CPU (workload): 6%
Wall clock: 0.03[s], CPU (userspace): 0.00[s], CPU (workload): 11%
Wall clock: 29.62[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 55.02[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 36.08[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 42.92[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 40.41[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 204.36[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 246.42[s], CPU (userspace): 0.00[s], CPU (workload): 0%
Wall clock: 51.50[s], CPU (userspace): 0.00[s], CPU (workload): 0%
答え1
GnuPGは から読み取りますが/dev/random
、十分なエントロピーがない場合にはブロックされます(これは議論の余地のある行動である)。実際の計算量はごくわずかです。また、エントロピー プールがまだ「新しいビット」で満たされているため、最初の実行や数回の実行はより速く終了することがわかるかもしれません。GnuPG がwatch cat /proc/sys/kernel/random/entropy_avail
「低エントロピー」モードで実行されるタイミングを理解するために、追加のターミナルで実行することをお勧めします。
現在のハードウェア プラットフォームでは、IO によってブロックされたプロセスやスリープ状態のプロセスはバックグラウンドに置かれるため、CPU 時間は考慮されません。
$ time --format='Wall clock: %e[s], CPU (userspace): %U[s], CPU (workload): %P%' sleep 5
Wall clock: 5.00[s], CPU (userspace): 0.00[s], CPU (workload): 0%
これは、次のバイトをコピーするときにも表示されます/dev/random
(特に仮想マシンでは、かなり時間がかかる場合があります)。
time --format='Wall clock: %e[s], CPU (userspace): %U[s], CPU (workload): %P%' dd if=/dev/random of=/dev/null bs=1 count=512
512+0 records in
512+0 records out
512 bytes copied, 210.672 s, 0.0 kB/s
Wall clock: 210.67[s], CPU (userspace): 0.00[s], CPU (workload): 0%
最後に、これは高速反復の CPU ワークロードがはるかに高くなる理由も説明しています。プロセスが IO 待機でブロックされる時間が非常に短いため、全体の実行時間に対する実際の計算時間の割合が非常に大きくなります。