diff options
author | patacongo <patacongo@42af7a65-404d-4744-a932-0658087f49c3> | 2008-01-29 20:13:18 +0000 |
---|---|---|
committer | patacongo <patacongo@42af7a65-404d-4744-a932-0658087f49c3> | 2008-01-29 20:13:18 +0000 |
commit | 0af596b1f19b3345984fefef55dc7831770b1752 (patch) | |
tree | 66cf981fcdd5a835b0de72413eb648bb1d3bb83a /nuttx/arch/z16/src/z16f | |
parent | 47d740d94dc4d326cd4237603af74e17589b0759 (diff) | |
download | px4-nuttx-0af596b1f19b3345984fefef55dc7831770b1752.tar.gz px4-nuttx-0af596b1f19b3345984fefef55dc7831770b1752.tar.bz2 px4-nuttx-0af596b1f19b3345984fefef55dc7831770b1752.zip |
Fix some Z16F serial bugs
git-svn-id: svn://svn.code.sf.net/p/nuttx/code/trunk@582 42af7a65-404d-4744-a932-0658087f49c3
Diffstat (limited to 'nuttx/arch/z16/src/z16f')
-rw-r--r-- | nuttx/arch/z16/src/z16f/z16f_serial.c | 55 |
1 files changed, 26 insertions, 29 deletions
diff --git a/nuttx/arch/z16/src/z16f/z16f_serial.c b/nuttx/arch/z16/src/z16f/z16f_serial.c index cf44618f4..ce40a497f 100644 --- a/nuttx/arch/z16/src/z16f/z16f_serial.c +++ b/nuttx/arch/z16/src/z16f/z16f_serial.c @@ -68,6 +68,10 @@ extern _Erom unsigned long SYS_CLK_FREQ; #define _DEFCLK ((unsigned long)&SYS_CLK_FREQ) +#define STATE_DISABLED 0 +#define STATE_RXENABLED 1 +#define STATE_TXENABLED 2 + /**************************************************************************** * Private Types ****************************************************************************/ @@ -246,7 +250,8 @@ static ubyte z16f_disableuartirq(struct uart_dev_s *dev) { struct z16f_uart_s *priv = (struct z16f_uart_s*)dev->priv; irqstate_t flags = irqsave(); - ubyte state = priv->rxenabled ? 1 : 0 | priv->txenabled ? 2 : 0; + ubyte state = priv->rxenabled ? STATE_RXENABLED : STATE_DISABLED | \ + priv->txenabled ? STATE_TXENABLED : STATE_DISABLED; z16f_txint(dev, FALSE); z16f_rxint(dev, FALSE); @@ -264,27 +269,29 @@ static void z16f_restoreuartirq(struct uart_dev_s *dev, ubyte state) struct z16f_uart_s *priv = (struct z16f_uart_s*)dev->priv; irqstate_t flags = irqsave(); - z16f_txint(dev, (state & 2) ? TRUE : FALSE); - z16f_rxint(dev, (state & 1) ? TRUE : FALSE); + z16f_txint(dev, (state & STATE_TXENABLED) ? TRUE : FALSE); + z16f_rxint(dev, (state & STATE_RXENABLED) ? TRUE : FALSE); irqrestore(flags); } /**************************************************************************** - * Name: z16f_waittx + * Name: z16f_consoleput ****************************************************************************/ -static void z16f_waittx(struct uart_dev_s *dev, boolean (*status)(struct uart_dev_s *)) +static void z16f_consoleput(ubyte ch) { + struct z16f_uart_s *priv = (struct z16f_uart_s*)CONSOLE_DEV.priv; int tmp; for (tmp = 1000 ; tmp > 0 ; tmp--) { - if (status(dev)) + if (z16f_txready(&CONSOLE_DEV)) { break; } } + putreg8(ch, priv->uartbase + Z16F_UART_TXD); } /**************************************************************************** @@ -379,23 +386,16 @@ static int z16f_attach(struct uart_dev_s *dev) /* Attach the RX IRQ */ ret = irq_attach(priv->rxirq, z16f_rxinterrupt); - if (ret != OK) + if (ret == OK) { - goto errout; - } + /* Attach the TX IRQ */ - /* Attach the TX IRQ */ - - ret = irq_attach(priv->txirq, z16f_txinterrupt); - if (ret != OK) - { - goto errout_with_rxirq; + ret = irq_attach(priv->txirq, z16f_txinterrupt); + if (ret != OK) + { + irq_detach(priv->rxirq); + } } - return OK; - -errout_with_rxirq: - irq_detach(priv->rxirq); -errout: return ret; } @@ -598,7 +598,7 @@ static boolean z16f_rxavailable(struct uart_dev_s *dev) static void z16f_send(struct uart_dev_s *dev, int ch) { struct z16f_uart_s *priv = (struct z16f_uart_s*)dev->priv; - putreg8(ch, priv->uartbase + Z16F_UART1_TXD); + putreg8(ch, priv->uartbase + Z16F_UART_TXD); } /**************************************************************************** @@ -707,7 +707,6 @@ void up_serialinit(void) int up_putc(int ch) { - struct z16f_uart_s *priv = (struct z16f_uart_s*)CONSOLE_DEV.priv; ubyte state; /* Keep interrupts disabled so that we do not interfere with normal @@ -722,20 +721,18 @@ int up_putc(int ch) { /* Add CR before LF */ - z16f_waittx(&CONSOLE_DEV, z16f_txready); - putreg8('\r', priv->uartbase + Z16F_UART_TXD); + z16f_consoleput('\r'); } /* Output the character */ - z16f_waittx(&CONSOLE_DEV, z16f_txready); - putreg8((ubyte)ch, priv->uartbase + Z16F_UART_TXD); + z16f_consoleput((ubyte)ch); - /* Now wait for all queue TX data to drain before restoring interrupts. The - * driver should receive one txdone interrupt which it may or may not ignore. + /* It is important to restore the TX interrupt while the send is pending. + * otherwise, TRDE interrupts can be lost since they do not pend after the + * TRDE false->true transition. */ - z16f_waittx(&CONSOLE_DEV, z16f_txempty); z16f_restoreuartirq(&CONSOLE_DEV, state); return ch; } |