OpenWrt Forum Archive

Topic: [how to]OpenWRT kernel debugging on AR9331

The content of this topic has been archived on 25 Apr 2018. There are no obvious gaps in this topic, but there may still be some posts missing at the end.

To enable kernel debugging on openwrt, you must make sureļ¼š

1. serial port driver support poll_get_char and poll_put_char routine.
2. disabled cpu watchdog.

otherwise, you will failing in kernel debugging
1. unable to configure kgdboc
2. cpu reset when kernel debugging


Do as following

1.make kernel_menuconfig
enable kernel debugging sysrq etc

2. modify serial port driver  /build_dir/..../driver/tty/serial/ar933x_uart.c

modify struct uart_ops ar933x_uart_ops:

static struct uart_ops ar933x_uart_ops = {
    .tx_empty    = ar933x_uart_tx_empty,
    .set_mctrl    = ar933x_uart_set_mctrl,
    .get_mctrl    = ar933x_uart_get_mctrl,
    .stop_tx    = ar933x_uart_stop_tx,
    .start_tx    = ar933x_uart_start_tx,
    .stop_rx    = ar933x_uart_stop_rx,
    .enable_ms    = ar933x_uart_enable_ms,
    .break_ctl    = ar933x_uart_break_ctl,
    .startup    = ar933x_uart_startup,
    .shutdown    = ar933x_uart_shutdown,
    .set_termios    = ar933x_uart_set_termios,
    .type        = ar933x_uart_type,
    .release_port    = ar933x_uart_release_port,
    .request_port    = ar933x_uart_request_port,
    .config_port    = ar933x_uart_config_port,
    .verify_port    = ar933x_uart_verify_port,
#ifdef CONFIG_CONSOLE_POLL                                         //add this
    .poll_get_char = ar933x_uart_get_poll_char,                  //add this
    .poll_put_char = ar933x_uart_put_poll_char,                 //add this
#endif                                                                             //add this
};

3. add following code before struct ar933x_uart_ops


#ifdef CONFIG_CONSOLE_POLL
int is_shutdown_watchdog = 0;

#define RST_WATCHDOG_TIMER_CONTROL      0x18060008      //refer to AR9331 datasheet 6.6.3

void shutdown_watchdog(void)
{
    if(!is_shutdown_watchdog)
    {
        unsigned long *p = (unsigned long *)ioremap_nocache(RST_WATCHDOG_TIMER_CONTROL,8);

        if(p)
        {
            writel(0,p);        //Action = 00 (NO ACTION)
            iounmap(p);
            is_shutdown_watchdog = 1;
        }
    }
}

static int ar933x_uart_get_poll_char(struct ar933x_uart_port *up)
{
    unsigned int rdata;

    shutdown_watchdog();

    do {
        rdata = ar933x_uart_read(up, AR933X_UART_DATA_REG);
        cpu_relax();
    } while ((rdata & AR933X_UART_DATA_RX_CSR) == 0);
   
    /* remove the character from the FIFO */
    ar933x_uart_write(up, AR933X_UART_DATA_REG,AR933X_UART_DATA_RX_CSR);

    return rdata & AR933X_UART_DATA_TX_RX_MASK;
}

static void ar933x_uart_put_poll_char(struct ar933x_uart_port *up, unsigned char c)
{
    unsigned int rdata;

    do {
        rdata = ar933x_uart_read(up, AR933X_UART_DATA_REG);
        cpu_relax();
    } while ((rdata & AR933X_UART_DATA_TX_CSR) == 0);

    ar933x_uart_putc(up, c);
}
#endif




now make openwrt
and try this

echo ttyATH0 > /sys/module/kgdboc/parameters/kgdboc
echo g > /proc/sysrq-trigger

type kgdboc protocol cmd:
$g#67

you will successfully communicate with kgdbstub


try you gdb client
gdb vmlinux
set remotebaud 115200
target remote /dev/ttyUSB0


have a fun!

snapshot

(Last edited by mengxp on 25 Oct 2014, 05:58)

Good.

The discussion might have continued from here.