Device Tree Debugging

DTB-DTS conversion (Linux kernel)

  • Convert DTS file to DTB
  • ./scripts/dtc/dtc -I dts -O dtb -o .dtb .dts
  • Convert DTB file to DTS

  • ./scripts/dtc/dtc -I dtb -O dts -o .dts .dtb

 U-boot FDT commands

  • print fdt address
  • print $fdt_addr_r (or $fdt_addr)
  • Set FDT node property
  • fdt addr $fdt_addr
    fdt set /testnode testprop testvalue
  • remove FDT node property
  • fdt addr $fdt_addr
    fdt rm /testnode testprop
  • Remove DT node
  • fdt rm /testnode
  • List FDT nodes
  • fdt list                         /* All nodes */
    fdt list /cpus                   /* All nodes under cups node */
  • Create node
  • fdt mknode / testnode


How to check Memory Leak in linux kernel

  • Compile kernel with
  • Mount debugfs (if it is not mounted)
    mount -t debugfs nodev /sys/kernel/debug/
  • Check memory leaks
    # echo scan > /sys/kernel/debug/kmemleak
    # cat /sys/kernel/debug/kmemleak

Example Trace:

unreferenced object 0xffff88021481d600 (size 16):
comm “swapper/0”, pid 1, jiffies 4294667622 (age 9531.310s)
hex dump (first 16 bytes):
70 6e 70 20 30 30 3a 30 31 00 38 81 ff ff ff ff pnp 00:01.8…..
[<ffffffff811619cf>] create_object+0xff/0x2a0
[<ffffffff8189ba63>] kmemleak_alloc+0x23/0x40
[<ffffffff8115bf37>] kmem_cache_alloc_trace+0xb7/0x160
[<ffffffff81395fe9>] reserve_range+0x59/0xf0
[<ffffffff81396102>] system_pnp_probe+0x82/0x90
[<ffffffff81392447>] pnp_device_probe+0x67/0xd0
[<ffffffff814c2a7f>] driver_probe_device+0x13f/0x2a0
[<ffffffff814c2ea5>] __device_attach_driver+0x85/0xa0
[<ffffffff814c0fa7>] bus_for_each_drv+0x57/0x90
[<ffffffff814c28d0>] __device_attach+0xb0/0xf0
[<ffffffff814c2ece>] device_initial_probe+0xe/0x10
[<ffffffff814c1f85>] bus_probe_device+0x95/0xa0
[<ffffffff814c00ce>] device_add+0x36e/0x570
[<ffffffff814c0469>] device_register+0x19/0x20
[<ffffffff813913d6>] __pnp_add_device+0x96/0xe0
[<ffffffff8139145b>] pnp_add_device+0x3b/0x100

How to Change Linux Kernel dmesg buffer size

Printk is implemented by using a ring buffer in the kernel with a size of __LOG_BUF_LEN bytes where __LOG_BUF_LEN equals (1 << CONFIG_LOG_BUF_SHIFT).

dmesg buffer size can be changed using “CONFIG_LOG_BUF_SHIFT” Kconfig.

As per kernel source (4.1.0), default value of this config is 17 (i.e. 1 << 17 = 128KB). The range for this config is 12 to 21.

Addign  below line in defconfig sets

Note: If invalid value (out of range value) is set, default value is taken.

CONFIG_LOG_BUF_SHIFT can be changed from menuconfig or from defconfig as below:


Device Tree

An useful way to debug device tree is to set CONFIG_PROC_DEVICETREE kernel config in defconfig file. This will show device tree information in /proc file system.

After building kernel with CONFIG_PROC_DEVICETREE Kconfig set, boot the kernel with new boot.img and check below proc entry:

# cat /proc/device-tree

Kernel Dynamic Debugging Control

Dynamic debug is designed to allow you to dynamically enable/disable kernel code to obtain additional kernel information.  Currently, if CONFIG_DYNAMIC_DEBUG is set, then all pr_debug()/dev_dbg() and print_hex_dump_debug()/print_hex_dump_bytes() calls can be dynamically enabled per-callsite.

The behaviour of pr_debug()/dev_dbg()s are controlled via writing to a control file in the ‘debugfs’ filesystem. Thus, you must first mount the debugfs filesystem, in order to make use of this feature.

    • Mount debug fs (one time only)
      # mount -t debugfs debugfs /sys/kernel/debug
    • Enable Debug from a file
      # echo -n ‘file slim-msm-ngd.c +p’ > /sys/kernel/debug/dynamic_debug/control
    • Enable debug from a line
      # echo ‘file svcsock.c line 1603 +p’ > /sys/kernel/debug/dynamic_debug/control
    • Disable debug from a file
      # echo -n ‘file slim-msm-ngd.c -p’ > /sys/kernel/debug/dynamic_debug/control

original document can be found in kernel source tree:Documentation/dynamic-debug-howto.txt