GNU/Linux >> Belajar Linux >  >> Linux

Debug Linux menggunakan ProcDump

Apresiasi Microsoft yang semakin besar terhadap Linux dan open source bukanlah rahasia lagi. Perusahaan terus meningkatkan kontribusinya ke open source dalam beberapa tahun terakhir, termasuk mem-porting beberapa perangkat lunak dan alatnya ke Linux. Pada akhir 2018, Microsoft mengumumkan akan mem-porting beberapa alat Sysinternals ke Linux sebagai open source, dan ProcDump untuk Linux adalah rilis pertama.

Jika Anda telah bekerja di Windows dalam debugging atau pemecahan masalah, Anda mungkin pernah mendengar tentang Sysinternals. Ini adalah seperangkat alat "Pisau Tentara Swiss" yang membantu administrator sistem, pengembang, dan profesional keamanan TI memantau dan memecahkan masalah lingkungan Windows.

Lebih banyak sumber daya Linux

  • Lembar contekan perintah Linux
  • Lembar contekan perintah Linux tingkat lanjut
  • Kursus online gratis:Ikhtisar Teknis RHEL
  • Lembar contekan jaringan Linux
  • Lembar contekan SELinux
  • Lembar contekan perintah umum Linux
  • Apa itu container Linux?
  • Artikel Linux terbaru kami

Salah satu alat Sysinternals yang paling populer adalah ProcDump. Seperti namanya, ini digunakan untuk membuang memori dari proses yang sedang berjalan ke file inti pada disk. File inti ini kemudian dapat dianalisis menggunakan debugger untuk memahami status proses saat dump diambil. Setelah menggunakan Sysinternals sebelumnya, saya penasaran untuk mencoba port Linux dari ProcDump.

Memulai ProcDump untuk Linux

Untuk mencoba ProcDump untuk Linux, Anda perlu mendownload alat dan mengompilasinya. (Saya menggunakan Red Hat Enterprise Linux, meskipun instruksi ini seharusnya bekerja sama di distro Linux lainnya):

$ cat /etc/redhat-release 
Red Hat Enterprise Linux rilis 8.2 (Ootpa)
$
$ uname -r
4.18.0-193.el8.x86_64
$

Pertama, klon repositori ProcDump untuk Linux:

$ git clone https://github.com/microsoft/ProcDump-for-Linux.git
Kloning ke 'ProcDump-for-Linux'...
jarak jauh:Menghitung objek:40, selesai.
jarak jauh:Menghitung objek:100% (40/40), selesai.
jarak jauh:Mengompresi objek:100% (33/33), selesai.
jarak jauh:Total 414 (delta 14), digunakan kembali 14 (delta 6), paket digunakan kembali 374
Menerima objek:100% (414/414), 335,28 KiB | 265.00 KiB/s, selesai.
Menyelesaikan delta:100% (232/232), selesai.
$
$ cd ProcDump-for-Linux/
$
$ ls
azure-pipelines.yml  CONTRIBUTING.md  docs     INSTALL.md  Makefile    procdump.gif  src
CODE_OF_CONDUCT.md   dist             termasuk  LISENSI Selanjutnya, buat program menggunakan make . Ini mencetak antarmuka baris perintah GCC yang tepat yang diperlukan untuk mengompilasi file sumber:

$ make
rm -rf obj
rm -rf bin
rm -rf /root/ProcDump-for-Linux/pkgbuild
gcc -c -g -o obj /Logging.o src/Logging.c -Wall -I ./include -pthread -std=gnu99
gcc -c -g -o obj/Events.o src/Events.c -Wall -I ./include -pthread -std=gnu99
gcc -c -g -o obj/ProcDumpConfiguration.o src/ProcDumpConfiguration.c -Wall -I ./include -pthread -std=gnu99
gcc -c -g - o obj/Handle.o src/Handle.c -Wall -I ./include -pthread -std=gnu99
gcc -c -g -o obj/Process.o src/Process.c -Wall -I . /include -pthread -std=gnu99
gcc -c -g -o obj/Procdump.o src/Procdump.c -Wall -I ./include -pthread -std=gnu99
gcc -c - g -o obj/TriggerThreadProcs.o src/TriggerThreadProcs.c -Wall -I ./include -pthread -std=gnu99
gcc -c -g -o obj/CoreDumpWriter.o src/CoreDumpWriter.c -Wall - Saya ./include -pthread -std=gnu99
gcc -o bin/procdump obj/Logging.o obj/Events.o obj/ProcDumpConfiguration.o obj/Handle.o obj/Process.o obj/Procdump.o obj/TriggerThreadProcs.o obj/CoreDumpWriter.o -Wall -I ./include -pthread -std=gnu99
gcc -c -g -o obj/ProcDumpTestApplication.o tes/integrasi/ProcDumpTestApplication.c -Wall -I ./include -pthread -std=gnu99
gcc -o bin/ProcDumpTestApplication obj/ProcDumpTestApplication.o -Wall -I ./include -pthread -std=gnu99
$

Kompilasi membuat dua direktori baru. Pertama adalah obj/ direktori, yang menyimpan file objek yang dibuat selama kompilasi. Direktori kedua (dan yang lebih penting) adalah bin/ , di situlah procdump yang dikompilasi program disimpan. Itu juga mengkompilasi biner tes lain yang disebut ProcDumpTestApplication :

$ ls obj/
CoreDumpWriter.o  Handle.o   ProcDumpConfiguration.o  ProcDumpTestApplication.o  TriggerThreadProcs.o
Events.o          Logging.o  Procdump<.o  >$
$ ls bin/
procdump  ProcDumpTestApplication
$
$ file bin/procdump
bin/procdump:ELF 64-bit LSB executable, x86-64, versi 1 (SYSV), tertaut secara dinamis, juru bahasa /lib64/ld-linux-x86-64.so.2, untuk GNU/Linux 3.2.0, BuildID[sha1]=6e8827db64835ea0d1f0941ac3ecff9ee8c06e6b, dengan debug_info, tidak dilucuti
$
$ file bin/ProcDumpTestApplication
bin/ProcDumpTestApplication:ELF 64-bit LSB executable, x86-64, versi 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so. 2, untuk GNU/Linux 3.2.0, BuildID[sha1]=c8fd86f53c07df142e52518815b2573d1c690e4e, dengan debug_info, tidak dilucuti
$

Dengan pengaturan ini, setiap kali Anda menjalankan procdump utilitas, Anda harus pindah ke bin/ map. Untuk membuatnya tersedia dari mana saja di dalam sistem, jalankan make install . Ini menyalin biner ke bin/ biasa direktori, yang merupakan bagian dari $PATH shell shell Anda :

$ yang procdump
/usr/bin/yang:tidak ada procdump di (/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin)
$
$ make install
mkdir -p //usr/bin
cp bin/procdump //usr/bin
mkdir -p //usr/share/man/man1
cp procdump.1 //usr/share/man/man1
$
$ yang procdump
/usr/bin/procdump
$

Dengan instalasi, ProcDump menyediakan halaman manual, yang dapat Anda akses dengan man procdump :

$ man procdump
$

Jalankan ProcDump

Untuk membuang memori proses, Anda perlu memberikan ID proses (PID) ke ProcDump. Anda dapat menggunakan salah satu program atau daemon yang sedang berjalan di mesin Anda. Untuk contoh ini, saya akan menggunakan program C kecil yang berulang selamanya. Kompilasi program dan jalankan (untuk keluar dari program, tekan Ctrl +C , atau jika berjalan di latar belakang, gunakan kill perintah dengan PID):

$ cat progxyz.c 
#include

int main() {
        for (;;)
        {
printf(".");
                sleep(1);
        }
        return 0;
}
$
$ gcc progxyz.c -o progxyz
$
$ ./progxyz &
[1] 350498
$

Dengan menjalankan program, Anda dapat menemukan PID-nya menggunakan pgrep atau ps . Catat PIDnya:

$ pgrep progxyz
350498
$
$ ps -ef | grep progxyz
root      350498  345445  0 03:29 pts/1    00:00:00 ./progxyz
root      350508  347350  0 03:29 pts/0    00:00:00 grep --color=auto progxyz
$

Saat proses pengujian sedang berjalan, aktifkan procdump dan memberikan PID. Output menyatakan nama proses dan PID, melaporkan bahwa Core dump dihasilkan, dan menunjukkan nama filenya:

$ procdump -p 350498

ProcDump v1.1.1 - Utilitas dump proses Sysinternals
Hak Cipta (C) 2020 Microsoft Corporation. Seluruh hak cipta. Dilisensikan di bawah lisensi MIT.
Mark Russinovich, Mario Hewardt, John Salem, Javid Habibi
Memantau proses dan menulis file dump ketika proses melebihi
kriteria yang ditentukan.

Proses:                progxyz (350498)
Ambang CPU:          t/a
Ambang Komit:      n/a
Interval polling (md):  1000
Ambang:  10
Jumlah Dumps:        1

Tekan Ctrl-C untuk mengakhiri pemantauan tanpa menghentikan proses.

[03:30:00 - INFO]:Jangka waktu:
[03:30:01 - INFO]:Core dump 0 dihasilkan:progxyz_time_2020-06-24_03:30:00.350498
$

Daftar isi direktori saat ini, dan Anda akan melihat file inti baru. Nama file cocok dengan yang ditunjukkan oleh procdump perintah, dan tanggal, waktu, dan PID ditambahkan padanya:

$ ls -l progxyz_time_2020-06-24_03\:30\:00.350498 
-rw-r--r--. 1 root root 356848 24 Jun 03:30 progxyz_time_2020-06-24_03:30:00.350498
$
$ file progxyz_time_2020-06-24_03\:30\:00.350498
progxyz_time_2020-06-24_03:30:00.350498:File inti LSB 64-bit ELF, x86-64, versi 1 (SYSV), gaya SVR4, dari './progxyz', uid nyata:0, uid efektif:0, gid nyata:0, gid efektif :0, execfn:'./progxyz', platform:'x86_64'
$

Analisis file inti dengan GNU Project Debugger

Untuk melihat apakah Anda dapat membaca file proc, aktifkan GNU Project Debugger (gdb ). Ingatlah untuk menyediakan jalur biner pengujian sehingga Anda dapat melihat semua nama fungsi di tumpukan. Di sini, bt (backtrace) menunjukkan bahwa sleep() fungsi sedang dieksekusi ketika dump diambil:

$ gdb -q ./progxyz ./progxyz_time_2020-06-24_03\:30\:00.350498 
Membaca simbol dari ./progxyz...(tidak ditemukan simbol debug)...selesai.
[LWP baru 350498]
Core dihasilkan oleh `./progxyz'.
#0  0x00007fb6947e9208 di nanosleep () dari /lib64/libc.so.6
Debug terpisah tidak ada, gunakan:yum debuginfo-install glibc-2.28-101.el8.x86_64
(gdb) bt
#0  0x00007fb6947e9208 di nanosleep () dari /lib64/libc.so.6
#1  0x00007fb6947e913e dalam tidur () dari /lib64/libc.so.6
#2  0x00000000004005f3 di main ()
(gdb)

Bagaimana dengan gcore?

Pengguna Linux akan segera menunjukkan bahwa Linux sudah memiliki perintah yang disebut gcore , yang dikirimkan dengan sebagian besar distro Linux dan melakukan hal yang sama persis seperti ProcDump. Ini adalah argumen yang valid. Jika Anda belum pernah menggunakannya, coba yang berikut ini untuk membuang inti proses dengan gcore . Jalankan kembali program pengujian, lalu jalankan gcore , dan berikan PID sebagai argumen:

$ ./progxyz &
[1] 350664
$
$
$ pgrep progxyz
350664
$
$
$ gcore 350664
0x00007fefd3be2208 di nanosleep () dari /lib64/libc.so.6
Disimpan corefile core.350664
[Inferior 1 (proses 350664) terlepas]
$

gcore mencetak pesan yang mengatakan telah menyimpan inti ke file tertentu. Periksa direktori saat ini untuk menemukan file inti ini, dan gunakan gdb lagi untuk memuatnya:

$ 
$ ls -l  core.350664
-rw-r--r--. 1 root root 356848 24 Jun 03:34 core.350664
$
$
$ file core.350664
core.350664:ELF 64-bit file inti LSB, x86-64 , versi 1 (SYSV), gaya SVR4, dari './progxyz', uid nyata:0, uid efektif:0, gid nyata:0, gid efektif:0, execfn:'./progxyz', platform:'x86_64 '
$
$ gdb -q ./progxyz ./core.350664
Membaca simbol dari ./progxyz...(tidak ditemukan simbol debug)...selesai.
[LWP 350664 baru]
Core dihasilkan oleh `./progxyz'.
#0  0x00007fefd3be2208 di nanosleep () dari /lib64/libc.so.6
Debug terpisah tidak ada, gunakan:yum debuginfo-install glibc-2.28-101.el8.x86_64
(gdb) bt
#0  0x00007fefd3be2208 di nanosleep () dari /lib64/libc.so.6
#1  0x00007fefd3be213e dalam tidur ( ) dari /lib64/libc.so.6
#2  0x00000000004005f3 di main ()
(gdb) q
$

Untuk gcore untuk bekerja, Anda perlu memastikan pengaturan berikut sudah ada. Pertama, pastikan ulimit diatur untuk file inti; jika disetel ke 0 , file inti tidak akan dibuat. Kedua, pastikan bahwa /proc/sys/kernel/core_pattern memiliki pengaturan yang tepat untuk menentukan pola inti:

$ ulimit -c
tidak terbatas
$

Haruskah Anda menggunakan ProcDump atau gcore?

Ada beberapa kasus di mana Anda mungkin lebih suka menggunakan ProcDump daripada gcore, dan ProcDump memiliki beberapa fitur bawaan yang mungkin berguna secara umum.

Menunggu biner pengujian untuk dieksekusi

Baik Anda menggunakan ProcDump atau gcore, proses pengujian harus dijalankan dan dalam status berjalan sehingga Anda dapat menyediakan PID untuk menghasilkan file inti. Tetapi ProcDump memiliki fitur yang menunggu hingga biner tertentu berjalan; setelah menemukan biner uji berjalan yang cocok dengan nama yang diberikan, itu menghasilkan file inti untuk biner uji itu. Itu dapat diaktifkan menggunakan -w argumen dan nama program, bukan PID. Fitur ini dapat berguna dalam kasus di mana program pengujian keluar dengan cepat.

Berikut cara kerjanya. Dalam contoh ini, tidak ada proses bernama progxyz berjalan:

$ pgrep progxyz 
$

Aktifkan procdump dengan -w perintah untuk membuatnya menunggu. Dari terminal lain, aktifkan tes biner progxyz :

$ procdump -w progxyz

ProcDump v1.1.1 - Utilitas dump proses Sysinternals
Hak Cipta (C) 2020 Microsoft Corporation. Seluruh hak cipta. Dilisensikan di bawah lisensi MIT.
Mark Russinovich, Mario Hewardt, John Salem, Javid Habibi
Memantau proses dan menulis file dump ketika proses melebihi
kriteria yang ditentukan.

Proses:                progxyz (tertunda)
Ambang CPU:          t/a
Ambang Komit:      n/a
Interval polling (md):  1000
Ambang:  10
Jumlah Dumps:        1

Tekan Ctrl-C untuk mengakhiri pemantauan tanpa menghentikan proses.

[03:39:23 - INFO]:Menunggu proses 'progxyz' akan diluncurkan...

Kemudian, dari terminal lain, aktifkan biner uji progxyz

$ ./progxyz &
[1] 350951
$

ProcDump segera mendeteksi bahwa biner sedang berjalan dan membuang file inti untuk biner ini:

[03:39:23 - INFO]:Menunggu proses 'progxyz' diluncurkan...
[03:43:22 - INFO]:Ditemukan proses dengan PID 350951
[03:43:22 - INFO]:Waktu:
[03:43:23 - INFO]:Core dump 0 dihasilkan:progxyz_time_2020-06-24_03:43:22.350951
$


$ ls -l progxyz_time_2020-06-24_03\:43\:22.350951
-rw-r--r--. 1 root root 356848 24 Jun 03:43 progxyz_time_2020-06-24_03:43:22.350951
$
$ file progxyz_time_2020-06-24_03\:43\:22.350951
progxyz_time_2020-06-24_03:43:22.350951:File inti LSB 64-bit ELF, x86-64, versi 1 (SYSV), gaya SVR4, dari './progxyz', uid nyata:0, uid efektif:0, gid nyata:0, gid efektif :0, execfn:'./progxyz', platform:'x86_64'
$

Beberapa dump inti

Fitur ProcDump penting lainnya adalah Anda dapat menentukan berapa banyak file inti yang akan dihasilkan dengan menggunakan argumen baris perintah -n <count> . Kesenjangan waktu default antara dump inti adalah 10 detik, tetapi Anda dapat mengubahnya menggunakan -s <sec> argumen. Contoh ini menggunakan ProcDump untuk mengambil tiga dump inti dari biner pengujian:

$ ./progxyz &
[1] 351014
$
$ procdump -n 3 -p 351014

ProcDump v1.1.1 - Utilitas dump proses Sysinternals
Hak Cipta (C) 2020 Microsoft Corporation. Seluruh hak cipta. Dilisensikan di bawah lisensi MIT.
Mark Russinovich, Mario Hewardt, John Salem, Javid Habibi
Memantau proses dan menulis file dump ketika proses melebihi
kriteria yang ditentukan.

Proses:                progxyz (351014)
Ambang CPU:          n/a
Ambang Komit:      n/a
Interval polling (md):  1000
Ambang:10
Jumlah Dumps:        3

Tekan Ctrl-C untuk mengakhiri pemantauan tanpa menghentikan proses.

[03:45:20 - INFO]:Jangka waktu:
[03:45:21 - INFO]:Core dump 0 dihasilkan:progxyz_time_2020-06-24_03:45:20.351014
[03:45:31 - INFO]:Jangka waktu:
[03:45:32 - INFO]:Core dump 1 dihasilkan:progxyz_time_2020-06-24_03:45:31.351014
[03:45:42 - INFO]:Jangka waktu:
[03:45:44 - INFO] :Core dump 2 dihasilkan:progxyz_time_2020-06-24_03:45:42.351014
$
$ ls -l progxyz_time_2020-06-24_03\:45\:*
-rw-r--r --. 1 root root 356848 24 Jun 03:45 progxyz_time_2020-06-24_03:45:20.351014
-rw-r--r--. 1 root root 356848 24 Jun 03:45 progxyz_time_2020-06-24_03:45:31.351014
-rw-r--r--. 1 root root 356848 24 Jun 03:45 progxyz_time_2020-06-24_03:45:42.351014
$

Core dump berdasarkan penggunaan CPU dan memori

ProcDump juga memungkinkan Anda untuk memicu dump inti ketika biner atau proses pengujian mencapai ambang CPU atau memori tertentu. Halaman manual ProcDump menunjukkan argumen baris perintah untuk digunakan saat menjalankan ProcDump:

-C          Memicu pembuatan core dump saat CPU melebihi atau sama dengan nilai yang ditentukan (0 hingga 100 * nCPU)
-c          Memicu pembuatan core dump saat CPU kurang dari nilai yang ditentukan (0 hingga 100 * nCPU)
-M          Memicu pembuatan core dump saat komit memori melebihi atau sama dengan nilai yang ditentukan (MB)
-m          Memicu pembuatan core dump saat komit memori kurang dari nilai yang ditentukan (MB)
-T          Memicu saat jumlah thread melebihi atau sama dengan nilai yang ditentukan.
-F          Memicu saat jumlah deskriptor file melebihi atau sama dengan nilai yang ditentukan.
-I          Frekuensi polling dalam milidetik (default adalah 1000)

Misalnya, Anda dapat meminta ProcDump untuk membuang inti saat penggunaan CPU PID yang diberikan melebihi 70%:

procdump -C 70 -n 3 -p 351014 

Kesimpulan

ProcDump adalah tambahan yang menarik untuk daftar panjang program Windows yang di-porting ke Linux. Tidak hanya menyediakan opsi alat tambahan untuk pengguna Linux, tetapi juga dapat membuat pengguna Windows merasa lebih betah saat bekerja di Linux.


Linux
  1. Menggunakan Perintah ripgrep (rg) di Linux

  2. Kali Linux di Android menggunakan Linux Deploy

  3. Contoh penggunaan perintah dmsetup di Linux

  1. Identifikasi properti keamanan di Linux menggunakan checksec

  2. Contoh penggunaan getnstimeofday di kernel Linux

  3. Sistem antrian Linux

  1. Memecahkan masalah menggunakan sistem file proc di Linux

  2. Cara men-debug program C di Linux menggunakan gdb

  3. Linux – Bagaimana Cara Men-debug Masalah Suspend-to-ram Di Linux?