はじめに
皆さんは、MySQL を使う上でPercona Toolkit を活用されているでしょうか?
Percona Toolkit は、Percona社が開発した、MySQLの“運用”、“監視”、“分析”といった複雑な作業を簡単に実施することができるコマンドツール群です。
誰でもPercona社のサイトでダウンロードすることができます。
本記事ではその中から、Linux上のスタックトレースを表示可能な「pt-pmp」というコマンドにスポットを当てます。
今年2024/6/12 にリリースされた最新バージョンの3.6.0 にて、pt-pmp のパフォーマンスが大幅に向上し、情報取得中のサーバーへの負荷が減少する画期的なアップデートが行われました。
Percona Toolkit 3.6.0 のリリースノート より抜粋
- eu-stack support in pt-pmp that significantly improves this tool’s performance and decreases the load it causes on production servers.
このアップデートにより、pt-pmp のどこがどう使いやすくなったのか?実際使うにはどうしたらいいのか?についてご紹介していきます。
なにが変わった?pt-pmp
先ほど、「pt-pmp でLinux上のスタックトレースを表示可能」とご紹介しました。
具体的にはMySQLサーバーのハングや、MySQLにおいて想定しない動作を確認したときなどのシチュエーションで取得したトレースを発生した事象の原因分析に利用したり、サポートに提供したりします。
2011年12月に書かれたPerconaブログ記事 に、デフォルトのgdb 方式でのトレース取得の難点が3つ挙げられていました。
- The server freezes for the duration of the process. This is the most obvious impact on the running server: GDB forklifts the process and gets a stack trace from every thread, then lets it go on working. But this can take a while. It’s usually a couple of seconds, but on big servers with a lot of memory and many threads, it can take much longer (I’ve seen tens of seconds, but heard reports of minutes).
- The server can crash. I haven’t seen this myself, but I’ve heard reports from others.
- The server can be left in an unstable state. Sometimes when GDB detaches, the process’s state isn’t quite as it was before. I have rarely seen this, but the other day I had a customer experience a very slow-running server that was using tons of CPU time and lots of system CPU, and exhibiting the classic signs of InnoDB kernel_mutex contention. I was not able to find anything wrong, and was still trying to determine whether the sudden slowness was due to some cause such as an increase in traffic or just InnoDB having trouble, when the customer Skyped me to say that they’d restarted the server and it resolved the problems. This server had previously been analyzed with GDB around the time the problems began.
上記の記載を要約すると以下の3点です。
- 処理中はサーバーがフリーズする
- サーバーがクラッシュする報告が複数上がっている
- トレース取得後、まれにサーバーの不安定な状態が継続することがある
これらの懸念は、記事が書かれてから約12年たった2024年においても変わっていませんでした。
しかしこの懸念が解消されるアップデートが提供されたのです。
それが、eu-stack のサポートです。
eu-stack を使ったpt-pmp の実行には、以下の2種類があります。
これらを指定して実行することで、サーバー稼働への影響を最小限に抑えながら情報を収集できます。
オプション | 詳細 |
---|---|
-dumper eu | eu-stack 方式。gdb 方式と同じ情報が取得でき、性能はgdb の7倍。 |
-dumper pteu | pt-eustack-resolver 方式。gdb 方式と違ってソースコードの座標は取得できないが、性能はgdb の65倍。 |
gdb 方式のpt-pmp との性能比較については、Perconaブログ記事 に結果が載っていますので、興味がありましたら併せて参照ください。
どう使う?eu-stack を使ったpt-pmp
eu-stack を使ったpt-pmp を利用するには事前準備が必要です。
- まず、elfutils パッケージをサーバーにインストールします。
1# yum -y install elfutils -
次に、pt-pmp, pt-eustack-resolver のダウンロードとセットアップを行います。
最新の Percona Toolkit を RPM インストールすると特別なセットアップは不要でそのまま実行することができます。
例:Red Hat Enterprise Linux 8 の場合1# yum -y install https://downloads.percona.com/downloads/percona-toolkit/3.6.0/binary/redhat/8/x86_64/percona-toolkit-3.6.0-1.el8.x86_64.rpm
※eu-stack の利用にはpt-pmp ならびにpt-eustack-resolver のバージョンが 3.6.0 以上である必要があります。
そのためもしすでにPercona Toolkit をお使いの場合でも、ご利用のシステムの Percona Toolkit のバージョンアップが必要となる場合があります。
Percona Toolkit 全体のバージョンアップが難しい場合は、下記のように必要なコンポーネントを個別でバージョンアップします。123$ wget percona.com/get/pt-pmp$ wget percona.com/get/pt-eustack-resolver$ chmod +x ./pt-*
※pt-pmp 実行ユーザの PATH に pt-eustack-resolver が実行できるよう PATH を通しておいてください。例:/root 配下に pt-eustack-resolver を配置した場合
1export PATH=$PATH:/root
これで事前準備が整いました。
あとは、スタックトレースを取得したいタイミング(事象発生中など)に、pt-pmp コマンドを実行することで取得可能です。
例:pt-eustack-resolver 方式で取得する場合
1 |
$ pt-pmp -d pteu -p $(pgrep -x mysqld) --save-samples=samples.log > output.log |
出力イメージ:
スレッドごとに稼働状況が確認できます。
1 2 3 4 5 6 7 |
Wed Aug 7 06:47:12 GMT 2024 36 syscall(libc-2.28.so),__io_getevents_0_4(libaio.so.1.0.1),LinuxAIOHandler::collect(mysqld),LinuxAIOHandler::poll(mysqld),os_aio_handler(mysqld),fil_aio_wait(mysqld),io_handler_thread(mysqld),std::thread::_State_impl<std::thread::_Invoker<std::tuple<Detached_thread,(mysqld),execute_native_thread_routine(libstdc++.so.6.0.25),start_thread(libpthread-2.28.so),__clone(libc-2.28.so) 24 -(libpthread-2.28.so),-(libpthread-2.28.so),std::ratio<1l,(mysqld),-(mysqld),(mysqld),-(libstdc++.so.6.0.25),-(libpthread-2.28.so),-(libc-2.28.so) 18 -(libc-2.28.so),-(libaio.so.1.0.1),-(mysqld),IORequest*)(mysqld),long,(mysqld),long)(mysqld),long)(mysqld),(mysqld),-(libstdc++.so.6.0.25),-(libpthread-2.28.so),-(libc-2.28.so) 8 pthread_cond_timedwait,xpl::Cond::timed_wait(mysqld),ngs::Scheduler_dynamic::wait_if_idle_then_delete_worker(mysqld),ngs::Scheduler_dynamic::worker(mysqld),pfs_spawn_thread(mysqld),start_thread(libpthread-2.28.so),__clone(libc-2.28.so) 6 -(libpthread-2.28.so),-(mysqld),-(mysqld),(mysqld),-(libstdc++.so.6.0.25),-(libpthread-2.28.so),-(libc-2.28.so) 4 __sigtimedwait(libc-2.28.so),signal_hand(mysqld),pfs_spawn_thread(mysqld),start_thread(libpthread-2.28.so),__clone(libc-2.28.so) |
おわりに
eu-stack を使ったpt-pmp を取得できるようになったことで、これまでよりもスタックトレースの取得へのハードルが下がったように感じます。
障害発生等でサポートからスタックトレースの提供を求められた際には、ぜひこの方法を使ってみてください。