Re: New kernel newbie column is up

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi Matthias,

On Tue, 2009-08-18 at 11:04 +0200, Matthias Kaehlcke wrote:
> hi,
> 
> El Wed, Aug 12, 2009 at 04:25:50AM +1000 Microbit_Ubuntu ha dit:
> 
> > On Tue, 2009-08-11 at 13:03 -0400, Robert P. J. Day wrote:
> > > Kernel and module debugging with gdb:  http://cli.gs/LHaA4a.
> > 
> > The article is quite interesting, however it seems hard to scratch
> > together relevant (should read : not outdated thus wrong) on debugging
> > kernel modules on a *remote* target..
> > 
> > I've been scouring away for yonks here and I don't seem to be getting
> > anywhere in a hurry :-(
> > I've recompiled my target's kernel with remote KGDB enabled, (sysfs et
> > al for possible manual configuration), full debug on the kernel - just
> > in case - but trying to pass kernel command argument using kgdbwait
> > (preceded with kgdboc=ttyS0,115200 eg. or kgdbcon etc) doesn't seem to
> > get the booting to halt and wait for the gdbmod debugger....
> > (I've also tried the sysrq-g break and consorts, no avail either).
> > 
> > I've had a close look at the kernel/kgdb.c source - added some extra
> > temp debug messages to try to track code flow and it seems I'm not even
> > entering these funcs.
> > 
> > Is there anyone here that can shed some more light on this black magic
> > cursed trick ? I'm using gdbmod-2.4 btw.
> > 
> > So, basically : I'm continuing trying to find out if there is a way to
> > step through kernel module code invoked on a remote (ARM) target by
> > insmod/modprobe. (gdbmod 2.4 claims it automatically picks up when
> > module is inserted, but at this stage the kernel just happily boots up
> > and chugs away, ignoring the wait for remote debugger...?.)
> > 
> > kgdb's URL has docs (kgdb_docu_full-2.4) but - as per usual - they're
> > either just plain wrong (eg. the syntax doesn't comply whatsoever with
> > the Documentation -> Docbook kgdb explained syntax) or others don't seem
> > to correlate with one another. It seems almost like a 'brute force' test
> > of all permutations of these various "solutions" is perhaps soon the
> > only way to remain sane.. :-)
> > 
> > Googling other resources seems to just bring up unanswered posts on
> > forums here and there where people seem to be just as confused as I
> > am :-)
> > 
> > In short, if anyone drops around here and has done this before (kernel =
> > 2.6.29.4, using built in remote kgdb), I would love to hear from them to
> > see if perhaps they've got a suggestion.
> > I don't mind doing the hard work to learn it properly - but it's always
> > more enjoyable when one is actually working towards something fruitful
> > in the end... !
> 
> some time ago i had a similar (the same?) problem, trying to debug an
> ARM device using kgdb. in my case the problem was that the serial port
> driver (AMBA PL010) lacked the poll_get_char() and poll_put_char()
> operations, which seem to be necessary for debugging over console.
> 
> if you happen to use a device with AMBA PL010 try again after applying
> the patch below. otherwise you might want to check if the driver of
> your serial port implements the poll functions
> 
> diff --git a/drivers/serial/amba-pl010.c b/drivers/serial/amba-pl010.c
> index 58a4879..4b27537 100644
> --- a/drivers/serial/amba-pl010.c
> +++ b/drivers/serial/amba-pl010.c
> @@ -308,6 +308,32 @@ static void pl010_break_ctl(struct uart_port *port, int break_state)
>  	spin_unlock_irqrestore(&uap->port.lock, flags);
>  }
>  
> +#ifdef CONFIG_CONSOLE_POLL
> +static int pl010_get_poll_char(struct uart_port *port)
> +{
> +	struct uart_amba_port *uap = (struct uart_amba_port *)port;
> +	unsigned int status;
> +
> +	do {
> +		status = readb(uap->port.membase + UART01x_FR);
> +	} while (!UART_RX_DATA(status))
> +
> +	return readb(uap->port.membase + UART01x_DR);
> +}
> +
> +static void pl010_put_poll_char(struct uart_port *port,
> +				unsigned char ch)
> +{
> +	struct uart_amba_port *uap = (struct uart_amba_port *)port;
> +
> +	while (!UART_TX_READY(readb(uap->port.membase + UART01x_FR)))
> +		barrier();
> +
> +	writeb(ch, uap->port.membase + UART01x_DR);
> +}
> +
> +#endif /* CONFIG_CONSOLE_POLL */
> +
>  static int pl010_startup(struct uart_port *port)
>  {
>  	struct uart_amba_port *uap = (struct uart_amba_port *)port;
> @@ -536,6 +562,10 @@ static struct uart_ops amba_pl010_pops = {
>  	.request_port	= pl010_request_port,
>  	.config_port	= pl010_config_port,
>  	.verify_port	= pl010_verify_port,
> +#ifdef CONFIG_CONSOLE_POLL
> +	.poll_get_char = pl010_get_poll_char,
> +	.poll_put_char = pl010_put_poll_char,
> +#endif
>  };
>  
>  static struct uart_amba_port *amba_ports[UART_NR];
> 

After a bit of a study of the patch above (and also tty_io.c et al
files), I expanded my own file, which is atmel_serial.c as mentioned.
(PS : I noticed there is a amba-pl011.c file in 2.6.29 kernel..)

So I added this :

#ifdef CONFIG_CONSOLE_POLL
static int atmel_get_poll_char(struct uart_port *port)
{
	unsigned int status;

	do {	
		status = UART_GET_CSR(port);
		} while (!(status & ATMEL_US_RXRDY));

	return UART_GET_CHAR(port);
}

static void atmel_put_poll_char(struct uart_port *port,
			 unsigned char ch)
{
	while (!(UART_GET_CSR(port) & ATMEL_US_TXRDY))
		barrier();

	UART_PUT_CHAR(port, ch);
}

#endif /* CONFIG_CONSOLE_POLL */


and the callbacks :

static struct uart_ops atmel_pops = {
	.tx_empty	= atmel_tx_empty,
	.set_mctrl	= atmel_set_mctrl,
	.get_mctrl	= atmel_get_mctrl,
	.stop_tx	= atmel_stop_tx,
	.start_tx	= atmel_start_tx,
	.stop_rx	= atmel_stop_rx,
	.enable_ms	= atmel_enable_ms,
	.break_ctl	= atmel_break_ctl,
	.startup	= atmel_startup,
	.shutdown	= atmel_shutdown,
	.flush_buffer	= atmel_flush_buffer,
	.set_termios	= atmel_set_termios,
	.type		= atmel_type,
	.release_port	= atmel_release_port,
	.request_port	= atmel_request_port,
	.config_port	= atmel_config_port,
	.verify_port	= atmel_verify_port,
	.pm		= atmel_serial_pm,
#ifdef CONFIG_CONSOLE_POLL
  .poll_get_char = atmel_get_poll_char,
  .poll_put_char = atmel_put_poll_char,
#endif


Well, at least I get the kgdb prompt now !!!! :
(and gdbmod gets the booting to continue)

atmel_usart.0: ttyS0 at MMIO 0xfefff200 (irq = 1) is a ATMEL_SERIAL
atmel_usart.1: ttyS1 at MMIO 0xfffb0000 (irq = 6) is a ATMEL_SERIAL
atmel_usart.2: ttyS2 at MMIO 0xfffb4000 (irq = 7) is a ATMEL_SERIAL
kgdb: Registered I/O driver kgdboc.
kgdb: Waiting for connection from remote gdb...


Big SIGH.... :-)

Well, now it's off to figure a way to massage gdbmod-2.4 into the
Eclipse Galileo (debug) GUI....

If anyone's interested, let me know and I'll keep you posted.

Again, many thanks !! No wonder I kept trying till the proverbial cows
come home.... I did have the impression it was to do with polling
callbacks, but somehow didn't see the light.....


-- 
Best regards,
Kris



--
To unsubscribe from this list: send an email with
"unsubscribe kernelnewbies" to ecartis@xxxxxxxxxxxx
Please read the FAQ at http://kernelnewbies.org/FAQ


[Index of Archives]     [Newbies FAQ]     [Linux Kernel Mentors]     [Linux Kernel Development]     [IETF Annouce]     [Git]     [Networking]     [Security]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux RAID]     [Linux SCSI]     [Linux ACPI]
  Powered by Linux