1 /* 2 * 8250/16550-type serial ports prom_putchar() 3 * 4 * Copyright (C) 2010 Yoichi Yuasa <yuasa@linux-mips.org> 5 * 6 * This program is free software; you can redistribute it and/or modify 7 * it under the terms of the GNU General Public License as published by 8 * the Free Software Foundation; either version 2 of the License, or 9 * (at your option) any later version. 10 * 11 * This program is distributed in the hope that it will be useful, 12 * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 * GNU General Public License for more details. 15 * 16 * You should have received a copy of the GNU General Public License 17 * along with this program; if not, write to the Free Software 18 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 19 */ 20 #include <linux/io.h> 21 #include <linux/serial_core.h> 22 #include <linux/serial_reg.h> 23 #include <asm/setup.h> 24 25 static void __iomem *serial8250_base; 26 static unsigned int serial8250_reg_shift; 27 static unsigned int serial8250_tx_timeout; 28 29 void setup_8250_early_printk_port(unsigned long base, unsigned int reg_shift, 30 unsigned int timeout) 31 { 32 serial8250_base = (void __iomem *)base; 33 serial8250_reg_shift = reg_shift; 34 serial8250_tx_timeout = timeout; 35 } 36 37 static inline u8 serial_in(int offset) 38 { 39 return readb(serial8250_base + (offset << serial8250_reg_shift)); 40 } 41 42 static inline void serial_out(int offset, char value) 43 { 44 writeb(value, serial8250_base + (offset << serial8250_reg_shift)); 45 } 46 47 void prom_putchar(char c) 48 { 49 unsigned int timeout; 50 int status, bits; 51 52 if (!serial8250_base) 53 return; 54 55 timeout = serial8250_tx_timeout; 56 bits = UART_LSR_TEMT | UART_LSR_THRE; 57 58 do { 59 status = serial_in(UART_LSR); 60 61 if (--timeout == 0) 62 break; 63 } while ((status & bits) != bits); 64 65 if (timeout) 66 serial_out(UART_TX, c); 67 } 68