- imported MVME3100 BSP (from SLAC repository)

This commit is contained in:
Till Straumann
2007-12-14 06:30:15 +00:00
commit b599faa1bb
25 changed files with 6293 additions and 0 deletions

View File

@@ -0,0 +1,8 @@
Makefile
Makefile.in
aclocal.m4
autom4te.cache
config.cache
config.log
config.status
configure

View File

@@ -0,0 +1 @@

View File

@@ -0,0 +1,77 @@
I have observed what seem to be strange
initialization problems with the ethernet
driver:
I usually configure RTEMS networking by
BOOTP (the problem has nothing to do with
BOOTP but I just want to describe my
environment). Sometimes (it can actually
happen quite frequently, like 1 out of 4
attempts but since yesterday when I decided
to hunt this down more systematically
the problem seems to have gone - typical!)
networking fails to initialize properly:
BOOTP requests are sent (to the MAC),
TX interrupts occur and the TX MIB
counters increment - i.e., everything
seems normal but no data can be seen on
the wire. Also, even though we are on
a quite busy network, the receiver
doesn't see anything, i.e., 0 RX
interrupts, RX MIB counters for broadcast
packets remain steady at zero etc.
In brief, everyting seems normal at the
MAC and higher layers but no connection
to the wire seems to be established.
Some further tests reveal (system under
test is in the 'bad' state):
1 communication with the BCM5461 PHY
is normal. Registers can be read/written
and everything seems normal. In particular,
the link status is reported OK: disconnect
the cable and MII - BMSR bit 1<<2 is clear,
reconnect the cable and BMSR[2] is set.
Restart autoneg, the link goes and comes
back after a short while.
2 setting the loopback bit in the TSEC's
MACCFG1 register correctly feeds packets
back into the RX, RX MIB counters now
increment and indicate data flow.
There are RX interrupts and all indicates
(I haven't actually looked at RX packet
data) that the RX would work normally.
After switching MACCFG1[LOOP_BACK] off
no RX traffic can be seen anymore.
3 resetting the PHY (BMCR = 0x8000) and/or
restarting autoneg (BMCR = 0x1200) seems
to perform the desired action (registers
take on expected values) but still no luck
with communication all the way through
to the wire.
Especially point 2 seems to indicate that
the problem is likely to be between the
wire and the MAC somewhere but re-setting
the PHY doesn't change things. Analysis is
much complicated by the fact that there
is no documentation on the BCM5461 chip
available.
Noteworthy is also that if the system
initializes OK then it continues to work
normally; if initialization fails then
only resetting the board and restarting
helps.
I wanted to test if it makes a difference
if MotLoad used the chip prior to RTEMS
being booted (in case MotLoad did some
magic step during initialization) but
before I could really test this the
problem went away.
Big Mystery...
12/12/2007, T.S.

View File

@@ -0,0 +1,49 @@
/* NOTE: The terms described in this LICENSE file apply only to the
* files created by the author (see below). Consult individual
* file headers for more details.
*/
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was
* created by Till Straumann <strauman@slac.stanford.edu>, 2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/

View File

@@ -0,0 +1,184 @@
##
## $Id$
##
ACLOCAL_AMFLAGS = -I ../../../../aclocal
# wrapup is the one that actually builds and installs the library
# from the individual .rel files built in other directories
SUBDIRS = .
include $(top_srcdir)/../../../../automake/compile.am
include $(top_srcdir)/../../bsp.am
dist_project_lib_DATA = bsp_specs
include_HEADERS = include/bsp.h
nodist_include_HEADERS = include/bspopts.h
DISTCLEANFILES = include/bspopts.h
noinst_PROGRAMS =
include_bspdir = $(includedir)/bsp
include_HEADERS += ../../shared/include/coverhd.h
include_HEADERS += ../../shared/tod.h
project_lib_DATA =
EXTRA_DIST = ./start/start.S
start.$(OBJEXT): ./start/start.S
$(CPPASCOMPILE) -o $@ -c $<
EXTRA_DIST += ../beatnik/start/ssrl/preload.S
preload.$(OBJEXT): ../beatnik/start/ssrl/preload.S
$(CPPASCOMPILE) -DASM -o $@ -c $<
motld_start.$(OBJEXT): preload.$(OBJEXT) start.$(OBJEXT)
$(LD) -o $@ -r $^
project_lib_DATA += motld_start.$(OBJEXT)
EXTRA_DIST += ../../powerpc/shared/start/rtems_crti.S
rtems_crti.$(OBJEXT): ../../powerpc/shared/start/rtems_crti.S
$(CPPASCOMPILE) -o $@ -c $<
project_lib_DATA += rtems_crti.$(OBJEXT)
dist_project_lib_DATA += ../shared/startup/linkcmds
build_date.c::
echo 'const char *BSP_build_date="'`date`'";' > $@
noinst_PROGRAMS += startup.rel
startup_rel_SOURCES = ./startup/bspstart.c build_date.c \
./startup/misc.c \
../../powerpc/shared/startup/pretaskinghook.c \
../../powerpc/shared/startup/zerobss.c \
../../powerpc/shared/startup/sbrk.c ../../shared/bootcard.c \
../../shared/bspclean.c ../../shared/bsplibc.c ../../shared/bsppost.c \
../../shared/gnatinstallhandler.c
startup_rel_CPPFLAGS = $(AM_CPPFLAGS)
startup_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
noinst_PROGRAMS += tod.rel
tod_rel_SOURCES = ../../shared/tod.c tod/todcfg.c
tod_rel_CPPFLAGS = $(AM_CPPFLAGS)
tod_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
noinst_PROGRAMS += pclock.rel
pclock_rel_SOURCES = ../../powerpc/shared/clock/p_clock.c
pclock_rel_CPPFLAGS = $(AM_CPPFLAGS)
pclock_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS = ../../powerpc/shared/console/uart.h
noinst_PROGRAMS += console.rel
console_rel_SOURCES = ../../powerpc/shared/console/uart.c \
../../powerpc/shared/console/console.c \
../../powerpc/shared/console/consoleIo.h \
../../powerpc/shared/console/uart.h
console_rel_CPPFLAGS = $(AM_CPPFLAGS) $(console_CPPFLAGS)
console_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += ./irq/irq.h
noinst_PROGRAMS += irq.rel
irq_rel_SOURCES = ./irq/irq_init.c ../../powerpc/shared/irq/openpic_i8259_irq.c \
../../powerpc/shared/irq/irq.h
irq_rel_CPPFLAGS = $(AM_CPPFLAGS)
irq_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += ../../powerpc/shared/openpic/openpic.h
noinst_PROGRAMS += openpic.rel
openpic_rel_SOURCES = ../../powerpc/shared/openpic/openpic.h \
../../powerpc/shared/openpic/openpic.c \
../../powerpc/shared/openpic/openpic.h
openpic_rel_CPPFLAGS = $(AM_CPPFLAGS)
openpic_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += ../../powerpc/shared/pci/pci.h
noinst_PROGRAMS += pci.rel
pci_rel_SOURCES = ../../powerpc/shared/pci/pci.c \
./pci/detect_host_bridge.c \
../../powerpc/shared/pci/generic_clear_hberrs.c \
../../powerpc/shared/pci/pcifinddevice.c ../../powerpc/shared/pci/pci.h
pci_rel_CPPFLAGS = $(AM_CPPFLAGS)
pci_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/vectors.h
include_bsp_HEADERS += ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/ppc_exc_bspsupp.h
include_bsp_HEADERS += ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/irq_supp.h
include_bsp_HEADERS += ./vme/VMEConfig.h \
../../shared/vmeUniverse/vmeTsi148.h \
../../shared/vmeUniverse/vme_am_defs.h \
../../shared/vmeUniverse/VME.h \
../../shared/vmeUniverse/vmeTsi148DMA.h\
../../shared/vmeUniverse/bspVmeDmaList.h\
../../shared/vmeUniverse/VMEDMA.h
noinst_PROGRAMS += vme.rel
vme_rel_SOURCES = ../../shared/vmeUniverse/vmeTsi148.c \
../../shared/vmeUniverse/bspVmeDmaList.c \
../../shared/vmeUniverse/vmeTsi148.h \
../../shared/vmeUniverse/vme_am_defs.h \
../../shared/vmeUniverse/VME.h \
../../powerpc/shared/vme/vmeconfig.c \
../../powerpc/shared/vme/vme_universe.c
vme_rel_CPPFLAGS = $(AM_CPPFLAGS)
vme_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += ../shared/flash/flashPgm.h \
../shared/flash/flashPgmPvt.h
noinst_PROGRAMS += flash.rel
flash_rel_SOURCES = ../shared/flash/flash.c \
../shared/flash/spansionFlash.c \
./flash/flashcfg.c
flash_rel_CPPFLAGS = $(AM_CPPFLAGS)
flash_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += i2c/mpc8540_i2c_busdrv.h
noinst_PROGRAMS += i2c.rel
i2c_rel_SOURCES = i2c/mpc8540_i2c.c i2c/i2c_init.c
i2c_rel_CPPFLAGS = $(AM_CPPFLAGS)
i2c_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += ../shared/motorola/vpd.h
noinst_PROGRAMS += vpd.rel
vpd_rel_SOURCES = ../shared/motorola/vpd.c
vpd_rel_CPPFLAGS = $(AM_CPPFLAGS)
vpd_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
include_bsp_HEADERS += network/if_tsec_pub.h
noinst_PROGRAMS += network.rel
network_rel_SOURCES = network/tsec.c
network_rel_CPPFLAGS = $(AM_CPPFLAGS)
network_rel_LDFLAGS = $(RTEMS_RELLDFLAGS)
noinst_LIBRARIES = libbsp.a
libbsp_a_SOURCES =
libbsp_a_LIBADD = startup.rel pclock.rel console.rel openpic.rel \
pci.rel irq.rel i2c.rel tod.rel vpd.rel network.rel vme.rel flash.rel
libbsp_a_LIBADD += ../../../libcpu/@RTEMS_CPU@/shared/cpuIdent.rel \
../../../libcpu/@RTEMS_CPU@/shared/stack.rel \
../../../libcpu/@RTEMS_CPU@/e500/clock.rel \
../../../libcpu/@RTEMS_CPU@/e500/timer.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/rtems-cpu.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/raw_exception.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/exc_bspsupport.rel \
../../../libcpu/@RTEMS_CPU@/@exceptions@/irq_bspsupport.rel
EXTRA_DIST += LICENSE ChangeLog README KNOWN_PROBLEMS
include $(srcdir)/preinstall.am
include $(top_srcdir)/../../../../automake/local.am

View File

@@ -0,0 +1,129 @@
Some information about this BSP
================================
ACKNOWLEDGEMENTS
----------------
Acknowledgements:
Valuable information was obtained from the following drivers
linux: (BCM54xx) Maciej W. Rozycki, Amy Fong.
This BSP also builds on top of the work of others who have contributed
to similar RTEMS (powerpc) BSPs, most notably Eric Valette, Eric Norum
and others.
This BSP was produced by the Stanford Linear Accelerator Center,
Stanford University under contract with the US Department of Energy.
LICENSE
-------
See ./LICENSE file.
Note that not all files that are part of this BSP were written by
myself. Consult individual file headers for copyright
and authorship information.
HARDWARE SUPPORT
===============
(some of the headers mentioned below contain more
detailed information)
NOTE: The BSP supports the mvme3100 board.
CONSOLE: 2 serial devices, UART driver from 'shared' - no surprises
("/dev/ttyS0", [="/dev/console"], "/dev/ttyS1"). (Only
/dev/ttyS0 is accessible from the front panel.)
CLOCK: Decrementer, same as other PPC BSPs. (FIXME: a openpic timer
could be used.) The bookE decrementer is slightly different
from the classic PPC decrementer but the differences are
hidden from the user.
PIC (interrupt controller) (bsp/irq.h): OpenPIC integrated with
the MPC8540. (see also: bsp/openpic.h).
PCI (bsp/pci.h):
In addition to rtems' PCI API, a call is available to scan
all devices executing a user callback on each device.
BSP_pciConfigDump() is a convenience wrapper dumping essential
information (IDs, BAs, IRQ pin/line) to the console or a file.
MEMORY MAP: MotLoad; all addresses (MEM + I/O) read from PCI config. space
are CPU addresses. For sake of portability, drivers should still
use the _IO_BASE, PCI_MEM_BASE, PCI_DRAM_OFFSET constants.
NVRAM: No NVRAM.
FLASH (bsp/flashPgm.h): Routines to write flash. Highest level
wrapper writes a file to flash.
NOTE: Writing to flash is disabled by default;
call BSP_flashWriteEnable().
I2C (bsp.h, rtems/libi2c.h, libchip/i2c-xxx.h): temp. sensor, eeprom
and real-time clock (RTC) are available as device files (bsp.h);
lower-level interface is provided by libi2c.h.
Available i2c devices are:
/dev/i2c0.vpd-eeprom
/dev/i2c0.usr-eeprom
/dev/i2c0.usr1-eeprom
/dev/i2c0.ds1621
/dev/i2c0.ds1621-raw
/dev/i2c0.ds1375-raw
You can e.g., read the board temperature:
fd = open("/dev/i2c0.ds1621",O_RDONLY)
read(fd,&temp,1)
close(fd);
printf("Board Temp. is %idegC\n",(int)temp);
VME: (bsp/VME.h, bsp/vme_am_defs.h, bsp/VMEDMA.h).
*always* use VME.h API, if possible; do *not* use chip driver
(vmeTsi148.h) directly unless you know what you are
doing (i.e., if you need specific features provided by the particular
chip)
VMEConfig.h should not be used by applications as it makes them
dependent on BSP internals. VMEConfig.h is intended to be used
by BSP designers only.
VME interrupt priorities: the VME bridge(s) do not implement
priorities in hardware.
However, on the 3100 multiple physical interrupt
lines/wires connect the VME bridge to the PIC. Hence, it is possible
to assign the different wires different priorities at the PIC
(see bsp/openpic.h) and to route VME interrupts to different
wires according to their priority.
You need to call driver specific routines
for this (vmeXXXIntRoute()), however (for driver-specific API
consult bsp/vmeTsi148.h).
For VME DMA *always* use the bsp/VMEDMA.h API. DO NOT use
chip-specific features. Applications written using the bsp/VMEDMA.h
API are portable between the UniverseII and the Tsi148.
HARDWARE TIMERS: (bsp/openpic.h). Programmable general-purpose
timers. Routines are provided to setup, start and stop
GPTs. The setup routine allows for specifying single-shot or periodic
mode and dispatches a user ISR when the GPT expires.
NETWORK: (bsp/if_tsec_pub.h). In addition to the standard bsdnet
'attach' function the driver offers a low-level API that
can be used to implement alternate communication links
which are totally decoupled from BSDNET.
Consult 'KNOWN_PROBLEMS'.
VPD: (bsp/vpd.h). The board's VPD (vital-product-data such as S/N,
MAC addresses and so forth) can be retrieved.
BOOTING: BSP has a relocator-header. Clear MSR and jump to the first
instruction in the binary. R3 and R4, if non-null, point to the
start/end of an optional command line string that is copied into
BSP_commandline_string. The BSP is compatible with 'netboot'.
Have fun.
-- Till Straumann <strauman@slac.stanford.edu>, 2007.

View File

@@ -0,0 +1,15 @@
%rename endfile old_endfile
%rename startfile old_startfile
%rename link old_link
*startfile:
%{!qrtems: %(old_startfile)} \
%{!nostdlib: %{qrtems: ecrti%O%s rtems_crti%O%s crtbegin.o%s \
%{!qrtems_debug: motld_start.o%s} \
%{qrtems_debug: motld_start_g.o%s}}}
*link:
%{!qrtems: %(old_link)} %{qrtems: -Qy -dp -Bstatic -e __rtems_entry_point -u __vectors}
*endfile:
%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s ecrtn.o%s}

View File

@@ -0,0 +1,43 @@
## Process this file with autoconf to produce a configure script.
##
## $Id$
AC_PREREQ(2.60)
AC_INIT([rtems-c-src-lib-libbsp-powerpc-mvme3100],[_RTEMS_VERSION],[http://www.rtems.org/bugzilla])
AC_CONFIG_SRCDIR([bsp_specs])
RTEMS_TOP(../../../../../..)
RTEMS_CANONICAL_TARGET_CPU
AM_INIT_AUTOMAKE([no-define nostdinc foreign 1.10])
RTEMS_BSP_CONFIGURE
RTEMS_PROG_CC_FOR_TARGET([-ansi -fasm])
RTEMS_CANONICALIZE_TOOLS
RTEMS_CHECK_TOOL(NM,nm,no)
RTEMS_PROG_CCAS
RTEMS_CHECK_NETWORKING
AM_CONDITIONAL(HAS_NETWORKING,test "$HAS_NETWORKING" = "yes")
AS=$CC
AM_PROG_AS
dnl AC_PATH_PROG([AMPOLISH3],[ampolish3],[])
dnl AM_CONDITIONAL([AMPOLISH3],[test x"$USE_MAINTAINER_MODE" = x"yes" \
dnl && test -n "$AMPOLISH3"])
RTEMS_BSPOPTS_SET([PPC_USE_DATA_CACHE],[*],[1])
RTEMS_BSPOPTS_HELP([PPC_USE_DATA_CACHE],
[If defined, then the PowerPC specific code in RTEMS will use
data cache instructions to optimize the context switch code.
This code can conflict with debuggers or emulators. It is known
to break the Corelis PowerPC emulator with at least some combinations
of PowerPC 603e revisions and emulator versions.
The BSP actually contains the call that enables this.])
# Explicitly list all Makefiles here
AC_CONFIG_FILES([Makefile])
RTEMS_PPC_EXCEPTIONS
AC_OUTPUT

View File

@@ -0,0 +1,118 @@
/* $Id$ */
/* BSP-specific bits of flash programmer support */
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was created by
*
* Till Straumann <strauman@slac.stanford.edu>, 2005-2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
#include <rtems.h>
#include <bsp.h>
#include <libcpu/spr.h>
#include <stdio.h>
#include <bsp/flashPgmPvt.h>
SPR_RO(TBRL)
#define STATIC static
static struct bankdesc mvme3100Flash[] = {
/*
* Bank is populated from the top; make max_size negative to
* indicate this
*/
{ 0xf8000000, 0, - 0x08000000, 2, BSP_flash_vendor_spansion, 0, 0, 0 },
};
STATIC struct bankdesc *
bankcheck(int bank, int quiet)
{
if ( bank ) {
if ( !quiet )
fprintf(stderr,"Invalid flash bank #%i\n",bank);
return 0;
}
return &mvme3100Flash[bank];
}
STATIC int
flash_wp(int bank, int enbl)
{
uint8_t mask = enbl < 0 ? 0 : BSP_MVME3100_FLASH_CSR_F_WP_SW;
uint8_t val;
if ( bank != 0 ) {
fprintf(stderr,"Invalid flash bank #%i\n",bank);
return -1;
}
if ( enbl )
val = BSP_setSysReg( BSP_MVME3100_FLASH_CSR, mask );
else
val = BSP_clrSysReg( BSP_MVME3100_FLASH_CSR, mask );
if ( BSP_MVME3100_FLASH_CSR_F_WP_HW & val ) {
fprintf(stderr,"Flash: hardware write-protection engaged (switch)\n");
return -1;
}
if ( enbl < 0 )
return val & (BSP_MVME3100_FLASH_CSR_F_WP_HW | BSP_MVME3100_FLASH_CSR_F_WP_SW );
return 0;
}
STATIC uint32_t
read_us_timer()
{
uint32_t mhz = BSP_bus_frequency/BSP_time_base_divisor/1000;
return _read_TBRL()/mhz;
}
/* BSP ops (detect banks, handle write-protection on board) */
struct flash_bsp_ops BSP_flashBspOps = {
bankcheck: bankcheck,
flash_wp: flash_wp,
read_us_timer: read_us_timer,
};

View File

@@ -0,0 +1,187 @@
/* $Id$ */
/* Register i2c bus driver & devices */
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was created by
*
* Till Straumann <strauman@slac.stanford.edu>, 2005-2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
#include <rtems.h>
#include <bsp.h>
#include <rtems/bspIo.h>
#include <rtems/libi2c.h>
#include <libchip/i2c-2b-eeprom.h>
#include <libchip/i2c-ds1621.h>
#include <bsp/mpc8540_i2c_busdrv.h>
#include <rtems/libio.h>
#include <stdio.h>
#include <sys/stat.h>
#include <sys/errno.h>
#include <stdarg.h>
static void
safe_printf (const char *fmt, ...)
{
va_list ap;
va_start(ap, fmt);
if ( _System_state_Is_up( _System_state_Get() ) )
vfprintf( stderr, fmt, ap );
else
vprintk( fmt, ap );
va_end(ap);
}
static void
safe_perror(const char *s)
{
safe_printf("%s :%s\n", s, strerror(errno));
}
int
BSP_i2c_initialize()
{
int busno, succ = 0;
/* Initialize the library */
if ( rtems_libi2c_initialize() ) {
safe_printf("Initializing I2C library failed\n");
return -1;
}
/* Register our bus driver */
if ( (busno=rtems_libi2c_register_bus(
BSP_I2C_BUS0_NAME,
BSP_I2C_BUS_DESCRIPTOR) ) < 0 ) {
safe_perror("Registering mpc8540 i2c bus driver");
return -1;
}
/* Now register higher level drivers; note that
* the i2c address in the manual is actually left-shifted
* by one bit, i.e., as it would go on the bus.
*/
/* Use read-only driver for VPD */
if ( rtems_libi2c_register_drv(
BSP_I2C_VPD_EEPROM_NAME,
i2c_2b_eeprom_ro_driver_descriptor,
busno,
BSP_VPD_I2C_ADDR) < 0 ) {
safe_perror("Registering i2c VPD eeprom driver failed");
} else {
succ++;
}
/* Use read-write driver for user eeprom -- you still might
* have to disable HW write-protection on your board.
*/
if ( rtems_libi2c_register_drv(
BSP_I2C_USR_EEPROM_NAME,
i2c_2b_eeprom_driver_descriptor,
busno,
BSP_USR0_I2C_ADDR) < 0 ) {
safe_perror("Registering i2c 1st USR eeprom driver failed");
} else {
succ++;
}
/* Use read-write driver for user eeprom -- you still might
* have to disable HW write-protection on your board.
*/
if ( rtems_libi2c_register_drv(
BSP_I2C_USR1_EEPROM_NAME,
i2c_2b_eeprom_driver_descriptor,
busno,
BSP_USR1_I2C_ADDR) < 0 ) {
safe_perror("Registering i2c 2nd USR eeprom driver failed");
} else {
succ++;
}
/* The thermostat */
if ( rtems_libi2c_register_drv(
BSP_I2C_DS1621_NAME,
i2c_ds1621_driver_descriptor,
busno,
BSP_THM_I2C_ADDR) < 0 ) {
safe_perror("Registering i2c ds1621 temp sensor. driver failed");
} else {
succ++;
}
/* Finally, as an example, register raw access to the
* ds1621. The driver above just reads the 8 msb of the
* temperature but doesn't support anything else. Using
* the raw device node you can write/read individual
* control bytes yourself and e.g., program the thermostat...
*/
if ( mknod(
BSP_I2C_DS1621_RAW_DEV_NAME,
0666 | S_IFCHR,
rtems_filesystem_make_dev_t(rtems_libi2c_major,
RTEMS_LIBI2C_MAKE_MINOR(busno,BSP_THM_I2C_ADDR))) ) {
safe_perror("Creating device node for raw ds1621 (temp. sensor) access failed");
} else {
succ++;
}
/* Raw access to RTC */
if ( mknod(
BSP_I2C_DS1375_RAW_DEV_NAME,
0666 | S_IFCHR,
rtems_filesystem_make_dev_t(rtems_libi2c_major,
RTEMS_LIBI2C_MAKE_MINOR(busno,BSP_RTC_I2C_ADDR))) ) {
safe_perror("Creating device node for raw ds1375 (rtc) access failed");
} else {
succ++;
}
safe_printf("%i I2C devices registered\n", succ);
return 0;
}

View File

@@ -0,0 +1,452 @@
/* I2C bus driver for mpc8540-based boards */
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was created by
*
* Till Straumann <strauman@slac.stanford.edu>, 2005-2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
/* Note: We maintain base address, IRQ etc. statically and
* globally. We don't bother creating driver-specific
* data or using the bus handle but simply assume
* this is the only 8540/i2c bus in the system.
* Proper support for multiple instances would not
* be very hard to add but I don't see the point...
*/
#include <rtems.h>
#include <bsp.h>
#include <rtems/libi2c.h>
#include <bsp/irq.h>
#include <libcpu/spr.h>
#include <libcpu/io.h>
#include <rtems/bspIo.h>
#include "mpc8540_i2c_busdrv.h"
#define STATIC
/* I2C controller register definitions */
#define I2CADR 0x3000
#define I2CFDR 0x3004
#define I2CCR 0x3008
#define I2CCR_MEN (1<<(7-0))
#define I2CCR_MIEN (1<<(7-1))
#define I2CCR_MSTA (1<<(7-2))
#define I2CCR_MTX (1<<(7-3))
#define I2CCR_TXAK (1<<(7-4))
#define I2CCR_RSTA (1<<(7-5))
#define I2CCR_BCST (1<<(7-7))
#define I2CSR 0x300c
#define I2CSR_MCF (1<<(7-0))
#define I2CSR_MAAS (1<<(7-1))
#define I2CSR_MBB (1<<(7-2))
#define I2CSR_MAL (1<<(7-3))
#define I2CSR_BCSTM (1<<(7-4))
#define I2CSR_SRW (1<<(7-5))
#define I2CSR_MIF (1<<(7-6))
#define I2CSR_RXAK (1<<(7-7))
#define I2CDR 0x3010
#define I2CDFSRR 0x3014
SPR_RO(TBRL)
/********* Global Variables **********/
/*
* Semaphore for synchronizing accessing task
* with the (slow) hardware operation.
* Task takes semaphore and blocks, ISR releases.
*/
static rtems_id syncsem = 0;
static inline int ok_to_block()
{
return syncsem && _System_state_Is_up( _System_state_Get() );
}
/*
* Wild guess for 0.2 s; this timeout is effective
* in polling mode; during early init we don't know
* the system clock rate yet - it's one of the things
* we have to read from VPD -- via i2c.
*/
static uint32_t poll_timeout = 333333333/8/5;
/********* Primitives ****************/
static inline uint8_t
i2c_rd(unsigned reg)
{
return in_8( (volatile uint8_t *)(BSP_8540_CCSR_BASE + reg) );
}
static inline void
i2c_wr(unsigned reg, uint8_t val)
{
out_8( (volatile uint8_t *)(BSP_8540_CCSR_BASE + reg), val );
}
static inline void
i2c_set(unsigned reg, uint8_t val)
{
i2c_wr( reg, i2c_rd( reg ) | val );
}
static inline void
i2c_clr(unsigned reg, uint8_t val)
{
i2c_wr( reg, i2c_rd( reg ) & ~val );
}
/********* Helper Routines ***********/
/* Synchronize (wait) for a condition on the
* i2c bus. Wait for START or STOP to be complete
* or wait for a byte-transfer.
* The latter is much slower (9 bit times vs. 1/2
* in the former cases).
*
* If the system is up (and we may block) then
* this routine attempts to block the current
* task rather than busy-waiting.
*
* NOTE: waiting for START/STOP always requires
* polling.
*/
/* wait until i2c status reg AND mask == cond */
static rtems_status_code
i2c_wait( uint8_t msk, uint8_t cond )
{
uint32_t then;
rtems_status_code sc;
static int warn = 0;
if ( I2CSR_MIF == msk && ok_to_block() ) {
/* block on semaphore only if system is up and sema initialized */
sc = rtems_semaphore_obtain( syncsem, RTEMS_WAIT, 100 );
if ( RTEMS_SUCCESSFUL != sc )
return sc;
} else {
/* system not up (no SEMA yet ) or waiting on something other
* than MIF
*/
if ( I2CSR_MIF == msk && _System_state_Is_up( _System_state_Get() ) ) {
if ( warn < 8 || ! (warn & 0x1f) )
printk("WARNING: i2c bus driver running in polled mode -- should initialize properly!\n");
warn++;
}
then = _read_TBRL();
do {
/* poll for .2 seconds */
if ( (_read_TBRL() - then) > poll_timeout )
return RTEMS_TIMEOUT;
} while ( (msk & i2c_rd( I2CSR )) != cond );
}
return RTEMS_SUCCESSFUL;
}
/*
* multi-byte transfer
* - set transfer direction (master read or master write)
* - transfer byte
* - wait/synchronize
* - check for ACK
*
* RETURNS: number of bytes transferred or negative error code.
*/
STATIC int
i2c_xfer(int rw, uint8_t *buf, int len)
{
int i;
rtems_status_code sc;
if ( rw ) {
i2c_clr( I2CCR, I2CCR_MTX );
} else {
i2c_set( I2CCR, I2CCR_MTX );
}
for ( i = 0; i< len; i++ ) {
i2c_clr( I2CSR, I2CSR_MIF );
/* Enable interrupts if necessary */
if ( ok_to_block() )
i2c_set( I2CCR, I2CCR_MIEN );
if ( rw ) {
buf[i] = i2c_rd( I2CDR );
} else {
i2c_wr( I2CDR, buf[i] );
}
if ( RTEMS_SUCCESSFUL != (sc = i2c_wait( I2CSR_MIF, I2CSR_MIF )) )
return -sc;
if ( (I2CSR_RXAK & i2c_rd( I2CSR )) ) {
/* NO ACK */
return -RTEMS_IO_ERROR;
}
}
return i;
}
/*
* This bus controller gives us lagging data, i.e.,
* when we read a byte from the data reg then that
* issues a read cycle on the bus and gives us the
* byte from the *previous* read cycle :-(
*
* This makes it impossible to properly terminate
* a read transaction w/o knowing ahead of time
* how many bytes are going to be read (API decouples
* 'START'/'STOP' from 'READ') since we would have to
* set TXAK when reading the next-to-last byte
* (i.e., when the last byte is read on the i2c bus).
*
* Hence, (if we are reading) we must do a dummy
* read-cycle here -- hopefully
* that has no side-effects! (i.e., EEPROM drivers should
* reposition file pointers after issuing STOP)
*
*/
static void
rd1byte_noack()
{
uint8_t dum;
uint8_t ccr;
/* If we are in reading state then read one more
* byte w/o acknowledge
*/
ccr = i2c_rd (I2CCR );
if ( ! ( I2CCR_MTX & ccr ) ) {
i2c_wr( I2CCR, ccr | I2CCR_TXAK );
i2c_xfer(1, &dum, 1);
/* restore original TXAK bit setting */
i2c_clr( I2CCR, (I2CCR_TXAK & ccr) );
}
}
/********* ISR ***********************/
static void i2c_isr(rtems_irq_hdl_param arg)
{
/* disable irq */
i2c_clr( I2CCR, I2CCR_MIEN );
/* release task */
rtems_semaphore_release( syncsem );
}
/********* IIC Bus Driver Ops ********/
STATIC rtems_status_code
i2c_init(rtems_libi2c_bus_t *bh)
{
rtems_status_code sc;
/* compute more accurate timeout */
if ( BSP_bus_frequency && BSP_time_base_divisor )
poll_timeout = BSP_bus_frequency/BSP_time_base_divisor*1000/5;
i2c_clr( I2CCR, I2CCR_MEN );
i2c_set( I2CCR, I2CCR_MEN );
i2c_wr( I2CADR, 0 );
/* leave motload settings for divisor and filter registers */
if ( SYSTEM_STATE_BEFORE_MULTITASKING <= _System_state_Get() && !syncsem ) {
sc = rtems_semaphore_create(
rtems_build_name('i','2','c','b'),
0,
RTEMS_SIMPLE_BINARY_SEMAPHORE | RTEMS_LOCAL,
0,
&syncsem);
if ( RTEMS_SUCCESSFUL == sc ) {
rtems_irq_connect_data xxx;
xxx.name = BSP_I2C_IRQ;
xxx.on = 0;
xxx.off = 0;
xxx.isOn = 0;
xxx.hdl = i2c_isr;
xxx.handle = 0;
if ( ! BSP_install_rtems_irq_handler( &xxx ) ) {
printk("Unable to install i2c ISR -- falling back to polling mode\n");
rtems_semaphore_delete( syncsem );
/* fall back to polling mode */
syncsem = 0;
}
} else {
syncsem = 0;
}
}
return RTEMS_SUCCESSFUL;
}
STATIC rtems_status_code
i2c_start(rtems_libi2c_bus_t *bh)
{
uint8_t v;
rtems_status_code sc = RTEMS_SUCCESSFUL;
v = i2c_rd( I2CCR );
if ( I2CCR_MSTA & v ) {
/* RESTART */
rd1byte_noack();
v |= I2CCR_RSTA;
} else {
v |= I2CCR_MSTA;
}
i2c_wr( I2CCR, v );
/* On MBB we can only poll-wait (no IRQ is generated)
* and this is also much faster than reading a byte
* (1/2-bit time) so the overhead of an IRQ may not
* be justified.
* OTOH, we can put this off into the 'send_addr' routine
*
sc = i2c_wait( I2CSR_MBB, I2CSR_MBB );
*/
return sc;
}
STATIC rtems_status_code
i2c_stop(rtems_libi2c_bus_t *bh)
{
rd1byte_noack();
/* STOP */
i2c_clr( I2CCR, I2CCR_TXAK | I2CCR_MSTA );
/* FIXME: should we really spend 1/2 bit-time polling
* or should we just go ahead and hope noone
* else will get a chance to do something to
* the bus until the STOP completes?
*/
return i2c_wait( I2CSR_MBB, 0 );
}
STATIC rtems_status_code
i2c_send_addr(rtems_libi2c_bus_t *bh, uint32_t addr, int rw)
{
uint8_t buf[2];
int l = 0;
uint8_t read_mask = rw ? 1 : 0;
rtems_status_code sc;
/* Make sure we are started; (i2c_start() didn't bother to wait
* so we do it here - some time already has expired.
*/
sc = i2c_wait( I2CSR_MBB, I2CSR_MBB );
if ( RTEMS_SUCCESSFUL != sc )
return sc;
if ( addr > 0x7f ) {
/* 10-bit request; 1st address byte is 0b11110<b9><b8><r/w> */
buf[l] = 0xf0 | ((addr >> 7) & 0x06) | read_mask;
read_mask = 0;
l++;
buf[l] = addr & 0xff;
} else {
buf[l] = (addr << 1) | read_mask;
l++;
}
/*
* After sending a an address for reading we must
* read a dummy byte (this actually clocks the first real
* byte on the i2c bus and makes it available in the
* data register so that the first 'read_bytes' operation
* obtains the byte we clock in here [and starts clocking
* the second byte]) to overcome the pipeline
* delay in the hardware (I don't like this design) :-(.
*/
sc = i2c_xfer( 0, buf, l );
if ( rw && l == sc ) {
sc = i2c_xfer( 1, buf, 1 );
}
return sc >=0 ? RTEMS_SUCCESSFUL : -sc;
}
STATIC int
i2c_read_bytes(rtems_libi2c_bus_t *bh, unsigned char *buf, int len)
{
return i2c_xfer( 1, buf, len );
}
STATIC int
i2c_write_bytes(rtems_libi2c_bus_t *bh, unsigned char *buf, int len)
{
return i2c_xfer( 0, buf, len );
}
/********* Driver Glue Vars **********/
static rtems_libi2c_bus_ops_t myops = {
init: i2c_init,
send_start: i2c_start,
send_stop: i2c_stop,
send_addr: i2c_send_addr,
read_bytes: i2c_read_bytes,
write_bytes: i2c_write_bytes,
};
static rtems_libi2c_bus_t my_bus_tbl = {
ops: &myops,
size: sizeof(my_bus_tbl),
};
/********* Global Driver Handle ******/
rtems_libi2c_bus_t *mpc8540_i2c_bus_descriptor = &my_bus_tbl;

View File

@@ -0,0 +1,64 @@
#ifndef MPC8540_I2C_BUS_DRIVER_H
#define MPC8540_I2C_BUS_DRIVER_H
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was created by
*
* Till Straumann <strauman@slac.stanford.edu>, 2005-2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
#ifdef __cplusplus
extern "C" {
#endif
#include <rtems.h>
#include <rtems/libi2c.h>
/* for registration with libi2c */
extern rtems_libi2c_bus_t *mpc8540_i2c_bus_descriptor;
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,329 @@
/*
* bsp.h -- contain BSP API definition.
*
* Copyright (C) 1999 Eric Valette. valette@crf.canon.fr
*
* The license and distribution terms for this file may be
* found in found in the file LICENSE in this distribution or at
* http://www.rtems.com/license/LICENSE.
*
* Adapted for the mvme3100 BSP by T. Straumann, 2007.
*
* $Id$
*/
#ifndef _BSP_H
#define _BSP_H
#include <bspopts.h>
#include <rtems.h>
#include <rtems/console.h>
#include <libcpu/io.h>
#include <rtems/clockdrv.h>
/*
* confdefs.h overrides for this BSP:
* - termios serial ports (defaults to 1)
* - Interrupt stack space is not minimum if defined.
*/
#define CONFIGURE_NUMBER_OF_TERMIOS_PORTS 2
#define CONFIGURE_INTERRUPT_STACK_MEMORY (16 * 1024)
/*
* diagram illustrating the role of the configuration
* constants
* PCI_MEM_WIN0: CPU starting addr where PCI memory space is visible
* PCI_MEM_BASE: CPU address of PCI mem addr. zero. (regardless of this
* address being 'visible' or not!).
* _VME_A32_WIN0_ON_PCI: PCI starting addr of the 1st window to VME
* _VME_A32_WIN0_ON_VME: VME address of that same window
*
* AFAIK, only PreP boards have a non-zero PCI_MEM_BASE (i.e., an offset between
* CPU and PCI addresses). The mvme2300 'ppcbug' firmware configures the PCI
* bus using PCI base addresses! I.e., drivers need to add PCI_MEM_BASE to
* the base address read from PCI config.space in order to translate that
* into a CPU address.
*
* NOTE: VME addresses should NEVER be translated using these constants!
* they are strictly for BSP internal use. Drivers etc. should use
* the translation routines int VME.h (BSP_vme2local_adrs/BSP_local2vme_adrs).
*
* CPU ADDR PCI_ADDR VME ADDR
*
* 00000000 XXXXXXXX XXXXXXXX
* ^ ^ ........
* | |
* | | e.g., RAM XXXXXXXX
* | | 00000000
* | | ......... ^
* | | (possible offset |
* | | between pci and XXXXXXXX | ......
* | | cpu addresses) |
* | v |
* | PCI_MEM_BASE -------------> 00000000 --------------- |
* | ........ ........ ^ |
* | invisible | |
* | ........ from CPU | |
* v | |
* PCI_MEM_WIN0 ============= first visible PCI addr | |
* | |
* pci devices pci window | |
* visible here v v
* mapped by ========== _VME_A32_WIN0_ON_PCI ======= _VME_A32_WIN0_ON_VME
* vme window
* VME devices hostbridge mapped by
* visible here universe
* =====================================================
*
*/
/* fundamental addresses for BSP (CHRPxxx and PREPxxx are from libcpu/io.h) */
#define _IO_BASE 0xe0000000 /* Motload's PCI IO base */
#define _ISA_MEM_BASE CHRP_ISA_MEM_BASE
/* address of our ram on the PCI bus */
#define PCI_DRAM_OFFSET CHRP_PCI_DRAM_OFFSET
/* offset of pci memory as seen from the CPU */
#define PCI_MEM_BASE 0
/* where (in CPU addr. space) does the PCI window start */
#define PCI_MEM_WIN0 0x80000000
/*
* Base address definitions for several devices
*/
#define BSP_OPEN_PIC_BASE_OFFSET 0x40000
#define BSP_OPEN_PIC_BIG_ENDIAN
#define BSP_8540_CCSR_BASE (0xe1000000)
#define BSP_UART_IOBASE_COM1 (BSP_8540_CCSR_BASE+0x4500)
#define BSP_UART_IOBASE_COM2 (BSP_8540_CCSR_BASE+0x4600)
#define PCI_CONFIG_ADDR (BSP_8540_CCSR_BASE+0x8000)
#define PCI_CONFIG_DATA (BSP_8540_CCSR_BASE+0x8004)
#define PCI_CONFIG_WR_ADDR( addr, val ) out_be32((unsigned int*)(addr), (val))
#define BSP_CONSOLE_PORT BSP_UART_COM1
#define BSP_UART_BAUD_BASE (-9600) /* use existing divisor to determine clock rate */
#define BSP_UART_USE_SHARED_IRQS
#define BSP_MVME3100_IRQ_DETECT_REG ((volatile uint8_t *)0xe2000007)
/* I2C Devices */
/* Note that the i2c addresses stated in the manual are
* left-shifted by one bit.
*/
#define BSP_VPD_I2C_ADDR (0xA8>>1) /* the VPD EEPROM */
#define BSP_USR0_I2C_ADDR (0xA4>>1) /* the 1st user EEPROM */
#define BSP_USR1_I2C_ADDR (0xA6>>1) /* the 2nd user EEPROM */
#define BSP_THM_I2C_ADDR (0x90>>1) /* the DS1621 temperature sensor & thermostat */
#define BSP_RTC_I2C_ADDR (0xD0>>1) /* the DS1375 wall-clock */
#define BSP_I2C_BUS_DESCRIPTOR mpc8540_i2c_bus_descriptor
#define BSP_I2C_BUS0_NAME "/dev/i2c0"
#define BSP_I2C_VPD_EEPROM_NAME "vpd-eeprom"
#define BSP_I2C_USR_EEPROM_NAME "usr-eeprom"
#define BSP_I2C_USR1_EEPROM_NAME "usr1-eeprom"
#define BSP_I2C_DS1621_NAME "ds1621"
#define BSP_I2C_THM_NAME BSP_I2C_DS1621_NAME
#define BSP_I2C_DS1621_RAW_NAME "ds1621-raw"
#define BSP_I2C_DS1375_RAW_NAME "ds1375-raw"
#define BSP_I2C_RTC_RAW_NAME BSP_I2C_DS1375_RAW_NAME
#define BSP_I2C_VPD_EEPROM_DEV_NAME (BSP_I2C_BUS0_NAME"."BSP_I2C_VPD_EEPROM_NAME)
#define BSP_I2C_USR_EEPROM_DEV_NAME (BSP_I2C_BUS0_NAME"."BSP_I2C_USR_EEPROM_NAME)
#define BSP_I2C_USR1_EEPROM_DEV_NAME (BSP_I2C_BUS0_NAME"."BSP_I2C_USR1_EEPROM_NAME)
#define BSP_I2C_DS1621_DEV_NAME (BSP_I2C_BUS0_NAME"."BSP_I2C_DS1621_NAME)
#define BSP_I2C_THM_DEV_NAME BSP_I2C_DS1621_DEV_NAME
#define BSP_I2C_DS1621_RAW_DEV_NAME (BSP_I2C_BUS0_NAME"."BSP_I2C_DS1621_RAW_NAME)
#define BSP_I2C_DS1375_RAW_DEV_NAME (BSP_I2C_BUS0_NAME"."BSP_I2C_DS1375_RAW_NAME)
/* Definitions useful for bootloader (netboot); where to find
* boot/'environment' parameters.
*/
#define BSP_EEPROM_BOOTPARMS_NAME BSP_I2C_USR1_EEPROM_DEV_NAME
#define BSP_EEPROM_BOOTPARMS_SIZE 1024
#define BSP_EEPROM_BOOTPARMS_OFFSET 0
#define BSP_BOOTPARMS_WRITE_ENABLE() do { BSP_eeprom_write_enable(); } while (0)
#define BSP_BOOTPARMS_WRITE_DISABLE() do { BSP_eeprom_write_protect();} while (0)
#ifdef __cplusplus
extern "C" {
#endif
/* Initialize the I2C driver and register all devices
* RETURNS 0 on success, -1 on error.
*
* Access to the VPD and user EEPROMS as well
* as the ds1621 temperature sensor is possible
* by means of file nodes
*
* /dev/i2c0.vpd-eeprom (read-only)
* /dev/i2c0.usr-eeprom (read-write)
* /dev/i2c0.usr1-eeprom (read-write)
* /dev/i2c0.ds1621 (read-only; one byte: board-temp in degC)
* /dev/i2c0.ds1621-raw (read-write; transfer bytes to/from the ds1621)
* /dev/i2c0.ds1375-raw (read-write; transfer bytes to/from the ds1375)
*
*/
int
BSP_i2c_initialize();
/* Misc utility definitions and routines */
void
rtemsReboot();
/* System Control Register */
#define BSP_MVME3100_SYS_CR ((volatile uint8_t *)0xe2000001)
#define BSP_MVME3100_SYS_CR_RESET_MSK (7<<5)
#define BSP_MVME3100_SYS_CR_RESET (5<<5)
#define BSP_MVME3100_SYS_CR_EEPROM_WP (1<<1)
#define BSP_MVME3100_SYS_CR_TSTAT_MSK (1<<0)
/* LED support */
#define BSP_MVME3100_SYS_IND_REG ((volatile uint8_t *)0xe2000002)
#define BSP_LED_BRD_FAIL (1<<0)
#define BSP_LED_USR1 (1<<1)
#define BSP_LED_USR2 (1<<2)
#define BSP_LED_USR3 (1<<3)
/* Flash CSR */
#define BSP_MVME3100_FLASH_CSR ((volatile uint8_t *)0xe2000003)
#define BSP_MVME3100_FLASH_CSR_FLASH_RDY (1<<0)
#define BSP_MVME3100_FLASH_CSR_FBT_BLK_SEL (1<<1)
#define BSP_MVME3100_FLASH_CSR_F_WP_HW (1<<2)
#define BSP_MVME3100_FLASH_CSR_F_WP_SW (1<<3)
#define BSP_MVME3100_FLASH_CSR_MAP_SEL (1<<4)
/* Phy interrupt detect */
#define BSP_MVME3100_IRQ_DETECT_REG ((volatile uint8_t *)0xe2000007)
/* Atomically set bits in a sys-register; The bits set in 'mask'
* are set in the register others; are left unmodified.
*
* RETURNS: old state.
*
* NOTE : since BSP_setSysReg( reg, 0 ) does not make
* any changes this call may be used
* to read the current status w/o modifying it.
*/
uint8_t
BSP_setSysReg(volatile uint8_t *r, uint8_t mask);
/* Atomically clear bits in a sys-register; The bits set in 'mask'
* are cleared in the register; others are left unmodified.
*
* RETURNS: old state.
*
* NOTE : since BSP_clrSysReg( reg, 0 ) does not make
* any changes this call may be used
* to read the current status w/o modifying it.
*/
uint8_t
BSP_clrSysReg(volatile uint8_t *r, uint8_t mask);
/* Convenience wrappers around BSP_setSysReg()/BSP_clrSysReg() */
/* Set write-protection for all EEPROM devices
* RETURNS: old status
*/
uint8_t
BSP_eeprom_write_protect();
/* Disengage write-protection for all EEPROM devices
* RETURNS: old status
*/
uint8_t
BSP_eeprom_write_enable();
/* Set LEDs that have their bit set in the mask
*
* RETURNS: old status.
*
* NOTE : since BSP_setLEDs( 0 ) does not make
* any changes this call may be used
* to read the current status w/o modifying it.
*/
uint8_t
BSP_setLEDs(uint8_t mask);
/* Clear LEDs that have their bit set in the mask
*
* RETURNS: old status
*
* NOTE: : see above (BSP_setLEDs)
*/
uint8_t
BSP_clrLEDs(uint8_t mask);
#if 0
#define outport_byte(port,value) outb(value,port)
#define outport_word(port,value) outw(value,port)
#define outport_long(port,value) outl(value,port)
#define inport_byte(port,value) (value = inb(port))
#define inport_word(port,value) (value = inw(port))
#define inport_long(port,value) (value = inl(port))
#endif
/*
* Total memory using RESIDUAL DATA
*/
extern unsigned int BSP_mem_size;
/*
* Start of the heap
*/
extern unsigned int BSP_heap_start;
/*
* PCI Bus Frequency
*/
extern unsigned int BSP_bus_frequency;
/*
* processor clock frequency
*/
extern unsigned int BSP_processor_frequency;
/*
* Time base divisior (how many tick for 1 second).
*/
extern unsigned int BSP_time_base_divisor;
#define BSP_Convert_decrementer( _value ) \
((unsigned long long) ((((unsigned long long)BSP_time_base_divisor) * 1000000ULL) /((unsigned long long) BSP_bus_frequency)) * ((unsigned long long) (_value)))
extern rtems_configuration_table BSP_Configuration;
extern void BSP_panic(char *s);
extern void rtemsReboot(void);
/* extern int printk(const char *, ...) __attribute__((format(printf, 1, 2))); */
extern int BSP_disconnect_clock_handler (void);
extern int BSP_connect_clock_handler (void);
/* clear hostbridge errors
*
* NOTE: The routine returns always (-1) if 'enableMCP==1'
* [semantics needed by libbspExt] if the MCP input is not wired.
* It returns and clears the error bits of the PCI status register.
* MCP support is disabled because:
* a) the 2100 has no raven chip
* b) the raven (2300) would raise machine check interrupts
* on PCI config space access to empty slots.
*/
extern unsigned long _BSP_clear_hostbridge_errors(int enableMCP, int quiet);
extern void BSP_motload_pci_fixup();
struct rtems_bsdnet_ifconfig;
int
rtems_tsec_attach(struct rtems_bsdnet_ifconfig *ifcfg, int attaching);
#define RTEMS_BSP_NETWORK_DRIVER_NAME "tse1"
#define RTEMS_BSP_NETWORK_DRIVER_ATTACH rtems_tsec_attach
#ifdef __cplusplus
}
#endif
#endif

View File

@@ -0,0 +1,23 @@
/* include/bspopts.h.in. Generated from configure.ac by autoheader. */
/* Define to the address where bug reports for this package should be sent. */
#undef PACKAGE_BUGREPORT
/* Define to the full name of this package. */
#undef PACKAGE_NAME
/* Define to the full name and version of this package. */
#undef PACKAGE_STRING
/* Define to the one symbol short name of this package. */
#undef PACKAGE_TARNAME
/* Define to the version of this package. */
#undef PACKAGE_VERSION
/* If defined, then the PowerPC specific code in RTEMS will use data cache
instructions to optimize the context switch code. This code can conflict
with debuggers or emulators. It is known to break the Corelis PowerPC
emulator with at least some combinations of PowerPC 603e revisions and
emulator versions. The BSP actually contains the call that enables this. */
#undef PPC_USE_DATA_CACHE

View File

@@ -0,0 +1,126 @@
/* irq.h
*
* This include file describe the data structure and the functions implemented
* by RTEMS to write interrupt handlers.
*
* Copyright (C) 1999 valette@crf.canon.fr
*
* This code is heavilly inspired by the public specification of STREAM V2
* that can be found at :
*
* <http://www.chorus.com/Documentation/index.html> by following
* the STREAM API Specification Document link.
*
* The license and distribution terms for this file may be
* found in found in the file LICENSE in this distribution or at
* http://www.rtems.com/license/LICENSE.
*
* Adapted for the mvme3100 BSP by T. Straumann, 2007.
*
* $Id$
*/
#ifndef BSP_POWERPC_IRQ_H
#define BSP_POWERPC_IRQ_H
#define BSP_SHARED_HANDLER_SUPPORT 1
#include <rtems/irq.h>
#ifndef ASM
#ifdef __cplusplus
extern "C" {
#endif
/*
* rtems_irq_number Definitions
*/
/* Must pad number of external sources to 16 because
* of the layout of vector/priority registers in the
* 8540's openpic where there is a gap between
* registers corresponding to external and core sources.
*/
#define BSP_EXT_IRQ_NUMBER (16)
#define BSP_CORE_IRQ_NUMBER (32)
/* openpic glue code from shared/irq assigns priorities and configures
* initial ISRs for BSP_PCI_IRQ_NUMBER entries (plus ISA stuff on legacy
* boards). Hence PCI_IRQ_NUMBER must also cover the internal sources
* even though they have nothing to do with PCI.
*/
#define BSP_PCI_IRQ_NUMBER (BSP_EXT_IRQ_NUMBER + BSP_CORE_IRQ_NUMBER)
#define BSP_PCI_IRQ_LOWEST_OFFSET (0)
#define BSP_PCI_IRQ_MAX_OFFSET (BSP_PCI_IRQ_LOWEST_OFFSET + BSP_PCI_IRQ_NUMBER - 1)
#define BSP_CORE_IRQ_LOWEST_OFFSET (BSP_PCI_IRQ_LOWEST_OFFSET + BSP_EXT_IRQ_NUMBER)
#define BSP_CORE_IRQ_MAX_OFFSET (BSP_CORE_IRQ_LOWEST_OFFSET + BSP_CORE_IRQ_NUMBER - 1)
/*
* PowerPC exceptions handled as interrupt where an RTEMS managed interrupt
* handler might be connected
*/
#define BSP_PROCESSOR_IRQ_NUMBER (1)
#define BSP_PROCESSOR_IRQ_LOWEST_OFFSET (BSP_CORE_IRQ_MAX_OFFSET + 1)
#define BSP_PROCESSOR_IRQ_MAX_OFFSET (BSP_PROCESSOR_IRQ_LOWEST_OFFSET + BSP_PROCESSOR_IRQ_NUMBER - 1)
/* Misc vectors for OPENPIC irqs (IPI, timers)
*/
#define BSP_MISC_IRQ_NUMBER (8)
#define BSP_MISC_IRQ_LOWEST_OFFSET (BSP_PROCESSOR_IRQ_MAX_OFFSET + 1)
#define BSP_MISC_IRQ_MAX_OFFSET (BSP_MISC_IRQ_LOWEST_OFFSET + BSP_MISC_IRQ_NUMBER - 1)
/*
* Summary
*/
#define BSP_IRQ_NUMBER (BSP_MISC_IRQ_MAX_OFFSET + 1)
#define BSP_LOWEST_OFFSET (BSP_PCI_IRQ_LOWEST_OFFSET)
#define BSP_MAX_OFFSET (BSP_MISC_IRQ_MAX_OFFSET)
/*
* Some PCI IRQ symbolic name definition
*/
#define BSP_PCI_IRQ0 (BSP_PCI_IRQ_LOWEST_OFFSET)
#define BSP_VME0_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 0)
#define BSP_VME1_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 1)
#define BSP_VME2_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 2)
#define BSP_VME3_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 3)
#define BSP_ABORT_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 8)
#define BSP_TEMP_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 9)
#define BSP_PHY_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 10)
#define BSP_RTC_IRQ (BSP_PCI_IRQ_LOWEST_OFFSET + 11)
/* Weird - they provide 3 different IRQ lines per ethernet controller
* but only one shared line for 2 UARTs ???
*/
#define BSP_UART_COM1_IRQ (BSP_CORE_IRQ_LOWEST_OFFSET + 26)
#define BSP_UART_COM2_IRQ (BSP_CORE_IRQ_LOWEST_OFFSET + 26)
#define BSP_I2C_IRQ (BSP_CORE_IRQ_LOWEST_OFFSET + 27)
/*
* Some internal (CORE) name definitions
*/
/* Ethernet (FEC) */
#define BSP_CORE_IRQ_FEC (BSP_CORE_IRQ_LOWEST_OFFSET + 25)
/* i2c controller */
#define BSP_CORE_IRQ_I2C (BSP_CORE_IRQ_LOWEST_OFFSET + 27)
/*
* Some Processor execption handled as RTEMS IRQ symbolic name definition
*/
#define BSP_DECREMENTER (BSP_PROCESSOR_IRQ_LOWEST_OFFSET)
/*-------------------------------------------------------------------------+
| Function Prototypes.
+--------------------------------------------------------------------------*/
extern void BSP_rtems_irq_mng_init(unsigned cpuId);
#include <bsp/irq_supp.h>
#ifdef __cplusplus
};
#endif
#endif
#endif

View File

@@ -0,0 +1,140 @@
/* irq_init.c
*
* This file contains the implementation of rtems initialization
* related to interrupt handling.
*
* CopyRight (C) 1999 valette@crf.canon.fr
*
* 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
*
* Adapted for the mvme3100 BSP by T. Straumann, 2007.
*
* The license and distribution terms for this file may be
* found in the file LICENSE in this distribution or at
* http://www.rtems.com/license/LICENSE.
*
* $Id$
*/
#include <libcpu/io.h>
#include <bsp/pci.h>
#include <bsp/openpic.h>
#include <bsp/irq.h>
#include <bsp.h>
#include <libcpu/raw_exception.h>
#include <rtems/bspIo.h>
static void nop_func()
{
printk("Unhandled IRQ\n");
}
static rtems_irq_connect_data rtemsIrq[BSP_IRQ_NUMBER];
static rtems_irq_global_settings initial_config;
static rtems_irq_connect_data defaultIrq = {
/* vectorIdex, hdl , handle , on , off , isOn */
0, nop_func , NULL , 0 , 0 , 0
};
static rtems_irq_prio irqPrioTable[BSP_IRQ_NUMBER]={
/*
* actual priorities for interrupt :
* 0 means that only current interrupt is masked
* 255 means all other interrupts are masked
*/
/*
* PCI Interrupts
*/
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, /* for raven prio 0 means unactive... */
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, /* for raven prio 0 means unactive... */
8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, 8, /* for raven prio 0 means unactive... */
/*
* Processor exceptions handled as interrupts
*/
0
};
/*
* This code assumes the exceptions management setup has already
* been done. We just need to replace the exceptions that will
* be handled like interrupt. On mcp750/mpc750 and many PPC processors
* this means the decrementer exception and the external exception.
*/
void BSP_rtems_irq_mng_init(unsigned cpuId)
{
/* We should really have a way to find the number of sources
* the driver will use so that the size of the polarity-array
* matches the driver's idea of it.
*/
unsigned char pol[56];
int i;
/* Note: The openpic driver initializes only as many
* 'pic-external' interrupt sources as reported
* by the feature register.
* The 8540's openpic supports 12 core-external
* and 23 core-internal (both of these groups
* are external to the PIC, i.e., 'pic-external')
* interrupts but between the corresponding
* banks of vector/priority registers there is
* a gap leaving space for 4 (unsupported) irqs.
* The driver, not knowing of this gap, would
* initialize the 12 core-external sources
* followed by 4 unsupported sources and 19
* core-internal sources thus leaving the last
* four core-internal sources uninitialized.
* Luckily, the feature register reports
* too many sources:
* - the 4 IPI plus 4 timer plus 4 messaging
* sources are included with the count
* - there are unused core-internal sources 24..32
* which are also supported by the pic
* bringing the reported number of sources to
* a count of 56 (12+32+4+4+4) which is enough
* so that all pic-external sources are covered
* and initialized.
*
* NOTE: All core-internal sources are active-high.
* The manual says that setting the polarity
* to 'low/0' will disable the interrupt but
* I found this not to be true: on the device
* I tested the interrupt was asserted hard.
*/
/* core-external sources on the mvme3100 are active-low,
* core-internal sources are active high.
*/
for (i=0; i<BSP_EXT_IRQ_NUMBER; i++)
pol[i]=0;
for (i=BSP_EXT_IRQ_NUMBER; i< BSP_EXT_IRQ_NUMBER + BSP_CORE_IRQ_NUMBER; i++)
pol[i]=1;
openpic_init(1, pol, 0, 0, 0, 0);
/*
* re-init the rtemsIrq table
*/
for (i = 0; i < BSP_IRQ_NUMBER; i++) {
rtemsIrq[i] = defaultIrq;
rtemsIrq[i].name = i;
}
/*
* Init initial Interrupt management config
*/
initial_config.irqNb = BSP_IRQ_NUMBER;
initial_config.defaultEntry = defaultIrq;
initial_config.irqHdlTbl = rtemsIrq;
initial_config.irqBase = BSP_LOWEST_OFFSET;
initial_config.irqPrioTbl = irqPrioTable;
if (!BSP_rtems_irq_mngt_set(&initial_config)) {
/*
* put something here that will show the failure...
*/
BSP_panic("Unable to initialize RTEMS interrupt Management!!! System locked\n");
}
}

View File

@@ -0,0 +1,346 @@
#ifndef IF_TSEC_PUBLIC_INTERFACE_H
#define IF_TSEC_PUBLIC_INTERFACE_H
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was created by
*
* Till Straumann <strauman@slac.stanford.edu>, 2005-2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
#include <rtems.h>
#include <stdio.h>
#ifdef __cplusplus
extern "C" {
#endif
/* Opaque driver handle */
struct tsec_private;
/********** Low-level Driver API ****************/
/*
* This API provides driver access to applications that
* want to use e.g., the second ethernet interface
* independently from the BSD TCP/IP stack. E.g., for
* raw ethernet packet communication...
*/
/*
* Setup an interface.
* Allocates resources for descriptor rings and sets up the driver software structure.
*
* Arguments:
* unit:
* interface # (1..2). The interface must not be attached to BSD already.
*
* driver_tid:
* ISR posts RTEMS event # ('unit' - 1) to task with ID 'driver_tid' and disables interrupts
* from this interface.
*
* void (*cleanup_txbuf)(void *user_buf, void *cleanup_txbuf_arg, int error_on_tx_occurred):
* Pointer to user-supplied callback to release a buffer that had been sent
* by BSP_tsec_send_buf() earlier. The callback is passed 'cleanup_txbuf_arg'
* and a flag indicating whether the send had been successful.
* The driver no longer accesses 'user_buf' after invoking this callback.
* CONTEXT: This callback is executed either by BSP_tsec_swipe_tx() or
* BSP_tsec_send_buf(), BSP_tsec_init_hw(), BSP_tsec_stop_hw() (the latter
* ones calling BSP_tsec_swipe_tx()).
* void *cleanup_txbuf_arg:
* Closure argument that is passed on to 'cleanup_txbuf()' callback;
*
* void *(*alloc_rxbuf)(int *p_size, uintptr_t *p_data_addr),
* Pointer to user-supplied callback to allocate a buffer for subsequent
* insertion into the RX ring by the driver.
* RETURNS: opaque handle to the buffer (which may be a more complex object
* such as an 'mbuf'). The handle is not used by the driver directly
* but passed back to the 'consume_rxbuf()' callback.
* Size of the available data area and pointer to buffer's data area
* in '*psize' and '*p_data_area', respectively.
* If no buffer is available, this routine should return NULL in which
* case the driver drops the last packet and re-uses the last buffer
* instead of handing it out to 'consume_rxbuf()'.
* CONTEXT: Called when initializing the RX ring (BSP_tsec_init_hw()) or when
* swiping it (BSP_tsec_swipe_rx()).
*
*
* void (*consume_rxbuf)(void *user_buf, void *consume_rxbuf_arg, int len);
* Pointer to user-supplied callback to pass a received buffer back to
* the user. The driver no longer accesses the buffer after invoking this
* callback (with 'len'>0, see below). 'user_buf' is the buffer handle
* previously generated by 'alloc_rxbuf()'.
* The callback is passed 'cleanup_rxbuf_arg' and a 'len'
* argument giving the number of bytes that were received.
* 'len' may be <=0 in which case the 'user_buf' argument is NULL.
* 'len' == 0 means that the last 'alloc_rxbuf()' had failed,
* 'len' < 0 indicates a receiver error. In both cases, the last packet
* was dropped/missed and the last buffer will be re-used by the driver.
* NOTE: the data are 'prefixed' with two bytes, i.e., the ethernet packet header
* is stored at offset 2 in the buffer's data area. Also, the FCS (4 bytes)
* is appended. 'len' accounts for both.
* CONTEXT: Called from BSP_tsec_swipe_rx().
* void *cleanup_rxbuf_arg:
* Closure argument that is passed on to 'consume_rxbuf()' callback;
*
* rx_ring_size, tx_ring_size:
* How many big to make the RX and TX descriptor rings. Note that the sizes
* may be 0 in which case a reasonable default will be used.
* If either ring size is < 0 then the RX or TX will be disabled.
* Note that it is illegal in this case to use BSP_tsec_swipe_rx() or
* BSP_tsec_swipe_tx(), respectively.
*
* irq_mask:
* Interrupts to enable. OR of flags from above.
*
*/
struct tsec_private *
BSP_tsec_setup(
int unit,
rtems_id driver_tid,
void (*cleanup_txbuf)(void *user_buf, void *cleanup_txbuf_arg, int error_on_tx_occurred),
void *cleanup_txbuf_arg,
void *(*alloc_rxbuf)(int *p_size, uintptr_t *p_data_addr),
void (*consume_rxbuf)(void *user_buf, void *consume_rxbuf_arg, int len),
void *consume_rxbuf_arg,
int rx_ring_size,
int tx_ring_size,
int irq_mask
);
/*
* Descriptor scavenger; cleanup the TX ring, passing all buffers
* that have been sent to the cleanup_tx() callback.
* This routine is called from BSP_tsec_send_buf(), BSP_tsec_init_hw(),
* BSP_tsec_stop_hw().
*
* RETURNS: number of buffers processed.
*/
int
BSP_tsec_swipe_tx(struct tsec_private *mp);
/*
* Reset statistics counters.
*/
void
BSP_tsec_reset_stats(struct tsec_private *mp);
/*
* Initialize interface hardware
*
* 'mp' handle obtained by from BSP_tsec_setup().
* 'promisc' whether to set promiscuous flag.
* 'enaddr' pointer to six bytes with MAC address. Read
* from the device if NULL.
*/
void
BSP_tsec_init_hw(struct tsec_private *mp, int promisc, unsigned char *enaddr);
/*
* Dump statistics to FILE 'f'. If NULL, stdout is used.
*/
void
BSP_tsec_dump_stats(struct tsec_private *mp, FILE *f);
/*
* Shutdown hardware and clean out the rings
*/
void
BSP_tsec_stop_hw(struct tsec_private *mp);
/*
* calls BSP_tsec_stop_hw(), releases all resources and marks the interface
* as unused.
* RETURNS 0 on success, nonzero on failure.
* NOTE: the handle MUST NOT be used after successful execution of this
* routine.
*/
int
BSP_tsec_detach(struct tsec_private *mp);
/*
* Enqueue a mbuf chain or a raw data buffer for transmission;
* RETURN: #bytes sent or -1 if there are not enough free descriptors
*
* If 'len' is <=0 then 'm_head' is assumed to point to a mbuf chain.
* OTOH, a raw data packet (or a different type of buffer)
* may be sent (non-BSD driver) by pointing data_p to the start of
* the data and passing 'len' > 0.
* 'm_head' is passed back to the 'cleanup_txbuf()' callback.
*
* Comments: software cache-flushing incurs a penalty if the
* packet cannot be queued since it is flushed anyways.
* The algorithm is slightly more efficient in the normal
* case, though.
*
* RETURNS: # bytes enqueued to device for transmission or -1 if no
* space in the TX ring was available.
*/
int
BSP_tsec_send_buf(struct tsec_private *mp, void *m_head, void *data_p, int len);
/*
* Retrieve all received buffers from the RX ring, replacing them
* by fresh ones (obtained from the alloc_rxbuf() callback). The
* received buffers are passed to consume_rxbuf().
*
* RETURNS: number of buffers processed.
*/
int
BSP_tsec_swipe_rx(struct tsec_private *mp);
/* read ethernet address from hw to buffer */
void
BSP_tsec_read_eaddr(struct tsec_private *mp, unsigned char *eaddr);
/* Read MII register */
uint32_t
BSP_tsec_mdio_rd(struct tsec_private *mp, unsigned reg);
/* Write MII register */
int
BSP_tsec_mdio_wr(struct tsec_private *mp, unsigned reg, uint32_t val);
/*
* read/write media word.
* 'cmd': can be SIOCGIFMEDIA, SIOCSIFMEDIA, 0 or 1. The latter
* are aliased to the former for convenience.
* 'parg': pointer to media word.
*
* RETURNS: 0 on success, nonzero on error
*/
int
BSP_tsec_media_ioctl(struct tsec_private *mp, int cmd, int *parg);
/* Interrupt related routines */
/*
* When it comes to interrupts the chip has two rather
* annoying features:
* 1 once an IRQ is pending, clearing the IMASK does not
* de-assert the interrupt line.
* 2 the chip has three physical interrupt lines even though
* all events are reported in a single register. Rather
* useless; we must hook 3 ISRs w/o any real benefit.
* In fact, it makes our life a bit more difficult:
*
* Hence, for (1) we would have to mask interrupts at the PIC
* but to re-enable them we would have to do that three times
* because of (2).
*
* Therefore, we take the following approach:
*
* ISR masks all interrupts on the TSEC, acks/clears them
* and stores the acked irqs in the device struct where
* it is picked up by BSP_tsec_ack_irqs().
* Since all interrupts are disabled until the daemon
* re-enables them after calling BSP_tsec_ack_irqs()
* no interrupts are lost.
*
* BUT: NO isr (including PHY isrs) MUST INTERRUPT ANY
* OTHER ONE, i.e., they all must have the same
* priority. Otherwise, integrity of the cached
* irq_pending variable may be compromised.
*/
/* Enable interrupts at device */
void
BSP_tsec_enable_irqs(struct tsec_private *mp);
/* Disable interrupts at device */
void
BSP_tsec_disable_irqs(struct tsec_private *mp);
/*
* Acknowledge (and clear) interrupts.
* RETURNS: interrupts that were raised.
*/
uint32_t
BSP_tsec_ack_irqs(struct tsec_private *mp);
/* Retrieve the driver daemon TID that was passed to
* BSP_tsec_setup().
*/
rtems_id
BSP_tsec_get_tid(struct tsec_private *mp);
struct tsec_private *
BSP_tsec_getp(unsigned index);
/*
*
* Example driver task loop (note: no synchronization of
* buffer access shown!).
* RTEMS_EVENTx = 0,1 or 2 depending on IF unit.
*
* / * setup (obtain handle) and initialize hw here * /
*
* do {
* / * ISR disables IRQs and posts event * /
* rtems_event_receive( RTEMS_EVENTx, RTEMS_WAIT | RTEMS_EVENT_ANY, RTEMS_NO_TIMEOUT, &evs );
* irqs = BSP_tsec_ack_irqs(handle);
* if ( irqs & BSP_TSEC_IRQ_TX ) {
* BSP_tsec_swipe_tx(handle); / * cleanup_txbuf() callback executed * /
* }
* if ( irqs & BSP_TSEC_IRQ_RX ) {
* BSP_tsec_swipe_rx(handle); / * alloc_rxbuf() and consume_rxbuf() executed * /
* }
* BSP_tsec_enable_irqs(handle);
* } while (1);
*
*/
/* PUBLIC RTEMS BSDNET ATTACH FUNCTION */
struct rtems_bsdnet_ifconfig;
int
rtems_tsec_attach(struct rtems_bsdnet_ifconfig *ifcfg, int attaching);
#ifdef __cplusplus
}
#endif
#endif

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,115 @@
/* $Id$ */
/* PCI Initialization */
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was created by
*
* Till Straumann <strauman@slac.stanford.edu>, 2005-2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
#include <bsp.h>
#include <bsp/pci.h>
#include <bsp/irq.h>
#include <bsp/openpic.h>
#include <inttypes.h>
/* Motload configures PCI interrupts to start at 16 and up but
* we'd rather have them starting at 0.
* Use this callback to fix them up.
*/
static int
fixup_irq_line(int bus, int slot, int fun, void *uarg)
{
unsigned char line;
pci_read_config_byte( bus, slot, fun, PCI_INTERRUPT_LINE, &line);
if ( line >= BSP_EXT_IRQ_NUMBER ) {
pci_write_config_byte( bus, slot, fun, PCI_INTERRUPT_LINE, line - BSP_EXT_IRQ_NUMBER );
}
return 0;
}
void BSP_motload_pci_fixup()
{
BSP_pciScan(0, fixup_irq_line, 0);
}
void detect_host_bridge()
{
OpenPIC = (volatile struct OpenPIC *) (BSP_8540_CCSR_BASE + BSP_OPEN_PIC_BASE_OFFSET);
}
static int
dump_dev_cb(
int bus,
int dev,
int fun,
void *uarg
)
{
uint16_t vi,di;
uint16_t cd,st;
uint32_t b1,b2;
uint8_t il,ip;
pci_read_config_word (bus, dev, fun, PCI_VENDOR_ID, &vi);
pci_read_config_word (bus, dev, fun, PCI_DEVICE_ID, &di);
pci_read_config_word (bus, dev, fun, PCI_COMMAND, &cd);
pci_read_config_word (bus, dev, fun, PCI_STATUS, &st);
pci_read_config_dword(bus, dev, fun, PCI_BASE_ADDRESS_0, &b1);
pci_read_config_dword(bus, dev, fun, PCI_BASE_ADDRESS_1, &b2);
pci_read_config_byte (bus, dev, fun, PCI_INTERRUPT_LINE, &il);
pci_read_config_byte (bus, dev, fun, PCI_INTERRUPT_PIN, &ip);
printk("%3d:0x%02x:%d 0x%04x-0x%04x: 0x%04x 0x%04x 0x%08x 0x%08x %d -> %3d (=0x%02x)\n",
bus, dev, fun, vi, di, cd, st, b1, b2, ip, il, il);
return 0;
}
void
BSP_pciConfigDump_early()
{
printk("BUS:SLOT:FUN VENDOR-DEV_ID: COMMAND STATUS BASE_ADDR0 BASE_ADDR1 IRQ_PIN -> IRQ_LINE\n");
BSP_pciScan(0, dump_dev_cb, 0);
}

View File

@@ -0,0 +1,143 @@
## Automatically generated by ampolish3 - Do not edit
if AMPOLISH3
$(srcdir)/preinstall.am: Makefile.am
$(AMPOLISH3) $(srcdir)/Makefile.am > $(srcdir)/preinstall.am
endif
PREINSTALL_DIRS =
DISTCLEANFILES += $(PREINSTALL_DIRS)
all-local: $(TMPINSTALL_FILES)
TMPINSTALL_FILES =
CLEANFILES = $(TMPINSTALL_FILES)
all-am: $(PREINSTALL_FILES)
PREINSTALL_FILES =
CLEANFILES += $(PREINSTALL_FILES)
$(PROJECT_LIB)/$(dirstamp):
@$(MKDIR_P) $(PROJECT_LIB)
@: > $(PROJECT_LIB)/$(dirstamp)
PREINSTALL_DIRS += $(PROJECT_LIB)/$(dirstamp)
$(PROJECT_INCLUDE)/$(dirstamp):
@$(MKDIR_P) $(PROJECT_INCLUDE)
@: > $(PROJECT_INCLUDE)/$(dirstamp)
PREINSTALL_DIRS += $(PROJECT_INCLUDE)/$(dirstamp)
$(PROJECT_LIB)/bsp_specs: bsp_specs $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/bsp_specs
PREINSTALL_FILES += $(PROJECT_LIB)/bsp_specs
$(PROJECT_INCLUDE)/bsp.h: include/bsp.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp.h
$(PROJECT_INCLUDE)/bspopts.h: include/bspopts.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bspopts.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bspopts.h
$(PROJECT_INCLUDE)/bsp/$(dirstamp):
@$(MKDIR_P) $(PROJECT_INCLUDE)/bsp
@: > $(PROJECT_INCLUDE)/bsp/$(dirstamp)
PREINSTALL_DIRS += $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(PROJECT_INCLUDE)/coverhd.h: ../../shared/include/coverhd.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/coverhd.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/coverhd.h
$(PROJECT_INCLUDE)/tod.h: ../../shared/tod.h $(PROJECT_INCLUDE)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/tod.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/tod.h
$(PROJECT_LIB)/motld_start.$(OBJEXT): motld_start.$(OBJEXT) $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/motld_start.$(OBJEXT)
TMPINSTALL_FILES += $(PROJECT_LIB)/motld_start.$(OBJEXT)
$(PROJECT_LIB)/rtems_crti.$(OBJEXT): rtems_crti.$(OBJEXT) $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/rtems_crti.$(OBJEXT)
TMPINSTALL_FILES += $(PROJECT_LIB)/rtems_crti.$(OBJEXT)
$(PROJECT_LIB)/linkcmds: ../shared/startup/linkcmds $(PROJECT_LIB)/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_LIB)/linkcmds
PREINSTALL_FILES += $(PROJECT_LIB)/linkcmds
$(PROJECT_INCLUDE)/bsp/uart.h: ../../powerpc/shared/console/uart.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/uart.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/uart.h
$(PROJECT_INCLUDE)/bsp/irq.h: ./irq/irq.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/irq.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/irq.h
$(PROJECT_INCLUDE)/bsp/openpic.h: ../../powerpc/shared/openpic/openpic.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/openpic.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/openpic.h
$(PROJECT_INCLUDE)/bsp/pci.h: ../../powerpc/shared/pci/pci.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/pci.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/pci.h
$(PROJECT_INCLUDE)/bsp/vectors.h: ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/vectors.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vectors.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vectors.h
$(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h: ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/ppc_exc_bspsupp.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/ppc_exc_bspsupp.h
$(PROJECT_INCLUDE)/bsp/irq_supp.h: ../../../libcpu/@RTEMS_CPU@/@exceptions@/bspsupport/irq_supp.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/irq_supp.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/irq_supp.h
$(PROJECT_INCLUDE)/bsp/VMEConfig.h: ./vme/VMEConfig.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/VMEConfig.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/VMEConfig.h
$(PROJECT_INCLUDE)/bsp/vmeTsi148.h: ../../shared/vmeUniverse/vmeTsi148.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vmeTsi148.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vmeTsi148.h
$(PROJECT_INCLUDE)/bsp/vme_am_defs.h: ../../shared/vmeUniverse/vme_am_defs.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vme_am_defs.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vme_am_defs.h
$(PROJECT_INCLUDE)/bsp/VME.h: ../../shared/vmeUniverse/VME.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/VME.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/VME.h
$(PROJECT_INCLUDE)/bsp/vmeTsi148DMA.h: ../../shared/vmeUniverse/vmeTsi148DMA.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vmeTsi148DMA.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vmeTsi148DMA.h
$(PROJECT_INCLUDE)/bsp/bspVmeDmaList.h: ../../shared/vmeUniverse/bspVmeDmaList.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/bspVmeDmaList.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/bspVmeDmaList.h
$(PROJECT_INCLUDE)/bsp/VMEDMA.h: ../../shared/vmeUniverse/VMEDMA.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/VMEDMA.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/VMEDMA.h
$(PROJECT_INCLUDE)/bsp/flashPgm.h: ../shared/flash/flashPgm.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/flashPgm.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/flashPgm.h
$(PROJECT_INCLUDE)/bsp/flashPgmPvt.h: ../shared/flash/flashPgmPvt.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/flashPgmPvt.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/flashPgmPvt.h
$(PROJECT_INCLUDE)/bsp/mpc8540_i2c_busdrv.h: i2c/mpc8540_i2c_busdrv.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/mpc8540_i2c_busdrv.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/mpc8540_i2c_busdrv.h
$(PROJECT_INCLUDE)/bsp/vpd.h: ../shared/motorola/vpd.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/vpd.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/vpd.h
$(PROJECT_INCLUDE)/bsp/if_tsec_pub.h: network/if_tsec_pub.h $(PROJECT_INCLUDE)/bsp/$(dirstamp)
$(INSTALL_DATA) $< $(PROJECT_INCLUDE)/bsp/if_tsec_pub.h
PREINSTALL_FILES += $(PROJECT_INCLUDE)/bsp/if_tsec_pub.h

View File

@@ -0,0 +1,67 @@
/*
* start.S : RTEMS entry point
*
* Copyright (C) 1999 Eric Valette. valette@crf.canon.fr
*
* The license and distribution terms for this file may be
* found in found in the file LICENSE in this distribution or at
* http://www.rtems.com/license/LICENSE.
*
* Modified for mvme3100 by T. Straumann, 2007.
*
* $Id$
*
*/
#include <rtems/asm.h>
#include <rtems/score/cpu.h>
#include <rtems/powerpc/powerpc.h>
#include <bspopts.h>
#define SYNC \
sync; \
isync
#define KERNELBASE 0x0
.text
.globl __rtems_entry_point
.type __rtems_entry_point,@function
__rtems_entry_point:
mr r31,r3
mr r30,r4
mr r29,r5
mr r28,r6
mr r27,r7
/* Use MotLoad's TLB setup for now; caches are on already */
bl __eabi /* setup EABI and SYSV environment */
bl zero_bss
/*
* restore original args
*/
mr r3,r31
mr r4,r30
mr r5,r29
mr r6,r28
mr r7,r27
bl save_boot_params
/*
* stack = &__rtems_end + 4096
*/
addis r9,r0, __rtems_end+(4096-PPC_MINIMUM_STACK_FRAME_SIZE)@ha
addi r9,r9, __rtems_end+(4096-PPC_MINIMUM_STACK_FRAME_SIZE)@l
/* align down to 16-bytes */
li r5, (CPU_STACK_ALIGNMENT - 1)
andc r1, r9, r5
/*
* We are now in a environment that is totally independent from
* bootloader setup.
*/
lis r5,environ@ha
la r5,environ@l(r5) /* environp */
li r4, 0 /* argv */
li r3, 0 /* argc */
bl boot_card
/* point of no return: reset board here ? */

View File

@@ -0,0 +1,480 @@
/*
* This routine starts the application. It includes application,
* board, and monitor specific initialization and configuration.
* The generic CPU dependent initialization has been performed
* before this routine is invoked.
*
* COPYRIGHT (c) 1989-1998.
* On-Line Applications Research Corporation (OAR).
*
* The license and distribution terms for this file may be
* found in the file LICENSE in this distribution or at
* http://www.rtems.com/license/LICENSE.
*
* Modified to support the MCP750.
* Modifications Copyright (C) 1999 Eric Valette. valette@crf.canon.fr
*
* Modified for mvme3100 by T. Straumann
*
* $Id$
*/
#include <string.h>
#include <stdlib.h>
#include <rtems.h>
#include <bsp.h>
#include <rtems/bspIo.h>
#include <libcpu/spr.h>
#include <libcpu/io.h>
#include <bsp/uart.h>
#include <bsp/irq.h>
#include <bsp/pci.h>
#include <bsp/vpd.h>
#include <libcpu/cpuIdent.h>
#include <bsp/vectors.h>
#include <rtems/powerpc/powerpc.h>
#define SHOW_MORE_INIT_SETTINGS
#undef DEBUG
#ifdef DEBUG
#define STATIC
#else
#define STATIC static
#endif
extern unsigned long __rtems_end[];
extern void bsp_cleanup(void);
extern void BSP_vme_config();
SPR_RW(SPRG0)
SPR_RW(SPRG1)
/*
* Copy Additional boot param passed by boot loader
*/
#define CMDLINE_BUF_SIZE 2048
static char cmdline_buf[CMDLINE_BUF_SIZE] = {0};
char *BSP_commandline_string = cmdline_buf;
extern const char *BSP_build_date;
/*
* Vital Board data Start using DATA RESIDUAL
*/
uint32_t bsp_clicks_per_usec = 0;
/*
* Total memory using RESIDUAL DATA
*/
unsigned int BSP_mem_size = 0;
/*
* Where the heap starts; is used by bsp_pretasking_hook;
*/
unsigned int BSP_heap_start = 0;
/*
* PCI Bus Frequency
*/
unsigned int BSP_pci_bus_frequency = 0xdeadbeef;
/*
* PPC Bus Frequency
*/
unsigned int BSP_bus_frequency = 0;
/*
* processor clock frequency
*/
unsigned int BSP_processor_frequency = 0;
/*
* Time base divisior (how many tick for 1 second).
*/
unsigned int BSP_time_base_divisor = 8000; /* if external RTC clock unused (HID0) */
/* Board identification string */
char BSP_productIdent[20] = {0};
char BSP_serialNumber[20] = {0};
/* VPD appends an extra char -- what for ? */
char BSP_enetAddr0[7] = {0};
char BSP_enetAddr1[7] = {0};
char BSP_enetAddr2[7] = {0};
static void
prether(char *b, int idx)
{
int i;
printk("Ethernet %i %02X", idx, *b++);
for ( i=0; i<5; i++ )
printk(":%02X",*b++);
printk("\n");
}
/*
* system init stack and soft ir stack size
*/
#define INIT_STACK_SIZE 0x1000
#define INTR_STACK_SIZE rtems_configuration_get_interrupt_stack_size()
BSP_output_char_function_type BSP_output_char = BSP_output_char_via_serial;
void BSP_panic(char *s)
{
printk("\n%s PANIC %s\n",_RTEMS_version, s);
__asm__ __volatile ("sc");
}
void _BSP_Fatal_error(unsigned int v)
{
printk("\n%s PANIC ERROR %x\n",_RTEMS_version, v);
__asm__ __volatile ("sc");
}
/*
* The original table from the application and our copy of it with
* some changes.
*/
extern rtems_configuration_table Configuration;
char *rtems_progname;
/*
* Use the shared implementations of the following routines
*/
void save_boot_params(void* r3, void *r4, void* r5, char *additional_boot_options)
{
strncpy(cmdline_buf, additional_boot_options, CMDLINE_BUF_SIZE);
cmdline_buf[CMDLINE_BUF_SIZE - 1] ='\0';
}
#define CS_CONFIG_CS_EN (1<<31)
#define CS_BNDS_SA(x) ((((uint32_t)(x))>>(31-15)) & 0xff)
#define CS_BNDS_EA(x) ((((uint32_t)(x))>>(31-31)) & 0xff)
static inline uint32_t
_ccsr_rd32(uint32_t off)
{
return in_be32( (volatile unsigned *)(BSP_8540_CCSR_BASE + off) );
}
static inline void
_ccsr_wr32(uint32_t off, uint32_t val)
{
out_be32( (volatile unsigned *)(BSP_8540_CCSR_BASE + off), val );
}
STATIC uint32_t
BSP_get_mem_size()
{
int i;
uint32_t cs_bnds, cs_config;
uint32_t memsz=0;
uint32_t v;
for ( cs_bnds = 0x2000, cs_config=0x2080, i=0; i<4; i++, cs_bnds+=8, cs_config+=4 ) {
if ( CS_CONFIG_CS_EN & _ccsr_rd32( cs_config ) ) {
v = _ccsr_rd32( cs_bnds );
memsz += CS_BNDS_EA(v) - CS_BNDS_SA(v) + 1;
}
}
return memsz << 24;
}
STATIC void
BSP_calc_freqs()
{
uint32_t porpllsr = _ccsr_rd32( 0xe0000 );
unsigned plat_ratio = (porpllsr >> (31-30)) & 0x1f;
unsigned e500_ratio = (porpllsr >> (31-15)) & 0x3f;
switch ( plat_ratio ) {
case 2: case 3: case 4: case 5: case 6:
case 8: case 9: case 10: case 12: case 16:
/* supported ratios */
BSP_bus_frequency = BSP_pci_bus_frequency * plat_ratio;
break;
default:
BSP_panic("Unknown PLL sys-clock ratio; something's wrong here");
}
switch ( e500_ratio ) {
case 4: case 5: case 6: case 7:
BSP_processor_frequency = (BSP_pci_bus_frequency * e500_ratio) >> 1;
break;
default:
BSP_panic("Unknown PLL e500-clock ratio; something's wrong here");
}
printk("Core Complex Bus (CCB) Clock Freq: %10u Hz\n", BSP_bus_frequency);
printk("CPU Clock Freq: %10u Hz\n", BSP_processor_frequency);
}
void
bsp_predriver_hook(void)
{
/* Some drivers (RTC) may need i2c */
BSP_i2c_initialize();
}
/*
* bsp_start
*
* This routine does the bulk of the system initialization.
*/
void bsp_start( void )
{
unsigned char *stack;
register uint32_t intrStack;
register uint32_t *intrStackPtr;
unsigned char *work_space_start;
char *chpt;
ppc_cpu_id_t myCpu;
ppc_cpu_revision_t myCpuRevision;
VpdBufRec vpdData [] = {
{ key: ProductIdent, instance: 0, buf: BSP_productIdent, buflen: sizeof(BSP_productIdent) - 1 },
{ key: SerialNumber, instance: 0, buf: BSP_serialNumber, buflen: sizeof(BSP_serialNumber) - 1 },
{ key: BusClockHz, instance: 0, buf: &BSP_pci_bus_frequency, buflen: sizeof(BSP_pci_bus_frequency) },
{ key: EthernetAddr, instance: 0, buf: BSP_enetAddr0, buflen: sizeof(BSP_enetAddr0) },
{ key: EthernetAddr, instance: 1, buf: BSP_enetAddr1, buflen: sizeof(BSP_enetAddr1) },
{ key: EthernetAddr, instance: 2, buf: BSP_enetAddr2, buflen: sizeof(BSP_enetAddr2) },
VPD_END
};
/* Intersperse messages with actions to help locate problems */
printk("-----------------------------------------\n");
/*
* Get CPU identification dynamically. Note that the get_ppc_cpu_type()
* function store the result in global variables so that it can be used
* later...
*/
myCpu = get_ppc_cpu_type();
myCpuRevision = get_ppc_cpu_revision();
printk("Welcome to %s\n", _RTEMS_version);
printk("BSP: %s, CVS Release ($Name$)\n", "mvme3100");
/*
* the initial stack has aready been set to this value in start.S
* so there is no need to set it in r1 again... It is just for info
* so that It can be printed without accessing R1.
*/
asm volatile("mr %0, 1":"=r"(stack));
#if 0
stack = ((unsigned char*) __rtems_end) +
INIT_STACK_SIZE - PPC_MINIMUM_STACK_FRAME_SIZE;
#endif
/* tag the bottom */
*((uint32_t*)stack) = 0;
/*
* Initialize the interrupt related settings
* SPRG1 = software managed IRQ stack
*
* This could be done later (e.g in IRQ_INIT) but it helps to understand
* some settings below...
*/
BSP_heap_start = ((uint32_t) __rtems_end) + INIT_STACK_SIZE + INTR_STACK_SIZE;
/* reserve space for the marker/tag frame */
intrStack = BSP_heap_start - PPC_MINIMUM_STACK_FRAME_SIZE;
/* make sure it's properly aligned */
intrStack &= ~(CPU_STACK_ALIGNMENT-1);
/* tag the bottom (T. Straumann 6/36/2001 <strauman@slac.stanford.edu>) */
intrStackPtr = (uint32_t*) intrStack;
*intrStackPtr = 0;
_write_SPRG1(intrStack);
/* signal them that we have fixed PR288 - eventually, this should go away */
_write_SPRG0(PPC_BSP_HAS_FIXED_PR288);
/*
* Initialize default raw exception handlers. See vectors/vectors_init.c
*/
initialize_exceptions();
printk("CPU 0x%x - rev 0x%x\n", myCpu, myCpuRevision);
#ifdef SHOW_MORE_INIT_SETTINGS
printk("Additionnal boot options are %s\n", BSP_commandline_string);
printk("Initial system stack at %x\n", stack);
printk("Software IRQ stack at %x\n", intrStack);
#endif
#ifdef SHOW_MORE_INIT_SETTINGS
printk("Going to start PCI buses scanning and initialization\n");
#endif
printk("Build Date: %s\n",BSP_build_date);
BSP_vpdRetrieveFields( vpdData );
printk("Board Type: %s (S/N %s)\n",
BSP_productIdent[0] ? BSP_productIdent : "n/a",
BSP_serialNumber[0] ? BSP_serialNumber : "n/a");
printk("External (=PCI Bus) Clock Freq ");
if ( 0xdeadbeef == BSP_pci_bus_frequency ) {
BSP_pci_bus_frequency = 66666666;
printk(" NOT FOUND in VPD; using %10u Hz\n",
BSP_pci_bus_frequency);
} else {
printk(": %10u Hz\n",
BSP_pci_bus_frequency);
}
/* Calculate CPU and CCB bus freqs */
BSP_calc_freqs();
pci_initialize();
prether(BSP_enetAddr0, 0);
prether(BSP_enetAddr1, 1);
prether(BSP_enetAddr2, 2);
/* need to tweak the motload setup */
BSP_motload_pci_fixup();
#ifdef SHOW_MORE_INIT_SETTINGS
printk("Number of PCI buses found is : %d\n", pci_bus_count());
{
void BSP_pciConfigDump_early();
BSP_pciConfigDump_early();
}
#endif
#ifdef TEST_RAW_EXCEPTION_CODE
printk("Testing exception handling Part 1\n");
/*
* Cause a software exception
*/
__asm__ __volatile ("sc");
/*
* Check we can still catch exceptions and return coorectly.
*/
printk("Testing exception handling Part 2\n");
__asm__ __volatile ("sc");
/*
* Somehow doing the above seems to clobber SPRG0 on the mvme2100. It
* is probably a not so subtle hint that you do not want to use PPCBug
* once RTEMS is up and running. Anyway, we still needs to indicate
* that we have fixed PR288. Eventually, this should go away.
*/
_write_SPRG0(PPC_BSP_HAS_FIXED_PR288);
#endif
BSP_mem_size = BSP_get_mem_size();
if ( (chpt = strstr(BSP_commandline_string,"MEMSZ=")) ) {
char *endp;
uint32_t sz;
chpt+=6 /* strlen("MEMSZ=") */;
sz = strtoul(chpt, &endp, 0);
if ( endp != chpt )
BSP_mem_size = sz;
}
printk("Memory: %10u bytes\n", BSP_mem_size);
BSP_bus_frequency = 333333333;
BSP_processor_frequency = 833333333;
BSP_time_base_divisor = 8000; /* if external RTC clock unused (HID0) */
/* clear hostbridge errors but leave MCP disabled -
* PCI config space scanning code will trip otherwise :-(
*/
_BSP_clear_hostbridge_errors(0 /* enableMCP */, 0/*quiet*/);
/*
* Set up our hooks
* Make sure libc_init is done before drivers initialized so that
* they can use atexit()
*/
#if 0
Cpu_table.interrupt_stack_size = CONFIGURE_INTERRUPT_STACK_MEMORY;
/* FIXME */
#endif
bsp_clicks_per_usec = BSP_bus_frequency/(BSP_time_base_divisor * 1000);
#ifdef SHOW_MORE_INIT_SETTINGS
printk("Configuration.work_space_size = %x\n",
Configuration.work_space_size);
#endif
work_space_start =
(unsigned char *)BSP_mem_size - Configuration.work_space_size;
if ( work_space_start <=
((unsigned char *)__rtems_end) + INIT_STACK_SIZE + INTR_STACK_SIZE) {
printk( "bspstart: Not enough RAM!!!\n" );
bsp_cleanup();
}
Configuration.work_space_start = work_space_start;
/*
* Initalize RTEMS IRQ system
*/
BSP_rtems_irq_mng_init(0);
if (1) {
int i;
unsigned msr,tcr;
asm volatile("mfmsr %0":"=r"(msr));
asm volatile("mftcr %0":"=r"(tcr));
printk("MSR is 0x%08x, TCR 0x%08x\n",msr,tcr);
asm volatile("mttcr %0"::"r"(0));
if (0) {
asm volatile("mtmsr %0"::"r"(msr|0x8000));
for (i=0; i<12; i++)
BSP_enable_irq_at_pic(i);
printk("IRQS enabled\n");
}
}
if (0) {
extern unsigned ppc_exc_lock_std, ppc_exc_gpr3_std;
unsigned x;
asm volatile("mfivpr %0":"=r"(x));
printk("IVPR: 0x%08x\n",x);
asm volatile("mfivor8 %0":"=r"(x));
printk("IVOR8: 0x%08x\n",x);
printk("0x%08x\n",*(unsigned *)0xc00);
printk("0x%08x\n",*(unsigned *)0xc04);
printk("0x%08x\n",*(unsigned *)0xc08);
printk("0x%08x\n\n\n",*(unsigned *)0xc0c);
if (0) {
*(unsigned *)0xc08 = 0x4c000064;
asm volatile("dcbf 0, %0; icbi 0, %0; sync; isync"::"r"(0xc00));
}
printk("0x%08x\n", ppc_exc_lock_std);
printk("0x%08x\n", ppc_exc_gpr3_std);
asm volatile("sc");
printk("0x%08x\n", ppc_exc_lock_std);
printk("0x%08x\n", ppc_exc_gpr3_std);
}
printk("-----------------------------------------\n");
#ifdef SHOW_MORE_INIT_SETTINGS
printk("Exit from bspstart\n");
#endif
}

View File

@@ -0,0 +1,133 @@
/* $Id$ */
/* Miscellaneous small BSP routines; reboot, board CSR, ... */
/*
* Authorship
* ----------
* This software ('mvme3100' RTEMS BSP) was created by
*
* Till Straumann <strauman@slac.stanford.edu>, 2005-2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* The 'mvme3100' BSP was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
#include <rtems.h>
#include <bsp.h>
void
rtemsReboot()
{
uint8_t v;
/*
* AFAIK, the hardest reset available; cleared
* some errors a VME-bus reset wouldn't (hung
* i2c bus)...
*/
v = in_8( BSP_MVME3100_SYS_CR );
v &= ~BSP_MVME3100_SYS_CR_RESET_MSK;
v |= BSP_MVME3100_SYS_CR_RESET;
out_8( BSP_MVME3100_SYS_CR, v );
}
uint8_t
BSP_setSysReg(volatile uint8_t *r, uint8_t mask)
{
uint8_t v;
rtems_interrupt_level l;
if ( !mask )
return in_8( r );
rtems_interrupt_disable(l);
v = in_8( r );
if ( mask ) {
out_8( r, v | mask );
}
rtems_interrupt_enable(l);
return v;
}
uint8_t
BSP_clrSysReg(volatile uint8_t *r, uint8_t mask)
{
uint8_t v;
rtems_interrupt_level l;
if ( !mask )
return in_8( r );
rtems_interrupt_disable(l);
v = in_8( r );
if ( mask ) {
out_8( r, v & ~mask );
}
rtems_interrupt_enable(l);
return v;
}
uint8_t
BSP_setLEDs(uint8_t mask)
{
return BSP_setSysReg( BSP_MVME3100_SYS_IND_REG, mask );
}
uint8_t
BSP_clrLEDs(uint8_t mask)
{
return BSP_clrSysReg( BSP_MVME3100_SYS_IND_REG, mask );
}
uint8_t
BSP_eeprom_write_protect()
{
uint8_t m = BSP_MVME3100_SYS_CR_EEPROM_WP;
volatile uint8_t *r = BSP_MVME3100_SYS_CR;
return m & BSP_setSysReg( r, m );
}
uint8_t
BSP_eeprom_write_enable()
{
uint8_t m = BSP_MVME3100_SYS_CR_EEPROM_WP;
volatile uint8_t *r = BSP_MVME3100_SYS_CR;
return m & BSP_clrSysReg( r, m );
}

View File

@@ -0,0 +1,28 @@
/*
* This file contains the RTC driver table for the MVME3100 BSP
*
* The license and distribution terms for this file may be
* found in the file LICENSE in this distribution or at
* http://www.rtems.com/license/LICENSE.
*
* Modified for mvme3100 by T. Straumann, 2007
*
* $Id$
*/
#include <bsp.h>
#include <libchip/rtc.h>
#include <libchip/ds1375-rtc.h>
/* The following table configures the RTC drivers used in this BSP */
rtc_tbl RTC_Table[] = {
DS1375_RTC_TBL_ENTRY(BSP_I2C_DS1375_RAW_DEV_NAME),
};
/* Some information used by the RTC driver */
#define NUM_RTCS (sizeof(RTC_Table)/sizeof(rtc_tbl))
size_t RTC_Count = NUM_RTCS;
rtems_device_minor_number RTC_Minor;

View File

@@ -0,0 +1,116 @@
#ifndef RTEMS_BSP_VME_CONFIG_H
#define RTEMS_BSP_VME_CONFIG_H
/* $Id$ */
/* mvme3100 BSP specific address space configuration parameters */
/*
* Authorship
* ----------
* This software was created by
* Till Straumann <strauman@slac.stanford.edu>, 2002..2007,
* Stanford Linear Accelerator Center, Stanford University.
*
* Acknowledgement of sponsorship
* ------------------------------
* This software was produced by
* the Stanford Linear Accelerator Center, Stanford University,
* under Contract DE-AC03-76SFO0515 with the Department of Energy.
*
* Government disclaimer of liability
* ----------------------------------
* Neither the United States nor the United States Department of Energy,
* nor any of their employees, makes any warranty, express or implied, or
* assumes any legal liability or responsibility for the accuracy,
* completeness, or usefulness of any data, apparatus, product, or process
* disclosed, or represents that its use would not infringe privately owned
* rights.
*
* Stanford disclaimer of liability
* --------------------------------
* Stanford University makes no representations or warranties, express or
* implied, nor assumes any liability for the use of this software.
*
* Stanford disclaimer of copyright
* --------------------------------
* Stanford University, owner of the copyright, hereby disclaims its
* copyright and all other rights in this software. Hence, anyone may
* freely use it for any purpose without restriction.
*
* Maintenance of notices
* ----------------------
* In the interest of clarity regarding the origin and status of this
* SLAC software, this and all the preceding Stanford University notices
* are to remain affixed to any copy or derivative of this software made
* or distributed by the recipient and are to be affixed to any copy of
* software made or distributed by the recipient that contains a copy or
* derivative of this software.
*
* ------------------ SLAC Software Notices, Set 4 OTT.002a, 2004 FEB 03
*/
/*
* NOTE: the BSP (startup/bspstart.c) uses
* hardcoded window lengths that match this
* layout:
*/
#define _VME_A32_WIN0_ON_PCI 0xc0000000
#define _VME_CSR_ON_PCI 0xce000000
#define _VME_A24_ON_PCI 0xcf000000
#define _VME_A16_ON_PCI 0xcfff0000
/* start of the A32 window on the VME bus
* TODO: this should perhaps be a run-time configuration option
*/
#define _VME_A32_WIN0_ON_VME 0x20000000
/* if _VME_DRAM_OFFSET is defined, the BSP
* will map the board RAM onto the VME bus, starting
* at _VME_DRAM_OFFSET
*/
#define _VME_DRAM_OFFSET 0xc0000000
/* If your BSP requires a non-standard way to configure
* the VME interrupt manager then define the symbol
*
* BSP_VME_INSTALL_IRQ_MGR
*
* to a proper instruction sequence that installs the
* universe interrupt manager. This requires knowledge
* of the wiring between the universe and the PIC (main
* interrupt controller), i.e., which IRQ 'pins' of the
* universe are wired to which 'lines'/inputs at the PIC.
* (consult vmeUniverse.h for more information).
*
* When installing the universe IRQ manager it is also
* possible to specify whether it should try to share
* PIC interrupts with other sources. This might not
* be supported by all BSPs (but the unverse driver
* recognizes that).
*
* If BSP_VME_INSTALL_IRQ_MGR is undefined then
* the default algorithm is used (vme_universe.c):
*
* This default setup uses only a single wire. It reads
* the PIC 'line' from PCI configuration space and assumes
* this to be wired to the first (LIRQ0) IRQ input at the
* universe. The default setup tries to use interrupt
* sharing.
*/
#define BSP_VME_INSTALL_IRQ_MGR(err) \
do { \
err = vmeTsi148InstallIrqMgrAlt(\
VMETSI148_IRQ_MGR_FLAG_SHARED, /* use shared IRQs */ \
0, BSP_VME0_IRQ, \
1, BSP_VME1_IRQ, \
2, BSP_VME2_IRQ, \
3, BSP_VME3_IRQ, \
-1 /* terminate list */ \
); \
} while (0)
/* This BSP uses the Tsi148 Driver */
#define _VME_DRIVER_TSI148
#endif