patch-2.4.22 linux-2.4.22/arch/mips/mips-boards/generic/printf.c

Next file: linux-2.4.22/arch/mips/mips-boards/generic/time.c
Previous file: linux-2.4.22/arch/mips/mips-boards/generic/pci.c
Back to the patch index
Back to the overall index

diff -urN linux-2.4.21/arch/mips/mips-boards/generic/printf.c linux-2.4.22/arch/mips/mips-boards/generic/printf.c
@@ -2,8 +2,6 @@
  * Carsten Langgaard, carstenl@mips.com
  * Copyright (C) 1999,2000 MIPS Technologies, Inc.  All rights reserved.
  *
- * ########################################################################
- *
  *  This program is free software; you can distribute it and/or modify it
  *  under the terms of the GNU General Public License (Version 2) as
  *  published by the Free Software Foundation.
@@ -17,101 +15,84 @@
  *  with this program; if not, write to the Free Software Foundation, Inc.,
  *  59 Temple Place - Suite 330, Boston MA 02111-1307, USA.
  *
- * ########################################################################
- *
  * Putting things on the screen/serial line using YAMONs facilities.
- *
  */
 #include <linux/config.h>
 #include <linux/init.h>
 #include <linux/kernel.h>
-#include <linux/serialP.h>
 #include <linux/serial_reg.h>
-#include <asm/system.h>
+#include <linux/spinlock.h>
 #include <asm/io.h>
-#include <asm/serial.h>
 
+#ifdef CONFIG_MIPS_ATLAS
+
+#include <asm/mips-boards/atlas.h>
 
-#if defined(CONFIG_MIPS_ATLAS) || defined(CONFIG_MIPS_SEAD)
 /*
  * Atlas registers are memory mapped on 64-bit aligned boundaries and
  * only word access are allowed.
  * When reading the UART 8 bit registers only the LSB are valid.
  */
-unsigned int atlas_serial_in(struct async_struct *info, int offset)
+static inline unsigned int serial_in(int offset)
 {
-	return (*(volatile unsigned int *)(info->port + mips_io_port_base + offset*8) & 0xff);
+	return (*(volatile unsigned int *)(mips_io_port_base + ATLAS_UART_REGS_BASE + offset*8) & 0xff);
 }
 
-void atlas_serial_out(struct async_struct *info, int offset, int value)
+static inline void serial_out(int offset, int value)
 {
-	*(volatile unsigned int *)(info->port + mips_io_port_base + offset*8) = value;
+	*(volatile unsigned int *)(mips_io_port_base + ATLAS_UART_REGS_BASE + offset*8) = value;
 }
 
-#define serial_in  atlas_serial_in
-#define serial_out atlas_serial_out
+#elif defined(CONFIG_MIPS_SEAD)
 
-#else
+#include <asm/mips-boards/sead.h>
 
-static unsigned int serial_in(struct async_struct *info, int offset)
+/*
+ * SEAD registers are just like Atlas registers.
+ */
+static inline unsigned int serial_in(int offset)
 {
-	return inb(info->port + offset);
+	return (*(volatile unsigned int *)(mips_io_port_base + SEAD_UART0_REGS_BASE + offset*8) & 0xff);
 }
 
-static void serial_out(struct async_struct *info, int offset,
-				int value)
+static inline void serial_out(int offset, int value)
 {
-	outb(value, info->port + offset);
+	*(volatile unsigned int *)(mips_io_port_base + SEAD_UART0_REGS_BASE + offset*8) = value;
 }
-#endif
-
-static struct serial_state rs_table[] = {
-	SERIAL_PORT_DFNS	/* Defined in serial.h */
-};
-
-/*
- * Hooks to fake "prom" console I/O before devices
- * are fully initialized.
- */
-static struct async_struct prom_port_info = {0};
 
-void __init setup_prom_printf(int tty_no) {
-	struct serial_state *ser = &rs_table[tty_no];
+#else
 
-	prom_port_info.state = ser;
-	prom_port_info.magic = SERIAL_MAGIC;
-	prom_port_info.port = ser->port;
-	prom_port_info.flags = ser->flags;
+static inline unsigned int serial_in(int offset)
+{
+	return inb(0x3f8 + offset);
+}
 
-	/* No setup of UART - assume YAMON left in sane state */
+static inline void serial_out(int offset, int value)
+{
+	outb(value, 0x3f8 + offset);
 }
+#endif
 
 int putPromChar(char c)
 {
-        if (!prom_port_info.state) { 	/* need to init device first */
-		return 0;
-	}
-
-	while ((serial_in(&prom_port_info, UART_LSR) & UART_LSR_THRE) == 0)
+	while ((serial_in(UART_LSR) & UART_LSR_THRE) == 0)
 		;
 
-	serial_out(&prom_port_info, UART_TX, c);
+	serial_out(UART_TX, c);
 
 	return 1;
 }
 
 char getPromChar(void)
 {
-	if (!prom_port_info.state) { 	/* need to init device first */
-		return 0;
-	}
-
-	while (!(serial_in(&prom_port_info, UART_LSR) & 1))
+	while (!(serial_in(UART_LSR) & 1))
 		;
 
-	return(serial_in(&prom_port_info, UART_RX));
+	return serial_in(UART_RX);
 }
 
+static spinlock_t con_lock = SPIN_LOCK_UNLOCKED;
+
 static char buf[1024];
 
 void __init prom_printf(char *fmt, ...)
@@ -123,8 +104,7 @@
 
 	int putPromChar(char);
 
-	/* Low level, brute force, not SMP safe... */
-	save_and_cli(flags);
+	spin_lock_irqsave(con_lock, flags);
 	va_start(args, fmt);
 	l = vsprintf(buf, fmt, args); /* hopefully i < sizeof(buf) */
 	va_end(args);
@@ -133,8 +113,9 @@
 
 	for (p = buf; p < buf_end; p++) {
 		/* Crude cr/nl handling is better than none */
-		if(*p == '\n')putPromChar('\r');
+		if (*p == '\n')
+			putPromChar('\r');
 		putPromChar(*p);
 	}
-	restore_flags(flags);
+	spin_unlock_irqrestore(con_lock, flags);
 }

FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)