Dear José Miguel Gonçalves, > Serial driver for the S3C24XX SoCs. > > Signed-off-by: José Miguel Gonçalves <jose.goncal...@inov.pt> > --- > drivers/serial/Makefile | 1 + > drivers/serial/s3c24xx_serial.c | 146 > +++++++++++++++++++++++++++++++++++++++ 2 files changed, 147 insertions(+) > create mode 100644 drivers/serial/s3c24xx_serial.c > > diff --git a/drivers/serial/Makefile b/drivers/serial/Makefile > index 65d0f23..2cbdaac 100644 > --- a/drivers/serial/Makefile > +++ b/drivers/serial/Makefile > @@ -52,6 +52,7 @@ COBJS-$(CONFIG_PL011_SERIAL) += serial_pl01x.o > COBJS-$(CONFIG_PXA_SERIAL) += serial_pxa.o > COBJS-$(CONFIG_SA1100_SERIAL) += serial_sa1100.o > COBJS-$(CONFIG_S3C24X0_SERIAL) += serial_s3c24x0.o > +COBJS-$(CONFIG_S3C24XX_SERIAL) += s3c24xx_serial.o
What's the difference between those two drivers ?! > COBJS-$(CONFIG_S3C44B0_SERIAL) += serial_s3c44b0.o > COBJS-$(CONFIG_XILINX_UARTLITE) += serial_xuartlite.o > COBJS-$(CONFIG_SANDBOX_SERIAL) += sandbox.o > diff --git a/drivers/serial/s3c24xx_serial.c > b/drivers/serial/s3c24xx_serial.c new file mode 100644 > index 0000000..11f13a5 > --- /dev/null > +++ b/drivers/serial/s3c24xx_serial.c > @@ -0,0 +1,146 @@ > +/* > + * (C) Copyright 2012 INOV - INESC Inovacao > + * Jose Goncalves <jose.goncal...@inov.pt> > + * > + * Based on drivers/serial/s3c64xx.c > + * > + * See file CREDITS for list of people who contributed to this > + * project. > + * > + * This program is free software; you can redistribute it and/or > + * modify it under the terms of the GNU General Public License as > + * published by the Free Software Foundation; either version 2 of > + * the License, or (at your option) any later version. > + * > + * This program is distributed in the hope that it will be useful, > + * but WITHOUT ANY WARRANTY; without even the implied warranty of > + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the > + * GNU General Public License for more details. > + * > + * You should have received a copy of the GNU General Public License > + * along with this program; if not, write to the Free Software > + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, > + * MA 02111-1307 USA > + */ > + > +#include <common.h> > +#include <asm/arch/s3c24xx_cpu.h> > + > +DECLARE_GLOBAL_DATA_PTR; > + > +#ifdef CONFIG_SERIAL0 > +#define UART_NR S3C24XX_UART0 > + > +#elif defined(CONFIG_SERIAL1) > +#define UART_NR S3C24XX_UART1 > + > +#elif defined(CONFIG_SERIAL2) > +#define UART_NR S3C24XX_UART2 > + > +#elif defined(CONFIG_SERIAL3) > +#define UART_NR S3C24XX_UART3 > + > +#else > +#error "Bad: you didn't configure serial ..." Error itself is "Bad:" so remove it > +#endif > + > +#define barrier() asm volatile("" ::: "memory") Is that even used ? > +/* > + * The coefficient, used to calculate the baudrate on S3C24XX UARTs is > + * calculated as C = UBRDIV * 16 + number_of_set_bits_in_UDIVSLOT > + * however, section 2.1.10 of the S3C2416 User's Manual doesn't recommend > + * using 1 for 1, 3 for 2, ... (2^n - 1) for n, instead, they suggest > using + * these constants: > + */ > +static const int udivslot[] = { const int const ... const array const members > + 0x0000, 0x0080, 0x0808, 0x0888, 0x2222, 0x4924, 0x4A52, 0x54AA, > + 0x5555, 0xD555, 0xD5D5, 0xDDD5, 0xDDDD, 0xDFDD, 0xDFDF, 0xFFDF, > +}; > + > +void serial_setbrg(void) > +{ > + s3c24xx_uart *const uart = s3c24xx_get_base_uart(UART_NR); > + u32 pclk; > + u32 baudrate; > + int i; > + > + pclk = get_PCLK(); > + baudrate = gd->baudrate; > + > + uart->ubrdiv = (pclk / baudrate / 16) - 1; > + uart->udivslot = udivslot[(pclk / baudrate) % 16]; > + > + for (i = 0; i < 100; i++) > + barrier(); > +} > + > +/* > + * Initialise the serial port with the given baudrate. The settings > + * are always 8 data bits, no parity, 1 stop bit, no start bits. > + */ > +int serial_init(void) > +{ > + s3c24xx_uart *const uart = s3c24xx_get_base_uart(UART_NR); > + > + /* FIFO enable, Tx/Rx FIFO clear */ > + uart->ufcon = 0x07; > + uart->umcon = 0x00; Magic numbers, fix > + /* Normal mode, No parity, 1 stop bit, 8 data bits */ > + uart->ulcon = 0x03; > + /* Polling mode */ > + uart->ucon = 0x005; > + > + serial_setbrg(); > + > + return 0; > +} > + > +/* > + * Read a single byte from the serial port. > + */ > +int serial_getc(void) > +{ > + s3c24xx_uart *const uart = s3c24xx_get_base_uart(UART_NR); > + > + /* Wait for character to arrive */ > + while (!(uart->utrstat & 0x1)) ; > + > + return uart->urxh & 0xff; > +} > + > +/* > + * Output a single byte to the serial port. > + */ > +void serial_putc(const char c) > +{ > + s3c24xx_uart *const uart = s3c24xx_get_base_uart(UART_NR); > + > + /* Wait for room in the TX FIFO */ > + while (!(uart->utrstat & 0x2)) ; > + > + uart->utxh = c; > + > + /* If \n, also do \r */ > + if (c == '\n') > + serial_putc('\r'); > +} > + > +/* > + * Test whether a character is in the RX buffer. > + */ > +int serial_tstc(void) > +{ > + s3c24xx_uart *const uart = s3c24xx_get_base_uart(UART_NR); > + > + return uart->utrstat & 0x1; > +} > + > +/* > + * Output a string to the serial port. > + */ > +void serial_puts(const char *s) > +{ > + while (*s) > + serial_putc(*s++); > +} Can you implement it as a serial multi (CONFIG_SERIAL_MULTI) right away ? thanks. Best regards, Marek Vasut _______________________________________________ U-Boot mailing list U-Boot@lists.denx.de http://lists.denx.de/mailman/listinfo/u-boot