GNU/Linux >> Belajar Linux >  >> Linux

Cara men-debug program C di Linux menggunakan gdb

Terlepas dari seberapa berpengalaman Anda sebagai pembuat kode, perangkat lunak apa pun yang Anda kembangkan tidak dapat sepenuhnya bebas dari bug. Jadi, mengidentifikasi bug dan memperbaikinya adalah salah satu tugas terpenting dalam siklus pengembangan perangkat lunak. Meskipun ada banyak cara untuk mengidentifikasi bug (pengujian, peninjauan kode sendiri, dan lainnya), ada perangkat lunak khusus - yang dijuluki debugger - yang membantu Anda memahami dengan tepat di mana masalahnya, sehingga Anda dapat memperbaikinya dengan mudah.

Jika Anda seorang programmer C/C++ atau mengembangkan perangkat lunak menggunakan bahasa pemrograman Fortran dan Modula-2, Anda akan senang mengetahui bahwa ada debugger yang sangat baik - dijuluki GDB - yang memungkinkan Anda dengan mudah men-debug kode untuk bug dan masalah lainnya. Dalam artikel ini, kita akan membahas dasar-dasar GDB, termasuk beberapa fitur/opsi berguna yang disediakannya.

Namun sebelum kita melanjutkan, perlu disebutkan bahwa semua petunjuk serta contoh yang disajikan dalam artikel ini telah diuji di Ubuntu 14.04LTS. Contoh kode yang digunakan dalam tutorial ditulis dalam bahasa C; shell baris perintah yang kami gunakan adalah bash (versi  4.3.11); dan versi GDB yang kami gunakan adalah 7.7.1.

Dasar-dasar debugger GDB

Dalam istilah awam, GDB memungkinkan Anda mengintip ke dalam program saat program dijalankan, sesuatu yang memungkinkan Anda membantu mengidentifikasi di mana sebenarnya masalahnya. Kami akan membahas penggunaan debugger GDB melalui contoh kerja di bagian berikutnya, tetapi sebelum itu, di sini, kami akan membahas beberapa poin dasar yang akan membantu Anda nanti.

Pertama, agar berhasil menggunakan debugger seperti GDB, Anda harus mengkompilasi program Anda sedemikian rupa sehingga kompiler juga menghasilkan informasi debug yang diperlukan oleh debugger. Misalnya, dalam hal kompiler gcc, yang akan kita gunakan untuk mengkompilasi contoh program C nanti pada tutorial ini, Anda perlu menggunakan -g opsi baris perintah saat mengkompilasi kode Anda.

Untuk mengetahui apa yang dikatakan halaman manual kompiler gcc tentang opsi baris perintah ini, buka di sini.

Langkah selanjutnya adalah memastikan bahwa Anda telah menginstal GDB di sistem Anda. Jika bukan itu masalahnya, dan Anda menggunakan sistem berbasis Debian seperti Ubuntu, Anda dapat dengan mudah menginstal alat ini menggunakan perintah berikut:

sudo apt-get install gdb

Untuk instalasi di distro lain, buka di sini.

Sekarang, setelah Anda mengkompilasi program Anda sedemikian rupa sehingga siap untuk debug, dan GDB ada di sistem Anda, Anda dapat menjalankan program Anda dalam mode debug menggunakan perintah berikut:

gdb [prog-executable-name]

Meskipun ini akan memulai debugger GDB, program Anda yang dapat dieksekusi tidak akan diluncurkan pada saat ini. Ini adalah waktu di mana Anda dapat menentukan pengaturan terkait debugging Anda. Misalnya, Anda dapat menentukan titik henti sementara yang memberi tahu GDB untuk menjeda eksekusi program pada nomor baris atau fungsi tertentu.

Selanjutnya, untuk benar-benar meluncurkan program Anda, Anda harus menjalankan perintah gdb berikut:

run

Perlu disebutkan di sini bahwa jika program Anda memerlukan beberapa argumen baris perintah untuk diteruskan, Anda dapat menentukannya di sini. Misalnya:

run [arguments]

GDB menyediakan banyak perintah berguna yang berguna saat debugging. Kami akan membahas beberapa di antaranya dalam contoh di bagian berikutnya.

Contoh penggunaan GDB

Sekarang kita memiliki ide dasar tentang GDB serta penggunaannya. Jadi mari kita ambil contoh dan terapkan ilmu di sana. Berikut contoh kodenya:

#include <stdio.h>

int main()
{
int out = 0, tot = 0, cnt = 0;
int val[] = {5, 54, 76, 91, 35, 27, 45, 15, 99, 0};

while(cnt < 10)
{
out = val[cnt];
tot = tot + 0xffffffff/out;
cnt++;
}

printf("\n Total = [%d]\n", tot);
return 0;
}

Jadi pada dasarnya, apa yang dilakukan kode ini adalah, ia mengambil setiap nilai yang terkandung dalam larik 'val', menetapkannya ke bilangan bulat 'keluar', lalu menghitung 'tot' dengan menjumlahkan nilai variabel sebelumnya dan hasil dari '0xffffffff/ keluar.'

Masalahnya di sini adalah ketika kode dijalankan, menghasilkan kesalahan berikut:

$ ./gdb-test 
Floating point exception (core dumped)

Jadi, untuk men-debug kode, langkah pertama adalah mengkompilasi program dengan -g. Berikut perintahnya:

gcc -g -Wall gdb-test.c -o gdb-test

Selanjutnya, jalankan GDB dan beri tahu executable mana yang ingin kita debug. Berikut perintah untuk itu:

gdb ./gdb-test 

Sekarang, kesalahan yang saya dapatkan adalah 'pengecualian floating point,' dan seperti yang mungkin sudah Anda ketahui, itu disebabkan oleh n % x, ketika x adalah 0. Jadi, dengan mengingat hal itu, saya meletakkan break point di nomor baris 11, di mana pembagian berlangsung. Ini dilakukan dengan cara berikut:

(gdb) break 11

Perhatikan bahwa '(gdb)' adalah perintah debugger, saya baru saja menulis perintah 'break'.

Sekarang, saya meminta GDB untuk memulai eksekusi program:

run

Jadi, ketika breakpoint terkena untuk pertama kalinya, inilah yang ditunjukkan GDB pada output:

Breakpoint 1, main () at gdb-test.c:11
11 tot = tot + 0xffffffff/out;
(gdb)

Seperti yang Anda lihat pada output di atas, debugger menunjukkan garis di mana breakpoint diletakkan. Sekarang, mari kita cetak nilai 'keluar' saat ini. Ini dapat dilakukan dengan cara berikut:

(gdb) print out
$1 = 5
(gdb)

Seperti yang Anda lihat, nilai '5' telah dicetak. Jadi, semuanya baik-baik saja saat ini. Saya meminta debugger untuk melanjutkan eksekusi program hingga breakpoint berikutnya, sesuatu yang dapat dilakukan dengan menggunakan perintah 'c'.

c  

Saya terus melakukan pekerjaan ini, sampai saya melihat bahwa nilai 'keluar' adalah nol.

...
...
...
Breakpoint 1, main () at gdb-test.c:11
11 tot = tot + 0xffffffff/out;
(gdb) print out
$2 = 99
(gdb) c
Continuing.

Breakpoint 1, main () at gdb-test.c:11
11 tot = tot + 0xffffffff/out;
(gdb) print out
$3 = 0
(gdb)

Sekarang, untuk mengonfirmasi bahwa ini adalah masalah yang sebenarnya, saya menggunakan perintah 's' (atau 'langkah') GDB kali ini alih-alih 'c'. Alasannya, saya hanya ingin baris 11, di mana eksekusi program saat ini dihentikan sementara, untuk dieksekusi, dan melihat apakah crash terjadi pada titik ini.

Inilah yang terjadi:

(gdb) s

Program received signal SIGFPE, Arithmetic exception.
0x080484aa in main () at gdb-test.c:11
11 tot = tot + 0xffffffff/out;

Ya, seperti yang dikonfirmasi oleh output yang disorot di atas, di sinilah pengecualian dilemparkan. Konfirmasi terakhir datang ketika saya mencoba menjalankan perintah 's' sekali lagi:

(gdb) s 

Program terminated with signal SIGFPE, Arithmetic exception.
The program no longer exists.

Jadi dengan cara ini, Anda dapat men-debug program Anda menggunakan GDB.

Kesimpulan

Kami baru saja menggores permukaan di sini, karena GDB menawarkan banyak fitur untuk dijelajahi dan digunakan pengguna. Buka halaman manual GDB untuk mengetahui lebih banyak tentang alat ini, dan coba gunakan setiap kali Anda men-debug sesuatu dalam kode Anda. Debugger memiliki sedikit kurva pembelajaran yang terkait dengannya, tetapi ini sepadan dengan kerja kerasnya.


Linux
  1. Cara membuat Pengguna Linux Menggunakan Ansible

  2. Cara Reboot Linux Menggunakan Command Line

  3. Bagaimana cara mematikan proses di Linux menggunakan perintah?

  1. Debug Linux menggunakan ProcDump

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

  3. Cara Debug Program C menggunakan gdb dalam 6 Langkah Sederhana

  1. Cara Memperpanjang Ruang Swap menggunakan file Swap di Linux

  2. Cara Mengotomatiskan tugas di Linux menggunakan Crontab

  3. Bagaimana cara men-debug kernel Linux dengan GDB dan QEMU?