| | 363 | \section{Debugging Kernelspace} |
|---|
| | 364 | |
|---|
| | 365 | To debug problems with kernel or modules, basically some debugger has to be |
|---|
| | 366 | enabled inside the kernel itself. There is more than only one implementation |
|---|
| | 367 | for doing the job, but FreeWRT sticks to the subsystem already being included |
|---|
| | 368 | into the vanilla kernel, namely \app{KGDB}. |
|---|
| | 369 | |
|---|
| | 370 | To be able to control the debugger on headless machines, some sort of |
|---|
| | 371 | client/server approach like with \app{gdbserver} has to be used. Luckily, our |
|---|
| | 372 | cross compiled \app{gdb} serves fine for this task. But unlike \app{gdbserver}, |
|---|
| | 373 | \app{KGDB} communicates via a serial port. As serial port access at the very |
|---|
| | 374 | early state \app{KGDB} starts using it (i.e. right after kernel execution |
|---|
| | 375 | starts) is very hardware--dependant, a few hardware--specific functions have to be |
|---|
| | 376 | provided for each supported device. At the time of this writing, only |
|---|
| | 377 | \code{rb-2.6} includes support for \app{KGDB}. |
|---|
| | 378 | |
|---|
| | 379 | First enable \code{FWRT\_DEBUG\_KGDB} in the ADK's config, then build the |
|---|
| | 380 | complete system. Besides enabling support for \app{KGDB} itself, this option |
|---|
| | 381 | causes the kernel and all modules to be built with debugging symbols included. |
|---|
| | 382 | |
|---|
| | 383 | \strong{BEWARE:} the generated kernel and modules are really huge in size, much |
|---|
| | 384 | too big to fit into any flash space (kernel around 20MB). So better build for |
|---|
| | 385 | use with nfsroot or compactflash disk. |
|---|
| | 386 | |
|---|
| | 387 | When booting the debug kernel, an attached serial terminal shows: |
|---|
| | 388 | \begin{Verbatim}[label=kernel with KGDB starting] |
|---|
| | 389 | GDB console initialized |
|---|
| | 390 | + |
|---|
| | 391 | \end{Verbatim} |
|---|
| | 392 | first line is actually some hard--coded string inside debug console |
|---|
| | 393 | initialisation, so the only magic part is the \code{+} sign at the end. In |
|---|
| | 394 | \app{KGDB} protocol language this means "successful transfer", and is used here |
|---|
| | 395 | to start communication. |
|---|
| | 396 | |
|---|
| | 397 | Exit your terminal emulation and start the debugger: |
|---|
| | 398 | \begin{Verbatim}[label=gdb initialisation] |
|---|
| | 399 | $ cd build_mipsel/linux |
|---|
| | 400 | $ mipsel-linux-gdb vmlinux |
|---|
| | 401 | GNU gdb 6.3 |
|---|
| | 402 | Copyright 2004 Free Software Foundation, Inc. |
|---|
| | 403 | GDB is free software, covered by the GNU General Public License, and you are |
|---|
| | 404 | welcome to change it and/or distribute copies of it under certain conditions. |
|---|
| | 405 | Type "show copying" to see the conditions. |
|---|
| | 406 | There is absolutely no warranty for GDB. Type "show warranty" for details. |
|---|
| | 407 | This GDB was configured as "--host=i686-pc-linux-gnu |
|---|
| | 408 | --target=mipsel-linux-uclibc"... |
|---|
| | 409 | (gdb) set remotebaud 115200 |
|---|
| | 410 | (gdb) target remote /dev/ttyUSB0 |
|---|
| | 411 | 0xffffffff8010dfcc in breakinst () at arch/mips/kernel/gdb-stub.c:1066 |
|---|
| | 412 | 1066 __asm__ __volatile__( |
|---|
| | 413 | warning: shared library handler failed to enable breakpoint |
|---|
| | 414 | (gdb) |
|---|
| | 415 | \end{Verbatim} |
|---|
| | 416 | Changing the directory into the kernel source's root is necessary as \app{gdb} |
|---|
| | 417 | automatically searches the current working directory for source files |
|---|
| | 418 | referenced by the debugging symbols inside the kernel. |
|---|
| | 419 | Alternatively/additionally you can specify search paths using the |
|---|
| | 420 | \code{directory} directive, e.g.: |
|---|
| | 421 | \begin{Verbatim}[label=specifying a search path in gdb] |
|---|
| | 422 | (gdb) directory ../../w-madwifi-0.9.3.1-4/madwifi-0.9.3.1/ |
|---|
| | 423 | Source directories searched: |
|---|
| | 424 | /var/tmp/portage/build_mipsel/linux-2.6-rb/linux-2.6.19.1/../../w-madwifi-0.9.3.1-4 |
|---|
| | 425 | /madwifi-0.9.3.1:$cdir:$cwd |
|---|
| | 426 | (gdb) |
|---|
| | 427 | \end{Verbatim} |
|---|
| | 428 | |
|---|
| | 429 | Specifying the correct tty with \code{target remote} triggers the start of |
|---|
| | 430 | communication with \app{KGDB}. To make life happy, right after communication |
|---|
| | 431 | has started, the kernel triggers a break itself, so you have time to specify |
|---|
| | 432 | other options before continuing. |
|---|
| | 433 | |
|---|
| | 434 | Finally hit \code{c} for \code{continue} and watch the kernel booting. (The gdb |
|---|
| | 435 | console registered inside the kernel is being enabled for use as a regular |
|---|
| | 436 | output device, and kernel log messages output is being redirected via the |
|---|
| | 437 | \code{console=gdb} kernel parameter. |
|---|
| | 438 | |
|---|
| | 439 | To be able to debug kernel modules, you need to specify a path to the object |
|---|
| | 440 | files being debugged: |
|---|
| | 441 | \begin{Verbatim}[label=setting solib-search-path] |
|---|
| | 442 | (gdb) set solib-search-path /tmp/t/lib/modules/2.6.19.1/ |
|---|
| | 443 | (gdb) |
|---|
| | 444 | \end{Verbatim} |
|---|
| | 445 | \app{gdb} should recognise loading of a module on the test machine and load the |
|---|
| | 446 | corresponding object file itself. |
|---|
| | 447 | |
|---|
| | 448 | While \app{gdb} is running, the serial console is unusable for I/O. This means |
|---|
| | 449 | if kernel bugs somehow have to be triggered interactively, it is handy to have |
|---|
| | 450 | networking being configured so you can log in via \app{SSH} in parallel. Though |
|---|
| | 451 | after exiting from \app{gdb} (hit \code{ctrl-c} twice), you can reattach your |
|---|
| | 452 | terminal emulator to the serial port and continue using the serial console as |
|---|
| | 453 | usual. |
|---|
| | 454 | |
|---|
| | 455 | From now on, you can use \app{gdb} like when debugging any other application. |
|---|
| | 456 | |
|---|