summaryrefslogtreecommitdiffstats
path: root/c/src/lib/libbsp/powerpc
diff options
context:
space:
mode:
authorJoel Sherrill <joel.sherrill@OARcorp.com>2002-05-14 17:10:17 +0000
committerJoel Sherrill <joel.sherrill@OARcorp.com>2002-05-14 17:10:17 +0000
commit69ed59f083a083fd96d08b5f6d54f2c80f267f03 (patch)
tree3d8fcd08bcface88cea636117b47dd1520b2874c /c/src/lib/libbsp/powerpc
parent2001-05-14 Till Straumann <strauman@slac.stanford.edu> (diff)
downloadrtems-69ed59f083a083fd96d08b5f6d54f2c80f267f03.tar.bz2
2001-05-14 Till Straumann <strauman@slac.stanford.edu>
* bootloader/misc.c, console/Makefile.am, console/console.c, console/consoleIo.h, console/inch.c, console/polled_io.c, console/uart.c, console/uart.h, include/bsp.h, irq/Makefile.am, irq/irq.c, irq/irq.h, irq/irq_init.c, openpic/openpic.c, openpic/openpic.h, pci/Makefile.am, pci/pci.c, pci/pci.h, residual/Makefile.am, start/start.S, startup/bspstart.c, vectors/vectors.S, vectors/vectors.h, vectors/vectors_init.c: Per PR216, "libbsp/powerpc/shared" BSP has been modified considerably with the goal to make it more flexible and reusable by other BSPs. The main strategies were: - eliminate hardcoded base addresses; devices use offsets and a BSP defined base address. - separate functionality into different files (e.g. reboot from inch.c to reboot.c) which can be overridden by a 'derived' BSP. - separate initialization code into separate files (e.g. PCI bridge detection/initialization was separated from the more generic PCI access routines), also to make it easier for 'derived' BSPs to substitute their own initialization code. There are also a couple of enhancements and fixes: - IRQ handling code now has a hook for attaching a VME bridge. - OpenPIC is now explicitely initialized (polarities, senses). Eliminated the implicit assumption on the presence of an ISA PIC. - UART and console driver now supports more than 1 port. The current maximum of 2 can easily be extended by enlarging a table (it would even be easier if the ISR API was not broken by design). - fixed polled_io.c so it correctly supports console on COM2 - fixed TLB invalidation code (start.S). - exception handler prints a stack backtrace. - added BSP_pciFindDevice() to scan the pci bus for a particular vendor/device/instance.
Diffstat (limited to 'c/src/lib/libbsp/powerpc')
-rw-r--r--c/src/lib/libbsp/powerpc/shared/ChangeLog23
-rw-r--r--c/src/lib/libbsp/powerpc/shared/bootloader/misc.c17
-rw-r--r--c/src/lib/libbsp/powerpc/shared/console/Makefile.am6
-rw-r--r--c/src/lib/libbsp/powerpc/shared/console/console.c187
-rw-r--r--c/src/lib/libbsp/powerpc/shared/console/consoleIo.h4
-rw-r--r--c/src/lib/libbsp/powerpc/shared/console/inch.c33
-rw-r--r--c/src/lib/libbsp/powerpc/shared/console/polled_io.c118
-rw-r--r--c/src/lib/libbsp/powerpc/shared/console/uart.c386
-rw-r--r--c/src/lib/libbsp/powerpc/shared/console/uart.h15
-rw-r--r--c/src/lib/libbsp/powerpc/shared/include/bsp.h26
-rw-r--r--c/src/lib/libbsp/powerpc/shared/irq/Makefile.am2
-rw-r--r--c/src/lib/libbsp/powerpc/shared/irq/irq.c12
-rw-r--r--c/src/lib/libbsp/powerpc/shared/irq/irq.h9
-rw-r--r--c/src/lib/libbsp/powerpc/shared/irq/irq_init.c12
-rw-r--r--c/src/lib/libbsp/powerpc/shared/openpic/openpic.c18
-rw-r--r--c/src/lib/libbsp/powerpc/shared/openpic/openpic.h4
-rw-r--r--c/src/lib/libbsp/powerpc/shared/pci/Makefile.am4
-rw-r--r--c/src/lib/libbsp/powerpc/shared/pci/pci.c118
-rw-r--r--c/src/lib/libbsp/powerpc/shared/pci/pci.h31
-rw-r--r--c/src/lib/libbsp/powerpc/shared/residual/Makefile.am2
-rw-r--r--c/src/lib/libbsp/powerpc/shared/start/start.S2
-rw-r--r--c/src/lib/libbsp/powerpc/shared/startup/bspstart.c11
-rw-r--r--c/src/lib/libbsp/powerpc/shared/vectors/vectors.S4
-rw-r--r--c/src/lib/libbsp/powerpc/shared/vectors/vectors.h3
-rw-r--r--c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c37
25 files changed, 519 insertions, 565 deletions
diff --git a/c/src/lib/libbsp/powerpc/shared/ChangeLog b/c/src/lib/libbsp/powerpc/shared/ChangeLog
index ff4fb24d3a..dce1744e2e 100644
--- a/c/src/lib/libbsp/powerpc/shared/ChangeLog
+++ b/c/src/lib/libbsp/powerpc/shared/ChangeLog
@@ -1,3 +1,26 @@
+2001-05-14 Till Straumann <strauman@slac.stanford.edu>
+
+ * bootloader/misc.c, console/Makefile.am, console/console.c,
+ console/consoleIo.h, console/inch.c, console/polled_io.c,
+ console/uart.c, console/uart.h, include/bsp.h, irq/Makefile.am,
+ irq/irq.c, irq/irq.h, irq/irq_init.c, openpic/openpic.c,
+ openpic/openpic.h, pci/Makefile.am, pci/pci.c, pci/pci.h,
+ residual/Makefile.am, start/start.S, startup/bspstart.c,
+ vectors/vectors.S, vectors/vectors.h, vectors/vectors_init.c:
+ Per PR216, "libbsp/powerpc/shared" BSP has been modified considerably
+ with the goal to make it more flexible and reusable by other
+ BSPs. The main strategies were:
+ - eliminate hardcoded base addresses; devices use offsets
+ and a BSP defined base address.
+ - separate functionality into different files (e.g. reboot from
+ inch.c to reboot.c) which can be overridden by a 'derived' BSP.
+ - separate initialization code into separate files (e.g. PCI
+ bridge detection/initialization was separated from the more
+ generic PCI access routines), also to make it easier for
+ 'derived' BSPs to substitute their own initialization code.
+ There are also a couple of enhancements and fixes:
+ - IRQ handling code now has a hook for attaching a VME bridge.
+ - OpenPIC is now explicitely initialized (polarities, senses).
Eliminated the implicit assumption on the presence of an ISA PIC.
- UART and console driver now supports more than 1 port. The current
maximum of 2 can easily be extended by enlarging a table (it
diff --git a/c/src/lib/libbsp/powerpc/shared/bootloader/misc.c b/c/src/lib/libbsp/powerpc/shared/bootloader/misc.c
index 88b7528fca..bd9d61baa2 100644
--- a/c/src/lib/libbsp/powerpc/shared/bootloader/misc.c
+++ b/c/src/lib/libbsp/powerpc/shared/bootloader/misc.c
@@ -233,6 +233,21 @@ void decompress_kernel(int kernel_size, void * zimage_start, int len,
codemove(bd->load_address, initrd_start, initrd_len, bd->cache_lsize);
}
+static int ticks_per_ms=0;
+
+/* this is from rtems_bsp_delay from libcpu */
+void
+boot_udelay(unsigned32 _microseconds)
+{
+ unsigned32 start, ticks, now;
+
+ ticks = _microseconds * ticks_per_ms / 1000;
+ CPU_Get_timebase_low( start );
+ do {
+ CPU_Get_timebase_low( now );
+ } while (now - start < ticks);
+}
+
void
setup_hw(void)
{
@@ -402,7 +417,7 @@ setup_hw(void)
}
break; /* Exit 'timer' loop */
}
- udelay(1000); /* 1 msec */
+ boot_udelay(1000); /* 1 msec */
}
*cp = 0;
}
diff --git a/c/src/lib/libbsp/powerpc/shared/console/Makefile.am b/c/src/lib/libbsp/powerpc/shared/console/Makefile.am
index 48711404c0..da98cb2a2b 100644
--- a/c/src/lib/libbsp/powerpc/shared/console/Makefile.am
+++ b/c/src/lib/libbsp/powerpc/shared/console/Makefile.am
@@ -3,7 +3,7 @@
##
-C_FILES = console.c inch.c polled_io.c uart.c
+C_FILES = console.c inch.c polled_io.c uart.c reboot.c
H_FILES = consoleIo.h keyboard.h uart.h
@@ -18,7 +18,7 @@ PREINSTALL_FILES = $(PROJECT_INCLUDE)/bsp \
all-local: $(PREINSTALL_FILES)
-EXTRA_DIST = console.c consoleIo.h inch.c keyboard.h polled_io.c uart.c \
- uart.h
+EXTRA_DIST = console.c inch.c polled_io.c uart.c \
+ reboot.c console.inl
include $(top_srcdir)/../../../../../automake/local.am
diff --git a/c/src/lib/libbsp/powerpc/shared/console/console.c b/c/src/lib/libbsp/powerpc/shared/console/console.c
index d797108f68..a79e0a5984 100644
--- a/c/src/lib/libbsp/powerpc/shared/console/console.c
+++ b/c/src/lib/libbsp/powerpc/shared/console/console.c
@@ -9,6 +9,9 @@
* (C) Copyright 1997 -
* - NavIST Group - Real-Time Distributed Systems and Industrial Automation
*
+ * Till Straumann, <strauman@slac.stanford.edu>, 12/20/2001
+ * separate BSP specific stuff from generics...
+ *
* http://pandora.ist.utl.pt
*
* Instituto Superior Tecnico * Lisboa * PORTUGAL
@@ -34,56 +37,24 @@ extern int close(int fd);
#include <termios.h>
#include <bsp/uart.h>
#include <bsp/consoleIo.h>
+#include <rtems/bspIo.h> /* printk */
/* Definitions for BSPConsolePort */
-#define BSP_CONSOLE_PORT_CONSOLE (-1)
-#define BSP_CONSOLE_PORT_COM1 (BSP_UART_COM1)
-#define BSP_CONSOLE_PORT_COM2 (BSP_UART_COM2)
/*
* Possible value for console input/output :
* BSP_CONSOLE_PORT_CONSOLE
* BSP_UART_COM1
* BSP_UART_COM2
*/
+int BSPConsolePort = BSP_CONSOLE_PORT;
-int BSPConsolePort = BSP_UART_COM1;
-
-/* int BSPConsolePort = BSP_UART_COM2; */
-int BSPBaseBaud = 115200;
+int BSPBaseBaud = BSP_UART_BAUD_BASE;
/*-------------------------------------------------------------------------+
| External Prototypes
+--------------------------------------------------------------------------*/
static int conSetAttr(int minor, const struct termios *);
-static void isr_on(const rtems_irq_connect_data *);
-static void isr_off(const rtems_irq_connect_data *);
-static int isr_is_on(const rtems_irq_connect_data *);
-
-
-static rtems_irq_connect_data console_isr_data = {BSP_ISA_UART_COM1_IRQ,
- BSP_uart_termios_isr_com1,
- isr_on,
- isr_off,
- isr_is_on};
-
-static void
-isr_on(const rtems_irq_connect_data *unused)
-{
- return;
-}
-
-static void
-isr_off(const rtems_irq_connect_data *unused)
-{
- return;
-}
-
-static int
-isr_is_on(const rtems_irq_connect_data *irq)
-{
- return BSP_irq_enabled_at_i8259s(irq->name);
-}
void __assert (const char *file, int line, const char *msg)
{
@@ -112,6 +83,28 @@ void __assert (const char *file, int line, const char *msg)
}
+typedef struct TtySTblRec_ {
+ char *name;
+ void (*isr)(void); /* STUPID API doesn't pass a parameter :-( */
+} TtySTblRec, *TtySTbl;
+
+static TtySTblRec ttyS[]={
+ { "/dev/ttyS0",
+#ifdef BSP_UART_IOBASE_COM1
+ BSP_uart_termios_isr_com1
+#else
+ 0
+#endif
+ },
+ { "/dev/ttyS1",
+#ifdef BSP_UART_IOBASE_COM2
+ BSP_uart_termios_isr_com2
+#else
+ 0
+#endif
+ },
+};
+
/*-------------------------------------------------------------------------+
| Console device driver INITIALIZE entry point.
@@ -130,7 +123,6 @@ console_initialize(rtems_device_major_number major,
* to be reinitialized.
*/
-
/*
* Set up TERMIOS
*/
@@ -139,57 +131,66 @@ console_initialize(rtems_device_major_number major,
/*
* Do device-specific initialization
*/
-
- /* 9600-8-N-1 */
- BSP_uart_init(BSPConsolePort, 9600, 0);
-
-
- /* Set interrupt handler */
- if(BSPConsolePort == BSP_UART_COM1)
- {
- console_isr_data.name = BSP_ISA_UART_COM1_IRQ;
- console_isr_data.hdl = BSP_uart_termios_isr_com1;
-
- }
- else
- {
- assert(BSPConsolePort == BSP_UART_COM2);
- console_isr_data.name = BSP_ISA_UART_COM2_IRQ;
- console_isr_data.hdl = BSP_uart_termios_isr_com2;
- }
- status = BSP_install_rtems_irq_handler(&console_isr_data);
-
- if (!status){
- printk("Error installing serial console interrupt handler!\n");
- rtems_fatal_error_occurred(status);
- }
- /*
- * Register the device
+ /* RTEMS calls this routine once with 'minor'==0; loop through
+ * all known instances...
*/
- status = rtems_io_register_name ("/dev/console", major, 0);
- if (status != RTEMS_SUCCESSFUL)
- {
- printk("Error registering console device!\n");
- rtems_fatal_error_occurred (status);
- }
+
+ for (minor=0; minor < sizeof(ttyS)/sizeof(ttyS[0]); minor++) {
+ char *nm;
+ /*
+ * Skip ports (possibly not supported by BSP...) we have no ISR for
+ */
+ if ( ! ttyS[minor].isr )
+ continue;
+ /*
+ * Register the device
+ */
+ status = rtems_io_register_name ((nm=ttyS[minor].name), major, minor);
+ if ( RTEMS_SUCCESSFUL==status && BSPConsolePort == minor)
+ {
+ printk("Registering /dev/console as minor %i (==%s)\n",
+ minor,
+ ttyS[minor].name);
+ /* also register an alias */
+ status = rtems_io_register_name (
+ (nm="/dev/console"),
+ major,
+ minor);
+ }
+ if (status != RTEMS_SUCCESSFUL)
+ {
+ printk("Error registering %s!\n",nm);
+ rtems_fatal_error_occurred (status);
+ }
- if(BSPConsolePort == BSP_UART_COM1)
- {
- printk("Initialized console on port COM1 9600-8-N-1\n\n");
- }
- else
- {
- printk("Initialized console on port COM2 9600-8-N-1\n\n");
- }
+ }
return RTEMS_SUCCESSFUL;
} /* console_initialize */
+static int console_first_open(int major, int minor, void *arg)
+{
+ rtems_status_code status;
+
+ /* must not open a minor device we have no ISR for */
+ assert( minor>=0 && minor < sizeof(ttyS)/sizeof(ttyS[0]) && ttyS[minor].isr );
+
+ /* 9600-8-N-1 */
+ BSP_uart_init(minor, 9600, 0);
+ status = BSP_uart_install_isr(minor, ttyS[minor].isr);
+ if (!status)
+ {
+ printk("Error installing serial console interrupt handler for '%s'!\n",
+ ttyS[minor].name);
+ rtems_fatal_error_occurred(status);
+ }
+ return 0;
+}
+
static int console_last_close(int major, int minor, void *arg)
{
- BSP_remove_rtems_irq_handler (&console_isr_data);
-
+ BSP_uart_remove_isr(minor, ttyS[minor].isr);
return 0;
}
@@ -204,21 +205,16 @@ console_open(rtems_device_major_number major,
rtems_status_code status;
static rtems_termios_callbacks cb =
{
- NULL, /* firstOpen */
- console_last_close, /* lastClose */
- NULL, /* pollRead */
- BSP_uart_termios_write_com1, /* write */
- conSetAttr, /* setAttributes */
- NULL, /* stopRemoteTx */
- NULL, /* startRemoteTx */
- 1 /* outputUsesInterrupts */
+ console_first_open, /* firstOpen */
+ console_last_close, /* lastClose */
+ NULL, /* pollRead */
+ BSP_uart_termios_write_com, /* write */
+ conSetAttr, /* setAttributes */
+ NULL, /* stopRemoteTx */
+ NULL, /* startRemoteTx */
+ 1 /* outputUsesInterrupts */
};
- if(BSPConsolePort == BSP_UART_COM2)
- {
- cb.write = BSP_uart_termios_write_com2;
- }
-
status = rtems_termios_open (major, minor, arg, &cb);
if(status != RTEMS_SUCCESSFUL)
@@ -230,10 +226,10 @@ console_open(rtems_device_major_number major,
/*
* Pass data area info down to driver
*/
- BSP_uart_termios_set(BSPConsolePort,
+ BSP_uart_termios_set(minor,
((rtems_libio_open_close_args_t *)arg)->iop->data1);
/* Enable interrupts on channel */
- BSP_uart_intr_ctrl(BSPConsolePort, BSP_UART_INTR_CTRL_TERMIOS);
+ BSP_uart_intr_ctrl(minor, BSP_UART_INTR_CTRL_TERMIOS);
return RTEMS_SUCCESSFUL;
}
@@ -362,10 +358,7 @@ conSetAttr(int minor, const struct termios *t)
return 0;
}
- BSP_uart_set_baud(BSPConsolePort, baud);
+ BSP_uart_set_baud(minor, baud);
return 0;
}
-
-
-
diff --git a/c/src/lib/libbsp/powerpc/shared/console/consoleIo.h b/c/src/lib/libbsp/powerpc/shared/console/consoleIo.h
index c88fe3def9..50ad0428a4 100644
--- a/c/src/lib/libbsp/powerpc/shared/console/consoleIo.h
+++ b/c/src/lib/libbsp/powerpc/shared/console/consoleIo.h
@@ -26,16 +26,12 @@ typedef volatile unsigned char * __io_ptr;
typedef struct {
__io_ptr io_base;
__io_ptr isa_mem_base;
- __io_ptr pci_mmio_base;
- __io_ptr pci_dma_offset;
} board_memory_map;
extern board_memory_map *ptr_mem_map;
-extern unsigned long ticks_per_ms;
extern int select_console(ioType t);
/* extern int printk(const char *, ...) __attribute__((format(printf, 1, 2))); */
-extern void udelay(int);
extern void debug_putc(const unsigned char c);
extern int debug_getc(void);
extern int debug_tstc(void);
diff --git a/c/src/lib/libbsp/powerpc/shared/console/inch.c b/c/src/lib/libbsp/powerpc/shared/console/inch.c
index 5cd7148e97..eaa6224529 100644
--- a/c/src/lib/libbsp/powerpc/shared/console/inch.c
+++ b/c/src/lib/libbsp/powerpc/shared/console/inch.c
@@ -22,12 +22,14 @@
#include <bsp.h>
#include <bsp/irq.h>
+#include "console.inl"
+
/*-------------------------------------------------------------------------+
| Constants
+--------------------------------------------------------------------------*/
-#define KBD_CTL 0x61 /* -------------------------------- */
-#define KBD_DATA 0x60 /* Ports for PC keyboard controller */
-#define KBD_STATUS 0x64 /* -------------------------------- */
+#define KBD_CTL 0x1 /* -------------------------------- */
+#define KBD_DATA 0x0 /* Port offsets for PC keyboard controller */
+#define KBD_STATUS 0x4 /* -------------------------------- */
#define KBD_BUF_SIZE 256
@@ -62,19 +64,6 @@ static rtems_unsigned16 kbd_last = 0;
static rtems_unsigned16 kbd_end = KBD_BUF_SIZE - 1;
/*-------------------------------------------------------------------------+
-| Function: rtemsReboot
-| Description: Reboot the PC.
-| Global Variables: None.
-| Arguments: None.
-| Returns: Nothing.
-+--------------------------------------------------------------------------*/
-void rtemsReboot(void)
-{
- /* shutdown and reboot */
- outport_byte(0x64, 0xFE); /* use keyboard controler to do the job... */
-} /* rtemsReboot */
-
-/*-------------------------------------------------------------------------+
| Function: _IBMPC_scankey
| Description: This function can be called during a poll for input, or by
| an ISR. Basically any time you want to process a keypress.
@@ -97,18 +86,18 @@ _IBMPC_scankey(char *outChar)
*outChar = NULL; /* default value if we return FALSE */
/* Read keyboard controller, toggle enable */
- inport_byte(KBD_CTL, inChar);
- outport_byte(KBD_CTL, inChar & ~0x80);
- outport_byte(KBD_CTL, inChar | 0x80);
- outport_byte(KBD_CTL, inChar & ~0x80);
+ inChar=kbd_inb(KBD_CTL);
+ kbd_outb(KBD_CTL, inChar & ~0x80);
+ kbd_outb(KBD_CTL, inChar | 0x80);
+ kbd_outb(KBD_CTL, inChar & ~0x80);
/* See if it has data */
- inport_byte(KBD_STATUS, inChar);
+ inChar=kbd_inb(KBD_STATUS);
if ((inChar & 0x01) == 0)
return FALSE;
/* Read the data. Handle nonsense with shift, control, etc. */
- inport_byte(KBD_DATA, inChar);
+ inChar=kbd_inb(KBD_DATA);
if (extended)
extended--;
diff --git a/c/src/lib/libbsp/powerpc/shared/console/polled_io.c b/c/src/lib/libbsp/powerpc/shared/console/polled_io.c
index 2f1a399e71..6c3e0b401e 100644
--- a/c/src/lib/libbsp/powerpc/shared/console/polled_io.c
+++ b/c/src/lib/libbsp/powerpc/shared/console/polled_io.c
@@ -20,17 +20,34 @@
#include <libcpu/byteorder.h>
#include <libcpu/page.h>
#include <libcpu/mmu.h>
-#include "keyboard.h"
#include <libcpu/io.h>
#include <string.h>
#include <stdarg.h>
#include <bsp/consoleIo.h>
+#include <bsp.h>
#include <libcpu/spr.h>
+#ifdef BSP_KBD_IOBASE
+#define USE_KBD_SUPPORT
+#endif
+#ifdef BSP_VGA_IOBASE
+#define USE_VGA_SUPPORT
+#endif
+
+#ifdef USE_KBD_SUPPORT
+#include "keyboard.h"
+#endif
+#include "console.inl"
+
+#ifdef __BOOT__
+extern void boot_udelay();
+#endif
+
typedef unsigned long long u64;
typedef long long s64;
typedef unsigned int u32;
+#ifdef USE_KBD_SUPPORT
unsigned short plain_map[NR_KEYS] = {
0xf200, 0xf01b, 0xf031, 0xf032, 0xf033, 0xf034, 0xf035, 0xf036,
0xf037, 0xf038, 0xf039, 0xf030, 0xf02d, 0xf03d, 0xf07f, 0xf009,
@@ -296,10 +313,11 @@ unsigned int accent_table_size = 68;
/* These #defines have been copied from drivers/char/pc_keyb.h, by
* Martin Mares (mj@ucw.cz).
+ * converted to offsets by Till Straumann <strauman@slac.stanford.edu>
*/
-#define KBD_STATUS_REG 0x64 /* Status register (R) */
-#define KBD_CNTL_REG 0x64 /* Controller command register (W) */
-#define KBD_DATA_REG 0x60 /* Keyboard data register (R/W) */
+#define KBD_STATUS_REG 0x4 /* Status register (R) */
+#define KBD_CNTL_REG 0x4 /* Controller command register (W) */
+#define KBD_DATA_REG 0x0 /* Keyboard data register (R/W) */
/*
* Keyboard Controller Commands
@@ -356,6 +374,8 @@ unsigned int accent_table_size = 68;
SPR_RW(DEC)
SPR_RO(PVR)
+#endif /* USE_KBD_SUPPORT */
+
/* Early messages after mm init but before console init are kept in log
* buffers.
@@ -377,10 +397,8 @@ static u_char log_page_pool [STATIC_LOG_DATA_PAGE_NB * PAGE_SIZE];
#endif
static board_memory_map mem_map = {
- (__io_ptr) 0x80000000,
- (__io_ptr) 0xc0000000,
- (__io_ptr) 0xc0000000,
- (__io_ptr) 0x80000000
+ (__io_ptr) _IO_BASE, /* from libcpu/io.h */
+ (__io_ptr) _ISA_MEM_BASE,
};
board_memory_map *ptr_mem_map = &mem_map;
@@ -404,18 +422,6 @@ typedef struct console_io {
extern console_io* curIo;
-unsigned long ticks_per_ms = 1000000; /* Decrementer ticks per ms (true for 601) */
-
-/* The decrementer is present on all processors and the RTC on the 601
- * has the annoying characteristic of jumping from 1e9 to 0, so we
- * use the decrementer.
- */
-void udelay(int us) {
- us = us*ticks_per_ms/1000;
- _write_DEC(us);
- while((int)_read_DEC() >= 0);
-}
-
void debug_putc(const u_char c)
{
curIo->putc(c);
@@ -473,7 +479,6 @@ int vacuum_tstc(void) {
#define LSR_TEMT 0x40 /* Xmitter empty */
#define LSR_ERR 0x80 /* Error */
-#define COM1 0x3F8
#ifdef STATIC_LOG_ALLOC
static int global_index = 0;
@@ -543,23 +548,28 @@ void flush_log(void) {
}
}
+#ifndef INL_CONSOLE_INB
+#error "BSP probably didn't define a console port"
+#endif
+
void serial_putc(const u_char c)
{
- while ((inb(COM1+lsr) & LSR_THRE) == 0) ;
- outb(c, COM1+thr);
+ while ((INL_CONSOLE_INB(lsr) & LSR_THRE) == 0) ;
+ INL_CONSOLE_OUTB(thr, c);
}
int serial_getc(void)
{
- while ((inb(COM1+lsr) & LSR_DR) == 0) ;
- return (inb(COM1+rbr));
+ while ((INL_CONSOLE_INB(lsr) & LSR_DR) == 0) ;
+ return (INL_CONSOLE_INB(rbr));
}
int serial_tstc(void)
{
- return ((inb(COM1+lsr) & LSR_DR) != 0);
+ return ((INL_CONSOLE_INB(lsr) & LSR_DR) != 0);
}
+#ifdef USE_VGA_SUPPORT
static void scroll(void)
{
int i;
@@ -579,10 +589,10 @@ static void
cursor(int x, int y)
{
int pos = console_global_data.cols*y + x;
- outb(14, 0x3D4);
- outb(pos>>8, 0x3D5);
- outb(15, 0x3D4);
- outb(pos, 0x3D5);
+ vga_outb(14, 0x14);
+ vga_outb(0x15, pos>>8);
+ vga_outb(0x14, 15);
+ vga_outb(0x15, pos);
}
void
@@ -620,16 +630,18 @@ vga_putc(const u_char c)
console_global_data.orig_x = x;
console_global_data.orig_y = y;
}
+#endif /* USE_VGA_SUPPORT */
+#ifdef USE_KBD_SUPPORT
/* Keyboard support */
static int kbd_getc(void)
{
unsigned char dt, brk, val;
unsigned code;
loop:
- while((inb(KBD_STATUS_REG) & KBD_STAT_OBF) == 0) ;
+ while((kbd_inb(KBD_STATUS_REG) & KBD_STAT_OBF) == 0) ;
- dt = inb(KBD_DATA_REG);
+ dt = kbd_inb(KBD_DATA_REG);
brk = dt & 0x80; /* brk == 1 on key release */
dt = dt & 0x7f; /* keycode */
@@ -667,8 +679,8 @@ loop:
else if (val == KVAL(K_ENTER)) {
enter: /* Wait for key up */
while (1) {
- while((inb(KBD_STATUS_REG) & KBD_STAT_OBF) == 0) ;
- dt = inb(KBD_DATA_REG);
+ while((kbd_inb(KBD_STATUS_REG) & KBD_STAT_OBF) == 0) ;
+ dt = kbd_inb(KBD_DATA_REG);
if (dt & 0x80) /* key up */ break;
}
return 10;
@@ -732,25 +744,33 @@ enter: /* Wait for key up */
static int kbd_get(int ms) {
int status, data;
while(1) {
- status = inb(KBD_STATUS_REG);
+ status = kbd_inb(KBD_STATUS_REG);
if (status & KBD_STAT_OBF) {
- data = inb(KBD_DATA_REG);
+ data = kbd_inb(KBD_DATA_REG);
if (status & (KBD_STAT_GTO | KBD_STAT_PERR))
return -1;
else
return data;
}
if (--ms < 0) return -1;
- udelay(1000);
+#ifdef __BOOT__
+ boot_udelay(1000);
+#else
+ rtems_bsp_delay(1000);
+#endif
}
}
static void kbd_put(u_char c, int ms, int port) {
- while (inb(KBD_STATUS_REG) & KBD_STAT_IBF) {
+ while (kbd_inb(KBD_STATUS_REG) & KBD_STAT_IBF) {
if (--ms < 0) return;
- udelay(1000);
+#ifdef __BOOT__
+ boot_udelay(1000);
+#else
+ rtems_bsp_delay(1000);
+#endif
}
- outb(c, port);
+ kbd_outb(port, c);
}
int kbdreset(void)
@@ -796,8 +816,9 @@ int kbdreset(void)
int kbd_tstc(void)
{
- return ((inb(KBD_STATUS_REG) & KBD_STAT_OBF) != 0);
+ return ((kbd_inb(KBD_STATUS_REG) & KBD_STAT_OBF) != 0);
}
+#endif /* USE_KBD_SUPPORT */
const struct console_io
vacuum_console_functions = {
@@ -811,19 +832,22 @@ log_console_functions = {
log_putc,
vacuum_getc,
vacuum_tstc
-},
-
+}
+,
serial_console_functions = {
serial_putc,
serial_getc,
serial_tstc
-},
-
+}
+#if defined(USE_KBD_SUPPORT) && defined(USE_VGA_SUPPORT)
+,
vga_console_functions = {
vga_putc,
kbd_getc,
kbd_tstc
-};
+}
+#endif
+;
console_io* curIo = (console_io*) &vacuum_console_functions;
@@ -834,7 +858,9 @@ int select_console(ioType t) {
case CONSOLE_VACUUM : curIo = (console_io*)&vacuum_console_functions; break;
case CONSOLE_LOG : curIo = (console_io*)&log_console_functions; break;
case CONSOLE_SERIAL : curIo = (console_io*)&serial_console_functions; break;
+#if defined(USE_KBD_SUPPORT) && defined(USE_VGA_SUPPORT)
case CONSOLE_VGA : curIo = (console_io*)&vga_console_functions; break;
+#endif
default : curIo = (console_io*)&vacuum_console_functions;break;
}
if (curType == CONSOLE_LOG) flush_log();
diff --git a/c/src/lib/libbsp/powerpc/shared/console/uart.c b/c/src/lib/libbsp/powerpc/shared/console/uart.c
index da44cc2e99..8ad744d06b 100644
--- a/c/src/lib/libbsp/powerpc/shared/console/uart.c
+++ b/c/src/lib/libbsp/powerpc/shared/console/uart.c
@@ -19,12 +19,42 @@
struct uart_data
{
+ unsigned long ioBase;
int hwFlow;
int baud;
};
-static struct uart_data uart_data[2];
+/*
+ * Initialization of BSP specific data.
+ * The constants are pulled in from a BSP
+ * specific file, whereas all of the code
+ * in this file is generic and makes no
+ * assumptions about addresses, irq vectors
+ * etc...
+ */
+
+#define UART_UNSUPP ((unsigned long)(-1))
+
+static struct uart_data uart_data[2] = {
+ {
+#ifdef BSP_UART_IOBASE_COM1
+ BSP_UART_IOBASE_COM1,
+#else
+ UART_UNSUPP,
+#endif
+ },
+ {
+#ifdef BSP_UART_IOBASE_COM2
+ BSP_UART_IOBASE_COM2,
+#else
+ UART_UNSUPP,
+#endif
+ },
+};
+#define MAX_UARTS (sizeof(uart_data)/sizeof(uart_data[0]))
+#define SANITY_CHECK(uart) \
+ assert( MAX_UARTS > (unsigned)(uart) && uart_data[(uart)].ioBase != UART_UNSUPP )
/*
* Macros to read/wirte register of uart, if configuration is
* different just rewrite these macros
@@ -33,31 +63,15 @@ static struct uart_data uart_data[2];
static inline unsigned char
uread(int uart, unsigned int reg)
{
- register unsigned char val;
- if(uart == 0)
- {
- inport_byte(COM1_BASE_IO+reg, val);
- }
- else
- {
- inport_byte(COM2_BASE_IO+reg, val);
- }
+ return in_8((unsigned char*)(uart_data[uart].ioBase + reg));
- return val;
}
static inline void
uwrite(int uart, int reg, unsigned int val)
{
- if(uart == 0)
- {
- outport_byte(COM1_BASE_IO+reg, val);
- }
- else
- {
- outport_byte(COM2_BASE_IO+reg, val);
- }
+ out_8((unsigned char*)(uart_data[uart].ioBase + reg), val);
}
#ifdef UARTDEBUG
@@ -103,7 +117,7 @@ BSP_uart_init(int uart, int baud, int hwFlow)
unsigned char tmp;
/* Sanity check */
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
switch(baud)
{
@@ -166,7 +180,7 @@ BSP_uart_set_baud(int uart, int baud)
unsigned char mcr, ier;
/* Sanity check */
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
/*
* This function may be called whenever TERMIOS parameters
@@ -197,7 +211,7 @@ void
BSP_uart_intr_ctrl(int uart, int cmd)
{
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
switch(cmd)
{
@@ -260,7 +274,7 @@ BSP_uart_throttle(int uart)
{
unsigned int mcr;
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
if(!uart_data[uart].hwFlow)
{
@@ -281,7 +295,7 @@ BSP_uart_unthrottle(int uart)
{
unsigned int mcr;
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
if(!uart_data[uart].hwFlow)
{
@@ -311,7 +325,7 @@ BSP_uart_polled_status(int uart)
{
unsigned char val;
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
val = uread(uart, LSR);
@@ -353,7 +367,7 @@ BSP_uart_polled_write(int uart, int val)
unsigned char val1;
/* Sanity check */
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
for(;;)
{
@@ -394,7 +408,7 @@ BSP_uart_polled_read(int uart)
{
unsigned char val;
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
for(;;)
{
@@ -415,20 +429,57 @@ BSP_poll_char_via_serial()
return BSP_uart_polled_read(BSPConsolePort);
}
+static void
+uart_noop(const rtems_irq_connect_data *unused)
+{
+ return;
+}
+
+/* note that the IRQ names contain _ISA_ for legacy
+ * reasons. They can be any interrupt, depending
+ * on the particular BSP...
+ */
-/* ================ Termios support =================*/
+static int
+uart_isr_is_on(const rtems_irq_connect_data *irq)
+{
+int uart = (irq->name == BSP_ISA_UART_COM1_IRQ) ?
+ BSP_UART_COM1 : BSP_UART_COM2;
+ return uread(uart,IER);
+}
-static volatile int termios_stopped_com1 = 0;
-static volatile int termios_tx_active_com1 = 0;
-static void* termios_ttyp_com1 = NULL;
-static char termios_tx_hold_com1 = 0;
-static volatile char termios_tx_hold_valid_com1 = 0;
+static int
+doit(int uart, rtems_irq_hdl handler, int (*p)(const rtems_irq_connect_data*))
+{
+ rtems_irq_connect_data d={0};
+ d.name = (uart == BSP_UART_COM1) ?
+ BSP_ISA_UART_COM1_IRQ : BSP_ISA_UART_COM2_IRQ;
+ d.off = d.on = uart_noop;
+ d.isOn = uart_isr_is_on;
+ d.hdl = handler;
+ return p(&d);
+}
-static volatile int termios_stopped_com2 = 0;
-static volatile int termios_tx_active_com2 = 0;
-static void* termios_ttyp_com2 = NULL;
-static char termios_tx_hold_com2 = 0;
-static volatile char termios_tx_hold_valid_com2 = 0;
+int
+BSP_uart_install_isr(int uart, rtems_irq_hdl handler)
+{
+ return doit(uart, handler, BSP_install_rtems_irq_handler);
+}
+
+int
+BSP_uart_remove_isr(int uart, rtems_irq_hdl handler)
+{
+ return doit(uart, handler, BSP_remove_rtems_irq_handler);
+}
+
+
+/* ================ Termios support =================*/
+
+static volatile int termios_stopped_com[2] = {0,0};
+static volatile int termios_tx_active_com[2] = {0,0};
+static void* termios_ttyp_com[2] = {NULL,NULL};
+static char termios_tx_hold_com[2] = {0,0};
+static volatile char termios_tx_hold_valid_com[2] = {0,0};
/*
* Set channel parameters
@@ -437,49 +488,30 @@ void
BSP_uart_termios_set(int uart, void *ttyp)
{
unsigned char val;
- assert(uart == BSP_UART_COM1 || uart == BSP_UART_COM2);
+ SANITY_CHECK(uart);
- if(uart == BSP_UART_COM1)
+ if(uart_data[uart].hwFlow)
{
- if(uart_data[uart].hwFlow)
- {
- val = uread(uart, MSR);
+ val = uread(uart, MSR);
- termios_stopped_com1 = (val & CTS) ? 0 : 1;
- }
- else
- {
- termios_stopped_com1 = 0;
- }
- termios_tx_active_com1 = 0;
- termios_ttyp_com1 = ttyp;
- termios_tx_hold_com1 = 0;
- termios_tx_hold_valid_com1 = 0;
+ termios_stopped_com[uart] = (val & CTS) ? 0 : 1;
}
else
- {
- if(uart_data[uart].hwFlow)
- {
- val = uread(uart, MSR);
-
- termios_stopped_com2 = (val & CTS) ? 0 : 1;
- }
- else
- {
- termios_stopped_com2 = 0;
- }
- termios_tx_active_com2 = 0;
- termios_ttyp_com2 = ttyp;
- termios_tx_hold_com2 = 0;
- termios_tx_hold_valid_com2 = 0;
- }
+ {
+ termios_stopped_com[uart] = 0;
+ }
+ termios_tx_active_com[uart] = 0;
+ termios_ttyp_com[uart] = ttyp;
+ termios_tx_hold_com[uart] = 0;
+ termios_tx_hold_valid_com[uart] = 0;
return;
}
int
-BSP_uart_termios_write_com1(int minor, const char *buf, int len)
+BSP_uart_termios_write_com(int minor, const char *buf, int len)
{
+ int uart=minor; /* could differ, theoretically */
assert(buf != NULL);
if(len <= 0)
@@ -491,22 +523,22 @@ BSP_uart_termios_write_com1(int minor, const char *buf, int len)
/* assert((uread(BSP_UART_COM1, LSR) & THRE) != 0); */
- if(termios_stopped_com1)
+ if(termios_stopped_com[uart])
{
/* CTS low */
- termios_tx_hold_com1 = *buf;
- termios_tx_hold_valid_com1 = 1;
+ termios_tx_hold_com[uart] = *buf;
+ termios_tx_hold_valid_com[uart] = 1;
return 0;
}
/* Write character */
- uwrite(BSP_UART_COM1, THR, *buf & 0xff);
+ uwrite(uart, THR, *buf & 0xff);
/* Enable interrupts if necessary */
- if(!termios_tx_active_com1 && uart_data[BSP_UART_COM1].hwFlow)
+ if(!termios_tx_active_com[uart] && uart_data[uart].hwFlow)
{
- termios_tx_active_com1 = 1;
- uwrite(BSP_UART_COM1, IER,
+ termios_tx_active_com[uart] = 1;
+ uwrite(uart, IER,
(RECEIVE_ENABLE |
TRANSMIT_ENABLE |
RECEIVER_LINE_ST_ENABLE |
@@ -514,10 +546,10 @@ BSP_uart_termios_write_com1(int minor, const char *buf, int len)
)
);
}
- else if(!termios_tx_active_com1)
+ else if(!termios_tx_active_com[uart])
{
- termios_tx_active_com1 = 1;
- uwrite(BSP_UART_COM1, IER,
+ termios_tx_active_com[uart] = 1;
+ uwrite(uart, IER,
(RECEIVE_ENABLE |
TRANSMIT_ENABLE |
RECEIVER_LINE_ST_ENABLE
@@ -528,61 +560,8 @@ BSP_uart_termios_write_com1(int minor, const char *buf, int len)
return 0;
}
-int
-BSP_uart_termios_write_com2(int minor, const char *buf, int len)
-{
- assert(buf != NULL);
-
- if(len <= 0)
- {
- return 0;
- }
-
-
- /* If there TX buffer is busy - something is royally screwed up */
- assert((uread(BSP_UART_COM2, LSR) & THRE) != 0);
-
- if(termios_stopped_com2)
- {
- /* CTS low */
- termios_tx_hold_com2 = *buf;
- termios_tx_hold_valid_com2 = 1;
- return 0;
- }
-
- /* Write character */
-
- uwrite(BSP_UART_COM2, THR, *buf & 0xff);
-
- /* Enable interrupts if necessary */
- if(!termios_tx_active_com2 && uart_data[BSP_UART_COM2].hwFlow)
- {
- termios_tx_active_com2 = 1;
- uwrite(BSP_UART_COM2, IER,
- (RECEIVE_ENABLE |
- TRANSMIT_ENABLE |
- RECEIVER_LINE_ST_ENABLE |
- MODEM_ENABLE
- )
- );
- }
- else if(!termios_tx_active_com2)
- {
- termios_tx_active_com2 = 1;
- uwrite(BSP_UART_COM2, IER,
- (RECEIVE_ENABLE |
- TRANSMIT_ENABLE |
- RECEIVER_LINE_ST_ENABLE
- )
- );
- }
-
- return 0;
-}
-
-
-void
-BSP_uart_termios_isr_com1(void)
+static void
+BSP_uart_termios_isr_com(int uart)
{
unsigned char buf[40];
unsigned char val;
@@ -592,29 +571,29 @@ BSP_uart_termios_isr_com1(void)
for(;;)
{
- vect = uread(BSP_UART_COM1, IIR) & 0xf;
+ vect = uread(uart, IIR) & 0xf;
switch(vect)
{
case MODEM_STATUS :
- val = uread(BSP_UART_COM1, MSR);
- if(uart_data[BSP_UART_COM1].hwFlow)
+ val = uread(uart, MSR);
+ if(uart_data[uart].hwFlow)
{
if(val & CTS)
{
/* CTS high */
- termios_stopped_com1 = 0;
- if(termios_tx_hold_valid_com1)
+ termios_stopped_com[uart] = 0;
+ if(termios_tx_hold_valid_com[uart])
{
- termios_tx_hold_valid_com1 = 0;
- BSP_uart_termios_write_com1(0, &termios_tx_hold_com1,
+ termios_tx_hold_valid_com[uart] = 0;
+ BSP_uart_termios_write_com(uart, &termios_tx_hold_com[uart],
1);
}
}
else
{
/* CTS low */
- termios_stopped_com1 = 1;
+ termios_stopped_com[uart] = 1;
}
}
break;
@@ -623,7 +602,7 @@ BSP_uart_termios_isr_com1(void)
if(off != 0)
{
/* Update rx buffer */
- rtems_termios_enqueue_raw_characters(termios_ttyp_com1,
+ rtems_termios_enqueue_raw_characters(termios_ttyp_com[uart],
(char *)buf,
off);
}
@@ -634,38 +613,38 @@ BSP_uart_termios_isr_com1(void)
* if there is nothing more to send.
*/
- ret = rtems_termios_dequeue_characters(termios_ttyp_com1, 1);
+ ret = rtems_termios_dequeue_characters(termios_ttyp_com[uart], 1);
/* If nothing else to send disable interrupts */
- if(ret == 0 && uart_data[BSP_UART_COM1].hwFlow)
+ if(ret == 0 && uart_data[uart].hwFlow)
{
- uwrite(BSP_UART_COM1, IER,
+ uwrite(uart, IER,
(RECEIVE_ENABLE |
RECEIVER_LINE_ST_ENABLE |
MODEM_ENABLE
)
);
- termios_tx_active_com1 = 0;
+ termios_tx_active_com[uart] = 0;
}
else if(ret == 0)
{
- uwrite(BSP_UART_COM1, IER,
+ uwrite(uart, IER,
(RECEIVE_ENABLE |
RECEIVER_LINE_ST_ENABLE
)
);
- termios_tx_active_com1 = 0;
+ termios_tx_active_com[uart] = 0;
}
break;
case RECEIVER_DATA_AVAIL :
case CHARACTER_TIMEOUT_INDICATION:
/* RX data ready */
assert(off < sizeof(buf));
- buf[off++] = uread(BSP_UART_COM1, RBR);
+ buf[off++] = uread(uart, RBR);
break;
case RECEIVER_ERROR:
/* RX error: eat character */
- uartError(BSP_UART_COM1);
+ uartError(uart);
break;
default:
/* Should not happen */
@@ -676,103 +655,14 @@ BSP_uart_termios_isr_com1(void)
}
void
-BSP_uart_termios_isr_com2()
+BSP_uart_termios_isr_com1(void)
{
- unsigned char buf[40];
- unsigned char val;
- int off, ret, vect;
-
- off = 0;
-
- for(;;)
- {
- vect = uread(BSP_UART_COM2, IIR) & 0xf;
-
- switch(vect)
- {
- case MODEM_STATUS :
- val = uread(BSP_UART_COM2, MSR);
- if(uart_data[BSP_UART_COM2].hwFlow)
- {
- if(val & CTS)
- {
- /* CTS high */
- termios_stopped_com2 = 0;
- if(termios_tx_hold_valid_com2)
- {
- termios_tx_hold_valid_com2 = 0;
- BSP_uart_termios_write_com2(0, &termios_tx_hold_com2,
- 1);
- }
- }
- else
- {
- /* CTS low */
- termios_stopped_com2 = 1;
- }
- }
- break;
- case NO_MORE_INTR :
- /* No more interrupts */
- if(off != 0)
- {
- /* Update rx buffer */
- rtems_termios_enqueue_raw_characters(termios_ttyp_com2,
- (char *)buf,
- off);
- }
- return;
- case TRANSMITTER_HODING_REGISTER_EMPTY :
- /*
- * TX holding empty: we have to disable these interrupts
- * if there is nothing more to send.
- */
-
- ret = rtems_termios_dequeue_characters(termios_ttyp_com2, 1);
-
- /* If nothing else to send disable interrupts */
- if(ret == 0 && uart_data[BSP_UART_COM2].hwFlow)
- {
- uwrite(BSP_UART_COM2, IER,
- (RECEIVE_ENABLE |
- RECEIVER_LINE_ST_ENABLE |
- MODEM_ENABLE
- )
- );
- termios_tx_active_com2 = 0;
- }
- else if(ret == 0)
- {
- uwrite(BSP_UART_COM2, IER,
- (RECEIVE_ENABLE |
- RECEIVER_LINE_ST_ENABLE
- )
- );
- termios_tx_active_com2 = 0;
- }
- break;
- case RECEIVER_DATA_AVAIL :
- case CHARACTER_TIMEOUT_INDICATION:
- /* RX data ready */
- assert(off < sizeof(buf));
- buf[off++] = uread(BSP_UART_COM2, RBR);
- break;
- case RECEIVER_ERROR:
- /* RX error: eat character */
- uartError(BSP_UART_COM2);
- break;
- default:
- /* Should not happen */
- assert(0);
- return;
- }
- }
+ BSP_uart_termios_isr_com(BSP_UART_COM1);
}
-
-
-
-
-
-
+void
+BSP_uart_termios_isr_com2(void)
+{
+ BSP_uart_termios_isr_com(BSP_UART_COM2);
+}
diff --git a/c/src/lib/libbsp/powerpc/shared/console/uart.h b/c/src/lib/libbsp/powerpc/shared/console/uart.h
index e43ac9900c..6fe17d47e8 100644
--- a/c/src/lib/libbsp/powerpc/shared/console/uart.h
+++ b/c/src/lib/libbsp/powerpc/shared/console/uart.h
@@ -10,6 +10,8 @@
#ifndef _BSPUART_H
#define _BSPUART_H
+#include <bsp/irq.h>
+
void BSP_uart_init(int uart, int baud, int hwFlow);
void BSP_uart_set_baud(int aurt, int baud);
void BSP_uart_intr_ctrl(int uart, int cmd);
@@ -19,12 +21,14 @@ int BSP_uart_polled_status(int uart);
void BSP_uart_polled_write(int uart, int val);
int BSP_uart_polled_read(int uart);
void BSP_uart_termios_set(int uart, void *ttyp);
-int BSP_uart_termios_write_com1(int minor, const char *buf, int len);
-int BSP_uart_termios_write_com2(int minor, const char *buf, int len);
+int BSP_uart_termios_write_com(int minor, const char *buf, int len);
void BSP_uart_termios_isr_com1();
void BSP_uart_termios_isr_com2();
void BSP_uart_dbgisr_com1(void);
void BSP_uart_dbgisr_com2(void);
+int BSP_uart_install_isr(int uart, rtems_irq_hdl handler);
+int BSP_uart_remove_isr(int uart, rtems_irq_hdl handler);
+
extern unsigned BSP_poll_char_via_serial(void);
extern void BSP_output_char_via_serial(int val);
extern int BSPConsolePort;
@@ -50,13 +54,6 @@ extern int BSPBaseBaud;
#define BSP_UART_COM2 (1)
/*
- * Base IO for UART
- */
-
-#define COM1_BASE_IO 0x3F8
-#define COM2_BASE_IO 0x2F8
-
-/*
* Offsets from base
*/
diff --git a/c/src/lib/libbsp/powerpc/shared/include/bsp.h b/c/src/lib/libbsp/powerpc/shared/include/bsp.h
index 1f969ce9ef..b2062c3914 100644
--- a/c/src/lib/libbsp/powerpc/shared/include/bsp.h
+++ b/c/src/lib/libbsp/powerpc/shared/include/bsp.h
@@ -26,9 +26,33 @@
* - Interrupt stack space is not minimum if defined.
*/
-/* #define CONFIGURE_NUMBER_OF_TERMIOS_PORTS 2 */
+#define CONFIGURE_NUMBER_OF_TERMIOS_PORTS 2
#define CONFIGURE_INTERRUPT_STACK_MEMORY (16 * 1024)
+
+/* fundamental addresses for this BSP (PREPxxx are from libcpu/io.h) */
+#define _IO_BASE PREP_ISA_IO_BASE
+#define _ISA_MEM_BASE PREP_ISA_MEM_BASE
+/* address of our ram on the PCI bus */
+#define PCI_DRAM_OFFSET PREP_PCI_DRAM_OFFSET
+/* offset of pci memory as seen from the CPU */
+#define PCI_MEM_BASE PREP_ISA_MEM_BASE
+
+/*
+ * base address definitions for several devices
+ *
+ */
+#define BSP_UART_IOBASE_COM1 ((_IO_BASE)+0x3f8)
+#define BSP_UART_IOBASE_COM2 ((_IO_BASE)+0x2f8)
+#define BSP_KBD_IOBASE ((_IO_BASE)+0x60)
+#define BSP_VGA_IOBASE ((_IO_BASE)+0x3c0)
+
+#define BSP_CONSOLE_PORT BSP_UART_COM1
+#define BSP_UART_BAUD_BASE 115200
+#include <bsp/openpic.h>
+#define BSP_PIC_DO_EOI openpic_eoi(0)
+
+
#ifndef ASM
#define outport_byte(port,value) outb(value,port)
#define outport_word(port,value) outw(value,port)
diff --git a/c/src/lib/libbsp/powerpc/shared/irq/Makefile.am b/c/src/lib/libbsp/powerpc/shared/irq/Makefile.am
index 326ec19e19..b6d083eb53 100644
--- a/c/src/lib/libbsp/powerpc/shared/irq/Makefile.am
+++ b/c/src/lib/libbsp/powerpc/shared/irq/Makefile.am
@@ -21,6 +21,6 @@ PREINSTALL_FILES = $(PROJECT_INCLUDE)/bsp \
all-local: $(PREINSTALL_FILES)
-EXTRA_DIST = i8259.c irq.c irq.h irq_asm.S irq_init.c
+EXTRA_DIST = i8259.c irq.c irq_asm.S irq_init.c
include $(top_srcdir)/../../../../../automake/local.am
diff --git a/c/src/lib/libbsp/powerpc/shared/irq/irq.c b/c/src/lib/libbsp/powerpc/shared/irq/irq.c
index b2c97de842..939e8678dc 100644
--- a/c/src/lib/libbsp/powerpc/shared/irq/irq.c
+++ b/c/src/lib/libbsp/powerpc/shared/irq/irq.c
@@ -20,6 +20,7 @@
#include <libcpu/raw_exception.h>
#include <bsp/vectors.h>
+#include <rtems/bspIo.h> /* for printk */
#define RAVEN_INTR_ACK_REG 0xfeff0030
/*
@@ -124,6 +125,7 @@ int BSP_install_rtems_irq_handler (const rtems_irq_connect_data* irq)
unsigned int level;
if (!isValidInterrupt(irq->name)) {
+ printk("Invalid interrupt vector %i\n",irq->name);
return 0;
}
/*
@@ -134,6 +136,7 @@ int BSP_install_rtems_irq_handler (const rtems_irq_connect_data* irq)
* to get the previous handler before accepting to disconnect.
*/
if (rtems_hdl_tbl[irq->name].hdl != default_rtems_entry.hdl) {
+ printk("IRQ vector %i already connected\n",irq->name);
return 0;
}
_CPU_ISR_Disable(level);
@@ -372,7 +375,14 @@ void C_dispatch_irq_handler (CPU_Interrupt_frame *frame, unsigned int excNum)
outport_byte(PIC_SLAVE_IMR_IO_PORT, ((i8259s_cache & 0xff00) >> 8));
}
else {
- openpic_eoi(0);
+#ifdef BSP_PCI_VME_BRIDGE_DOES_EOI
+ /* leave it to the VME bridge to do EOI, so
+ * it can re-enable the openpic while handling
+ * VME interrupts (-> VME priorities in software)
+ */
+ if (BSP_PCI_VME_BRIDGE_IRQ!=irq)
+#endif
+ openpic_eoi(0);
}
}
diff --git a/c/src/lib/libbsp/powerpc/shared/irq/irq.h b/c/src/lib/libbsp/powerpc/shared/irq/irq.h
index aaf438c8dd..a356762e4f 100644
--- a/c/src/lib/libbsp/powerpc/shared/irq/irq.h
+++ b/c/src/lib/libbsp/powerpc/shared/irq/irq.h
@@ -87,12 +87,17 @@ typedef enum {
BSP_PROCESSOR_IRQ_NUMBER = 1,
BSP_PROCESSOR_IRQ_LOWEST_OFFSET = BSP_PCI_IRQ_MAX_OFFSET + 1,
BSP_PROCESSOR_IRQ_MAX_OFFSET = BSP_PROCESSOR_IRQ_LOWEST_OFFSET + BSP_PROCESSOR_IRQ_NUMBER - 1,
+ /* Misc vectors for OPENPIC irqs (IPI, timers)
+ */
+ BSP_MISC_IRQ_NUMBER = 8,
+ BSP_MISC_IRQ_LOWEST_OFFSET = BSP_PROCESSOR_IRQ_MAX_OFFSET + 1,
+ BSP_MISC_IRQ_MAX_OFFSET = BSP_MISC_IRQ_LOWEST_OFFSET + BSP_MISC_IRQ_NUMBER - 1,
/*
* Summary
*/
- BSP_IRQ_NUMBER = BSP_PROCESSOR_IRQ_MAX_OFFSET + 1,
+ BSP_IRQ_NUMBER = BSP_MISC_IRQ_MAX_OFFSET + 1,
BSP_LOWEST_OFFSET = BSP_ISA_IRQ_LOWEST_OFFSET,
- BSP_MAX_OFFSET = BSP_PROCESSOR_IRQ_MAX_OFFSET,
+ BSP_MAX_OFFSET = BSP_MISC_IRQ_MAX_OFFSET,
/*
* Some ISA IRQ symbolic name definition
*/
diff --git a/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c b/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c
index 00ad78b319..d3fb5aec59 100644
--- a/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c
+++ b/c/src/lib/libbsp/powerpc/shared/irq/irq_init.c
@@ -8,6 +8,9 @@
* Enhanced by Jay Kulpinski <jskulpin@eng01.gdds.com>
* to make it valid for MVME2300 Motorola boards.
*
+ * Till Straumann <strauman@slac.stanford.edu>, 12/20/2001:
+ * Use the new interface to openpic_init
+ *
* The license and distribution terms for this file may be
* found in the file LICENSE in this distribution or at
* http://www.OARcorp.com/rtems/license.html.
@@ -89,6 +92,11 @@ static rtems_irq_prio irqPrioTable[BSP_IRQ_NUMBER]={
0
};
+static unsigned char mcp750_openpic_initpolarities[16] = {
+ 1, /* 8259 cascade */
+ 0, /* all the rest of them */
+};
+
static unsigned char mcp750_openpic_initsenses[] = {
1, /* MCP750_INT_PCB(8259) */
0, /* MCP750_INT_FALCON_ECC_ERR */
@@ -226,12 +234,10 @@ void BSP_rtems_irq_mng_init(unsigned cpuId)
/*
* First initialize the Interrupt management hardware
*/
- OpenPIC_InitSenses = mcp750_openpic_initsenses;
- OpenPIC_NumInitSenses = sizeof(mcp750_openpic_initsenses) / sizeof(char);
#ifdef TRACE_IRQ_INIT
printk("Going to initialize raven interrupt controller (openpic compliant)\n");
#endif
- openpic_init(1);
+ openpic_init(1, mcp750_openpic_initsenses, mcp750_openpic_initpolarities);
#ifdef TRACE_IRQ_INIT
printk("Going to initialize the PCI/ISA bridge IRQ related setting (VIA 82C586)\n");
#endif
diff --git a/c/src/lib/libbsp/powerpc/shared/openpic/openpic.c b/c/src/lib/libbsp/powerpc/shared/openpic/openpic.c
index b27790a757..918ddfad10 100644
--- a/c/src/lib/libbsp/powerpc/shared/openpic/openpic.c
+++ b/c/src/lib/libbsp/powerpc/shared/openpic/openpic.c
@@ -26,15 +26,16 @@
#include <libcpu/io.h>
#include <libcpu/byteorder.h>
#include <bsp.h>
+#include <rtems/bspIo.h>
+#ifndef NULL
#define NULL 0
+#endif
#define REGISTER_DEBUG
#undef REGISTER_DEBUG
volatile struct OpenPIC *OpenPIC = NULL;
-unsigned int OpenPIC_NumInitSenses = 0;
-unsigned char *OpenPIC_InitSenses = NULL;
static unsigned int NumProcessors;
static unsigned int NumSources;
@@ -157,9 +158,13 @@ static void openpic_safe_writefield(volatile unsigned int *addr, unsigned int ma
* Add some kludge to use the Motorola Raven OpenPIC which does not
* report vendor and device id, and gets the wrong number of interrupts.
* (Motorola did a great job on that one!)
+ *
+ * T. Straumann, 12/20/2001: polarities and senses are now passed as
+ * parameters, eliminated global vars.
+ * IRQ0 is no longer treated specially.
*/
-void openpic_init(int main_pic)
+void openpic_init(int main_pic, unsigned char *polarities, unsigned char *senses)
{
unsigned int t, i;
unsigned int vendorid, devid, stepping, timerfreq;
@@ -250,10 +255,11 @@ void openpic_init(int main_pic)
openpic_initirq(0, 8, OPENPIC_VEC_SOURCE, 1, 1);
/* Processor 0 */
openpic_mapirq(0, 1<<0);
- for (i = 1; i < NumSources; i++) {
+ for (i = 0; i < NumSources; i++) {
/* Enabled, Priority 8 */
- openpic_initirq(i, 8, OPENPIC_VEC_SOURCE+i, 0,
- i < OpenPIC_NumInitSenses ? OpenPIC_InitSenses[i] : 1);
+ openpic_initirq(i, 8, OPENPIC_VEC_SOURCE+i,
+ polarities ? polarities[i] : 0,
+ senses ? senses[i] : 1);
/* Processor 0 */
openpic_mapirq(i, 1<<0);
}
diff --git a/c/src/lib/libbsp/powerpc/shared/openpic/openpic.h b/c/src/lib/libbsp/powerpc/shared/openpic/openpic.h
index 97faec1e9d..152636df82 100644
--- a/c/src/lib/libbsp/powerpc/shared/openpic/openpic.h
+++ b/c/src/lib/libbsp/powerpc/shared/openpic/openpic.h
@@ -191,8 +191,6 @@ struct OpenPIC {
};
extern volatile struct OpenPIC *OpenPIC;
-extern unsigned int OpenPIC_NumInitSenses;
-extern unsigned char *OpenPIC_InitSenses;
/*
@@ -309,7 +307,7 @@ extern unsigned char *OpenPIC_InitSenses;
*/
/* Global Operations */
-extern void openpic_init(int);
+extern void openpic_init(int,unsigned char *, unsigned char *);
extern void openpic_reset(void);
extern void openpic_enable_8259_pass_through(void);
extern void openpic_disable_8259_pass_through(void);
diff --git a/c/src/lib/libbsp/powerpc/shared/pci/Makefile.am b/c/src/lib/libbsp/powerpc/shared/pci/Makefile.am
index 4dc5a15453..e196f26c44 100644
--- a/c/src/lib/libbsp/powerpc/shared/pci/Makefile.am
+++ b/c/src/lib/libbsp/powerpc/shared/pci/Makefile.am
@@ -3,7 +3,7 @@
##
-C_FILES = pci.c
+C_FILES = pci.c detect_raven_bridge.c pcifinddevice.c
H_FILES = pci.h
@@ -18,6 +18,6 @@ PREINSTALL_FILES = $(PROJECT_INCLUDE)/bsp \
all-local: $(PREINSTALL_FILES)
-EXTRA_DIST = pci.c pci.h
+EXTRA_DIST = pci.c pci.h detect_raven_bridge.c pcifinddevice.c
include $(top_srcdir)/../../../../../automake/local.am
diff --git a/c/src/lib/libbsp/powerpc/shared/pci/pci.c b/c/src/lib/libbsp/powerpc/shared/pci/pci.c
index 233a2efc00..a6d615cea6 100644
--- a/c/src/lib/libbsp/powerpc/shared/pci/pci.c
+++ b/c/src/lib/libbsp/powerpc/shared/pci/pci.c
@@ -14,26 +14,27 @@
* http://www.OARcorp.com/rtems/license.html.
*
* $Id$
+ *
+ * Till Straumann, <strauman@slac.stanford.edu>, 1/2002
+ * - separated bridge detection code out of this file
*/
-#include <bsp/consoleIo.h>
#include <libcpu/io.h>
#include <bsp/pci.h>
-#include <bsp/residual.h>
-#include <bsp/openpic.h>
-#include <bsp.h>
+/* allow for overriding these definitions */
+#ifndef PCI_CONFIG_ADDR
#define PCI_CONFIG_ADDR 0xcf8
+#endif
+#ifndef PCI_CONFIG_DATA
#define PCI_CONFIG_DATA 0xcfc
+#endif
+
#define PCI_INVALID_VENDORDEVICEID 0xffffffff
#define PCI_MULTI_FUNCTION 0x80
-#define RAVEN_MPIC_IOSPACE_ENABLE 0x1
-#define RAVEN_MPIC_MEMSPACE_ENABLE 0x2
-#define RAVEN_MASTER_ENABLE 0x4
-#define RAVEN_PARITY_CHECK_ENABLE 0x40
-#define RAVEN_SYSTEM_ERROR_ENABLE 0x100
-#define RAVEN_CLEAR_EVENTS_MASK 0xf9000000
+/* define a shortcut */
+#define pci BSP_pci_configuration
/*
* Bit encode for PCI_CONFIG_HEADER_TYPE register
@@ -106,7 +107,7 @@ indirect_pci_write_config_dword(unsigned char bus, unsigned char slot,
return PCIBIOS_SUCCESSFUL;
}
-static const pci_config_access_functions indirect_functions = {
+const pci_config_access_functions pci_indirect_functions = {
indirect_pci_read_config_byte,
indirect_pci_read_config_word,
indirect_pci_read_config_dword,
@@ -115,9 +116,9 @@ static const pci_config_access_functions indirect_functions = {
indirect_pci_write_config_dword
};
-pci_config pci = {(volatile unsigned char*)PCI_CONFIG_ADDR,
+pci_config BSP_pci_configuration = {(volatile unsigned char*)PCI_CONFIG_ADDR,
(volatile unsigned char*)PCI_CONFIG_DATA,
- &indirect_functions};
+ &pci_indirect_functions};
static int
direct_pci_read_config_byte(unsigned char bus, unsigned char slot,
@@ -205,7 +206,7 @@ direct_pci_write_config_dword(unsigned char bus, unsigned char slot,
return PCIBIOS_SUCCESSFUL;
}
-static const pci_config_access_functions direct_functions = {
+const pci_config_access_functions pci_direct_functions = {
direct_pci_read_config_byte,
direct_pci_read_config_word,
direct_pci_read_config_dword,
@@ -215,99 +216,12 @@ static const pci_config_access_functions direct_functions = {
};
-void detect_host_bridge()
-{
- PPC_DEVICE *hostbridge;
- unsigned int id0;
- unsigned int tmp;
-
- /*
- * This code assumes that the host bridge is located at
- * bus 0, dev 0, func 0 AND that the old pre PCI 2.1
- * standart devices detection mecahnism that was used on PC
- * (still used in BSD source code) works.
- */
- hostbridge=residual_find_device(&residualCopy, PROCESSORDEVICE, NULL,
- BridgeController,
- PCIBridge, -1, 0);
- if (hostbridge) {
- if (hostbridge->DeviceId.Interface==PCIBridgeIndirect) {
- pci.pci_functions=&indirect_functions;
- /* Should be extracted from residual data,
- * indeed MPC106 in CHRP mode is different,
- * but we should not use residual data in
- * this case anyway.
- */
- pci.pci_config_addr = ((volatile unsigned char *)
- (ptr_mem_map->io_base+0xcf8));
- pci.pci_config_data = ptr_mem_map->io_base+0xcfc;
- } else if(hostbridge->DeviceId.Interface==PCIBridgeDirect) {
- pci.pci_functions=&direct_functions;
- pci.pci_config_data=(unsigned char *) 0x80800000;
- } else {
- }
- } else {
- /* Let us try by experimentation at our own risk! */
- pci.pci_functions = &direct_functions;
- /* On all direct bridges I know the host bridge itself
- * appears as device 0 function 0.
- */
- pci_read_config_dword(0, 0, 0, PCI_VENDOR_ID, &id0);
- if (id0==~0U) {
- pci.pci_functions = &indirect_functions;
- pci.pci_config_addr = ((volatile unsigned char*)
- (ptr_mem_map->io_base+0xcf8));
- pci.pci_config_data = ((volatile unsigned char*)ptr_mem_map->io_base+0xcfc);
- }
- /* Here we should check that the host bridge is actually
- * present, but if it not, we are in such a desperate
- * situation, that we probably can't even tell it.
- */
- }
- pci_read_config_dword(0, 0, 0, 0, &id0);
- if(id0 == PCI_VENDOR_ID_MOTOROLA +
- (PCI_DEVICE_ID_MOTOROLA_RAVEN<<16)) {
- /*
- * We have a Raven bridge. We will get information about its settings
- */
- pci_read_config_dword(0, 0, 0, PCI_COMMAND, &id0);
-#ifdef SHOW_RAVEN_SETTING
- printk("RAVEN PCI command register = %x\n",id0);
-#endif
- id0 |= RAVEN_CLEAR_EVENTS_MASK;
- pci_write_config_dword(0, 0, 0, PCI_COMMAND, id0);
- pci_read_config_dword(0, 0, 0, PCI_COMMAND, &id0);
-#ifdef SHOW_RAVEN_SETTING
- printk("After error clearing RAVEN PCI command register = %x\n",id0);
-#endif
-
- if (id0 & RAVEN_MPIC_IOSPACE_ENABLE) {
- pci_read_config_dword(0, 0, 0,PCI_BASE_ADDRESS_0, &tmp);
-#ifdef SHOW_RAVEN_SETTING
- printk("Raven MPIC is accessed via IO Space Access at address : %x\n",(tmp & ~0x1));
-#endif
- }
- if (id0 & RAVEN_MPIC_MEMSPACE_ENABLE) {
- pci_read_config_dword(0, 0, 0,PCI_BASE_ADDRESS_1, &tmp);
-#ifdef SHOW_RAVEN_SETTING
- printk("Raven MPIC is accessed via memory Space Access at address : %x\n", tmp);
-#endif
- OpenPIC=(volatile struct OpenPIC *) (tmp + PREP_ISA_MEM_BASE);
- printk("OpenPIC found at %p.\n",
- OpenPIC);
- }
- }
- if (OpenPIC == (volatile struct OpenPIC *)0) {
- BSP_panic("OpenPic Not found\n");
- }
-
-}
-
/*
* This routine determines the maximum bus number in the system
*/
void InitializePCI()
{
+ extern void detect_host_bridge();
unsigned char ucSlotNumber, ucFnNumber, ucNumFuncs;
unsigned char ucHeader;
unsigned char ucMaxSubordinate;
diff --git a/c/src/lib/libbsp/powerpc/shared/pci/pci.h b/c/src/lib/libbsp/powerpc/shared/pci/pci.h
index 2070bb434d..7327a6afbc 100644
--- a/c/src/lib/libbsp/powerpc/shared/pci/pci.h
+++ b/c/src/lib/libbsp/powerpc/shared/pci/pci.h
@@ -1082,7 +1082,10 @@
#define PCIBIOS_SET_FAILED 0x88
#define PCIBIOS_BUFFER_TOO_SMALL 0x89
-#define PCI_MAX_DEVICES 16
+/* T. Straumann, 7/31/2001: increased to 32 - PMC slots are not
+ * scanned on mvme2306 otherwise
+ */
+#define PCI_MAX_DEVICES 32
#define PCI_MAX_FUNCTIONS 8
typedef struct {
@@ -1103,45 +1106,45 @@ typedef struct {
typedef struct {
volatile unsigned char* pci_config_addr;
volatile unsigned char* pci_config_data;
- pci_config_access_functions* pci_functions;
+ const pci_config_access_functions* pci_functions;
} pci_config;
-extern pci_config pci;
+extern pci_config BSP_pci_configuration;
extern inline int
pci_read_config_byte(unsigned char bus, unsigned char slot, unsigned char function,
unsigned char where, unsigned char * val) {
- return pci.pci_functions->read_config_byte(bus, slot, function, where, val);
+ return BSP_pci_configuration.pci_functions->read_config_byte(bus, slot, function, where, val);
}
extern inline int
pci_read_config_word(unsigned char bus, unsigned char slot, unsigned char function,
unsigned char where, unsigned short * val) {
- return pci.pci_functions->read_config_word(bus, slot, function, where, val);
+ return BSP_pci_configuration.pci_functions->read_config_word(bus, slot, function, where, val);
}
extern inline int
pci_read_config_dword(unsigned char bus, unsigned char slot, unsigned char function,
unsigned char where, unsigned int * val) {
- return pci.pci_functions->read_config_dword(bus, slot, function, where, val);
+ return BSP_pci_configuration.pci_functions->read_config_dword(bus, slot, function, where, val);
}
extern inline int
pci_write_config_byte(unsigned char bus, unsigned char slot, unsigned char function,
unsigned char where, unsigned char val) {
- return pci.pci_functions->write_config_byte(bus, slot, function, where, val);
+ return BSP_pci_configuration.pci_functions->write_config_byte(bus, slot, function, where, val);
}
extern inline int
pci_write_config_word(unsigned char bus, unsigned char slot, unsigned char function,
unsigned char where, unsigned short val) {
- return pci.pci_functions->write_config_word(bus, slot, function, where, val);
+ return BSP_pci_configuration.pci_functions->write_config_word(bus, slot, function, where, val);
}
extern inline int
pci_write_config_dword(unsigned char bus, unsigned char slot, unsigned char function,
unsigned char where, unsigned int val) {
- return pci.pci_functions->write_config_dword(bus, slot, function, where, val);
+ return BSP_pci_configuration.pci_functions->write_config_dword(bus, slot, function, where, val);
}
/*
@@ -1150,4 +1153,14 @@ pci_write_config_dword(unsigned char bus, unsigned char slot, unsigned char func
extern unsigned char BusCountPCI();
extern void InitializePCI();
+/* scan for a specific device */
+/* find a particular PCI device
+ * (currently, only bus0 is scanned for device/fun0)
+ *
+ * RETURNS: zero on success, bus/dev/fun in *pbus / *pdev / *pfun
+ */
+int
+BSP_pciFindDevice(unsigned short vendorid, unsigned short deviceid,
+ int instance, int *pbus, int *pdev, int *pfun);
+
#endif /* RTEMS_PCI_H */
diff --git a/c/src/lib/libbsp/powerpc/shared/residual/Makefile.am b/c/src/lib/libbsp/powerpc/shared/residual/Makefile.am
index ad7f8f9a06..7fcb10f5ef 100644
--- a/c/src/lib/libbsp/powerpc/shared/residual/Makefile.am
+++ b/c/src/lib/libbsp/powerpc/shared/residual/Makefile.am
@@ -18,6 +18,6 @@ PREINSTALL_FILES = $(PROJECT_INCLUDE)/bsp \
all-local: $(PREINSTALL_FILES)
-EXTRA_DIST = pnp.h residual.c residual.h
+EXTRA_DIST = residual.c
include $(top_srcdir)/../../../../../automake/local.am
diff --git a/c/src/lib/libbsp/powerpc/shared/start/start.S b/c/src/lib/libbsp/powerpc/shared/start/start.S
index f2cedc9a6c..4746ab3a46 100644
--- a/c/src/lib/libbsp/powerpc/shared/start/start.S
+++ b/c/src/lib/libbsp/powerpc/shared/start/start.S
@@ -192,7 +192,7 @@ flush_tlbs:
lis r20, 0x1000
1: addic. r20, r20, -0x1000
tlbie r20
- blt 1b
+ bgt 1b
sync
blr
diff --git a/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c b/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c
index 04c6f48b8d..0c0ac29382 100644
--- a/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c
+++ b/c/src/lib/libbsp/powerpc/shared/startup/bspstart.c
@@ -200,6 +200,10 @@ void bsp_start( void )
* so that It can be printed without accessing R1.
*/
stack = ((unsigned char*) &__rtems_end) + INIT_STACK_SIZE - CPU_MINIMUM_STACK_FRAME_SIZE;
+
+ /* tag the bottom (T. Straumann 6/36/2001 <strauman@slac.stanford.edu>) */
+ *((unsigned32 *)stack) = 0;
+
/*
* Initialize the interrupt related settings
* SPRG0 = interrupt nesting level count
@@ -209,6 +213,10 @@ void bsp_start( void )
* some settings below...
*/
intrStack = ((unsigned char*) &__rtems_end) + INIT_STACK_SIZE + INTR_STACK_SIZE - CPU_MINIMUM_STACK_FRAME_SIZE;
+
+ /* tag the bottom (T. Straumann 6/36/2001 <strauman@slac.stanford.edu>) */
+ *((unsigned32 *)intrStack) = 0;
+
asm volatile ("mtspr 273, %0" : "=r" (intrStack) : "0" (intrStack));
asm volatile ("mtspr 272, %0" : "=r" (intrNestingLevel) : "0" (intrNestingLevel));
/*
@@ -228,7 +236,8 @@ void bsp_start( void )
* PCI devices memory area. Needed to access OPENPIC features
* provided by the RAVEN
*/
- setdbat(2, 0xc0000000, 0xc0000000, 0x08000000, IO_PAGE);
+ /* T. Straumann: give more PCI address space */
+ setdbat(2, 0xc0000000, 0xc0000000, 0x10000000, IO_PAGE);
/*
* Must have acces to open pic PCI ACK registers
* provided by the RAVEN
diff --git a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S
index d33f8549fb..692c1259c2 100644
--- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S
+++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.S
@@ -85,6 +85,10 @@ SYM (push_normalized_frame):
stw r30, EXC_CTR_OFFSET(r1)
mfxer r28
stw r28, EXC_XER_OFFSET(r1)
+ mfmsr r28
+ stw r28, EXC_MSR_OFFSET(r1)
+ mfdar r28
+ stw r28, EXC_DAR_OFFSET(r1)
/*
* compute SP at exception entry
*/
diff --git a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h
index 101f46f121..15eb7b6bfa 100644
--- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h
+++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors.h
@@ -60,7 +60,8 @@
#define EXC_CTR_OFFSET 152
#define EXC_XER_OFFSET 156
#define EXC_LR_OFFSET 160
-#define EXC_DAR_OFFSET 164
+#define EXC_MSR_OFFSET 164
+#define EXC_DAR_OFFSET 168
/*
* maintain the EABI requested 8 bytes aligment
* As SVR4 ABI requires 16, make it 16 (as some
diff --git a/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c b/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c
index 9a339250e2..40b360e461 100644
--- a/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c
+++ b/c/src/lib/libbsp/powerpc/shared/vectors/vectors_init.c
@@ -23,6 +23,38 @@ static rtems_raw_except_connect_data exception_table[LAST_VALID_EXC + 1];
exception_handler_t globalExceptHdl;
+/* T. Straumann: provide a stack trace
+ * <strauman@slac.stanford.edu>, 6/26/2001
+ */
+typedef struct LRFrameRec_ {
+ struct LRFrameRec_ *frameLink;
+ unsigned long *lr;
+} LRFrameRec, *LRFrame;
+
+#define STACK_CLAMP 50 /* in case we have a corrupted bottom */
+
+void
+BSP_printStackTrace(BSP_Exception_frame* excPtr)
+{
+LRFrame f;
+int i;
+
+ printk("Stack Trace: ");
+ printk(" IP: 0x%08x, LR: 0x%08x\n",
+ excPtr->EXC_SRR0, excPtr->EXC_LR);
+ for (f=(LRFrame)excPtr->GPR1, i=0; f->frameLink && i<STACK_CLAMP; f=f->frameLink) {
+ printk("--^ 0x%08x", (long)(f->frameLink->lr));
+ if (!(++i%5))
+ printk("\n");
+ }
+ if (i>=STACK_CLAMP) {
+ printk("Too many stack frames (stack possibly corrupted), giving up...\n");
+ } else {
+ if (i%5)
+ printk("\n");
+ }
+}
+
void C_exception_handler(BSP_Exception_frame* excPtr)
{
int recoverable = 0;
@@ -66,7 +98,10 @@ void C_exception_handler(BSP_Exception_frame* excPtr)
printk("\t CTR = %x\n", excPtr->EXC_CTR);
printk("\t XER = %x\n", excPtr->EXC_XER);
printk("\t LR = %x\n", excPtr->EXC_LR);
- printk("\t MSR = %x\n", excPtr->EXC_MSR);
+ printk("\t DAR = %x\n", excPtr->EXC_DAR);
+
+ BSP_printStackTrace(excPtr);
+
if (excPtr->_EXC_number == ASM_DEC_VECTOR)
recoverable = 1;
if (excPtr->_EXC_number == ASM_SYS_VECTOR)