diff options
author | Sebastian Huber <sebastian.huber@embedded-brains.de> | 2018-04-20 10:35:35 +0200 |
---|---|---|
committer | Sebastian Huber <sebastian.huber@embedded-brains.de> | 2018-04-20 13:52:14 +0200 |
commit | 99648958668d3a33ee57974479b36201fe303f34 (patch) | |
tree | 6f27ea790e2823c6156e71219a4f54680263fac6 /bsps/m68k | |
parent | bsps: Move start files to bsps (diff) | |
download | rtems-99648958668d3a33ee57974479b36201fe303f34.tar.bz2 |
bsps: Move startup files to bsps
Adjust build support files to new directory layout.
This patch is a part of the BSP source reorganization.
Update #3285.
Diffstat (limited to 'bsps/m68k')
81 files changed, 10630 insertions, 0 deletions
diff --git a/bsps/m68k/av5282/start/bsp_specs b/bsps/m68k/av5282/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/av5282/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/av5282/start/bspstart.c b/bsps/m68k/av5282/start/bspstart.c new file mode 100644 index 0000000000..c2dd362a6d --- /dev/null +++ b/bsps/m68k/av5282/start/bspstart.c @@ -0,0 +1,65 @@ +/* + * This routine does the bulk of the system initialisation. + */ + +/* + * Author: + * David Fiddes, D.J@fiddes.surfaid.org + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <string.h> + +/* + * Cacheable areas + */ +#define SDRAM_BASE 0 +#define SDRAM_SIZE (16*1024*1024) +#define FLASH_BASE 0xFF800000 +#define FLASH_SIZE (8*1024*1024) + +void bsp_start( void ) +{ + /* + * Invalidate the cache and disable it + */ + m68k_set_acr0(0); + m68k_set_acr1(0); + m68k_set_cacr(MCF5XXX_CACR_CINV); + + /* + * Cache SDRAM and FLASH + */ + m68k_set_acr0( + MCF5XXX_ACR_AB(SDRAM_BASE) | + MCF5XXX_ACR_AM(SDRAM_SIZE-1) | + MCF5XXX_ACR_EN | + MCF5XXX_ACR_BWE | + MCF5XXX_ACR_SM_IGNORE + ); + + /* + * Enable the cache + */ + mcf5xxx_initialize_cacr( + MCF5XXX_CACR_CENB | + MCF5XXX_CACR_DBWE | + MCF5XXX_CACR_DCM + ); +} + +extern char _CPUClockSpeed[]; + +uint32_t get_CPU_clock_speed(void) +{ + return( (uint32_t)_CPUClockSpeed); +} diff --git a/bsps/m68k/av5282/start/init5282.c b/bsps/m68k/av5282/start/init5282.c new file mode 100644 index 0000000000..df5eedb2fd --- /dev/null +++ b/bsps/m68k/av5282/start/init5282.c @@ -0,0 +1,88 @@ +/* + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + * + * This routine is pretty simple for the uC5282 because all the hard + * work has been done by the bootstrap dBUG code. + */ + +#include <bsp.h> + +#define m68k_set_cacr(_cacr) \ + __asm__ volatile ("movec %0,%%cacr" : : "d" (_cacr)) +#define m68k_set_acr0(_acr0) \ + __asm__ volatile ("movec %0,%%acr0" : : "d" (_acr0)) +#define m68k_set_acr1(_acr1) \ + __asm__ volatile ("movec %0,%%acr1" : : "d" (_acr1)) +#define MM_SDRAM_BASE (0x00000000) + +/* + * External methods used by this file + */ +extern void CopyDataClearBSSAndStart (void); +extern void INTERRUPT_VECTOR(void); + +void Init5282 (void) +{ + int x; + int temp = 0; + + /*Setup the GPIO Registers */ + MCF5282_GPIO_PBCDPAR = 0x80; + MCF5282_GPIO_PEPAR = 0x5100; + MCF5282_GPIO_PJPAR = 0xFF; + MCF5282_GPIO_PASPAR = 0x0000; + MCF5282_GPIO_PEHLPAR = 0xC0; + MCF5282_GPIO_PUAPAR = 0x0F; + MCF5282_QADC_DDRQB = 0x07; + MCF5282_GPTA_GPTDDR = 0x0C; + MCF5282_GPTA_GPTPORT = 0x4; + + /*Setup the Chip Selects so CS0 is flash */ + MCF5282_CS0_CSAR =(0xff800000 & 0xffff0000)>>16; + MCF5282_CS0_CSMR = 0x007f0001; + MCF5282_CS0_CSCR =(((0xf)&0x0F)<<10)|(1<<8)|(0x80); + + /*Setup the SDRAM */ + for(x=0; x<20000; x++) { + temp +=1; + } + MCF5282_SDRAMC_DCR = 0x00000239; + MCF5282_SDRAMC_DACR0 = 0x00001320; + MCF5282_SDRAMC_DMR0 = (0x00FC0000) | (0x00000001); + for(x=0; x<20000; x++) { + temp +=1; + } + /* set ip ( bit 3 ) in dacr */ + MCF5282_SDRAMC_DACR0 |= (0x00000008) ; + /* init precharge */ + *((short *)MM_SDRAM_BASE) = 0; + /* set RE in dacr */ + MCF5282_SDRAMC_DACR0 |= (0x00008000); + /* wait */ + for(x=0; x<20000; x++) { + temp +=1; + } + /* issue IMRS */ + MCF5282_SDRAMC_DACR0 |= (0x00000040); + *((short *)MM_SDRAM_BASE) = 0x0000; + for(x=0; x<60000; x++) { + temp +=1; + } + *((unsigned long*)MM_SDRAM_BASE)=0x12345678; + + /* Copy the interrupt vector table to address 0x0 in SDRAM */ + { + uint32_t *inttab = (uint32_t *)&INTERRUPT_VECTOR; + uint32_t *intvec = (uint32_t *)0x0; + register int i; + for (i = 0; i < 256; i++) { + *(intvec++) = *(inttab++); + } + } + /* + * Copy data, clear BSS and call boot_card() + */ + CopyDataClearBSSAndStart (); +} diff --git a/bsps/m68k/av5282/start/linkcmds b/bsps/m68k/av5282/start/linkcmds new file mode 100644 index 0000000000..ff0fdda163 --- /dev/null +++ b/bsps/m68k/av5282/start/linkcmds @@ -0,0 +1,196 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Arcturus uC DIMM ColdFire 5282 + * + * COPYRIGHT (c) 1989-2007. + * 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.org/license/LICENSE. + */ + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 16M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; +_VBR = 0x0; + +/* + * System clock speed + */ +_CPUClockSpeed = DEFINED(_CPUClockSpeed) ? _CPUClockSpeed : 58976000 ; + +/* + * Location of on-chip devicesa + */ +__IPSBAR = DEFINED(__IPSBAR) ? __IPSBAR : 0x40000000 ; +__SRAMBASE = DEFINED(__SRAMBASE) ? __SRAMBASE : 0x20000000 ; + + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + ram : ORIGIN = 0, LENGTH = 16M + sram : ORIGIN = 0x20000000, LENGTH = 64K + flash : ORIGIN = 0xFF800000, LENGTH = 8M +} + +SECTIONS +{ + + _header_offset = 0; + + /* + * Text, data and bss segments + */ + .text 0x40000 : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } >ram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + _clear_end = .; + + WorkAreaBase = .; + } >ram + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + +PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/av5282/start/linkcmdsflash b/bsps/m68k/av5282/start/linkcmdsflash new file mode 100644 index 0000000000..e194add7b8 --- /dev/null +++ b/bsps/m68k/av5282/start/linkcmdsflash @@ -0,0 +1,196 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Arcturus uC DIMM ColdFire 5282 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + */ + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 16M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; +_VBR = 0x0; + +/* + * System clock speed + */ +_CPUClockSpeed = DEFINED(_CPUClockSpeed) ? _CPUClockSpeed : 58976000 ; + +/* + * Location of on-chip devicesa + */ +__IPSBAR = DEFINED(__IPSBAR) ? __IPSBAR : 0x40000000 ; +__SRAMBASE = DEFINED(__SRAMBASE) ? __SRAMBASE : 0x20000000 ; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + ram : ORIGIN = 0, LENGTH = 16M + sram : ORIGIN = 0x20000000, LENGTH = 64K + flash : ORIGIN = 0xFF800000, LENGTH = 8M +} + +SECTIONS +{ + + _header_offset = 0; + + /* + * Text, data and bss segments + */ + .text : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >flash + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >flash + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >flash + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data 0x1000 : AT ( ADDR(.tdata) + SIZEOF ( .tdata ) ) + { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + _clear_end = .; + + WorkAreaBase = .; + } + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + +PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/av5282/start/linkcmdsram b/bsps/m68k/av5282/start/linkcmdsram new file mode 100644 index 0000000000..976c08a308 --- /dev/null +++ b/bsps/m68k/av5282/start/linkcmdsram @@ -0,0 +1,195 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Arcturus uC DIMM ColdFire 5282 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + */ + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 16M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; +_VBR = 0x0; + +/* + * System clock speed + */ +_CPUClockSpeed = DEFINED(_CPUClockSpeed) ? _CPUClockSpeed : 58976000 ; + +/* + * Location of on-chip devicesa + */ +__IPSBAR = DEFINED(__IPSBAR) ? __IPSBAR : 0x40000000 ; +__SRAMBASE = DEFINED(__SRAMBASE) ? __SRAMBASE : 0x20000000 ; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + ram : ORIGIN = 0, LENGTH = 16M + sram : ORIGIN = 0x20000000, LENGTH = 64K + flash : ORIGIN = 0xFF800000, LENGTH = 8M +} + +SECTIONS +{ + + _header_offset = 0; + + /* + * Text, data and bss segments + */ + .text 0x40000 : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } >ram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + _clear_end = .; + + WorkAreaBase = .; + } >ram + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + +PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/csb360/start/bsp_specs b/bsps/m68k/csb360/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/csb360/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/csb360/start/init5272.c b/bsps/m68k/csb360/start/init5272.c new file mode 100644 index 0000000000..267fd551b4 --- /dev/null +++ b/bsps/m68k/csb360/start/init5272.c @@ -0,0 +1,146 @@ +/* + * CSB360 hardware startup routines + * + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + * + * This initialization code based on hardware settings of dBUG + * monitor. This must be changed if you like to run it immediately + * after reset. + */ + +/* + * Copyright (C) 2000 OKTET Ltd., St.-Petersburg, Russia + * Author: Victor V. Vengerov <vvv@oktet.ru> + * + * Based on work: + * Author: + * David Fiddes, D.J@fiddes.surfaid.org + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <mcf5272/mcf5272.h> + +/* externs */ +extern void clear_bss(void); +extern void start_csb360(void); +extern void INTERRUPT_VECTOR(void); + +/* Set the pointers to the modules */ +sim_regs_t *g_sim_regs = (void *) MCF5272_SIM_BASE(BSP_MBAR); +intctrl_regs_t *g_intctrl_regs = (void *) MCF5272_INT_BASE(BSP_MBAR); +chipsel_regs_t *g_chipsel_regs = (void *) MCF5272_CS_BASE(BSP_MBAR); +gpio_regs_t *g_gpio_regs = (void *) MCF5272_GPIO_BASE(BSP_MBAR); +qspi_regs_t *g_qspi_regs = (void *) MCF5272_QSPI_BASE(BSP_MBAR); +pwm_regs_t *g_pwm_regs = (void *) MCF5272_PWM_BASE(BSP_MBAR); +dma_regs_t *g_dma_regs = (void *) MCF5272_DMAC_BASE(BSP_MBAR); +uart_regs_t *g_uart0_regs = (void *) MCF5272_UART0_BASE(BSP_MBAR); +uart_regs_t *g_uart1_regs = (void *) MCF5272_UART1_BASE(BSP_MBAR); +timer_regs_t *g_timer_regs = (void *) MCF5272_TIMER_BASE(BSP_MBAR); +plic_regs_t *g_plic_regs = (void *) MCF5272_PLIC_BASE(BSP_MBAR); +enet_regs_t *g_enet_regs = (void *) MCF5272_ENET_BASE(BSP_MBAR); +usb_regs_t *g_usb_regs = (void *) MCF5272_USB_BASE(BSP_MBAR); + +#define m68k_set_srambar( _rambar0 ) \ + __asm__ volatile ( "movec %0,%%rambar0\n\t" \ + "nop\n\t" \ + : : "d" (_rambar0) ) + +#define m68k_set_mbar( _mbar ) \ + __asm__ volatile ( "movec %0,%%mbar\n\t" \ + "nop\n\t" \ + : : "d" (_mbar) ) + +#define mcf5272_enable_cache() \ + m68k_set_cacr( MCF5272_CACR_CENB ) + + +#define mcf5272_disable_cache() \ + __asm__ volatile ( "nop\n\t" \ + "movec %0,%%cacr\n\t" \ + "nop\n\t" \ + "movec %0,%%cacr\n\t" \ + "nop\n\t" \ + : : "d" (MCF5272_CACR_CINV) ) + +/* + * Initialize MCF5272 on-chip modules + */ +void init5272(void) +{ + /* Invalidate the cache - WARNING: It won't complete for 64 clocks */ + m68k_set_cacr(MCF5272_CACR_CINV); + + /* Set Module Base Address register */ + m68k_set_mbar((BSP_MBAR & MCF5272_MBAR_BA) | MCF5272_MBAR_V); + + /* Set RAM Base Address register */ + m68k_set_srambar((BSP_RAMBAR & MCF5272_RAMBAR_BA) | MCF5272_RAMBAR_V); + + /* Set System Control Register: + * Enet has highest priority, 16384 bus cycles before timeout + */ + g_sim_regs->scr = (MCF5272_SCR_HWR_16384); + + /* System Protection Register: + * Enable Hardware watchdog timer. + */ + g_sim_regs->spr = MCF5272_SPR_HWTEN; + + /* Clear and mask all interrupts */ + g_intctrl_regs->icr1 = 0x88888888; + g_intctrl_regs->icr2 = 0x88888888; + g_intctrl_regs->icr3 = 0x88888888; + g_intctrl_regs->icr4 = 0x88880000; + + /* Copy the interrupt vector table to SRAM */ + { + uint32_t *inttab = (uint32_t *)&INTERRUPT_VECTOR; + uint32_t *intvec = (uint32_t *)BSP_RAMBAR; + register int i; + for (i = 0; i < 256; i++) { + *(intvec++) = *(inttab++); + } + } + m68k_set_vbr(BSP_RAMBAR); + + + /* + * Setup ACRs so that if cache turned on, periphal accesses + * are not messed up. (Non-cacheable, serialized) + */ + m68k_set_acr0(MCF5272_ACR_BASE(BSP_MEM_ADDR_SDRAM) | + MCF5272_ACR_MASK(BSP_MEM_MASK_SDRAM) | + MCF5272_ACR_EN | + MCF5272_ACR_SM_ANY); + +/* + m68k_set_acr1 (MCF5206E_ACR_BASE(BSP_MEM_ADDR_FLASH) | + MCF5206E_ACR_MASK(BSP_MEM_MASK_FLASH) | + MCF5206E_ACR_EN | + MCF5206E_ACR_SM_ANY); +*/ + + /* Enable the caches */ + m68k_set_cacr(MCF5272_CACR_CENB | + MCF5272_CACR_DCM); /* Default is not cached */ + +/* + * Copy data, clear BSS, switch stacks and call boot_card() + */ +/* +CopyDataClearBSSAndStart(BSP_MEM_SIZE_ESRAM - 0x400); +*/ + clear_bss(); + start_csb360(); + +} diff --git a/bsps/m68k/csb360/start/linkcmds b/bsps/m68k/csb360/start/linkcmds new file mode 100644 index 0000000000..09670c156d --- /dev/null +++ b/bsps/m68k/csb360/start/linkcmds @@ -0,0 +1,174 @@ +/* + * This file contains GNU linker directives for the Cogent + * CSB360 development board. + * + * Copyright (C) 2004 Cogent Computer Systems + * Author: Jay Monkman <jtm@lopingdog.com> + */ + +/* + * Declare size of heap. + * A heap size of 0 means "Use all available memory for the heap". + * Initial stack located in on-chip SRAM and not declared there. + */ +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +RamBase = DEFINED(RamBase) ? RamBase : 0x00100000; +RamSize = DEFINED(RamSize) ? RamSize : 31M; + +/* This is needed for _CPU_ISR_install_vector - +* WARNING: it MUST match BSP_RAMBAR !!!!!!!!!!! */ +_VBR = 0x20000000; + +ENTRY(start) +STARTUP(start.o) + +/* + * Setup the memory map of the CSB360 board + * + * The "ram" section is placed in RAM after the space used by umon. + * + */ +MEMORY +{ + ram : ORIGIN = 0x00100000, LENGTH = 31M +} + +SECTIONS +{ + + /* + * Text, data and bss segments + */ + .text : + { + RamBase = .; + RamBase = .; + CREATE_OBJECT_SYMBOLS + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + */ + . = ALIGN (16); + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + . = ALIGN (16); + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = .; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (etext = .); + + } > ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + + .data : + { + copy_start = .; + *(.shdata) + . = ALIGN (0x10); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + . = ALIGN (0x10); + *(.gcc_exc) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (0x10); + *(.gnu.linkonce.d*) + . = ALIGN (0x10); + _edata = .; + copy_end = .; + } > ram + + .bss : + { + clear_start = . ; + *(.shbss) + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN(0x10); + _end = .; + + clear_end = .; + + WorkAreaBase = .; + WorkAreaBase = .; + + } > ram + + .stab 0 (NOLOAD) : + { + *(.stab) + } + + .stabstr 0 (NOLOAD) : + { + *(.stabstr) + } + +} diff --git a/bsps/m68k/gen68340/start/bsp_specs b/bsps/m68k/gen68340/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/gen68340/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/gen68340/start/dumpanic.c b/bsps/m68k/gen68340/start/dumpanic.c new file mode 100644 index 0000000000..7f82ab3a77 --- /dev/null +++ b/bsps/m68k/gen68340/start/dumpanic.c @@ -0,0 +1,190 @@ +/* + * M68340/349 registers and stack dump if an exception is raised + */ + +/* + * Author: + * Pascal Cadic + * France Telecom - CNET/DSM/TAM/CAT + * 4, rue du Clos Courtel + * 35512 CESSON-SEVIGNE + * FRANCE + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <rtems/bspIo.h> + +const char *exceptionName[] = { + "INITIAL STACK POINTER", + "INITIAL PROGRAM COUNTER", + "BUS ERROR", + "ADDRESS ERROR", + "ILLEGAL INSTRUCTION", + "DIVISION BY ZERO", + "CHK, CHK2", + "TRAPcc, TRAPv", + "PRIVILEGE VIOLATION", + "TRACE", + "LINE A EMULATOR", + "LINE F EMULATOR", + "HARDWARE BREAK", + "COPROCESSOR PROTOCOL VIOLATION", + "FORMAT ERROR", + "UNINITIALIZED INTERRUPT", + "RESERVED 16", + "RESERVED 17", + "RESERVED 18", + "RESERVED 19", + "RESERVED 20", + "RESERVED 21", + "RESERVED 22", + "RESERVED 23", + "SPURIOUS INTERRUPT", + "LEVEL 1 AUTOVECTOR", + "LEVEL 2 AUTOVECTOR", + "LEVEL 3 AUTOVECTOR", + "LEVEL 4 AUTOVECTOR", + "LEVEL 5 AUTOVECTOR", + "LEVEL 6 AUTOVECTOR", + "LEVEL 7 AUTOVECTOR", + "TRAP 1", + "TRAP 2", + "TRAP 3", + "TRAP 4", + "TRAP 5", + "TRAP 6", + "TRAP 7", + "TRAP 8", + "TRAP 9", + "TRAP 10", + "TRAP 11", + "TRAP 12", + "TRAP 13", + "TRAP 14", + "TRAP 15", + "VECTOR 48", + "VECTOR 49", + "VECTOR 50", + "VECTOR 51", + "VECTOR 52", + "VECTOR 53", + "VECTOR 54", + "VECTOR 55", + "VECTOR 56", + "VECTOR 57", + "VECTOR 58", + "VECTOR 59", + "VECTOR 60", + "VECTOR 61", + "VECTOR 62", + "VECTOR 63", + }; + +typedef struct { + unsigned long pc; + unsigned short sr; + unsigned short format_id; + unsigned long d0, d1, d2, d3, d4, d5, d6, d7; + unsigned long a0, a1, a2, a3, a4, a5, a6, a7; + unsigned long sfc, dfc, vbr; +} boot_panic_registers_t; + +boot_panic_registers_t _boot_panic_registers; + +/****************************************************** + Name: _dbug_dump + Input parameters: sr, pc, stack pointer, + size to display + Output parameters: - + Description: display the supervisor stack + *****************************************************/ +static void _dbug_dump( + unsigned short sr, + void* pc, + unsigned short *stack, + int size +) +{ + int i; + + printk("%x : %x \t%x",0,sr,(unsigned short)(((unsigned)pc)>>16)); + for (i=2; i<size; i++) { + if ((i%8)==0) printk("\n%x :",i/8); + printk(" %x\t",stack[i-2]); + } + printk("\n"); +} + +/****************************************************** + Name: _dbug_dump + Input parameters: - + Output parameters: - + Description: display microcontroler state. Registers + values are stored in _boot_panic_registers + which is filled in _uhoh ASM routine + *****************************************************/ +void _dbug_dumpanic(void) +{ + int c; + void *faultedAddr, *pc; + unsigned short vector, status; + unsigned char frametype, *stack; + #define ESCAPE 27 + + stack = (unsigned char*)(_boot_panic_registers.a7); + do { + status = _boot_panic_registers.sr; + pc = (void*)_boot_panic_registers.pc; + faultedAddr = *(void**)(stack+4); + vector = (_boot_panic_registers.format_id&0x0FFF)>>2; + frametype = (_boot_panic_registers.format_id&0xF000)>>12; + + printk("\n---------------------------------------------\n"); + if (vector<64) + printk("%s",exceptionName[vector]); + else { + printk("RESERVED USER"); + } + printk(" exception (vector %x, type %x)\n",vector,frametype); + printk("---------------------------------------------\n"); + printk("PC : %p ",pc); + printk("A7 : 0x%lx ",_boot_panic_registers.a7); + printk("SR : 0x%x\n",status); + if (frametype==0x0c) { + printk("\nfaulted address = %p\n",faultedAddr); + } + printk("---------------------------------------------\n"); + printk(" panic regs\n"); + printk("---------------------------------------------\n"); + printk("D[0..3] : %lx \t%lx \t%lx \t%lx\n", + _boot_panic_registers.d0,_boot_panic_registers.d1, + _boot_panic_registers.d2,_boot_panic_registers.d3); + printk("D[4..7] : %lx \t%lx \t%lx \t%lx\n", + _boot_panic_registers.d4,_boot_panic_registers.d5, + _boot_panic_registers.d6,_boot_panic_registers.d7); + printk("A[0..3] : %lx \t%lx \t%lx \t%lx\n", + _boot_panic_registers.a0,_boot_panic_registers.a1, + _boot_panic_registers.a2,_boot_panic_registers.a3); + printk("A[4..7] : %lx \t%lx \t%lx \t%lx\n", + _boot_panic_registers.a4,_boot_panic_registers.a5, + _boot_panic_registers.a6,_boot_panic_registers.a7); + + printk(" SFC : %lx",_boot_panic_registers.sfc); + printk(" DFC : %lx\n",_boot_panic_registers.dfc); + printk(" VBR : %lx\n",_boot_panic_registers.vbr); + printk("---------------------------------------------\n"); + printk(" panic stack\n"); + printk("---------------------------------------------\n"); + _dbug_dump(status, pc, (unsigned short*)stack,64*2); + + printk("---------------------------------------------\n"); + printk("press escape to reboot\n"); + } while ((c=getchark())!=ESCAPE); +} diff --git a/bsps/m68k/gen68340/start/init68340.c b/bsps/m68k/gen68340/start/init68340.c new file mode 100644 index 0000000000..ee30f415e9 --- /dev/null +++ b/bsps/m68k/gen68340/start/init68340.c @@ -0,0 +1,38 @@ +/* + * MC68340/349 support routines + * + * Geoffroy Montel + * France Telecom - CNET/DSM/TAM/CAT + * 4, rue du Clos Courtel + * 35512 CESSON-SEVIGNE + * FRANCE + * + * e-mail: g_montel@yahoo.com + */ + +#include <rtems.h> +#include <bsp.h> + +extern void _CopyDataClearBSSAndStart (void); + +/* + * Initialize MC68340 + */ +void _Init68340 (void) +{ + rtems_isr_entry *vbr; + int i; + + /* + * Copy the exception vector table to system RAM + */ + m68k_get_vbr (vbr); + for (i = 0; i < 256; ++i) + M68Kvec[i] = vbr[i]; + m68k_set_vbr (M68Kvec); + + /* + * Copy data, clear BSS, switch stacks and call main() + */ + _CopyDataClearBSSAndStart (); +} diff --git a/bsps/m68k/gen68340/start/linkcmds b/bsps/m68k/gen68340/start/linkcmds new file mode 100644 index 0000000000..860115930e --- /dev/null +++ b/bsps/m68k/gen68340/start/linkcmds @@ -0,0 +1,248 @@ +/* + * This file contains GNU linker directives for a generic MC68340/349 board. + * Variations in hardware type and dynamic memory size can be made + * by overriding some values with linker command-line arguments. + * + * ATTENTION: RAM and ROM placement must accord those in start340.S!! + * (next time I'll use some shared variables :) ) + * + * Geoffroy Montel + * France Telecom - CNET/DSM/TAM/CAT + * 4, rue du Clos Courtel + * 35512 CESSON-SEVIGNE + * FRANCE + * + * e-mail: g_montel@yahoo.com + */ + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x10000000; +RamSize = DEFINED(RamSize) ? RamSize : 4M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x1000; + +/* + * Declare on-board memory. + * It would be nice if the ram length could be given as + * LENGTH=RamSize, but gld doesn't allow non-constant + * values in the LENGTH expression. + */ +MEMORY { + ram : ORIGIN = 0x10000000, LENGTH = 4M + rom : ORIGIN = 0x01000000, LENGTH = 4M +/* dpram : ORIGIN = 0xFE000000, LENGTH = 8k */ +} + +ENTRY(start) +STARTUP(start.o) + +/* + * Declare low-order three octets of Ethernet address. + */ +ETHERNET_ADDRESS = DEFINED(ETHERNET_ADDRESS) ? ETHERNET_ADDRESS : 0xDEAD12; + +/* + * Load objects + */ +SECTIONS { + + /* + * Boot PROM + */ + rom : { + _RomBase = .; + __RomBase = .; + } >rom + + /* + * Dynamic RAM + */ + ram : { + . = .; + } >ram + + /* + * Text, data and bss segments + */ + .text : { + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (_etext = .); + } >ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : { + PROVIDE (_copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + } >ram + .bss : { + M68Kvec = .; + . += (256 * 4); + _clear_start = .; + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + + . += _StackSize; + . = ALIGN (16); + _stack_init = .; + _clear_end = .; + + WorkAreaBase = .; + } >ram + + /* + * On-chip memory/peripherals + * + */ + dpram : { + m340 = .; + _m340 = .; + . += (8 * 1024); + } >ram + + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + + /* DWARF debug sections. + Symbols in the DWARF debugging sections are relative to the beginning + of the section so we begin them at 0. */ + /* DWARF 1 */ + .debug 0 : { *(.debug) } + .line 0 : { *(.line) } + + /* GNU DWARF 1 extensions */ + .debug_srcinfo 0 : { *(.debug_srcinfo) } + .debug_sfnames 0 : { *(.debug_sfnames) } + + /* DWARF 1.1 and DWARF 2 */ + .debug_aranges 0 : { *(.debug_aranges) } + .debug_pubnames 0 : { *(.debug_pubnames) } + + /* DWARF 2 */ + .debug_info 0 : { *(.debug_info) } + .debug_abbrev 0 : { *(.debug_abbrev) } + .debug_line 0 : { *(.debug_line) } + .debug_frame 0 : { *(.debug_frame) } + .debug_str 0 : { *(.debug_str) } + .debug_loc 0 : { *(.debug_loc) } + .debug_macinfo 0 : { *(.debug_macinfo) } + + /* SGI/MIPS DWARF 2 extensions */ + .debug_weaknames 0 : { *(.debug_weaknames) } + .debug_funcnames 0 : { *(.debug_funcnames) } + .debug_typenames 0 : { *(.debug_typenames) } + .debug_varnames 0 : { *(.debug_varnames) } + /* These must appear regardless of . */ +} diff --git a/bsps/m68k/gen68360/start/alloc360.c b/bsps/m68k/gen68360/start/alloc360.c new file mode 100644 index 0000000000..53f90876e4 --- /dev/null +++ b/bsps/m68k/gen68360/start/alloc360.c @@ -0,0 +1,94 @@ +/* + * MC68360 buffer descriptor allocation routines + * + * W. Eric Norum + * Saskatchewan Accelerator Laboratory + * University of Saskatchewan + * Saskatoon, Saskatchewan, CANADA + * eric@skatter.usask.ca + */ + +#include <rtems.h> +#include <bsp.h> +#include <rtems/m68k/m68360.h> +#include <rtems/error.h> + +/* + * Allocation order: + * - Dual-Port RAM section 1 + * - Dual-Port RAM section 3 + * - Dual-Port RAM section 0 + * - Dual-Port RAM section 2 + */ +static struct { + uint8_t *base; + uint32_t size; + uint32_t used; +} bdregions[] = { + { (uint8_t *)&m360.dpram1[0], sizeof m360.dpram1, 0 }, + { (uint8_t *)&m360.dpram3[0], sizeof m360.dpram3, 0 }, + { (uint8_t *)&m360.dpram0[0], sizeof m360.dpram0, 0 }, + { (uint8_t *)&m360.dpram2[0], sizeof m360.dpram2, 0 }, +}; + +/* + * Send a command to the CPM RISC processer + */ +void * +M360AllocateBufferDescriptors (int count) +{ + unsigned int i; + ISR_Level level; + void *bdp = NULL; + unsigned int want = count * sizeof(m360BufferDescriptor_t); + + /* + * Running with interrupts disabled is usually considered bad + * form, but this routine is probably being run as part of an + * initialization sequence so the effect shouldn't be too severe. + */ + _ISR_Local_disable (level); + for (i = 0 ; i < sizeof(bdregions) / sizeof(bdregions[0]) ; i++) { + /* + * Verify that the region exists. + * This test is necessary since some chips have + * less dual-port RAM. + */ + if (bdregions[i].used == 0) { + volatile uint8_t *cp = bdregions[i].base; + *cp = 0xAA; + if (*cp != 0xAA) { + bdregions[i].used = bdregions[i].size; + continue; + } + *cp = 0x55; + if (*cp != 0x55) { + bdregions[i].used = bdregions[i].size; + continue; + } + *cp = 0x0; + } + if (bdregions[i].size - bdregions[i].used >= want) { + bdp = bdregions[i].base + bdregions[i].used; + bdregions[i].used += want; + break; + } + } + _ISR_Local_enable (level); + if (bdp == NULL) + rtems_panic ("Can't allocate %d buffer descriptor(s).\n", count); + return bdp; +} + +void * +M360AllocateRiscTimers (int count) +{ + /* + * Convert the count to the number of buffer descriptors + * of equal or larger size. This ensures that all buffer + * descriptors are allocated with appropriate alignment. + */ + return M360AllocateBufferDescriptors (((count * 4) + + sizeof(m360BufferDescriptor_t) - 1) / + sizeof(m360BufferDescriptor_t)); +} diff --git a/bsps/m68k/gen68360/start/bsp_specs b/bsps/m68k/gen68360/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/gen68360/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/gen68360/start/init68360.c b/bsps/m68k/gen68360/start/init68360.c new file mode 100644 index 0000000000..67fed27a3b --- /dev/null +++ b/bsps/m68k/gen68360/start/init68360.c @@ -0,0 +1,846 @@ +/* + * MC68360 support routines + */ + +/* + * W. Eric Norum + * Saskatchewan Accelerator Laboratory + * University of Saskatchewan + * Saskatoon, Saskatchewan, CANADA + * eric@skatter.usask.ca + */ + +#include <bsp.h> +#include <rtems/m68k/m68360.h> + +extern void _CopyDataClearBSSAndStart (unsigned long ramSize); +extern void *RamBase; +extern void *_RomBase; /* From linkcmds */ + +/* + * Declare the m360 structure here for the benefit of the debugger + */ + +volatile m360_t m360; + +/* + * Send a command to the CPM RISC processer + */ + +void M360ExecuteRISC(uint16_t command) +{ + uint16_t sr; + + m68k_disable_interrupts (sr); + while (m360.cr & M360_CR_FLG) + continue; + m360.cr = command | M360_CR_FLG; + m68k_enable_interrupts (sr); +} + +/* + * Initialize MC68360 + */ +void _Init68360 (void) +{ + int i; + rtems_isr_entry *vbr; + unsigned long ramSize; + +#if (defined (__mc68040__)) + volatile unsigned long *RamBase_p; + + RamBase_p = (volatile unsigned long *)&RamBase; + + /* + ******************************************* + * Motorola 68040 and companion-mode 68360 * + ******************************************* + */ + + /* + * Step 6: Is this a power-up reset? + * For now we just ignore this and do *all* the steps + * Someday we might want to: + * if (Hard, Loss of Clock, Power-up) + * Do all steps + * else if (Double bus fault, watchdog or soft reset) + * Skip to step 12 + * else (must be a reset command) + * Skip to step 14 + */ + + /* + * Step 7: Deal with clock synthesizer + * HARDWARE: + * Change if you're not using an external 25 MHz oscillator. + */ + m360.clkocr = 0x83; /* No more writes, full-power CLKO2 */ + m360.pllcr = 0xD000; /* PLL, no writes, no prescale, + no LPSTOP slowdown, PLL X1 */ + m360.cdvcr = 0x8000; /* No more writes, no clock division */ + + /* + * Step 8: Initialize system protection + * Enable watchdog + * Watchdog causes system reset + * Next-to-slowest watchdog timeout (21 seconds with 25 MHz oscillator) + * Enable double bus fault monitor + * Enable bus monitor for external cycles + * 1024 clocks for external timeout + */ + m360.sypcr = 0xEC; + + /* + * Step 9: Clear parameter RAM and reset communication processor module + */ + for (i = 0 ; i < 192 ; i += sizeof (long)) { + *((long *)((char *)&m360 + 0xC00 + i)) = 0; + *((long *)((char *)&m360 + 0xD00 + i)) = 0; + *((long *)((char *)&m360 + 0xE00 + i)) = 0; + *((long *)((char *)&m360 + 0xF00 + i)) = 0; + } + M360ExecuteRISC (M360_CR_RST); + + /* + * Step 10: Write PEPAR + * SINTOUT standard M68000 family interrupt level encoding + * CF1MODE=10 (BCLRO* output) + * No RAS1* double drive + * A31 - A28 + * AMUX output + * CAS2* - CAS3* + * CAS0* - CAS1* + * CS7* + * AVEC* + */ + m360.pepar = 0x3440; + + /* + * Step 11: Remap Chip Select 0 (CS0*), set up GMR + */ + /* + * 512 addresses per DRAM page (256K DRAM chips) + * 70 nsec DRAM + * 180 nsec ROM (3 wait states) + */ + m360.gmr = M360_GMR_RCNT(23) | M360_GMR_RFEN | + M360_GMR_RCYC(0) | M360_GMR_PGS(1) | + M360_GMR_DPS_32BIT | M360_GMR_NCS | + M360_GMR_TSS40; + m360.memc[0].br = (unsigned long)&_RomBase | M360_MEMC_BR_WP | + M360_MEMC_BR_V; + m360.memc[0].or = M360_MEMC_OR_WAITS(3) | M360_MEMC_OR_1MB | + M360_MEMC_OR_32BIT; + + /* + * Step 12: Initialize the system RAM + */ + /* + * Set up option/base registers + * 1M DRAM + * 70 nsec DRAM + * Enable burst mode + * No parity checking + * Wait for chips to power up + * Perform 8 read cycles + */ + ramSize = 1 * 1024 * 1024; + m360.memc[1].or = M360_MEMC_OR_TCYC(0) | + M360_MEMC_OR_1MB | + M360_MEMC_OR_DRAM; + m360.memc[1].br = (unsigned long)&RamBase | + M360_MEMC_BR_BACK40 | + M360_MEMC_BR_V; + for (i = 0; i < 50000; i++) + continue; + for (i = 0; i < 8; ++i) { + unsigned long rambase_value; + rambase_value = *RamBase_p; + (void) rambase_value; /* avoid set but not used warning */ + } + + /* + * Step 13: Copy the exception vector table to system RAM + */ + m68k_get_vbr (vbr); + for (i = 0; i < 256; ++i) + M68Kvec[i] = vbr[i]; + m68k_set_vbr (M68Kvec); + + /* + * Step 14: More system initialization + * SDCR (Serial DMA configuration register) + * Enable SDMA during FREEZE + * Give SDMA priority over all interrupt handlers + * Set DMA arbiration level to 4 + * CICR (CPM interrupt configuration register): + * SCC1 requests at SCCa position + * SCC2 requests at SCCb position + * SCC3 requests at SCCc position + * SCC4 requests at SCCd position + * Interrupt request level 4 + * Maintain original priority order + * Vector base 128 + * SCCs priority grouped at top of table + */ + m360.sdcr = M360_SDMA_SISM_7 | M360_SDMA_SAID_4; + m360.cicr = (3 << 22) | (2 << 20) | (1 << 18) | (0 << 16) | + (4 << 13) | (0x1F << 8) | (128); + + /* + * Step 15: Set module configuration register + * Bus request MC68040 Arbitration ID 3 + * Bus asynchronous timing mode (work around bug in Rev. B) + * Arbitration asynchronous timing mode + * Disable timers during FREEZE + * Disable bus monitor during FREEZE + * BCLRO* arbitration level 3 + * No show cycles + * User/supervisor access + * Bus clear in arbitration ID level 3 + * SIM60 interrupt sources higher priority than CPM + */ + m360.mcr = 0x6000EC3F; + +#elif (defined (M68360_ATLAS_HSB)) + /* + ****************************************** + * Standalone Motorola 68360 -- ATLAS HSB * + ****************************************** + */ + + /* + * Step 6: Is this a power-up reset? + * For now we just ignore this and do *all* the steps + * Someday we might want to: + * if (Hard, Loss of Clock, Power-up) + * Do all steps + * else if (Double bus fault, watchdog or soft reset) + * Skip to step 12 + * else (must be a CPU32+ reset command) + * Skip to step 14 + */ + + /* + * Step 7: Deal with clock synthesizer + * HARDWARE: + * Change if you're not using an external 25 MHz oscillator. + */ + m360.clkocr = 0x8F; /* No more writes, no clock outputs */ + m360.pllcr = 0xD000; /* PLL, no writes, no prescale, + no LPSTOP slowdown, PLL X1 */ + m360.cdvcr = 0x8000; /* No more writes, no clock division */ + + /* + * Step 8: Initialize system protection + * Enable watchdog + * Watchdog causes system reset + * Next-to-slowest watchdog timeout (21 seconds with 25 MHz oscillator) + * Enable double bus fault monitor + * Enable bus monitor for external cycles + * 1024 clocks for external timeout + */ + m360.sypcr = 0xEC; + + /* + * Step 9: Clear parameter RAM and reset communication processor module + */ + for (i = 0 ; i < 192 ; i += sizeof (long)) { + *((long *)((char *)&m360 + 0xC00 + i)) = 0; + *((long *)((char *)&m360 + 0xD00 + i)) = 0; + *((long *)((char *)&m360 + 0xE00 + i)) = 0; + *((long *)((char *)&m360 + 0xF00 + i)) = 0; + } + M360ExecuteRISC (M360_CR_RST); + + /* + * Step 10: Write PEPAR + * SINTOUT not used (CPU32+ mode) + * CF1MODE=00 (CONFIG1 input) + * RAS1* double drive + * WE0* - WE3* + * OE* output + * CAS2* - CAS3* + * CAS0* - CAS1* + * CS7* + * AVEC* + * HARDWARE: + * Change if you are using a different memory configuration + * (static RAM, external address multiplexing, etc). + */ + m360.pepar = 0x0180; + + /* + * Step 11: Remap Chip Select 0 (CS0*), set up GMR + */ + m360.gmr = M360_GMR_RCNT(12) | M360_GMR_RFEN | + M360_GMR_RCYC(0) | M360_GMR_PGS(1) | + M360_GMR_DPS_32BIT | M360_GMR_DWQ | + M360_GMR_GAMX; + m360.memc[0].br = (unsigned long)&_RomBase | M360_MEMC_BR_WP | + M360_MEMC_BR_V; + m360.memc[0].or = M360_MEMC_OR_WAITS(3) | M360_MEMC_OR_1MB | + M360_MEMC_OR_8BIT; + + /* + * Step 12: Initialize the system RAM + */ + ramSize = 2 * 1024 * 1024; + /* first bank 1MByte DRAM */ + m360.memc[1].or = M360_MEMC_OR_TCYC(2) | M360_MEMC_OR_1MB | + M360_MEMC_OR_PGME | M360_MEMC_OR_DRAM; + m360.memc[1].br = (unsigned long)&RamBase | M360_MEMC_BR_V; + + /* second bank 1MByte DRAM */ + m360.memc[2].or = M360_MEMC_OR_TCYC(2) | M360_MEMC_OR_1MB | + M360_MEMC_OR_PGME | M360_MEMC_OR_DRAM; + m360.memc[2].br = ((unsigned long)&RamBase + 0x100000) | + M360_MEMC_BR_V; + + /* flash rom socket U6 on CS5 */ + m360.memc[5].br = (unsigned long)ATLASHSB_ROM_U6 | M360_MEMC_BR_WP | + M360_MEMC_BR_V; + m360.memc[5].or = M360_MEMC_OR_WAITS(2) | M360_MEMC_OR_512KB | + M360_MEMC_OR_8BIT; + + /* CSRs on CS7 */ + m360.memc[7].or = M360_MEMC_OR_TCYC(4) | M360_MEMC_OR_64KB | + M360_MEMC_OR_8BIT; + m360.memc[7].br = ATLASHSB_ESR | 0x01; + for (i = 0; i < 50000; i++) + continue; + for (i = 0; i < 8; ++i) + *((volatile unsigned long *)(unsigned long)&RamBase); + + /* + * Step 13: Copy the exception vector table to system RAM + */ + m68k_get_vbr (vbr); + for (i = 0; i < 256; ++i) + M68Kvec[i] = vbr[i]; + m68k_set_vbr (M68Kvec); + + /* + * Step 14: More system initialization + * SDCR (Serial DMA configuration register) + * Enable SDMA during FREEZE + * Give SDMA priority over all interrupt handlers + * Set DMA arbiration level to 4 + * CICR (CPM interrupt configuration register): + * SCC1 requests at SCCa position + * SCC2 requests at SCCb position + * SCC3 requests at SCCc position + * SCC4 requests at SCCd position + * Interrupt request level 4 + * Maintain original priority order + * Vector base 128 + * SCCs priority grouped at top of table + */ + m360.sdcr = M360_SDMA_SISM_7 | M360_SDMA_SAID_4; + m360.cicr = (3 << 22) | (2 << 20) | (1 << 18) | (0 << 16) | + (4 << 13) | (0x1F << 8) | (128); + + /* + * Step 15: Set module configuration register + * Disable timers during FREEZE + * Enable bus monitor during FREEZE + * BCLRO* arbitration level 3 + */ + +#elif defined(PGH360) + /* + * Step 6: Is this a power-up reset? + * For now we just ignore this and do *all* the steps + * Someday we might want to: + * if (Hard, Loss of Clock, Power-up) + * Do all steps + * else if (Double bus fault, watchdog or soft reset) + * Skip to step 12 + * else (must be a CPU32+ reset command) + * Skip to step 14 + */ + + /* + * Step 7: Deal with clock synthesizer + * HARDWARE: + * Change if you're not using an external 25 MHz oscillator. + */ + m360.clkocr = 0x8e; /* No more writes, CLKO1=1/3, CLKO2=off */ + /* + * adjust crystal to average between 4.19 MHz and 4.00 MHz + * reprogram pll + */ + m360.pllcr = 0xA000+(24576000/((4000000+4194304)/2/128))-1; + /* LPSTOP slowdown, PLL /128*??? */ + m360.cdvcr = 0x8000; /* No more writes, no clock division */ + + /* + * Step 8: Initialize system protection + * Enable watchdog + * Watchdog causes system reset + * 128 sec. watchdog timeout + * Enable double bus fault monitor + * Enable bus monitor external + * 128 clocks for external timeout + */ + m360.sypcr = 0xEF; + /* + * also initialize the SWP bit in PITR to 1 + */ + m360.pitr |= 0x0200; + /* + * and trigger SWSR twice to ensure, that interval starts right now + */ + m360.swsr = 0x55; + m360.swsr = 0xAA; + m360.swsr = 0x55; + m360.swsr = 0xAA; + /* + * Step 9: Clear parameter RAM and reset communication processor module + */ + for (i = 0 ; i < 192 ; i += sizeof (long)) { + *((long *)((char *)&m360 + 0xC00 + i)) = 0; + *((long *)((char *)&m360 + 0xD00 + i)) = 0; + *((long *)((char *)&m360 + 0xE00 + i)) = 0; + *((long *)((char *)&m360 + 0xF00 + i)) = 0; + } + M360ExecuteRISC (M360_CR_RST); + + /* + * Step 10: Write PEPAR + * SINTOUT not used (CPU32+ mode) + * CF1MODE=00 (CONFIG1 input) + * IPIPE1 + * WE0-3 + * OE* output + * CAS2* / CAS3* + * CAS0* / CAS1* + * CS7* + * AVEC* + * HARDWARE: + * Change if you are using a different memory configuration + * (static RAM, external address multiplexing, etc). + */ + m360.pepar = 0x0080; + /* + * Step 11: Remap Chip Select 0 (CS0*), set up GMR + * no DRAM support + * HARDWARE: + * Change if you are using a different memory configuration + */ + m360.gmr = M360_GMR_RCNT(23) | M360_GMR_RFEN | M360_GMR_RCYC(0) | + M360_GMR_PGS(6) | M360_GMR_DPS_32BIT | M360_GMR_DWQ | + M360_GMR_GAMX; + + m360.memc[0].br = (unsigned long)&_RomBase | M360_MEMC_BR_WP | + M360_MEMC_BR_V; + m360.memc[0].or = M360_MEMC_OR_WAITS(3) | M360_MEMC_OR_512KB | + M360_MEMC_OR_8BIT; + + /* + * Step 12: Initialize the system RAM + * Set up option/base registers + * 16 MB DRAM + * 1 wait state + * HARDWARE: + * Change if you are using a different memory configuration + * NOTE: no Page mode possible for EDO RAMs (?) + */ + ramSize = 16 * 1024 * 1024; + m360.memc[7].or = M360_MEMC_OR_TCYC(1) | M360_MEMC_OR_16MB | + M360_MEMC_OR_FCMC(0) | /* M360_MEMC_OR_PGME | */ + M360_MEMC_OR_32BIT | M360_MEMC_OR_DRAM; + m360.memc[7].br = (unsigned long)&RamBase | M360_MEMC_BR_V; + + /* + * FIXME: here we should wait for 8 refresh cycles... + */ + /* + * Step 12a: test the ram, if wanted + * FIXME: when do we call this? + * -> only during firmware execution + * -> perform intesive test only on request + * -> ensure, that results are stored properly + */ +#if 0 /* FIXME: activate RAM tests again */ + { + void *ram_base, *ram_end, *code_loc; + extern char ramtest_start,ramtest_end; + ram_base = &ramtest_start; + ram_end = &ramtest_end; + code_loc = (void *)ramtest_exec; + if ((ram_base < ram_end) && + !((ram_base <= code_loc) && (code_loc < ram_end))) { + ramtest_exec(ram_base,ram_end); + } + } +#endif + /* + * Step 13: Copy the exception vector table to system RAM + */ + m68k_get_vbr (vbr); + for (i = 0; i < 256; ++i) + M68Kvec[i] = vbr[i]; + m68k_set_vbr (M68Kvec); + + /* + * Step 14: More system initialization + * SDCR (Serial DMA configuration register) + * Disable SDMA during FREEZE + * Give SDMA priority over all interrupt handlers + * Set DMA arbiration level to 4 + * CICR (CPM interrupt configuration register): + * SCC1 requests at SCCa position + * SCC2 requests at SCCb position + * SCC3 requests at SCCc position + * SCC4 requests at SCCd position + * Interrupt request level 4 + * Maintain original priority order + * Vector base 128 + * SCCs priority grouped at top of table + */ + m360.sdcr = M360_SDMA_SISM_7 | M360_SDMA_SAID_4; + m360.cicr = (3 << 22) | (2 << 20) | (1 << 18) | (0 << 16) | + (4 << 13) | (0x1F << 8) | (128); + + /* + * Step 15: Set module configuration register + * Disable timers during FREEZE + * Enable bus monitor during FREEZE + * BCLRO* arbitration level 3 + * No show cycles + * User/supervisor access + * Bus clear interupt service level 7 + * SIM60 interrupt sources higher priority than CPM + */ + m360.mcr = 0x4C7F; + +#elif (defined (GEN68360_WITH_SRAM)) + /* + *************************************************** + * Generic Standalone Motorola 68360 * + * As described in MC68360 User's Manual * + * But uses SRAM instead of DRAM * + * CS0* - 512kx8 flash memory * + * CS1* - 512kx32 static RAM * + * CS2* - 512kx32 static RAM * + *************************************************** + */ + + /* + * Step 7: Deal with clock synthesizer + * HARDWARE: + * Change if you're not using an external oscillator which + * oscillates at the system clock rate. + */ + m360.clkocr = 0x8F; /* No more writes, no clock outputs */ + m360.pllcr = 0xD000; /* PLL, no writes, no prescale, + no LPSTOP slowdown, PLL X1 */ + m360.cdvcr = 0x8000; /* No more writes, no clock division */ + + /* + * Step 8: Initialize system protection + * Enable watchdog + * Watchdog causes system reset + * Next-to-slowest watchdog timeout (21 seconds with 25 MHz oscillator) + * Enable double bus fault monitor + * Enable bus monitor for external cycles + * 1024 clocks for external timeout + */ + m360.sypcr = 0xEC; + + /* + * Step 9: Clear parameter RAM and reset communication processor module + */ + for (i = 0 ; i < 192 ; i += sizeof (long)) { + *((long *)((char *)&m360 + 0xC00 + i)) = 0; + *((long *)((char *)&m360 + 0xD00 + i)) = 0; + *((long *)((char *)&m360 + 0xE00 + i)) = 0; + *((long *)((char *)&m360 + 0xF00 + i)) = 0; + } + M360ExecuteRISC (M360_CR_RST); + + /* + * Step 10: Write PEPAR + * SINTOUT not used (CPU32+ mode) + * CF1MODE=00 (CONFIG1 input) + * IPIPE1* + * WE0* - WE3* + * OE* output + * CAS2* - CAS3* + * CAS0* - CAS1* + * CS7* + * AVEC* + * HARDWARE: + * Change if you are using a different memory configuration + * (static RAM, external address multiplexing, etc). + */ + m360.pepar = 0x0080; + + /* + * Step 11: Set up GMR + * + */ + m360.gmr = 0x0; + + /* + * Step 11a: Remap 512Kx8 flash memory on CS0* + * 2 wait states + * Make it read-only for now + */ + m360.memc[0].br = (unsigned long)&_RomBase | M360_MEMC_BR_WP | + M360_MEMC_BR_V; + m360.memc[0].or = M360_MEMC_OR_WAITS(2) | M360_MEMC_OR_512KB | + M360_MEMC_OR_8BIT; + /* + * Step 12: Set up main memory + * 512Kx32 SRAM on CS1* + * 512Kx32 SRAM on CS2* + * 0 wait states + */ + ramSize = 4 * 1024 * 1024; + m360.memc[1].br = (unsigned long)&RamBase | M360_MEMC_BR_V; + m360.memc[1].or = M360_MEMC_OR_WAITS(0) | M360_MEMC_OR_2MB | + M360_MEMC_OR_32BIT; + m360.memc[2].br = ((unsigned long)&RamBase + 0x200000) | M360_MEMC_BR_V; + m360.memc[2].or = M360_MEMC_OR_WAITS(0) | M360_MEMC_OR_2MB | + M360_MEMC_OR_32BIT; + /* + * Step 13: Copy the exception vector table to system RAM + */ + m68k_get_vbr (vbr); + for (i = 0; i < 256; ++i) + M68Kvec[i] = vbr[i]; + m68k_set_vbr (M68Kvec); + + /* + * Step 14: More system initialization + * SDCR (Serial DMA configuration register) + * Enable SDMA during FREEZE + * Give SDMA priority over all interrupt handlers + * Set DMA arbiration level to 4 + * CICR (CPM interrupt configuration register): + * SCC1 requests at SCCa position + * SCC2 requests at SCCb position + * SCC3 requests at SCCc position + * SCC4 requests at SCCd position + * Interrupt request level 4 + * Maintain original priority order + * Vector base 128 + * SCCs priority grouped at top of table + */ + m360.sdcr = M360_SDMA_SISM_7 | M360_SDMA_SAID_4; + m360.cicr = (3 << 22) | (2 << 20) | (1 << 18) | (0 << 16) | + (4 << 13) | (0x1F << 8) | (128); + + /* + * Step 15: Set module configuration register + * Disable timers during FREEZE + * Enable bus monitor during FREEZE + * BCLRO* arbitration level 3 + * No show cycles + * User/supervisor access + * Bus clear interrupt service level 7 + * SIM60 interrupt sources higher priority than CPM + */ + m360.mcr = 0x4C7F; + +#else + volatile unsigned long *RamBase_p; + + RamBase_p = (volatile unsigned long *)&RamBase; + /* + *************************************************** + * Generic Standalone Motorola 68360 * + * As described in MC68360 User's Manual * + * Atlas ACE360 * + *************************************************** + */ + + /* + * Step 6: Is this a power-up reset? + * For now we just ignore this and do *all* the steps + * Someday we might want to: + * if (Hard, Loss of Clock, Power-up) + * Do all steps + * else if (Double bus fault, watchdog or soft reset) + * Skip to step 12 + * else (must be a CPU32+ reset command) + * Skip to step 14 + */ + + /* + * Step 7: Deal with clock synthesizer + * HARDWARE: + * Change if you're not using an external 25 MHz oscillator. + */ + m360.clkocr = 0x8F; /* No more writes, no clock outputs */ + m360.pllcr = 0xD000; /* PLL, no writes, no prescale, + no LPSTOP slowdown, PLL X1 */ + m360.cdvcr = 0x8000; /* No more writes, no clock division */ + + /* + * Step 8: Initialize system protection + * Enable watchdog + * Watchdog causes system reset + * Next-to-slowest watchdog timeout (21 seconds with 25 MHz oscillator) + * Enable double bus fault monitor + * Enable bus monitor for external cycles + * 1024 clocks for external timeout + */ + m360.sypcr = 0xEC; + + /* + * Step 9: Clear parameter RAM and reset communication processor module + */ + for (i = 0 ; i < 192 ; i += sizeof (long)) { + *((long *)((char *)&m360 + 0xC00 + i)) = 0; + *((long *)((char *)&m360 + 0xD00 + i)) = 0; + *((long *)((char *)&m360 + 0xE00 + i)) = 0; + *((long *)((char *)&m360 + 0xF00 + i)) = 0; + } + M360ExecuteRISC (M360_CR_RST); + + /* + * Step 10: Write PEPAR + * SINTOUT not used (CPU32+ mode) + * CF1MODE=00 (CONFIG1 input) + * RAS1* double drive + * WE0* - WE3* + * OE* output + * CAS2* - CAS3* + * CAS0* - CAS1* + * CS7* + * AVEC* + * HARDWARE: + * Change if you are using a different memory configuration + * (static RAM, external address multiplexing, etc). + */ + m360.pepar = 0x0180; + + /* + * Step 11: Remap Chip Select 0 (CS0*), set up GMR + * 32-bit DRAM + * Internal DRAM address multiplexing + * 60 nsec DRAM + * 180 nsec ROM (3 wait states) + * 15.36 usec DRAM refresh interval + * The DRAM page size selection is not modified since this + * startup code may be running in a bootstrap PROM or in + * a program downloaded by the bootstrap PROM. + */ + m360.gmr = (m360.gmr & 0x001C0000) | M360_GMR_RCNT(23) | + M360_GMR_RFEN | M360_GMR_RCYC(0) | + M360_GMR_DPS_32BIT | M360_GMR_NCS | + M360_GMR_GAMX; + m360.memc[0].br = (unsigned long)&_RomBase | M360_MEMC_BR_WP | + M360_MEMC_BR_V; + m360.memc[0].or = M360_MEMC_OR_WAITS(3) | M360_MEMC_OR_1MB | + M360_MEMC_OR_8BIT; + + /* + * Step 12: Initialize the system RAM + * Do this only if the DRAM has not already been set up + */ + if ((m360.memc[1].br & M360_MEMC_BR_V) == 0) { + /* + * Set up GMR DRAM page size, option and base registers + * Assume 16Mbytes of DRAM + * 60 nsec DRAM + */ + m360.gmr = (m360.gmr & ~0x001C0000) | M360_GMR_PGS(5); + m360.memc[1].or = M360_MEMC_OR_TCYC(0) | + M360_MEMC_OR_16MB | + M360_MEMC_OR_DRAM; + m360.memc[1].br = (unsigned long)&RamBase | M360_MEMC_BR_V; + + /* + * Wait for chips to power up + * Perform 8 read cycles + */ + for (i = 0; i < 50000; i++) + continue; + for (i = 0; i < 8; ++i) + *RamBase_p; + + /* + * Determine memory size (1, 4, or 16 Mbytes) + * Set GMR DRAM page size appropriately. + * The OR is left at 16 Mbytes. The bootstrap PROM places its + * .data and .bss segments at the top of the 16 Mbyte space. + * A 1 Mbyte or 4 Mbyte DRAM will show up several times in + * the memory map, but will work with the same bootstrap PROM. + */ + *(volatile char *)&RamBase = 0; + *((volatile char *)&RamBase+0x00C01800) = 1; + if (*(volatile char *)&RamBase) { + m360.gmr = (m360.gmr & ~0x001C0000) | M360_GMR_PGS(1); + } + else { + *((volatile char *)&RamBase+0x00801000) = 1; + if (*(volatile char *)&RamBase) { + m360.gmr = (m360.gmr & ~0x001C0000) | M360_GMR_PGS(3); + } + } + + /* + * Enable parity checking + */ + m360.memc[1].br |= M360_MEMC_BR_PAREN; + } + switch (m360.gmr & 0x001C0000) { + default: ramSize = 4 * 1024 * 1024; break; + case M360_GMR_PGS(1): ramSize = 1 * 1024 * 1024; break; + case M360_GMR_PGS(3): ramSize = 4 * 1024 * 1024; break; + case M360_GMR_PGS(5): ramSize = 16 * 1024 * 1024; break; + } + + /* + * Step 13: Copy the exception vector table to system RAM + */ + m68k_get_vbr (vbr); + for (i = 0; i < 256; ++i) + M68Kvec[i] = vbr[i]; + m68k_set_vbr (M68Kvec); + + /* + * Step 14: More system initialization + * SDCR (Serial DMA configuration register) + * Enable SDMA during FREEZE + * Give SDMA priority over all interrupt handlers + * Set DMA arbiration level to 4 + * CICR (CPM interrupt configuration register): + * SCC1 requests at SCCa position + * SCC2 requests at SCCb position + * SCC3 requests at SCCc position + * SCC4 requests at SCCd position + * Interrupt request level 4 + * Maintain original priority order + * Vector base 128 + * SCCs priority grouped at top of table + */ + m360.sdcr = M360_SDMA_SISM_7 | M360_SDMA_SAID_4; + m360.cicr = (3 << 22) | (2 << 20) | (1 << 18) | (0 << 16) | + (4 << 13) | (0x1F << 8) | (128); + + /* + * Step 15: Set module configuration register + * Disable timers during FREEZE + * Enable bus monitor during FREEZE + * BCLRO* arbitration level 3 + * No show cycles + * User/supervisor access + * Bus clear interrupt service level 7 + * SIM60 interrupt sources higher priority than CPM + */ + m360.mcr = 0x4C7F; +#endif + + /* + * Copy data, clear BSS, switch stacks and call main() + * Must pass ramSize as argument since the data/bss segment + * may be overwritten. + */ + _CopyDataClearBSSAndStart (ramSize); +} diff --git a/bsps/m68k/gen68360/start/linkcmds b/bsps/m68k/gen68360/start/linkcmds new file mode 100644 index 0000000000..4ffc8bb57a --- /dev/null +++ b/bsps/m68k/gen68360/start/linkcmds @@ -0,0 +1,209 @@ +/* + * This file contains GNU linker directives for a generic MC68360 board. + * Variations in memory size and allocation can be made by + * overriding some values with linker command-line arguments. + * + * Saskatchewan Accelerator Laboratory + * University of Saskatchewan + * Saskatoon, Saskatchewan, CANADA + * eric@skatter.usask.ca + */ + +/* + * Declare some sizes. + * A heap size of 0 means `use all available memory for the heap'. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 64M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x1000; + +/* + * Declare on-board memory. + */ +MEMORY { + ram : ORIGIN = 0x00000000, LENGTH = 64M + rom : ORIGIN = 0x0F000000, LENGTH = 1M + dpram : ORIGIN = 0x0E000000, LENGTH = 8k +} + +ENTRY(start) +STARTUP(start.o) + +/* + * Load objects + */ +SECTIONS { + /* + * Boot PROM + */ + rom : { + _RomBase = .; + } >rom + + /* + * Dynamic RAM + */ + ram : { + RamBase = .; + } >ram + + /* + * Text, data and bss segments + */ + .text : { + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (etext = .); + } >ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : { + _copy_start = .; + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (edata = .); + _copy_end = .; + } >ram + .bss : { + M68Kvec = .; + . += (256 * 4); + _clear_start = .; + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + + . += _StackSize; + . = ALIGN (16); + _stack_init = .; + _clear_end = .; + + WorkAreaBase = .; + } >ram + + /* + * On-chip memory/peripherals + */ + dpram : { + m360 = .; + . += (8 * 1024); + } >dpram + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + + /* DWARF debug sections. + Symbols in the DWARF debugging sections are relative to the beginning + of the section so we begin them at 0. */ + /* DWARF 1 */ + .debug 0 : { *(.debug) } + .line 0 : { *(.line) } + + /* GNU DWARF 1 extensions */ + .debug_srcinfo 0 : { *(.debug_srcinfo) } + .debug_sfnames 0 : { *(.debug_sfnames) } + + /* DWARF 1.1 and DWARF 2 */ + .debug_aranges 0 : { *(.debug_aranges) } + .debug_pubnames 0 : { *(.debug_pubnames) } + + /* DWARF 2 */ + .debug_info 0 : { *(.debug_info) } + .debug_abbrev 0 : { *(.debug_abbrev) } + .debug_line 0 : { *(.debug_line) } + .debug_frame 0 : { *(.debug_frame) } + .debug_str 0 : { *(.debug_str) } + .debug_loc 0 : { *(.debug_loc) } + .debug_macinfo 0 : { *(.debug_macinfo) } + + /* SGI/MIPS DWARF 2 extensions */ + .debug_weaknames 0 : { *(.debug_weaknames) } + .debug_funcnames 0 : { *(.debug_funcnames) } + .debug_typenames 0 : { *(.debug_typenames) } + .debug_varnames 0 : { *(.debug_varnames) } + /* These must appear regardless of . */ +} diff --git a/bsps/m68k/gen68360/start/linkcmds.bootp b/bsps/m68k/gen68360/start/linkcmds.bootp new file mode 100644 index 0000000000..ccd08a14a2 --- /dev/null +++ b/bsps/m68k/gen68360/start/linkcmds.bootp @@ -0,0 +1,171 @@ +/* + * This file contains GNU linker directives for a generic MC68360 board. + * Variations in memory size and allocation can be made by + * overriding some values with linker command-line arguments. + * + * These linker directives are for producing a bootstrap PROM version. + * The data segment is placed at the end of the text segment in the PROM. + * The start-up code takes care of copying this region to RAM. + * + * Saskatchewan Accelerator Laboratory + * University of Saskatchewan + * Saskatoon, Saskatchewan, CANADA + * eric@skatter.usask.ca + */ + +/* + * Declare some sizes. + * A heap size of 0 means `use all available memory for the heap'. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 64M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x1000; + +/* + * Declare on-board memory. + */ +MEMORY { + ram : ORIGIN = 0x00000000, LENGTH = 64M + myram : ORIGIN = 16M-400k, LENGTH = 400k + rom : ORIGIN = 0x0F000000, LENGTH = 1M + dpram : ORIGIN = 0x0E000000, LENGTH = 8k +} + +/* + * Load objects + */ +SECTIONS { + /* + * Boot PROM + */ + rom : { + _RomBase = .; + } >rom + + /* + * Dynamic RAM + */ + ram : { + RamBase = .; + } >ram + + /* + * Text, data and bss segments + */ + .text : AT(0x0) { + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (etext = .); + } >rom + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >rom + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >rom + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : AT(SIZEOF(.text)) { + _copy_start = .; + *(.data) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.jcr) + *(.gcc_except_table*) + . = ALIGN (16); + PROVIDE (edata = .); + _copy_end = .; + } >myram + .bss : { + M68Kvec = .; + . += (256 * 4); + _clear_start = .; + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + + . += _StackSize; + . = ALIGN (16); + _stack_init = .; + _clear_end = .; + + WorkAreaBase = .; + } >myram + + /* + * On-chip memory/peripherals + */ + dpram : { + m360 = .; + . += (8 * 1024); + } >dpram +} diff --git a/bsps/m68k/gen68360/start/linkcmds.prom b/bsps/m68k/gen68360/start/linkcmds.prom new file mode 100644 index 0000000000..777700e6a1 --- /dev/null +++ b/bsps/m68k/gen68360/start/linkcmds.prom @@ -0,0 +1,169 @@ +/* + * This file contains GNU linker directives for a generic MC68360 board. + * Variations in memory size and allocation can be made by + * overriding some values with linker command-line arguments. + * + * These linker directives are for producing a PROM version. + * The data segment is placed at the end of the text segment in the PROM. + * The start-up code takes care of copying this region to RAM. + * + * Saskatchewan Accelerator Laboratory + * University of Saskatchewan + * Saskatoon, Saskatchewan, CANADA + * eric@skatter.usask.ca + */ + +/* + * Declare some sizes. + * A heap size of 0 means `use all available memory for the heap'. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 64M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x1000; + +/* + * Declare on-board memory. + */ +MEMORY { + ram : ORIGIN = 0x00000000, LENGTH = 64M + rom : ORIGIN = 0x0F000000, LENGTH = 1M + dpram : ORIGIN = 0x0E000000, LENGTH = 8k +} + +/* + * Load objects + */ +SECTIONS { + /* + * Boot PROM + */ + rom : { + _RomBase = .; + } >rom + + /* + * Dynamic RAM + */ + ram : { + RamBase = .; + } >ram + + /* + * Text, data and bss segments + */ + .text : AT(0x0) { + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (etext = .); + } >rom + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >rom + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >rom + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : AT(SIZEOF(.text)) { + _copy_start = .; + *(.data) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.jcr) + *(.gcc_except_table*) + . = ALIGN (16); + PROVIDE (edata = .); + _copy_end = .; + } >ram + .bss : { + M68Kvec = .; + . += (256 * 4); + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + + . += _StackSize; + . = ALIGN (16); + _stack_init = .; + _clear_end = .; + + WorkAreaBase = .; + } >ram + + /* + * On-chip memory/peripherals + */ + dpram : { + m360 = .; + . += (8 * 1024); + } >dpram +} diff --git a/bsps/m68k/genmcf548x/start/bsp_specs b/bsps/m68k/genmcf548x/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/genmcf548x/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/genmcf548x/start/bspstart.c b/bsps/m68k/genmcf548x/start/bspstart.c new file mode 100644 index 0000000000..6c1da2a738 --- /dev/null +++ b/bsps/m68k/genmcf548x/start/bspstart.c @@ -0,0 +1,206 @@ +/*===============================================================*\ +| Project: RTEMS generic mcf548x BSP | ++-----------------------------------------------------------------+ +| File: bspstart.c | ++-----------------------------------------------------------------+ +| The file contains the startup code of generic MCF548x BSP | ++-----------------------------------------------------------------+ +| Copyright (c) 2007 | +| Embedded Brains GmbH | +| Obere Lagerstr. 30 | +| D-82178 Puchheim | +| Germany | +| rtems@embedded-brains.de | ++-----------------------------------------------------------------+ +| | +| Parts of the code has been derived from the "dBUG source code" | +| package Freescale is providing for M548X EVBs. The usage of | +| the modified or unmodified code and it's integration into the | +| generic mcf548x BSP has been done according to the Freescale | +| license terms. | +| | +| The Freescale license terms can be reviewed in the file | +| | +| Freescale_license.txt | +| | ++-----------------------------------------------------------------+ +| | +| The generic mcf548x BSP has been developed on the basic | +| structures and modules of the av5282 BSP. | +| | ++-----------------------------------------------------------------+ +| | +| The license and distribution terms for this file may be | +| found in the file LICENSE in this distribution or at | +| | +| http://www.rtems.org/license/LICENSE. | +| | ++-----------------------------------------------------------------+ +| | +| date history ID | +| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | +| 12.11.07 1.0 ras | +| | +\*===============================================================*/ + +#include <bsp.h> +#include <bsp/bootcard.h> + +extern uint32_t _CPU_cacr_shadow; + +/* +* These labels (!) are defined in the linker command file or when the linker is +* invoked. +* NOTE: The information (size) is the address of the object, not the object +* itself. +*/ + +extern char _SdramBase[]; +extern char _BootFlashBase[]; +extern char _CodeFlashBase[]; +extern char _SdramSize[]; +extern char _BootFlashSize[]; +extern char _CodeFlashSize[]; +extern char _TopRamReserved []; +extern char WorkAreaBase []; + +/* + * CPU-space access + */ +#define m68k_set_acr2(_acr2) __asm__ volatile ("movec %0,#0x0005" : : "d" (_acr2)) +#define m68k_set_acr3(_acr3) __asm__ volatile ("movec %0,#0x0007" : : "d" (_acr3)) + +/* + * Set initial CACR mode, mainly enables branch/instruction/data cache. The + * FPU must be switched on in the BSP startup code since the + * _Thread_Start_multitasking() will restore the floating-point context of the + * initialization task if necessary. + */ +static const uint32_t BSP_CACR_INIT = MCF548X_CACR_DEC /* enable data cache */ + | MCF548X_CACR_BEC /* enable branch cache */ + | MCF548X_CACR_IEC /* enable instruction cache */ + | MCF548X_CACR_DDCM(DCACHE_ON_WRIGHTTHROUGH) + /* set data cache mode to write-through */ + | MCF548X_CACR_DESB /* enable data store buffer */ + | MCF548X_CACR_DDSP /* data access only in supv. mode */ + | MCF548X_CACR_IDSP; /* instr. access only in supv. mode */ + +/* + * CACR maintenance functions + */ + +void bsp_cacr_set_flags( uint32_t flags) +{ + rtems_interrupt_level level; + + rtems_interrupt_disable( level); + _CPU_cacr_shadow |= flags; + m68k_set_cacr( _CPU_cacr_shadow); + rtems_interrupt_enable( level); +} + +void bsp_cacr_set_self_clear_flags( uint32_t flags) +{ + rtems_interrupt_level level; + uint32_t cacr = 0; + + rtems_interrupt_disable( level); + cacr = _CPU_cacr_shadow | flags; + m68k_set_cacr( cacr); + rtems_interrupt_enable( level); +} + +void bsp_cacr_clear_flags( uint32_t flags) +{ + rtems_interrupt_level level; + + rtems_interrupt_disable( level); + _CPU_cacr_shadow &= ~flags; + m68k_set_cacr( _CPU_cacr_shadow); + rtems_interrupt_enable( level); +} + +/* + * Coldfire acr and mmu settings + */ + static void acr_mmu_mapping(void) + { + + /* + * Cache disabled for internal register area (256 kB). + * Choose the smallest maskable size of 1MB. + */ + m68k_set_acr0(MCF548X_ACR_BA((uint32_t)(__MBAR)) | + MCF548X_ACR_ADMSK_AMM((uint32_t)(0xFFFFF)) | + MCF548X_ACR_E | + MCF548X_ACR_SP /* supervisor protection */ | + MCF548X_ACR_S(S_ACCESS_SUPV) /* always in supervisor mode */ | + MCF548X_ACR_CM(CM_OFF_PRECISE)); + +#ifdef M5484FIREENGINE + + + /* + * Cache enabled for entire SDRAM (64 MB) + */ + m68k_set_acr1(MCF548X_ACR_BA((uint32_t)(_SdramBase)) | + MCF548X_ACR_ADMSK_AMM((uint32_t)(_SdramSize - 1)) | + MCF548X_ACR_E | + MCF548X_ACR_SP /* supervisor protection */ | + MCF548X_ACR_S(S_ACCESS_SUPV) /* always in supervisor mode */ | + MCF548X_ACR_CM(CM_ON_WRIGHTTHROUGH)); + + /* + * Cache enabled for entire boot flash (2 MB) + */ + m68k_set_acr2(MCF548X_ACR_BA((uint32_t)(_BootFlashBase)) | + MCF548X_ACR_ADMSK_AMM((uint32_t)(_BootFlashSize - 1)) | + MCF548X_ACR_E | + MCF548X_ACR_SP /* supervisor protection */ | + MCF548X_ACR_S(S_ACCESS_SUPV) /* always in supervisor mode */ | + MCF548X_ACR_CM(CM_ON_COPYBACK)); + + /* + * Cache enabled for entire code flash (16 MB) + */ + m68k_set_acr3(MCF548X_ACR_BA((uint32_t)(_CodeFlashBase)) | + MCF548X_ACR_ADMSK_AMM((uint32_t)(_CodeFlashSize - 1)) | + MCF548X_ACR_E | + MCF548X_ACR_SP /* supervisor protection */ | + MCF548X_ACR_S(S_ACCESS_SUPV) /* always in supervisor mode */ | + MCF548X_ACR_CM(CM_ON_COPYBACK)); +#endif + + } + +/* + * bsp_start + * + * This routine does the bulk of the system initialisation. + */ +void bsp_start( void ) +{ + /* Initialize CACR shadow register */ + _CPU_cacr_shadow = BSP_CACR_INIT; + + /* + * Load the shadow variable of CACR with initial mode and write it to the + * CACR. Interrupts are still disabled, so there is no need for surrounding + * rtems_interrupt_enable() / rtems_interrupt_disable(). + */ + m68k_set_cacr( _CPU_cacr_shadow); + + /* + * do mapping of acr's and/or mmu + */ + acr_mmu_mapping(); +} + + +/* + * Get the XLB clock speed + */ +uint32_t get_CPU_clock_speed(void) +{ + return (uint32_t)BSP_CPU_CLOCK_SPEED; +} diff --git a/bsps/m68k/genmcf548x/start/init548x.c b/bsps/m68k/genmcf548x/start/init548x.c new file mode 100644 index 0000000000..c83c061f31 --- /dev/null +++ b/bsps/m68k/genmcf548x/start/init548x.c @@ -0,0 +1,321 @@ +/*===============================================================*\ +| Project: RTEMS generic mcf548x BSP | ++-----------------------------------------------------------------+ +| File: init548x.c | ++-----------------------------------------------------------------+ +| The file contains the c part of MCF548x init code | ++-----------------------------------------------------------------+ +| Copyright (c) 2007 | +| Embedded Brains GmbH | +| Obere Lagerstr. 30 | +| D-82178 Puchheim | +| Germany | +| rtems@embedded-brains.de | ++-----------------------------------------------------------------+ +| | +| Parts of the code has been derived from the "dBUG source code" | +| package Freescale is providing for M548X EVBs. The usage of | +| the modified or unmodified code and it's integration into the | +| generic mcf548x BSP has been done according to the Freescale | +| license terms. | +| | +| The Freescale license terms can be reviewed in the file | +| | +| Freescale_license.txt | +| | ++-----------------------------------------------------------------+ +| | +| The generic mcf548x BSP has been developed on the basic | +| structures and modules of the av5282 BSP. | +| | ++-----------------------------------------------------------------+ +| | +| The license and distribution terms for this file may be | +| found in the file LICENSE in this distribution or at | +| | +| http://www.rtems.org/license/LICENSE. | +| | ++-----------------------------------------------------------------+ +| | +| date history ID | +| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | +| 12.11.07 1.0 ras | +| | +\*===============================================================*/ + +#include <bsp.h> + +#include <string.h> + +#include <bsp/linker-symbols.h> + +#if defined(HAS_LOW_LEVEL_INIT) +#define SYSTEM_PERIOD 10 /* system bus period in ns */ + +/* SDRAM Timing Parameters */ +#define SDRAM_TWR 2 /* in clocks */ +#define SDRAM_CASL 2.5 /* in clocks */ +#define SDRAM_TRCD 20 /* in ns */ +#define SDRAM_TRP 20 /* in ns */ +#define SDRAM_TRFC 75 /* in ns */ +#define SDRAM_TREFI 7800 /* in ns */ +#endif /* defined(HAS_LOW_LEVEL_INIT) */ + +extern uint8_t _DataRom[]; +extern uint8_t _DataRam[]; +extern uint8_t _DataEnd[]; +extern uint8_t _BssStart[]; +extern uint8_t _BssEnd[]; +extern uint8_t _BootFlashBase[]; +extern uint8_t _CodeFlashBase[]; +extern uint8_t RamBase[]; + +void gpio_init(void); +void fbcs_init(void); +void sdramc_init(void); +void mcf548x_init(void); + + +void mcf548x_init(void) +{ + size_t i; + +#if defined(HAS_LOW_LEVEL_INIT) + /* set XLB arbiter timeouts */ + MCF548X_XLB_ADRTO = 0x00000100; + MCF548X_XLB_DATTO = 0x00000100; + MCF548X_XLB_BUSTO = 0x00000100; +#endif + + gpio_init(); +#if defined(HAS_LOW_LEVEL_INIT) + fbcs_init(); + sdramc_init(); +#endif /* defined(HAS_LOW_LEVEL_INIT) */ + + /* Copy the vector table to RAM if necessary */ + if (bsp_vector0_size == bsp_vector1_size) { + memcpy(bsp_vector1_begin, bsp_vector0_begin, (size_t) bsp_vector1_size); + m68k_set_vbr((uint32_t)bsp_vector1_begin); + } + + /* Move initialized data from ROM to RAM. */ + if (bsp_section_data_begin != bsp_section_data_load_begin) { + memcpy( + bsp_section_data_begin, + bsp_section_data_load_begin, + (size_t) bsp_section_data_size + ); + } + + /* Zero uninitialized data */ + memset(bsp_section_bss_begin, 0, (size_t) bsp_section_bss_size); + + for (i = 8; i < RTEMS_ARRAY_SIZE(mcf548x_intc_icr_init_values); ++i) { + volatile uint8_t *icr = &MCF548X_INTC_ICR0; + + icr[i] = mcf548x_intc_icr_init_values[i]; + } +} +/********************************************************************/ +#if defined(HAS_LOW_LEVEL_INIT) +void +fbcs_init (void) +{ +#ifdef M5484FIREENGINE + +volatile uint32_t cscr, clk_ratio, fb_period, ws; + +/* boot flash already valid ? */ +if(!(MCF548X_FBCS_CSMR0 & MCF548X_FBCS_CSMR_V)) + { + + /* + * Boot Flash + */ + MCF548X_FBCS_CSAR0 = MCF548X_FBCS_CSAR_BA((uint32_t)(_BootFlashBase)); + + cscr = (0 + | MCF548X_FBCS_CSCR_ASET(1) + | MCF548X_FBCS_CSCR_WRAH(0) + | MCF548X_FBCS_CSCR_RDAH(0) + | MCF548X_FBCS_CSCR_AA + | MCF548X_FBCS_CSCR_PS_16); + + /* + * Determine the necessary wait states based on the defined system + * period (XLB clock period) and the CLKIN to XLB ratio. + * The boot flash has a max access time of 110ns. + */ + clk_ratio = (MCF548X_PCI_PCIGSCR >> 24) & 0x7; + fb_period = SYSTEM_PERIOD * clk_ratio; + ws = 110 / fb_period; + + MCF548X_FBCS_CSCR0 = cscr | MCF548X_FBCS_CSCR_WS(ws); + MCF548X_FBCS_CSMR0 = (0 + | MCF548X_FBCS_CSMR_BAM_2M + | MCF548X_FBCS_CSMR_V); + + } + +/* code flash already valid ? */ +if(!(MCF548X_FBCS_CSMR1 & MCF548X_FBCS_CSMR_V)) + { + + /* + * Code Flash + */ + MCF548X_FBCS_CSAR1 = MCF548X_FBCS_CSAR_BA((uint32_t)(_CodeFlashBase)); + + /* + * Determine the necessary wait states based on the defined system + * period (XLB clock period) and the CLKIN to XLB ratio. + * The user/code flash has a max access time of 120ns. + */ + ws = 120 / fb_period; + MCF548X_FBCS_CSCR1 = cscr | MCF548X_FBCS_CSCR_WS(ws); + MCF548X_FBCS_CSMR1 = (0 + | MCF548X_FBCS_CSMR_BAM_16M + | MCF548X_FBCS_CSMR_V); + } + +#endif +} +#endif /* defined(HAS_LOW_LEVEL_INIT) */ + +/********************************************************************/ +#if defined(HAS_LOW_LEVEL_INIT) +void +sdramc_init (void) +{ + + /* + * Check to see if the SDRAM has already been initialized + * by a run control tool + */ + if (!(MCF548X_SDRAMC_SDCR & MCF548X_SDRAMC_SDCR_REF)) + { + /* + * Basic configuration and initialization + */ + MCF548X_SDRAMC_SDRAMDS = (0 + | MCF548X_SDRAMC_SDRAMDS_SB_E(MCF548X_SDRAMC_SDRAMDS_DRIVE_8MA) + | MCF548X_SDRAMC_SDRAMDS_SB_C(MCF548X_SDRAMC_SDRAMDS_DRIVE_8MA) + | MCF548X_SDRAMC_SDRAMDS_SB_A(MCF548X_SDRAMC_SDRAMDS_DRIVE_8MA) + | MCF548X_SDRAMC_SDRAMDS_SB_S(MCF548X_SDRAMC_SDRAMDS_DRIVE_8MA) + | MCF548X_SDRAMC_SDRAMDS_SB_D(MCF548X_SDRAMC_SDRAMDS_DRIVE_8MA) + ); + MCF548X_SDRAMC_CS0CFG = (0 + | MCF548X_SDRAMC_CSnCFG_CSBA((uint32_t)(RamBase)) + | MCF548X_SDRAMC_CSnCFG_CSSZ(MCF548X_SDRAMC_CSnCFG_CSSZ_64MBYTE) + ); + MCF548X_SDRAMC_SDCFG1 = (0 + | MCF548X_SDRAMC_SDCFG1_SRD2RW(7) + | MCF548X_SDRAMC_SDCFG1_SWT2RD(SDRAM_TWR + 1) + | MCF548X_SDRAMC_SDCFG1_RDLAT((int)((SDRAM_CASL*2) + 2)) + | MCF548X_SDRAMC_SDCFG1_ACT2RW((int)(((SDRAM_TRCD/SYSTEM_PERIOD) - 1) + 0.5)) + | MCF548X_SDRAMC_SDCFG1_PRE2ACT((int)(((SDRAM_TRP/SYSTEM_PERIOD) - 1) + 0.5)) + | MCF548X_SDRAMC_SDCFG1_REF2ACT((int)(((SDRAM_TRFC/SYSTEM_PERIOD) - 1) + 0.5)) + | MCF548X_SDRAMC_SDCFG1_WTLAT(3) + ); + MCF548X_SDRAMC_SDCFG2 = (0 + | MCF548X_SDRAMC_SDCFG2_BRD2PRE(4) + | MCF548X_SDRAMC_SDCFG2_BWT2RW(6) + | MCF548X_SDRAMC_SDCFG2_BRD2WT(7) + | MCF548X_SDRAMC_SDCFG2_BL(7) + ); + + /* + * Precharge and enable write to SDMR + */ + MCF548X_SDRAMC_SDCR = (0 + | MCF548X_SDRAMC_SDCR_MODE_EN + | MCF548X_SDRAMC_SDCR_CKE + | MCF548X_SDRAMC_SDCR_DDR + | MCF548X_SDRAMC_SDCR_MUX(1) + | MCF548X_SDRAMC_SDCR_RCNT((int)(((SDRAM_TREFI/(SYSTEM_PERIOD*64)) - 1) + 0.5)) + | MCF548X_SDRAMC_SDCR_IPALL + ); + + /* + * Write extended mode register + */ + MCF548X_SDRAMC_SDMR = (0 + | MCF548X_SDRAMC_SDMR_BNKAD_LEMR + | MCF548X_SDRAMC_SDMR_AD(0x0) + | MCF548X_SDRAMC_SDMR_CMD + ); + + /* + * Write mode register and reset DLL + */ + MCF548X_SDRAMC_SDMR = (0 + | MCF548X_SDRAMC_SDMR_BNKAD_LMR + | MCF548X_SDRAMC_SDMR_AD(0x163) + | MCF548X_SDRAMC_SDMR_CMD + ); + + /* + * Execute a PALL command + */ + MCF548X_SDRAMC_SDCR |=MCF548X_SDRAMC_SDCR_IPALL; + + /* + * Perform two REF cycles + */ + MCF548X_SDRAMC_SDCR |= MCF548X_SDRAMC_SDCR_IREF; + MCF548X_SDRAMC_SDCR |= MCF548X_SDRAMC_SDCR_IREF; + + /* + * Write mode register and clear reset DLL + */ + MCF548X_SDRAMC_SDMR = (0 + | MCF548X_SDRAMC_SDMR_BNKAD_LMR + | MCF548X_SDRAMC_SDMR_AD(0x063) + | MCF548X_SDRAMC_SDMR_CMD + ); + + /* + * Enable auto refresh and lock SDMR + */ + MCF548X_SDRAMC_SDCR &= ~MCF548X_SDRAMC_SDCR_MODE_EN; + MCF548X_SDRAMC_SDCR |= (0 + | MCF548X_SDRAMC_SDCR_REF + | MCF548X_SDRAMC_SDCR_DQS_OE(0xF) + ); + } + +} +#endif /* defined(HAS_LOW_LEVEL_INIT) */ + +/********************************************************************/ +void +gpio_init(void) +{ + +#ifdef M5484FIREENGINE + + /* + * Enable Ethernet signals so that, if a cable is plugged into + * the ports, the lines won't be floating and potentially cause + * erroneous transmissions + */ + MCF548X_GPIO_PAR_FECI2CIRQ = (0 + + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E1MDC_EMDC + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E1MDIO_EMDIO + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E1MII + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E17 + + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E0MDC + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E0MDIO + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E0MII + | MCF548X_GPIO_PAR_FECI2CIRQ_PAR_E07 + ); + +#endif + /* + * make sure the "edge port" has all interrupts disabled + */ + MCF548X_EPORT_EPIER = 0; +} diff --git a/bsps/m68k/genmcf548x/start/linkcmds.COBRA5475 b/bsps/m68k/genmcf548x/start/linkcmds.COBRA5475 new file mode 100644 index 0000000000..52bca8d018 --- /dev/null +++ b/bsps/m68k/genmcf548x/start/linkcmds.COBRA5475 @@ -0,0 +1,82 @@ +/*===============================================================*\ +| Project: RTEMS generic mcf548x BSP | ++-----------------------------------------------------------------+ +| File: linkcmds.COBRA5475 | ++-----------------------------------------------------------------+ +| The file contains the linker directives for the generic MCF548x | +| BSP to be used with an COBRA5475 board to load and execute | +| code in the RAM. | ++-----------------------------------------------------------------+ +| Copyright (c) 2007 | +| Embedded Brains GmbH | +| Obere Lagerstr. 30 | +| D-82178 Puchheim | +| Germany | +| rtems@embedded-brains.de | ++-----------------------------------------------------------------+ +| | +| Parts of the code has been derived from the "dBUG source code" | +| package Freescale is providing for M548X EVBs. The usage of | +| the modified or unmodified code and it's integration into the | +| generic mcf548x BSP has been done according to the Freescale | +| license terms. | +| | +| The Freescale license terms can be reviewed in the file | +| | +| Freescale_license.txt | +| | ++-----------------------------------------------------------------+ +| | +| The generic mcf548x BSP has been developed on the basic | +| structures and modules of the av5282 BSP. | +| | ++-----------------------------------------------------------------+ +| | +| The license and distribution terms for this file may be | +| found in the file LICENSE in this distribution or at | +| | +| http://www.rtems.org/license/LICENSE. | +| | ++-----------------------------------------------------------------+ +| | +| date history ID | +| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | +| 12.11.07 1.0 ras | +| 15.10.09 1.1, adapted to COBRA5475 doe | +| | +\*===============================================================*/ + +/* + * Location and size of on-chip devices + */ +_SdramBase = DEFINED(_SdramBase) ? _SdramBase : 0xf0000000; +_SdramSize = DEFINED(_SdramSize) ? _SdramSize : (128 * 1024*1024); +_SysSramBase = DEFINED(_SysSramBase) ? _SysSramBase : __MBAR + 0x00010000; +_SysSramSize = DEFINED(_SysSramSize) ? _SysSramSize : (32 * 1024); +_McdapiBase = DEFINED(_McdapiBase) ? _McdapiBase : _SysSramBase; +_McdapiSize = DEFINED(_McdapiSize) ? _McdapiSize : (12 * 1024); +_CoreSramBase0 = DEFINED(_CoreSramBase0) ? _CoreSramBase0 : 0xFF000000; +_CoreSramBase1 = DEFINED(_CoreSramBase1) ? _CoreSramBase1 : 0xFF001000; +_CoreSramSize0 = DEFINED(_CoreSramSize0) ? _CoreSramSize0 : (4 * 1024); +_CoreSramSize1 = DEFINED(_CoreSramSize1) ? _CoreSramSize1 : (4 * 1024); +_BootFlashBase = DEFINED(_BootFlashBase) ? _BootFlashBase : 0xFC000000; +_BootFlashSize = DEFINED(_BootFlashSize) ? _BootFlashSize : (32 * 1024*1024); + +bsp_initstack_size = DEFINED(StackSize) ? StackSize : 0x800; /* 2 kB */ + +_VBR = DEFINED(_VBR) ? _VBR : _SdramBase; + +__MBAR = DEFINED(__MBAR) ? __MBAR : 0xFE000000; + +MEMORY +{ + sdram : ORIGIN = 0xF0000000, LENGTH = 128M + boot_flash : ORIGIN = 0xFC000000, LENGTH = 32M +} + +REGION_ALIAS ("REGION_TEXT", sdram); +REGION_ALIAS ("REGION_TEXT_LOAD", sdram); +REGION_ALIAS ("REGION_DATA", sdram); +REGION_ALIAS ("REGION_DATA_LOAD", sdram); + +INCLUDE linkcmds.base diff --git a/bsps/m68k/genmcf548x/start/linkcmds.m5484FireEngine b/bsps/m68k/genmcf548x/start/linkcmds.m5484FireEngine new file mode 100644 index 0000000000..be746af7ff --- /dev/null +++ b/bsps/m68k/genmcf548x/start/linkcmds.m5484FireEngine @@ -0,0 +1,84 @@ +/*===============================================================*\ +| Project: RTEMS generic mcf548x BSP | ++-----------------------------------------------------------------+ +| File: linkcmd | ++-----------------------------------------------------------------+ +| The file contains the linker directives for the generic MCF548x | +| BSP to be used with an m5484FireEngine EVB to load and execute | +| code in the RAM. | ++-----------------------------------------------------------------+ +| Copyright (c) 2007 | +| Embedded Brains GmbH | +| Obere Lagerstr. 30 | +| D-82178 Puchheim | +| Germany | +| rtems@embedded-brains.de | ++-----------------------------------------------------------------+ +| | +| Parts of the code has been derived from the "dBUG source code" | +| package Freescale is providing for M548X EVBs. The usage of | +| the modified or unmodified code and it's integration into the | +| generic mcf548x BSP has been done according to the Freescale | +| license terms. | +| | +| The Freescale license terms can be reviewed in the file | +| | +| Freescale_license.txt | +| | ++-----------------------------------------------------------------+ +| | +| The generic mcf548x BSP has been developed on the basic | +| structures and modules of the av5282 BSP. | +| | ++-----------------------------------------------------------------+ +| | +| The license and distribution terms for this file may be | +| found in the file LICENSE in this distribution or at | +| | +| http://www.rtems.org/license/LICENSE. | +| | ++-----------------------------------------------------------------+ +| | +| date history ID | +| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | +| 12.11.07 1.0 ras | +| | +\*===============================================================*/ + +/* + * Location and size of on-chip devices + */ +_SdramBase = DEFINED(_SdramBase) ? _SdramBase : 0x00000000; +_SdramSize = DEFINED(_SdramSize) ? _SdramSize : (64 * 1024*1024); +_SysSramBase = DEFINED(_SysSramBase) ? _SysSramBase : __MBAR + 0x00010000; +_SysSramSize = DEFINED(_SysSramSize) ? _SysSramSize : (32 * 1024); +_McdapiBase = DEFINED(_McdapiBase) ? _McdapiBase : _SysSramBase; +_McdapiSize = DEFINED(_McdapiSize) ? _McdapiSize : (12 * 1024); +_CoreSramBase0 = DEFINED(_CoreSramBase0) ? _CoreSramBase0 : 0x20000000; +_CoreSramBase1 = DEFINED(_CoreSramBase1) ? _CoreSramBase1 : 0x20001000; +_CoreSramSize0 = DEFINED(_CoreSramSize0) ? _CoreSramSize0 : (4 * 1024); +_CoreSramSize1 = DEFINED(_CoreSramSize1) ? _CoreSramSize1 : (4 * 1024); +_BootFlashBase = DEFINED(_BootFlashBase) ? _BootFlashBase : 0xFF800000; +_BootFlashSize = DEFINED(_BootFlashSize) ? _BootFlashSize : (2 * 1024*1024); +_CodeFlashBase = DEFINED(_CodeFlashBase) ? _CodeFlashBase : 0xE0000000; +_CodeFlashSize = DEFINED(_CodeFlashSize) ? _CodeFlashSize : (16 * 1024*1024); + +bsp_initstack_size = DEFINED(StackSize) ? StackSize : 0x800; /* 2 kB */ + +_VBR = DEFINED(_VBR) ? _VBR : _SdramBase; + +__MBAR = DEFINED(__MBAR) ? __MBAR : 0x10000000; + +MEMORY +{ + sdram : ORIGIN = 0x00000000, LENGTH = 64M + code_flash : ORIGIN = 0xE0000000, LENGTH = 16M + boot_flash : ORIGIN = 0xFF800000, LENGTH = 2M +} + +REGION_ALIAS ("REGION_TEXT", sdram); +REGION_ALIAS ("REGION_TEXT_LOAD", sdram); +REGION_ALIAS ("REGION_DATA", sdram); +REGION_ALIAS ("REGION_DATA_LOAD", sdram); + +INCLUDE linkcmds.base diff --git a/bsps/m68k/genmcf548x/start/linkcmds.m5484FireEngine.flash b/bsps/m68k/genmcf548x/start/linkcmds.m5484FireEngine.flash new file mode 100644 index 0000000000..4db960f111 --- /dev/null +++ b/bsps/m68k/genmcf548x/start/linkcmds.m5484FireEngine.flash @@ -0,0 +1,84 @@ +/*===============================================================*\ +| Project: RTEMS generic mcf548x BSP | ++-----------------------------------------------------------------+ +| File: linkcmd.m5484FireEngine.flash | ++-----------------------------------------------------------------+ +| The file contains the linker directives for the generic MCF548x | +| BSP to be used with an m5484FireEngine EVB to load and execute | +| code in the boot FLASH. | ++-----------------------------------------------------------------+ +| Copyright (c) 2007 | +| Embedded Brains GmbH | +| Obere Lagerstr. 30 | +| D-82178 Puchheim | +| Germany | +| rtems@embedded-brains.de | ++-----------------------------------------------------------------+ +| | +| Parts of the code has been derived from the "dBUG source code" | +| package Freescale is providing for M548X EVBs. The usage of | +| the modified or unmodified code and it's integration into the | +| generic mcf548x BSP has been done according to the Freescale | +| license terms. | +| | +| The Freescale license terms can be reviewed in the file | +| | +| Freescale_license.txt | +| | ++-----------------------------------------------------------------+ +| | +| The generic mcf548x BSP has been developed on the basic | +| structures and modules of the av5282 BSP. | +| | ++-----------------------------------------------------------------+ +| | +| The license and distribution terms for this file may be | +| found in the file LICENSE in this distribution or at | +| | +| http://www.rtems.org/license/LICENSE. | +| | ++-----------------------------------------------------------------+ +| | +| date history ID | +| ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ | +| 12.11.07 1.0 ras | +| | +\*===============================================================*/ + +/* + * Location and size of on-chip devices + */ +_SdramBase = DEFINED(_SdramBase) ? _SdramBase : 0x00000000; +_SdramSize = DEFINED(_SdramSize) ? _SdramSize : (64 * 1024 * 1024); +_SysSramBase = DEFINED(_SysSramBase) ? _SysSramBase : __MBAR + 0x00010000; +_SysSramSize = DEFINED(_SysSramSize) ? _SysSramSize : (32 * 1024); +_McdapiBase = DEFINED(_McdapiBase) ? _McdapiBase : _SysSramBase; +_McdapiSize = DEFINED(_McdapiSize) ? _McdapiSize : (12 * 1024); +_CoreSramBase0 = DEFINED(_CoreSramBase0) ? _CoreSramBase0 : 0x20000000; +_CoreSramBase1 = DEFINED(_CoreSramBase1) ? _CoreSramBase1 : 0x20001000; +_CoreSramSize0 = DEFINED(_CoreSramSize0) ? _CoreSramSize0 : (4 * 1024); +_CoreSramSize1 = DEFINED(_CoreSramSize1) ? _CoreSramSize1 : (4 * 1024); +_BootFlashBase = DEFINED(_BootFlashBase) ? _BootFlashBase : 0xFF800000; +_BootFlashSize = DEFINED(_BootFlashSize) ? _BootFlashSize : (2 * 1024 * 1024); +_CodeFlashBase = DEFINED(_CodeFlashBase) ? _CodeFlashBase : 0xE0000000; +_CodeFlashSize = DEFINED(_CodeFlashSize) ? _CodeFlashSize : (16 * 1024 * 1024); + +bsp_initstack_size = DEFINED(StackSize) ? StackSize : 0x800; /* 2 kB */ + +_VBR = DEFINED(_VBR) ? _VBR : _SdramBase; + +__MBAR = DEFINED(__MBAR) ? __MBAR : 0x10000000; + +MEMORY +{ + sdram : ORIGIN = 0x00000000, LENGTH = 64M + code_flash : ORIGIN = 0xE0000000, LENGTH = 16M + boot_flash : ORIGIN = 0xFF800000, LENGTH = 2M +} + +REGION_ALIAS ("REGION_TEXT", boot_flash); +REGION_ALIAS ("REGION_TEXT_LOAD", boot_flash); +REGION_ALIAS ("REGION_DATA", sdram); +REGION_ALIAS ("REGION_DATA_LOAD", boot_flash); + +INCLUDE linkcmds.base diff --git a/bsps/m68k/mcf5206elite/start/bsp_specs b/bsps/m68k/mcf5206elite/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/mcf5206elite/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/mcf5206elite/start/gdbinit b/bsps/m68k/mcf5206elite/start/gdbinit new file mode 100644 index 0000000000..9954b8cb9a --- /dev/null +++ b/bsps/m68k/mcf5206elite/start/gdbinit @@ -0,0 +1,217 @@ +# +# GDB Init script for the Coldfire 5206e processor. +# +# The main purpose of this script is to perform minimum initialization of +# processor so code can be loaded. Also, exception handling is performed. +# +# Copyright (C) OKTET Ltd., St.-Petersburg, Russia +# Author: Victor V. Vengerov <vvv@oktet.ru> +# +# This script partially based on gdb scripts written by +# Eric Norum, <eric@skatter.usask.ca> +# +# +# The license and distribution terms for this file may be +# found in the file LICENSE in this distribution or at +# http://www.rtems.org/license/LICENSE. +# + +define addresses + +set $mbar = 0x10000001 +set $simr = $mbar - 1 + 0x003 +set $icr1 = $mbar - 1 + 0x014 +set $icr2 = $mbar - 1 + 0x015 +set $icr3 = $mbar - 1 + 0x016 +set $icr4 = $mbar - 1 + 0x017 +set $icr5 = $mbar - 1 + 0x018 +set $icr6 = $mbar - 1 + 0x019 +set $icr7 = $mbar - 1 + 0x01A +set $icr8 = $mbar - 1 + 0x01B +set $icr9 = $mbar - 1 + 0x01C +set $icr10 = $mbar - 1 + 0x01D +set $icr11 = $mbar - 1 + 0x01E +set $icr12 = $mbar - 1 + 0x01F +set $icr13 = $mbar - 1 + 0x020 +set $imr = $mbar - 1 + 0x036 +set $ipr = $mbar - 1 + 0x03A +set $rsr = $mbar - 1 + 0x040 +set $sypcr = $mbar - 1 + 0x041 +set $swivr = $mbar - 1 + 0x042 +set $swsr = $mbar - 1 + 0x043 +set $dcrr = $mbar - 1 + 0x046 +set $dctr = $mbar - 1 + 0x04A +set $dcar0 = $mbar - 1 + 0x04C +set $dcmr0 = $mbar - 1 + 0x050 +set $dccr0 = $mbar - 1 + 0x057 +set $dcar1 = $mbar - 1 + 0x058 +set $dcmr1 = $mbar - 1 + 0x05C +set $dccr1 = $mbar - 1 + 0x063 +set $csar0 = $mbar - 1 + 0x064 +set $csmr0 = $mbar - 1 + 0x068 +set $cscr0 = $mbar - 1 + 0x06E +set $csar1 = $mbar - 1 + 0x070 +set $csmr1 = $mbar - 1 + 0x074 +set $cscr1 = $mbar - 1 + 0x07A +set $csar2 = $mbar - 1 + 0x07C +set $csmr2 = $mbar - 1 + 0x080 +set $cscr2 = $mbar - 1 + 0x086 +set $csar3 = $mbar - 1 + 0x088 +set $csmr3 = $mbar - 1 + 0x08C +set $cscr3 = $mbar - 1 + 0x092 +set $csar4 = $mbar - 1 + 0x094 +set $csmr4 = $mbar - 1 + 0x098 +set $cscr4 = $mbar - 1 + 0x09E +set $csar5 = $mbar - 1 + 0x0A0 +set $csmr5 = $mbar - 1 + 0x0A4 +set $cscr5 = $mbar - 1 + 0x0AA +set $csar6 = $mbar - 1 + 0x0AC +set $csmr6 = $mbar - 1 + 0x0B0 +set $cscr6 = $mbar - 1 + 0x0B6 +set $csar7 = $mbar - 1 + 0x0B8 +set $csmr7 = $mbar - 1 + 0x0BC +set $cscr7 = $mbar - 1 + 0x0C2 +set $dmcr = $mbar - 1 + 0x0C6 +set $par = $mbar - 1 + 0x0CA +set $tmr1 = $mbar - 1 + 0x100 +set $trr1 = $mbar - 1 + 0x104 +set $tcr1 = $mbar - 1 + 0x108 +set $tcn1 = $mbar - 1 + 0x10C +set $ter1 = $mbar - 1 + 0x111 +set $tmr2 = $mbar - 1 + 0x120 +set $trr2 = $mbar - 1 + 0x124 +set $tcr2 = $mbar - 1 + 0x128 +set $tcn2 = $mbar - 1 + 0x12C +set $ter2 = $mbar - 1 + 0x131 + +end + +# +# Setup CSAR0 for the FLASH ROM. +# + +define setup-cs + +set *((short*) $csar0) = 0xffe0 +set *((int*) $csmr0) = 0x000f0000 +set *((short*) $cscr0) = 0x1da3 +set *((short*) $csar1) = 0x5000 +set *((int*) $csmr1) = 0x00000000 +set *((short*) $cscr1) = 0x3d43 +set *((short*) $csar2) = 0x3000 +set *((int*) $csmr2) = 0x000f0000 +set *((short*) $cscr2) = 0x1903 +set *((short*) $csar3) = 0x4000 +set *((int*) $csmr3) = 0x000f0000 +set *((short*) $cscr3) = 0x0083 + +end + +# +# Setup the DRAM controller. +# + +define setup-dram + +set *((short*) $dcrr) = 24 +set *((short*) $dctr) = 0x0000 +set *((short*) $dcar0) = 0x0000 +set *((long*) $dcmr0) = 0x000e0000 +set *((char*) $dccr0) = 0x07 +set *((short*) $dcar1) = 0x0000 +set *((long*) $dcmr1) = 0x00000000 +set *((char*) $dccr1) = 0x00 + +end + + +# +# Wake up the board +# + +define initboard + +addresses +setup-cs +# setup-dram + +end + +define ss +si +x/i $pc +end + +# +# Display exception information +# +define exception-info +set $excpc = *(unsigned int *)($sp+4) +set $excfmt = (*(unsigned int *)$sp >> 28) & 0x0f +set $excfs = ((*(unsigned int *)$sp >> 24) & 0x0c) | \ + ((*(unsigned int *)$sp >> 16) & 0x03) +set $excvec = (*(unsigned int *)$sp >> 18) & 0xff +set $excsr = *(unsigned int *)$sp & 0xffff + +printf "EXCEPTION -- SR:0x%X PC:0x%X FRAME:0x%X VECTOR:%d\n", \ + $excsr, $excpc, $sp, $excvec +if $excvec == 2 + printf "Access error exception" +end +if $excvec == 3 + printf "Address error exception" +end +if $excvec == 4 + printf "Illegal instruction exception" +end +if $excvec == 8 + printf "Privelege violation exception" +end +if $excvec == 9 + printf "Trace exception" +end +if $excvec == 10 + printf "Unimplemented LINE-A opcode exception" +end +if $excvec == 11 + printf "Unimplemented LINE-F opcode exception" +end +if $excvec == 12 + printf "Debug interrupt" +end +if $excvec == 14 + printf "Format error exception" +end +if $excfs == 0x04 + printf " on instruction fetch" +end +if $excfs == 0x08 + printf " on operand write" +end +if $excfs == 0x09 + printf " on write to write-protected space" +end +if $excfs == 0x0c + printf " on operand read" +end +printf "\n" +x/4i $excpc +set $pc=$excpc +set $sp=$sp+8 +end + +target bdm /dev/bdmcf0 +initboard +load +set $pc=start +set $sp=0x20001ffc +b bsp_cleanup +b _stop +b _unexp_exception +commands +silent +exception-info +end +b _unexp_int +b _reserved_int +b _spurious_int diff --git a/bsps/m68k/mcf5206elite/start/init5206e.c b/bsps/m68k/mcf5206elite/start/init5206e.c new file mode 100644 index 0000000000..a128b81fd7 --- /dev/null +++ b/bsps/m68k/mcf5206elite/start/init5206e.c @@ -0,0 +1,229 @@ +/* + * MCF5206e hardware startup routines + * + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + * + * This initialization code based on hardware settings of dBUG + * monitor. This must be changed if you like to run it immediately + * after reset. + */ + +/* + * Copyright (C) 2000 OKTET Ltd., St.-Petersburg, Russia + * Author: Victor V. Vengerov <vvv@oktet.ru> + * + * Based on work: + * Author: + * David Fiddes, D.J@fiddes.surfaid.org + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * 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.org/license/LICENSE. + */ + +#include <rtems.h> +#include <bsp.h> +#include "mcf5206/mcf5206e.h" + +extern void CopyDataClearBSSAndStart(unsigned long ramsize); +extern void INTERRUPT_VECTOR(void); + +#define m68k_set_srambar( _rambar0 ) \ + __asm__ volatile ( "movec %0,%%rambar0\n\t" \ + "nop\n\t" \ + : : "d" (_rambar0) ) + +#define m68k_set_mbar( _mbar ) \ + __asm__ volatile ( "movec %0,%%mbar\n\t" \ + "nop\n\t" \ + : : "d" (_mbar) ) + +#define mcf5206e_enable_cache() \ + m68k_set_cacr( MCF5206E_CACR_CENB ) + +#define mcf5206e_disable_cache() \ + __asm__ volatile ( "nop\n\t" \ + "movec %0,%%cacr\n\t" \ + "nop\n\t" \ + "movec %0,%%cacr\n\t" \ + "nop\n\t" \ + : : "d" (MCF5206E_CACR_CINV) ) + +/* + * Initialize MCF5206e on-chip modules + */ +void Init5206e(void) +{ + /* Set Module Base Address register */ + m68k_set_mbar((MBAR & MCF5206E_MBAR_BA) | MCF5206E_MBAR_V); + + /* Set System Protection Control Register (SYPCR): + * Bus Monitor Enable, Bus Monitor Timing = 1024 clocks, + * Software watchdog disabled + */ + *MCF5206E_SYPCR(MBAR) = MCF5206E_SYPCR_BME | + MCF5206E_SYPCR_BMT_1024; + + /* Set Pin Assignment Register (PAR): + * Output Timer 0 (not DREQ) on *TOUT[0] / *DREQ[1] + * Input Timer 0 (not DREQ) on *TIN[0] / *DREQ[0] + * IRQ, not IPL + * UART2 RTS signal (not \RSTO) + * PST/DDATA (not PPIO) + * *WE (not CS/A) + */ + *MCF5206E_PAR(MBAR) = MCF5206E_PAR_PAR9_TOUT | + MCF5206E_PAR_PAR8_TIN0 | + MCF5206E_PAR_PAR7_UART2 | + MCF5206E_PAR_PAR6_IRQ | + MCF5206E_PAR_PAR5_PST | + MCF5206E_PAR_PAR4_DDATA | + MCF5206E_PAR_WE0_WE1_WE2_WE3; + + /* Set SIM Configuration Register (SIMR): + * Disable software watchdog timer and bus timeout monitor when + * internal freeze signal is asserted. + */ + *MCF5206E_SIMR(MBAR) = MCF5206E_SIMR_FRZ0 | MCF5206E_SIMR_FRZ1; + + /* Set Interrupt Mask Register: Disable all interrupts */ + *MCF5206E_IMR(MBAR) = 0xFFFF; + + /* Assign Interrupt Control Registers as it is defined in bsp.h */ + *MCF5206E_ICR(MBAR,MCF5206E_INTR_EXT_IPL1) = + (BSP_INTLVL_AVEC1 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_AVEC1 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_EXT_IPL2) = + (BSP_INTLVL_AVEC2 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_AVEC2 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_EXT_IPL3) = + (BSP_INTLVL_AVEC3 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_AVEC3 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_EXT_IPL4) = + (BSP_INTLVL_AVEC4 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_AVEC4 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_EXT_IPL5) = + (BSP_INTLVL_AVEC5 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_AVEC5 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_EXT_IPL6) = + (BSP_INTLVL_AVEC6 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_AVEC6 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_EXT_IPL7) = + (BSP_INTLVL_AVEC7 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_AVEC7 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_TIMER_1) = + (BSP_INTLVL_TIMER1 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_TIMER1 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_TIMER_2) = + (BSP_INTLVL_TIMER2 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_TIMER2 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_MBUS) = + (BSP_INTLVL_MBUS << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_MBUS << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_UART_1) = + (BSP_INTLVL_UART1 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_UART1 << MCF5206E_ICR_IP_S); + *MCF5206E_ICR(MBAR,MCF5206E_INTR_UART_2) = + (BSP_INTLVL_UART2 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_UART2 << MCF5206E_ICR_IP_S); + *MCF5206E_ICR(MBAR,MCF5206E_INTR_DMA_0) = + (BSP_INTLVL_DMA0 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_DMA0 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + *MCF5206E_ICR(MBAR,MCF5206E_INTR_DMA_1) = + (BSP_INTLVL_DMA1 << MCF5206E_ICR_IL_S) | + (BSP_INTPRIO_DMA1 << MCF5206E_ICR_IP_S) | + MCF5206E_ICR_AVEC; + + /* Software Watchdog timer (not used now) */ + *MCF5206E_SWIVR(MBAR) = 0x0F; /* Uninitialized interrupt */ + *MCF5206E_SWSR(MBAR) = MCF5206E_SWSR_KEY1; + *MCF5206E_SWSR(MBAR) = MCF5206E_SWSR_KEY2; + + /* Configuring Chip Selects */ + /* CS2: SRAM memory */ + *MCF5206E_CSAR(MBAR,2) = BSP_MEM_ADDR_ESRAM >> 16; + *MCF5206E_CSMR(MBAR,2) = BSP_MEM_MASK_ESRAM; + *MCF5206E_CSCR(MBAR,2) = MCF5206E_CSCR_WS1 | + MCF5206E_CSCR_PS_32 | + MCF5206E_CSCR_AA | + MCF5206E_CSCR_EMAA | + MCF5206E_CSCR_WR | + MCF5206E_CSCR_RD; + + /* CS3: GPIO on eLITE board */ + *MCF5206E_CSAR(MBAR,3) = BSP_MEM_ADDR_GPIO >> 16; + *MCF5206E_CSMR(MBAR,3) = BSP_MEM_MASK_GPIO; + *MCF5206E_CSCR(MBAR,3) = MCF5206E_CSCR_WS15 | + MCF5206E_CSCR_PS_16 | + MCF5206E_CSCR_AA | + MCF5206E_CSCR_EMAA | + MCF5206E_CSCR_WR | + MCF5206E_CSCR_RD; + + { + uint32_t *inttab = (uint32_t*)&INTERRUPT_VECTOR; + uint32_t *intvec = (uint32_t*)BSP_MEM_ADDR_ESRAM; + register int i; + + for (i = 0; i < 256; i++) { + *(intvec++) = *(inttab++); + } + } + m68k_set_vbr(BSP_MEM_ADDR_ESRAM); + + /* CS0: Flash EEPROM */ + *MCF5206E_CSAR(MBAR,0) = BSP_MEM_ADDR_FLASH >> 16; + *MCF5206E_CSCR(MBAR,0) = MCF5206E_CSCR_WS3 | + MCF5206E_CSCR_AA | + MCF5206E_CSCR_PS_16 | + MCF5206E_CSCR_EMAA | + MCF5206E_CSCR_WR | + MCF5206E_CSCR_RD; + *MCF5206E_CSMR(MBAR,0) = BSP_MEM_MASK_FLASH; + + /* + * Invalidate the cache and disable it + */ + mcf5206e_disable_cache(); + + /* + * Setup ACRs so that if cache turned on, periphal accesses + * are not messed up. (Non-cacheable, serialized) + */ + m68k_set_acr0 ( 0 + | MCF5206E_ACR_BASE(BSP_MEM_ADDR_ESRAM) + | MCF5206E_ACR_MASK(BSP_MEM_MASK_ESRAM) + | MCF5206E_ACR_EN + | MCF5206E_ACR_SM_ANY + ); + m68k_set_acr1 ( 0 + | MCF5206E_ACR_BASE(BSP_MEM_ADDR_FLASH) + | MCF5206E_ACR_MASK(BSP_MEM_MASK_FLASH) + | MCF5206E_ACR_EN + | MCF5206E_ACR_SM_ANY + ); + + mcf5206e_enable_cache(); + + /* + * Copy data, clear BSS, switch stacks and call boot_card() + */ + CopyDataClearBSSAndStart (BSP_MEM_SIZE_ESRAM - 0x400); +} diff --git a/bsps/m68k/mcf5206elite/start/linkcmds b/bsps/m68k/mcf5206elite/start/linkcmds new file mode 100644 index 0000000000..817c80e298 --- /dev/null +++ b/bsps/m68k/mcf5206elite/start/linkcmds @@ -0,0 +1,207 @@ +/* + * This file contains GNU linker directives for an MCF5206eLITE + * evaluation board. + * + * Variations in memory size and allocation can be made by + * overriding some values with linker command-line arguments. + * + * Copyright (C) 2000 OKTET Ltd., St.-Petersburg, Russia + * Author: Victor V. Vengerov <vvv@oktet.ru> + * + * This file based on work: + * David Fiddes, D.J.Fiddes@hw.ac.uk + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * + * http://www.rtems.org/license/LICENSE. + */ + +/* + * Declare some sizes. + * XXX: The assignment of ". += XyzSize;" fails in older gld's if the + * number used there is not constant. If this happens to you, edit + * the lines marked XXX below to use a constant value. + */ + +/* + * Declare system clock frequency. + */ +_SYS_CLOCK_FREQUENCY = DEFINED(_SYS_CLOCK_FREQUENCY) ? + _SYS_CLOCK_FREQUENCY : 54000000; + +/* + * Declare size of heap. + * A heap size of 0 means "Use all available memory for the heap". + * Initial stack located in on-chip SRAM and not declared there. + */ +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +RamBase = DEFINED(RamBase) ? RamBase : 0x30000000; +RamSize = DEFINED(RamSize) ? RamSize : 0x00100000; + +/* + * Setup the memory map of the MCF5206eLITE evaluation board + * + * The "rom" section is in USER Flash on the board + * The "ram" section is placed in USER RAM starting at 10000h + * + */ +MEMORY +{ + ram : ORIGIN = 0x30000000, LENGTH = 0x00100000 + rom : ORIGIN = 0xFFE20000, LENGTH = 128k +} + +MBase = 0x10000000; + +ENTRY(start) +STARTUP(start.o) + +/* Interrupt Vector table located at start of external static RAM */ +_VBR = 0x30000000; + +SECTIONS +{ + + /* + * Dynamic RAM + */ + ram : { + RamBase = .; + RamBase = .; + /* Reserve space for interrupt table */ + . += 0x400; + } >ram + + /* + * Text, data and bss segments + */ + .text : { + CREATE_OBJECT_SYMBOLS + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + */ + . = ALIGN (16); + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + . = ALIGN (16); + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = .; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (etext = .); + + } > ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data BLOCK (0x4) : { + copy_start = .; + *(.shdata) + . = ALIGN (0x10); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + . = ALIGN (0x10); + *(.gcc_exc) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (0x10); + *(.gnu.linkonce.d*) + . = ALIGN (0x10); + _edata = .; + copy_end = .; + } > ram + + .bss BLOCK (0x4) : + { + clear_start = . ; + *(.shbss) + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN(0x10); + _end = .; + + clear_end = .; + + WorkAreaBase = .; + WorkAreaBase = .; + + } > ram + + .stab 0 (NOLOAD) : + { + *(.stab) + } + + .stabstr 0 (NOLOAD) : + { + *(.stabstr) + } + +} diff --git a/bsps/m68k/mcf5206elite/start/linkcmds.flash b/bsps/m68k/mcf5206elite/start/linkcmds.flash new file mode 100644 index 0000000000..8d429ab209 --- /dev/null +++ b/bsps/m68k/mcf5206elite/start/linkcmds.flash @@ -0,0 +1,207 @@ +/* + * This file contains GNU linker directives for an MCF5206eLITE + * evaluation board. + * + * Variations in memory size and allocation can be made by + * overriding some values with linker command-line arguments. + * + * Copyright (C) 2000 OKTET Ltd., St.-Petersburg, Russia + * Author: Victor V. Vengerov <vvv@oktet.ru> + * + * This file based on work: + * David Fiddes, D.J.Fiddes@hw.ac.uk + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * + * http://www.rtems.org/license/LICENSE. + */ + +/* + * Declare some sizes. + * XXX: The assignment of ". += XyzSize;" fails in older gld's if the + * number used there is not constant. If this happens to you, edit + * the lines marked XXX below to use a constant value. + */ +/* + * Declare size of heap. + * A heap size of 0 means "Use all available memory for the heap". + * Initial stack located in on-chip SRAM and not declared there. + */ +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; + +/* + * Declare system clock frequency. + */ +_SYS_CLOCK_FREQUENCY = DEFINED(_SYS_CLOCK_FREQUENCY) ? _SYS_CLOCK_FREQUENCY : 54000000; + +/* + * Setup the memory map of the MCF5206eLITE evaluation board + * + * The "rom" section is in USER Flash on the board + * The "ram" section is placed in USER RAM starting at 10000h + * + */ +MEMORY +{ + ram : ORIGIN = 0x30000000, LENGTH = 0x00100000 + rom : ORIGIN = 0xFFE00000, LENGTH = 0x00100000 +} + +MBase = 0x10000000; + +ENTRY(start) +STARTUP(start.o) + +/* Interrupt Vector table located at start of external static RAM */ +_VBR = 0x30000000; + +SECTIONS +{ + /* + * Flash ROM + */ + rom : { + _RomBase = .; + } >rom + + /* + * Dynamic RAM + */ + ram : { + RamBase = .; + RamBase = .; + } >ram + + /* + * Text, data and bss segments + */ + .text : AT(0x30020000) { + CREATE_OBJECT_SYMBOLS + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + */ + . = ALIGN (16); + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + . = ALIGN (16); + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (etext = .); + + } >rom + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >rom + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >rom + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data 0x30000400 : AT(LOADADDR(.text) + SIZEOF(.text)) { + copy_start = .; + . = ALIGN (0x10); + *(.shdata) + . = ALIGN (0x10); + *(.data) + KEEP (*(SORT(.rtemsrwset.*))) + . = ALIGN (0x10); + *(.gcc_exc) + *(.gcc_except_table*) + . = ALIGN (0x10); + *(.gnu.linkonce.d*) + . = ALIGN (0x10); + _edata = .; + copy_end = .; + } >ram + + .bss BLOCK (0x4) : + { + clear_start = . ; + *(.shbss) + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN(0x10); + _end = .; + + clear_end = .; + + WorkAreaBase = .; + WorkAreaBase = .; + + } > ram + + .stab 0 (NOLOAD) : + { + *(.stab) + } + + .stabstr 0 (NOLOAD) : + { + *(.stabstr) + } + +} diff --git a/bsps/m68k/mcf52235/start/bsp_specs b/bsps/m68k/mcf52235/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/mcf52235/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/mcf52235/start/bspgetcpuclockspeed.c b/bsps/m68k/mcf52235/start/bspgetcpuclockspeed.c new file mode 100644 index 0000000000..563044394a --- /dev/null +++ b/bsps/m68k/mcf52235/start/bspgetcpuclockspeed.c @@ -0,0 +1,15 @@ +/* + * COPYRIGHT (c) 1989-2008. + * 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.org/license/LICENSE. + */ + +#include <bsp.h> + +uint32_t bsp_get_CPU_clock_speed(void) +{ + return 60000000; +} diff --git a/bsps/m68k/mcf52235/start/cfinit.c b/bsps/m68k/mcf52235/start/cfinit.c new file mode 100644 index 0000000000..0007f9a449 --- /dev/null +++ b/bsps/m68k/mcf52235/start/cfinit.c @@ -0,0 +1,554 @@ +/********************************************************************* +* Initialisation Code for ColdFire MCF52235 Processor * +********************************************************************** + Generated by ColdFire Initialisation Utility 2.10.8 + Fri May 23 14:39:00 2008 + + MicroAPL Ltd makes no warranties in respect of the suitability + of this code for any particular purpose, and accepts + no liability for any loss arising out of its use. The person or + persons making use of this file must make the final evaluation + as to its suitability and correctness for a particular application. + +*/ + +/* Processor/internal bus clocked at 60.00 MHz */ + +#include <bsp.h> + +/* Additional register read/write macros (missing in headers) */ +#define MCF_CIM_CCON (*(vuint16*)(void*)(&__IPSBAR[0x00110004])) + +/* Bit definitions and macros for MCF_CIM_CCON */ +#define MCF_CIM_CCON_SZEN (0x00000040) +#define MCF_CIM_CCON_PSTEN (0x00000020) +#define MCF_CIM_CCON_BME (0x00000008) +#define MCF_CIM_CCON_BMT(x) (((x)&0x00000007)<<0) + +/* Function prototypes */ +void init_main(void); +static void disable_interrupts(void); +static void disable_watchdog_timer(void); +static void init_ipsbar(void); +static void init_clock_config(void); +static void init_sram(void); +static void init_flash_controller(void); +static void init_eport(void); +static void init_flexcan(void); +static void init_bus_config(void); +static void init_power_management(void); +static void init_dma_timers(void); +static void init_gp_timer(void); +static void init_interrupt_timers(void); +static void init_real_time_clock(void); +static void init_watchdog_timer(void); +static void init_pin_assignments(void); +static void init_interrupt_controller(void); + +/********************************************************************* +* init_main - Main entry point for initialisation code * +**********************************************************************/ +void init_main(void) +{ + /* Mask all interrupts */ + __asm__ ("move.w #0x2700,%sr"); + + /* Initialise base address of peripherals, VBR, etc */ + init_ipsbar(); + init_clock_config(); + + /* Disable interrupts and watchdog timer */ + disable_interrupts(); + disable_watchdog_timer(); + + /* Initialise individual modules */ + init_sram(); + init_flash_controller(); + init_eport(); + init_flexcan(); + init_bus_config(); + init_power_management(); + init_dma_timers(); + init_gp_timer(); + init_interrupt_timers(); + init_real_time_clock(); + init_watchdog_timer(); + init_pin_assignments(); + + /* Initialise interrupt controller */ + init_interrupt_controller(); +} + +/********************************************************************* +* disable_interrupts - Disable all interrupt sources * +**********************************************************************/ +static void disable_interrupts(void) +{ + vuint8 *p; + int i; + + /* Set ICR008-ICR063 to 0x0 */ + p = (vuint8 *) & MCF_INTC0_ICR8; + for (i = 8; i <= 63; i++) + *p++ = 0x0; + + /* Set ICR108-ICR139 to 0x0 */ + p = (vuint8 *) & MCF_INTC1_ICR8; + for (i = 108; i <= 139; i++) + *p++ = 0x0; +} + +/********************************************************************* +* disable_watchdog_timer - Disable system watchdog timer * +**********************************************************************/ +static void disable_watchdog_timer(void) +{ + /* Disable Core Watchdog Timer */ + MCF_SCM_CWCR = 0; +} + +/********************************************************************* +* init_clock_config - Clock Module * +**********************************************************************/ +static void init_clock_config(void) +{ + /* Clock source is 25.0000 MHz external crystal + Clock mode: Normal PLL mode + Processor/Bus clock frequency = 60.00 MHz + Loss of clock detection disabled + Reset on loss of lock disabled + */ + + /* Divide 25.0000 MHz clock to get 5.00 MHz PLL input clock */ + MCF_CLOCK_CCHR = MCF_CLOCK_CCHR_PFD(0x4); + + /* Set RFD+1 to avoid frequency overshoot and wait for PLL to lock */ + MCF_CLOCK_SYNCR = 0x4103; + while ((MCF_CLOCK_SYNSR & 0x08) == 0) ; + + /* Set desired RFD=0 and MFD=4 and wait for PLL to lock */ + MCF_CLOCK_SYNCR = 0x4003; + while ((MCF_CLOCK_SYNSR & 0x08) == 0) ; + MCF_CLOCK_SYNCR = 0x4007; /* Switch to using PLL */ +} + +/********************************************************************* +* init_ipsbar - Internal Peripheral System Base Address (IPSBAR) * +**********************************************************************/ +static void init_ipsbar(void) +{ + /* Base address of internal peripherals (IPSBAR) = 0x40000000 + + Note: Processor powers up with IPS base address = 0x40000000 + Write to IPS base + 0x00000000 to set new value + */ + *(vuint32 *) 0x40000000 = (vuint32) __IPSBAR + 1; /* +1 for Enable */ +} + +/********************************************************************* +* init_flash_controller - Flash Module * +**********************************************************************/ +static void init_flash_controller(void) +{ + /* Internal Flash module enabled, address = $00000000 + Flash state machine clock = 197.37 kHz + All access types except CPU space/interrupt acknowledge cycle allowed + Flash is Write-Protected + All interrupts disabled + */ + MCF_CFM_CFMCLKD = MCF_CFM_CFMCLKD_PRDIV8 | MCF_CFM_CFMCLKD_DIV(0x12); + MCF_CFM_CFMMCR = 0; + + /* WARNING: Setting FLASHBAR[6]=1 in order to turn off address speculation + This is a workaround for a hardware problem whereby a speculative + access to the Flash occuring at the same time as an SRAM access + can return corrupt data. + + This workaround can result in a 4% - 9% performance penalty. Other workarounds + are possible for certain applications. + + For example, if you know that you will not be using the top 32 KB of the Flash + you can place the SRAM base address at 0x20038000 + + See Device Errata for further details + */ + __asm__ ("move.l #0x00000161,%d0"); + __asm__ ("movec %d0,%FLASHBAR"); +} + +/********************************************************************* +* init_eport - Edge Port Module (EPORT) * +**********************************************************************/ +static void init_eport(void) +{ + /* Pins 1-15 configured as GPIO inputs */ + MCF_EPORT_EPDDR0 = 0; + MCF_EPORT_EPDDR1 = 0; + MCF_EPORT_EPPAR0 = 0; + MCF_EPORT_EPPAR1 = 0; + MCF_EPORT_EPIER0 = 0; + MCF_EPORT_EPIER1 = 0; +} + +/********************************************************************* +* init_flexcan - FlexCAN Module * +**********************************************************************/ +static void init_flexcan(void) +{ + /* FlexCAN controller disabled (CANMCR0[MDIS]=1) */ + MCF_CAN_IMASK = 0; + MCF_CAN_RXGMASK = MCF_CAN_RXGMASK_MI(0x1fffffff); + MCF_CAN_RX14MASK = MCF_CAN_RX14MASK_MI(0x1fffffff); + MCF_CAN_RX15MASK = MCF_CAN_RX15MASK_MI(0x1fffffff); + MCF_CAN_CANCTRL = 0; + MCF_CAN_CANMCR = MCF_CAN_CANMCR_MDIS | + MCF_CAN_CANMCR_FRZ | + MCF_CAN_CANMCR_HALT | MCF_CAN_CANMCR_SUPV | MCF_CAN_CANMCR_MAXMB(0xf); +} + +/********************************************************************* +* init_bus_config - Internal Bus Arbitration * +**********************************************************************/ +static void init_bus_config(void) +{ + /* Use round robin arbitration scheme + Assigned priorities (highest first): + Ethernet + DMA Controller + ColdFire Core + DMA bandwidth control disabled + Park on last active bus master + */ + MCF_SCM_MPARK = MCF_SCM_MPARK_M3PRTY(0x3) | + MCF_SCM_MPARK_M2PRTY(0x2) | (0x1 << 16); +} + +/********************************************************************* +* init_sram - On-chip SRAM * +**********************************************************************/ +static void init_sram(void) +{ + /* Internal SRAM module enabled, address = $20000000 + DMA access to SRAM block disabled + All access types (supervisor and user) allowed + */ + __asm__ ("move.l #0x20000001,%d0"); + __asm__ ("movec %d0,%RAMBAR"); +} + +/********************************************************************* +* init_power_management - Power Management * +**********************************************************************/ +static void init_power_management(void) +{ + /* On executing STOP instruction, processor enters RUN mode + Mode is exited when an interrupt of level 1 or higher is received + */ + MCF_PMM_LPICR = MCF_PMM_LPICR_ENBSTOP; + MCF_PMM_LPCR = MCF_PMM_LPCR_LPMD_RUN; +} + +/********************************************************************* +* init_dma_timers - DMA Timer Modules * +**********************************************************************/ +static void init_dma_timers(void) +{ + /* DMA Timer 0 disabled (DTMR0[RST] = 0) */ + MCF_DTIM0_DTMR = MCF_DTIM_DTMR_CLK(0x1); + MCF_DTIM0_DTXMR = 0; + MCF_DTIM0_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); + + /* DMA Timer 1 disabled (DTMR1[RST] = 0) */ + MCF_DTIM1_DTMR = 0; + MCF_DTIM1_DTXMR = 0; + MCF_DTIM1_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); + + /* DMA Timer 2 disabled (DTMR2[RST] = 0) */ + MCF_DTIM2_DTMR = 0; + MCF_DTIM2_DTXMR = 0; + MCF_DTIM2_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); + + /* DMA Timer 3 disabled (DTMR3[RST] = 0) */ + MCF_DTIM3_DTMR = MCF_DTIM_DTMR_CLK(0x1); + MCF_DTIM3_DTXMR = 0; + MCF_DTIM3_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); +} + +/********************************************************************* +* init_gp_timer - General Purpose Timer (GPT) Module * +**********************************************************************/ +static void init_gp_timer(void) +{ + /* + GPT disabled (GPTASCR1[GPTEN] = 0) + Channel 0 configured as GPIO input + Channel 1 configured as GPIO input + Channel 2 configured as GPIO input + Channel 3 configured as GPIO input + */ + MCF_GPT_GPTSCR1 = 0; + MCF_GPT_GPTDDR = 0; +} + +/********************************************************************** +* init_interrupt_timers - Programmable Interrupt Timer (PIT) Modules * +***********************************************************************/ +static void init_interrupt_timers(void) +{ + /* PIT0 disabled (PCSR0[EN]=0) */ + MCF_PIT0_PCSR = 0; + + /* PIT1 disabled (PCSR1[EN]=0) */ + MCF_PIT1_PCSR = 0; +} + +/********************************************************************* +* init_real_time_clock - Real-Time Clock (RTC) * +**********************************************************************/ +static void init_real_time_clock(void) +{ + /* Disable the RTC */ + MCF_RTC_CR = 0; +} + +/********************************************************************* +* init_watchdog_timer - Watchdog Timer * +**********************************************************************/ +static void init_watchdog_timer(void) +{ + /* Core Watchdog Timer disabled (CWCR[CWE]=0) */ + MCF_SCM_CWCR = 0; +} + +/********************************************************************* +* init_interrupt_controller - Interrupt Controller * +**********************************************************************/ +static void init_interrupt_controller(void) +{ + /* Configured interrupt sources in order of priority... + Level 7: External interrupt /IRQ7, (initially masked) + Level 6: External interrupt /IRQ6, (initially masked) + Level 5: External interrupt /IRQ5, (initially masked) + Level 4: External interrupt /IRQ4, (initially masked) + Level 3: External interrupt /IRQ3, (initially masked) + Level 2: External interrupt /IRQ2, (initially masked) + Level 1: External interrupt /IRQ1, (initially masked) + */ + MCF_INTC0_ICR1 = 0; + MCF_INTC0_ICR2 = 0; + MCF_INTC0_ICR3 = 0; + MCF_INTC0_ICR4 = 0; + MCF_INTC0_ICR5 = 0; + MCF_INTC0_ICR6 = 0; + MCF_INTC0_ICR7 = 0; + MCF_INTC0_ICR8 = 0; + MCF_INTC0_ICR9 = 0; + MCF_INTC0_ICR10 = 0; + MCF_INTC0_ICR11 = 0; + MCF_INTC0_ICR12 = 0; + MCF_INTC0_ICR13 = 0; + MCF_INTC0_ICR14 = 0; + MCF_INTC0_ICR15 = 0; + MCF_INTC0_ICR17 = 0; + MCF_INTC0_ICR18 = 0; + MCF_INTC0_ICR19 = 0; + MCF_INTC0_ICR20 = 0; + MCF_INTC0_ICR21 = 0; + MCF_INTC0_ICR22 = 0; + MCF_INTC0_ICR23 = 0; + MCF_INTC0_ICR24 = 0; + MCF_INTC0_ICR25 = 0; + MCF_INTC0_ICR26 = 0; + MCF_INTC0_ICR27 = 0; + MCF_INTC0_ICR28 = 0; + MCF_INTC0_ICR29 = 0; + MCF_INTC0_ICR30 = 0; + MCF_INTC0_ICR31 = 0; + MCF_INTC0_ICR32 = 0; + MCF_INTC0_ICR33 = 0; + MCF_INTC0_ICR34 = 0; + MCF_INTC0_ICR35 = 0; + MCF_INTC0_ICR36 = 0; + MCF_INTC0_ICR41 = 0; + MCF_INTC0_ICR42 = 0; + MCF_INTC0_ICR43 = 0; + MCF_INTC0_ICR44 = 0; + MCF_INTC0_ICR45 = 0; + MCF_INTC0_ICR46 = 0; + MCF_INTC0_ICR47 = 0; + MCF_INTC0_ICR48 = 0; + MCF_INTC0_ICR49 = 0; + MCF_INTC0_ICR50 = 0; + MCF_INTC0_ICR51 = 0; + MCF_INTC0_ICR52 = 0; + MCF_INTC0_ICR53 = 0; + MCF_INTC0_ICR55 = 0; + MCF_INTC0_ICR56 = 0; + MCF_INTC0_ICR59 = 0; + MCF_INTC0_ICR60 = 0; + MCF_INTC0_ICR61 = 0; + MCF_INTC0_ICR62 = 0; + MCF_INTC0_ICR63 = 0; + MCF_INTC1_ICR8 = 0; + MCF_INTC1_ICR9 = 0; + MCF_INTC1_ICR10 = 0; + MCF_INTC1_ICR11 = 0; + MCF_INTC1_ICR12 = 0; + MCF_INTC1_ICR13 = 0; + MCF_INTC1_ICR14 = 0; + MCF_INTC1_ICR15 = 0; + MCF_INTC1_ICR16 = 0; + MCF_INTC1_ICR17 = 0; + MCF_INTC1_ICR18 = 0; + MCF_INTC1_ICR19 = 0; + MCF_INTC1_ICR20 = 0; + MCF_INTC1_ICR21 = 0; + MCF_INTC1_ICR22 = 0; + MCF_INTC1_ICR23 = 0; + MCF_INTC1_ICR24 = 0; + MCF_INTC1_ICR25 = 0; + MCF_INTC1_ICR32 = 0; + MCF_INTC1_ICR33 = 0; + MCF_INTC1_ICR34 = 0; + MCF_INTC1_ICR35 = 0; + MCF_INTC1_ICR36 = 0; + MCF_INTC1_ICR37 = 0; + MCF_INTC1_ICR38 = 0; + MCF_INTC1_ICR39 = 0; + MCF_INTC0_IMRH = 0xffffffff; + MCF_INTC0_IMRL = 0xfffffffe; + MCF_INTC1_IMRH = 0xffffffff; + MCF_INTC1_IMRL = 0xfffffffe; +} + +/********************************************************************* +* init_pin_assignments - Pin Assignment and General Purpose I/O * +**********************************************************************/ +static void init_pin_assignments(void) +{ + /* Pin assignments for port NQ + Pins NQ7-NQ1 : EdgePort GPIO/IRQ + */ + MCF_GPIO_DDRNQ = 0; + MCF_GPIO_PNQPAR = MCF_GPIO_PNQPAR_PNQPAR7(0x1) | + MCF_GPIO_PNQPAR_PNQPAR6(0x1) | + MCF_GPIO_PNQPAR_PNQPAR5(0x1) | + MCF_GPIO_PNQPAR_PNQPAR4(0x1) | + MCF_GPIO_PNQPAR_PNQPAR3(0x1) | + MCF_GPIO_PNQPAR_PNQPAR2(0x1) | MCF_GPIO_PNQPAR_PNQPAR1(0x1); + + /* Pin assignments for port GP + Pins PG7-PG0 : EdgePort GPIO/IRQ + */ + MCF_GPIO_DDRGP = 0; + MCF_GPIO_PGPPAR = MCF_GPIO_PGPPAR_PGPPAR7 | + MCF_GPIO_PGPPAR_PGPPAR6 | + MCF_GPIO_PGPPAR_PGPPAR5 | + MCF_GPIO_PGPPAR_PGPPAR4 | + MCF_GPIO_PGPPAR_PGPPAR3 | + MCF_GPIO_PGPPAR_PGPPAR2 | + MCF_GPIO_PGPPAR_PGPPAR1 | MCF_GPIO_PGPPAR_PGPPAR0; + + /* Pin assignments for port DD + Pin DD7 : DDATA[3] + Pin DD6 : DDATA[2] + Pin DD5 : DDATA[1] + Pin DD4 : DDATA[0] + Pin DD3 : PST[3] + Pin DD2 : PST[2] + Pin DD1 : PST[1] + Pin DD0 : PST[0] + CCON[PSTEN] = 1 to enable PST/DDATA function + */ + MCF_GPIO_DDRDD = 0; + MCF_GPIO_PDDPAR = MCF_GPIO_PDDPAR_PDDPAR7 | + MCF_GPIO_PDDPAR_PDDPAR6 | + MCF_GPIO_PDDPAR_PDDPAR5 | + MCF_GPIO_PDDPAR_PDDPAR4 | + MCF_GPIO_PDDPAR_PDDPAR3 | + MCF_GPIO_PDDPAR_PDDPAR2 | + MCF_GPIO_PDDPAR_PDDPAR1 | MCF_GPIO_PDDPAR_PDDPAR0; + MCF_CIM_CCON = 0x0021; + + /* Pin assignments for port AN + Pins are all GPIO inputs + */ + MCF_GPIO_DDRAN = 0; + MCF_GPIO_PANPAR = 0; + + /* Pin assignments for port AS + Pins are all GPIO inputs + */ + MCF_GPIO_DDRAS = 0; + MCF_GPIO_PASPAR = 0; + + /* Pin assignments for port LD + Pins are all GPIO inputs + */ + MCF_GPIO_DDRLD = 0; + MCF_GPIO_PLDPAR = 0; + + /* Pin assignments for port QS + Pins are all GPIO inputs + */ + MCF_GPIO_DDRQS = 0; + MCF_GPIO_PQSPAR = 0; + + /* Pin assignments for port TA + Pins are all GPIO inputs + */ + MCF_GPIO_DDRTA = 0; + MCF_GPIO_PTAPAR = 0; + + /* Pin assignments for port TC + Pins are all GPIO inputs + */ + MCF_GPIO_DDRTC = 0; + MCF_GPIO_PTCPAR = 0; + + /* Pin assignments for port TD + Pins are all GPIO inputs + */ + MCF_GPIO_DDRTD = 0; + MCF_GPIO_PTDPAR = 0; + + /* Pin assignments for port UA + Pin UA3 : UART 0 clear-to-send, UCTS0 + Pin UA2 : UART 0 request-to-send, URTS0 + Pin UA1 : UART 0 receive data, URXD0 + Pin UA0 : UART 0 transmit data, UTXD0 + */ + MCF_GPIO_DDRUA = 0; + MCF_GPIO_PUAPAR = MCF_GPIO_PUAPAR_PUAPAR3(0x1) | + MCF_GPIO_PUAPAR_PUAPAR2(0x1) | + MCF_GPIO_PUAPAR_PUAPAR1(0x1) | MCF_GPIO_PUAPAR_PUAPAR0(0x1); + + /* Pin assignments for port UB + Pin UB3 : UART 1 clear-to-send, UCTS1 + Pin UB2 : UART 1 request-to-send, URTS1 + Pin UB1 : UART 1 receive data, URXD1 + Pin UB0 : UART 1 transmit data, UTXD1 + */ + MCF_GPIO_DDRUB = 0; + MCF_GPIO_PUBPAR = MCF_GPIO_PUBPAR_PUBPAR3(0x1) | + MCF_GPIO_PUBPAR_PUBPAR2(0x1) | + MCF_GPIO_PUBPAR_PUBPAR1(0x1) | MCF_GPIO_PUBPAR_PUBPAR0(0x1); + + /* Pin assignments for port UC + Pin UC3 : UART 2 clear-to-send, UCTS2 + Pin UC2 : UART 2 request-to-send, URTS2 + Pin UC1 : UART 2 receive data, URXD2 + Pin UC0 : UART 2 transmit data, UTXD2 + */ + MCF_GPIO_DDRUC = 0; + MCF_GPIO_PUCPAR = MCF_GPIO_PUCPAR_PUCPAR3 | + MCF_GPIO_PUCPAR_PUCPAR2 | + MCF_GPIO_PUCPAR_PUCPAR1 | MCF_GPIO_PUCPAR_PUCPAR0; + + /* Configure drive strengths */ + MCF_GPIO_PDSRH = 0; + MCF_GPIO_PDSRL = 0; + + /* Configure Wired-OR register */ + MCF_GPIO_PWOR = 0; +}
\ No newline at end of file diff --git a/bsps/m68k/mcf52235/start/init52235.c b/bsps/m68k/mcf52235/start/init52235.c new file mode 100644 index 0000000000..d54b624fdd --- /dev/null +++ b/bsps/m68k/mcf52235/start/init52235.c @@ -0,0 +1,79 @@ +/* + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +extern void _wr_vbr(uint32_t); +extern void init_main(void); + +/* + * From linkcmds + */ + +extern uint8_t _INTERRUPT_VECTOR[]; + +extern uint8_t _clear_start[]; +extern uint8_t _clear_end[]; + +extern uint8_t _data_src_start[]; +extern uint8_t _data_dest_start[]; +extern uint8_t _data_dest_end[]; + +void Init52235(void) +{ + register uint32_t i; + register uint32_t *dp, *sp; + register uint8_t *dbp, *sbp; + + /* + * Initialize the hardware + */ + init_main(); + + /* + * Copy the vector table to RAM + */ + if (&_VBR != (void *) _INTERRUPT_VECTOR) { + sp = (uint32_t *) _INTERRUPT_VECTOR; + dp = (uint32_t *) &_VBR; + for (i = 0; i < 256; i++) { + *dp++ = *sp++; + } + } + + _wr_vbr((uint32_t) &_VBR); + + /* + * Move initialized data from ROM to RAM. + */ + if (_data_src_start != _data_dest_start) { + dbp = (uint8_t *) _data_dest_start; + sbp = (uint8_t *) _data_src_start; + i = _data_dest_end - _data_dest_start; + while (i--) + *dbp++ = *sbp++; + } + + /* + * Zero uninitialized data + */ + + if (_clear_start != _clear_end) { + sbp = _clear_start; + dbp = _clear_end; + i = dbp - sbp; + while (i--) + *sbp++ = 0; + } + + /* + * We have to call some kind of RTEMS function here! + */ + + boot_card(0); + for (;;) ; +} diff --git a/bsps/m68k/mcf52235/start/linkcmds b/bsps/m68k/mcf52235/start/linkcmds new file mode 100644 index 0000000000..7c7755cc21 --- /dev/null +++ b/bsps/m68k/mcf52235/start/linkcmds @@ -0,0 +1,195 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Freescale ColdFire mcf52235 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE.e + */ + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x20000000; +RamSize = DEFINED(RamSize) ? RamSize : 32K; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x400; +_FlashBase = DEFINED(_FlashBase) ? _FlashBase : 0x00000000; + +_VBR = 0x20000000; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + sram : ORIGIN = 0x20000000, LENGTH = 32K + flash : ORIGIN = 0x00000000, LENGTH = 256K +} + +SECTIONS +{ + /* + * Text, data and bss segments + */ + .text : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + } >flash + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >flash + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >flash + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data 0x20000400 : AT (_estuff) + { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data) + *(.data.*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } >sram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : + { + PROVIDE (_clear_start = .); + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (_end = .); + PROVIDE (_clear_end = .); + } >sram + + .stack : + { + /* + * Starting Stack + */ + . += _StackSize; + . = ALIGN (16); + PROVIDE(_StackInit = .); + PROVIDE(WorkAreaBase = .); + } >sram + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + + PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/mcf5225x/start/bsp_specs b/bsps/m68k/mcf5225x/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/mcf5225x/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/mcf5225x/start/bspclean.c b/bsps/m68k/mcf5225x/start/bspclean.c new file mode 100644 index 0000000000..5cd1aed1e9 --- /dev/null +++ b/bsps/m68k/mcf5225x/start/bspclean.c @@ -0,0 +1,27 @@ +/* + * This routine returns control from RTEMS to the monitor. + * + * Author: + * David Fiddes, D.J@fiddes.surfaid.org + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <rtems/bspIo.h> + +void bsp_fatal_extension( + rtems_fatal_source source, + bool always_set_to_false, + rtems_fatal_code error +) +{ + printk("\nRTEMS exited!\n"); +} diff --git a/bsps/m68k/mcf5225x/start/bspstart.c b/bsps/m68k/mcf5225x/start/bspstart.c new file mode 100644 index 0000000000..d5e0f37dc8 --- /dev/null +++ b/bsps/m68k/mcf5225x/start/bspstart.c @@ -0,0 +1,35 @@ +/* + * This routine does the bulk of the system initialisation. + */ + +/* + * Author: + * David Fiddes, D.J@fiddes.surfaid.org + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +void __attribute__((weak)) bsp_start(void) +{ +} + +uint32_t __attribute__((weak)) bsp_get_CPU_clock_speed(void) +{ + #define DEF_CLOCK_SPEED 8000000.0F //8.0 MHz + #define MCF_MFD0_2_MASK 0x7000U + #define MCF_RFD0_2_MASK 0x0700U + #define MCF_MFD0_2_OFFSET 4U + + #define SPEED_BIAS ((((MCF_CLOCK_SYNCR & MCF_MFD0_2_MASK) >> 11) + MCF_MFD0_2_OFFSET) / (float)(((MCF_CLOCK_SYNCR & MCF_RFD0_2_MASK)>>7) ? : 1.0F)) + + return MCF_CLOCK_SYNCR & MCF_CLOCK_SYNCR_PLLEN ? SPEED_BIAS * DEF_CLOCK_SPEED : DEF_CLOCK_SPEED; +} diff --git a/bsps/m68k/mcf5225x/start/init5225x.c b/bsps/m68k/mcf5225x/start/init5225x.c new file mode 100644 index 0000000000..caf7db1953 --- /dev/null +++ b/bsps/m68k/mcf5225x/start/init5225x.c @@ -0,0 +1,84 @@ +/* + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + * + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +extern void _wr_vbr(uint32_t); + +extern long _d0_reset,_d1_reset,_M68kSpuriousInterruptCount; + +/* + * From linkcmds + */ + +extern uint8_t _INTERRUPT_VECTOR[]; + +extern uint8_t _clear_start[]; +extern uint8_t _clear_end[]; + +extern uint8_t _data_src_start[]; +extern uint8_t _data_dest_start[]; +extern uint8_t _data_dest_end[]; + +void Init5225x(void) +{ + register uint32_t i; + register uint32_t *dp, *sp; + register uint8_t *dbp, *sbp; + + /* + * Copy the vector table to RAM + */ + + if (&_VBR != (void *)_INTERRUPT_VECTOR) { + sp = (uint32_t *) _INTERRUPT_VECTOR; + dp = (uint32_t *) &_VBR; + for (i = 0; i < 256; i++) { + *dp++ = *sp++; + } + } + + /* + * Move initialized data from ROM to RAM. + */ + if (_data_src_start != _data_dest_start) { + dbp = (uint8_t *) _data_dest_start; + sbp = (uint8_t *) _data_src_start; + i = _data_dest_end - _data_dest_start; + while (i--) + *dbp++ = *sbp++; + } + + asm __volatile__ ("move.l %%d5,%0\n\t":"=r" (_d0_reset)); + asm __volatile__ ("move.l %%d6,%0\n\t":"=r" (_d1_reset)); + + /* + * Zero uninitialized data + */ + + if (_clear_start != _clear_end) { + sbp = _clear_start; + dbp = _clear_end; + i = dbp - sbp; + while (i--) + *sbp++ = 0; + } + +//_wr_vbr((uint32_t) &_VBR); + asm volatile("move.l %0,%%d7;movec %%d7,%%vbr\n\t"::"i"(&_VBR): "cc"); + + /* + * We have to call some kind of RTEMS function here! + */ + + boot_card(0); + for (;;) ; +} diff --git a/bsps/m68k/mcf5225x/start/linkcmds b/bsps/m68k/mcf5225x/start/linkcmds new file mode 100644 index 0000000000..81d2058872 --- /dev/null +++ b/bsps/m68k/mcf5225x/start/linkcmds @@ -0,0 +1,195 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Freescale ColdFire mcf52258 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE.e + */ + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x20000000; +RamSize = DEFINED(RamSize) ? RamSize : 64K; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x400; +_FlashBase = DEFINED(_FlashBase) ? _FlashBase : 0x00000000; + +_VBR = 0x20000000; + +ENTRY(start) +STARTUP(start.o) + + +MEMORY +{ + sram : ORIGIN = 0x20000000, LENGTH = 64K + flash : ORIGIN = 0x00000000, LENGTH = 512K +} + +SECTIONS +{ + /* + * Text, data and bss segments + */ + .text : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + } >flash + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >flash + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >flash + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data 0x20000400 : AT (_estuff) + { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } >sram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : + { + PROVIDE (_clear_start = .); + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (_end = .); + PROVIDE (_clear_end = .); + } >sram + + .stack : + { + /* + * Starting Stack + */ + . += _StackSize; + . = ALIGN (16); + PROVIDE(_StackInit = .); + PROVIDE(WorkAreaBase = .); + } >sram + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + + PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/mcf5235/start/bsp_specs b/bsps/m68k/mcf5235/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/mcf5235/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/mcf5235/start/bspgetcpuclockspeed.c b/bsps/m68k/mcf5235/start/bspgetcpuclockspeed.c new file mode 100644 index 0000000000..548caaa9b8 --- /dev/null +++ b/bsps/m68k/mcf5235/start/bspgetcpuclockspeed.c @@ -0,0 +1,17 @@ +/* + * COPYRIGHT (c) 1989-2008. + * 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.org/license/LICENSE. + */ + +#include <bsp.h> + +extern char _CPUClockSpeed[]; + +uint32_t get_CPU_clock_speed(void) +{ + return( (uint32_t)_CPUClockSpeed); +} diff --git a/bsps/m68k/mcf5235/start/bspstart.c b/bsps/m68k/mcf5235/start/bspstart.c new file mode 100644 index 0000000000..744d4c9142 --- /dev/null +++ b/bsps/m68k/mcf5235/start/bspstart.c @@ -0,0 +1,60 @@ +/* + * This routine does the bulk of the system initialization. + */ + +/* + * COPYRIGHT (c) 1989-2008. + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +/* + * Read/write copy of common cache + * Split I/D cache + * Allow CPUSHL to invalidate a cache line + * Enable buffered writes + * No burst transfers on non-cacheable accesses + * Default cache mode is *disabled* (cache only ACRx areas) + */ +uint32_t cacr_mode = MCF5XXX_CACR_CENB | MCF5XXX_CACR_DBWE | MCF5XXX_CACR_DCM; + +/* + * Cacheable areas + */ +extern char RamBase[]; +extern char RamSize[]; + +/* + * bsp_start + * + * This routine does the bulk of the system initialisation. + */ +void bsp_start( void ) +{ + /* + * Invalidate the cache and disable it + */ + m68k_set_acr0(0); + m68k_set_acr1(0); + m68k_set_cacr(MCF5XXX_CACR_CINV); + + /* + * Cache SDRAM + */ + m68k_set_acr0(MCF5XXX_ACR_AB((uintptr_t)RamBase) | + MCF5XXX_ACR_AM((uintptr_t)RamSize-1) | + MCF5XXX_ACR_EN | + MCF5XXX_ACR_BWE | + MCF5XXX_ACR_SM_IGNORE); + + /* + * Enable the cache + */ + m68k_set_cacr(cacr_mode); +} diff --git a/bsps/m68k/mcf5235/start/copyvectors.c b/bsps/m68k/mcf5235/start/copyvectors.c new file mode 100644 index 0000000000..2c54c31a44 --- /dev/null +++ b/bsps/m68k/mcf5235/start/copyvectors.c @@ -0,0 +1,19 @@ +/* + * Move the copy out of the Init5235 file because gcc is broken. + */ + +#include <stdint.h> + +void CopyVectors(const uint32_t* old, uint32_t* new); + +void CopyVectors(const uint32_t* old, uint32_t* new) +{ + int v = 0; + while (v < 256) + { + *new = *old; + ++v; + ++new; + ++old; + } +} diff --git a/bsps/m68k/mcf5235/start/init5235.c b/bsps/m68k/mcf5235/start/init5235.c new file mode 100644 index 0000000000..5066941be0 --- /dev/null +++ b/bsps/m68k/mcf5235/start/init5235.c @@ -0,0 +1,89 @@ +/* + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + * + * This routine is pretty simple for the uC5235 because all the hard + * work has been done by the bootstrap dBUG code. + */ + +#include <rtems.h> +#include <bsp.h> + +#define MM_SDRAM_BASE (0x00000000) + +/* + * MCF5235_BSP_START_FROM_FLASH comes from the linker script + * If it is set to 0 then it is assumed that the motorola debug monitor + * is present and we do not need to re-initialize the SDRAM. Otherwise, + * if it is set to 1 then we want to boot our own code from flash and we + * do need to initialize the SDRAM. + */ + +extern uint32_t MCF5235_BSP_START_FROM_FLASH; +extern void CopyDataClearBSSAndStart (void); +extern void INTERRUPT_VECTOR(void); + +extern void CopyVectors(const uint32_t* old, uint32_t* new); + +void Init5235 (void) +{ + int x; + volatile int temp = 0; + int *address_of_MCF5235_BSP_START_FROM_FLASH; + + /*Setup the GPIO Registers */ + MCF5235_GPIO_UART=0x3FFF; + MCF5235_GPIO_PAR_AD=0xE1; + + /*Setup the Chip Selects so CS0 is flash */ + MCF5235_CS_CSAR0 =(0xFFE00000 & 0xffff0000)>>16; + MCF5235_CS_CSMR0 = 0x001f0001; + MCF5235_CS_CSCR0 = 0x1980; + + address_of_MCF5235_BSP_START_FROM_FLASH = (int *) & MCF5235_BSP_START_FROM_FLASH; + if ( (int)address_of_MCF5235_BSP_START_FROM_FLASH == 1) { + /*Setup the SDRAM */ + for(x=0; x<20000; x++) + { + temp +=1; + } + MCF5235_SDRAMC_DCR = 0x042E; + MCF5235_SDRAMC_DACR0 = 0x00001300; + MCF5235_SDRAMC_DMR0 = (0x00FC0000) | (0x00000001); + for(x=0; x<20000; x++) + { + temp +=1; + } + /* set ip ( bit 3 ) in dacr */ + MCF5235_SDRAMC_DACR0 |= (0x00000008) ; + /* init precharge */ + *((unsigned long *)MM_SDRAM_BASE) = 0xDEADBEEF; + /* set RE in dacr */ + MCF5235_SDRAMC_DACR0 |= (0x00008000); + /* wait */ + for(x=0; x<20000; x++) + { + temp +=1; + } + /* issue IMRS */ + MCF5235_SDRAMC_DACR0 |= (0x00000040); + *((short *)MM_SDRAM_BASE) = 0; + for(x=0; x<60000; x++) + { + temp +=1; + } + *((unsigned long*)MM_SDRAM_BASE)=0x12345678; + } /* we have finished setting up the sdram */ + + /* Copy the interrupt vector table to address 0x0 in SDRAM */ + CopyVectors((const uint32_t *)&INTERRUPT_VECTOR, (uint32_t*)0); + + m68k_set_vbr(0); + + /* + * Copy data, clear BSS and call boot_card() + */ + CopyDataClearBSSAndStart (); + +} diff --git a/bsps/m68k/mcf5235/start/linkcmds b/bsps/m68k/mcf5235/start/linkcmds new file mode 100644 index 0000000000..660c931e26 --- /dev/null +++ b/bsps/m68k/mcf5235/start/linkcmds @@ -0,0 +1,203 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Freescale ColdFire mcf5235 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + */ + +/* + * declare for the MCF5235_BSP_START_FROM_FLASH + * 0 - use debug monitor to load to ram + * 1 - load everything from flash from scratch + */ +MCF5235_BSP_START_FROM_FLASH = 0; + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 16M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; + + +/* + * System clock speed + */ +_CPUClockSpeed = DEFINED(_CPUClockSpeed) ? _CPUClockSpeed : 150000000 ; + +/* + * Location of on-chip devices + */ +__IPSBAR = DEFINED(__IPSBAR) ? __IPSBAR : 0x40000000 ; +__SRAMBASE = DEFINED(__SRAMBASE) ? __SRAMBASE : 0x20000000 ; +_VBR = 0x0; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + dram : ORIGIN = 0, LENGTH = 16M + sram : ORIGIN = 0x20000000, LENGTH = 64K + flash : ORIGIN = 0xFFE00000, LENGTH = 2M +} + +SECTIONS +{ + + _header_offset = 0; + + /* + * Text, data and bss segments + */ + .text 0x40000 : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } > dram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } > dram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } > dram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } > dram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + _clear_end = .; + + WorkAreaBase = .; + } > dram + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + +PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/mcf5235/start/linkcmdsflash b/bsps/m68k/mcf5235/start/linkcmdsflash new file mode 100644 index 0000000000..832424a2d9 --- /dev/null +++ b/bsps/m68k/mcf5235/start/linkcmdsflash @@ -0,0 +1,208 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Freescale ColdFire mcf5235 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + */ + +/* + * declare for the MCF5235_BSP_START_FROM_FLASH + * 0 - use debug monitor to load to ram + * 1 - load everything from flash from scratch + */ +MCF5235_BSP_START_FROM_FLASH = 1; + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 16M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; + + +/* + * System clock speed + */ +_CPUClockSpeed = DEFINED(_CPUClockSpeed) ? _CPUClockSpeed : 150000000 ; + +/* + * Location of on-chip devices + */ +__IPSBAR = DEFINED(__IPSBAR) ? __IPSBAR : 0x40000000 ; +__SRAMBASE = DEFINED(__SRAMBASE) ? __SRAMBASE : 0x20000000 ; +_VBR = 0x0; + +ENTRY(start) +STARTUP(start.o) + +/* + * NOTE: If loading to flash with dBUG remember to change the origin to 0xFFF00000 because that's where user flash is + * located. + */ +MEMORY +{ + ram : ORIGIN = 0, LENGTH = 16M + sram : ORIGIN = 0x20000000, LENGTH = 64K + flash : ORIGIN = 0xFFE00000, LENGTH = 2M +} + +SECTIONS +{ + + _header_offset = 0; + + /* + * Text, data and bss segments + */ + .text : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >flash + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >flash + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >flash + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data 0x4000 : AT ( ADDR(.tdata) + SIZEOF ( .tdata ) ) + { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } >ram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + _clear_end = .; + + WorkAreaBase = .; + } >ram + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + +PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/mcf5235/start/linkcmdsram b/bsps/m68k/mcf5235/start/linkcmdsram new file mode 100644 index 0000000000..ec7483001e --- /dev/null +++ b/bsps/m68k/mcf5235/start/linkcmdsram @@ -0,0 +1,203 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Freescale ColdFire mcf5235 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + */ + +/* + * declare for the MCF5235_BSP_START_FROM_FLASH + * 0 - use debug monitor to load to ram + * 1 - load everything from flash from scratch + */ +MCF5235_BSP_START_FROM_FLASH = 0; + +/* + * Declare some sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 16M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; + + +/* + * System clock speed + */ +_CPUClockSpeed = DEFINED(_CPUClockSpeed) ? _CPUClockSpeed : 150000000 ; + +/* + * Location of on-chip devices + */ +__IPSBAR = DEFINED(__IPSBAR) ? __IPSBAR : 0x40000000 ; +__SRAMBASE = DEFINED(__SRAMBASE) ? __SRAMBASE : 0x20000000 ; +_VBR = 0x0; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + ram : ORIGIN = 0, LENGTH = 16M + sram : ORIGIN = 0x20000000, LENGTH = 64K + flash : ORIGIN = 0xFFE00000, LENGTH = 2M +} + +SECTIONS +{ + + _header_offset = 0; + + /* + * Text, data and bss segments + */ + .text 0x40000 : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } >ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } >ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } >ram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + _clear_end = .; + + WorkAreaBase = .; + } >ram + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + +PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/mcf5329/start/bsp_specs b/bsps/m68k/mcf5329/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/mcf5329/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/mcf5329/start/bspstart.c b/bsps/m68k/mcf5329/start/bspstart.c new file mode 100644 index 0000000000..d5a258da47 --- /dev/null +++ b/bsps/m68k/mcf5329/start/bspstart.c @@ -0,0 +1,41 @@ +/* + * This routine does the bulk of the system initialisation. + */ + +/* + * Author: + * David Fiddes, D.J@fiddes.surfaid.org + * http://www.calm.hw.ac.uk/davidf/coldfire/ + * + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <rtems/rtems/cache.h> + +void bsp_start(void) +{ + /* cfinit invalidates cache and sets acr registers */ + + /* + * Enable the cache, we only need to enable the instruction cache as the + * 532x has a unified data and instruction cache. + */ + rtems_cache_enable_instruction(); +} + +uint32_t bsp_get_CPU_clock_speed(void) +{ + return 240000000; +} + +uint32_t bsp_get_BUS_clock_speed(void) +{ + return 80000000; +} diff --git a/bsps/m68k/mcf5329/start/cfinit.c b/bsps/m68k/mcf5329/start/cfinit.c new file mode 100644 index 0000000000..1fe9015449 --- /dev/null +++ b/bsps/m68k/mcf5329/start/cfinit.c @@ -0,0 +1,707 @@ +/********************************************************************* +* Initialisation Code for ColdFire MCF5329 Processor * +********************************************************************** + Generated by ColdFire Initialisation Utility 2.10.8 + Wed Jul 02 14:26:25 2008 + + MicroAPL Ltd makes no warranties in respect of the suitability + of this code for any particular purpose, and accepts + no liability for any loss arising out of its use. The person or + persons making use of this file must make the final evaluation + as to its suitability and correctness for a particular application. + +*/ + +/* External reference frequency is 16.0000 MHz + Internal bus clock frequency = 80.00 MHz + Processor core frequency = 240.00 MHz +*/ + +#include <bsp.h> + +/* eDMA Transfer Control Descriptor definitions */ +#define MCF_EDMA_TCD_W0(channel) (*(vuint32 *)(0xFC045000+((channel)*0x20))) /* Transfer Control Descriptor Word 0 */ +#define MCF_EDMA_TCD_W1(channel) (*(vuint32 *)(0xFC045004+((channel)*0x20))) /* Transfer Control Descriptor Word 1 */ +#define MCF_EDMA_TCD_W2(channel) (*(vuint32 *)(0xFC045008+((channel)*0x20))) /* Transfer Control Descriptor Word 2 */ +#define MCF_EDMA_TCD_W3(channel) (*(vuint32 *)(0xFC04500C+((channel)*0x20))) /* Transfer Control Descriptor Word 3 */ +#define MCF_EDMA_TCD_W4(channel) (*(vuint32 *)(0xFC045010+((channel)*0x20))) /* Transfer Control Descriptor Word 4 */ +#define MCF_EDMA_TCD_W5(channel) (*(vuint32 *)(0xFC045014+((channel)*0x20))) /* Transfer Control Descriptor Word 5 */ +#define MCF_EDMA_TCD_W6(channel) (*(vuint32 *)(0xFC045018+((channel)*0x20))) /* Transfer Control Descriptor Word 6 */ +#define MCF_EDMA_TCD_W7(channel) (*(vuint32 *)(0xFC04501C+((channel)*0x20))) /* Transfer Control Descriptor Word 7 */ + +/* Function prototypes */ +void init_main(void); +static void disable_interrupts(void); +static void disable_watchdog_timer(void); +static void disable_cache(void); +extern void init_clock_config(void) __attribute__ ((section(".ram_code"))); +static void init_cache(void); +static void init_crossbar(void); +extern void init_chip_selects(void) __attribute__ ((section(".ram_code"))); +static void init_eport(void); +static void init_flexcan(void); +static void init_dma_timers(void); +static void init_interrupt_timers(void); +static void init_real_time_clock(void); +static void init_watchdog_timers(void); +static void init_edma(void); +static void init_pin_assignments(void); +extern void init_sdram_controller(void) + __attribute__ ((section(".ram_code"))); +static void init_interrupt_controller(void); + +/********************************************************************* +* init_main - Main entry point for initialisation code * +**********************************************************************/ +void init_main(void) +{ + init_clock_config(); + + /* Disable interrupts, watchdog timer, cache */ + disable_interrupts(); + disable_watchdog_timer(); + disable_cache(); + + /* Initialise individual modules */ + init_cache(); + init_crossbar(); + init_chip_selects(); + init_eport(); + init_flexcan(); + init_dma_timers(); + init_interrupt_timers(); + init_real_time_clock(); + init_watchdog_timers(); + init_edma(); + init_pin_assignments(); + + /* Initialise SDRAM controller (must be done after pin assignments) */ + init_sdram_controller(); + + /* Initialise interrupt controller */ + init_interrupt_controller(); +} + +/********************************************************************* +* disable_interrupts - Disable all interrupt sources * +**********************************************************************/ +static void disable_interrupts(void) +{ + vuint8 *p; + int i; + + /* Set ICR001-ICR063 to 0x0 */ + p = (vuint8 *) & MCF_INTC0_ICR1; + for (i = 1; i <= 63; i++) + *p++ = 0x0; + + /* Set ICR100-ICR163 to 0x0 */ + p = (vuint8 *) & MCF_INTC1_ICR0; + for (i = 100; i <= 163; i++) + *p++ = 0x0; +} + +/********************************************************************* +* disable_watchdog_timer - Disable system watchdog timer * +**********************************************************************/ +static void disable_watchdog_timer(void) +{ + /* Disable Core Watchdog Timer */ + MCF_SCM_CWCR = 0; +} + +/********************************************************************* +* disable_cache - Disable and invalidate cache * +**********************************************************************/ +static void disable_cache(void) +{ + __asm__ ("move.l #0x01000000,%d0"); + __asm__ ("movec %d0,%CACR"); +} + +/********************************************************************* +* init_clock_config - Clock Module * +**********************************************************************/ +void init_clock_config(void) +{ + /* Clock module uses normal PLL mode with 16.0000 MHz external reference + Bus clock frequency = 80.00 MHz + Processor clock frequency = 3 x bus clock = 240.00 MHz + Dithering disabled + */ + + /* Check to see if the SDRAM has already been initialized + by a run control tool. If it has, put SDRAM into self-refresh mode before + initializing the PLL + */ + if (MCF_SDRAMC_SDCR & MCF_SDRAMC_SDCR_REF) + MCF_SDRAMC_SDCR &= ~MCF_SDRAMC_SDCR_CKE; + + /* Temporarily switch to LIMP mode + NOTE: Ensure that this code is not executing from SDRAM, since the + SDRAM Controller is disabled in LIMP mode + */ + MCF_CCM_CDR = (MCF_CCM_CDR & 0xf0ff) | MCF_CCM_CDR_LPDIV(0x2); + MCF_CCM_MISCCR |= MCF_CCM_MISCCR_LIMP; + + /* Configure the PLL settings */ + MCF_PLL_PODR = MCF_PLL_PODR_CPUDIV(0x2) | MCF_PLL_PODR_BUSDIV(0x6); + MCF_PLL_PFDR = MCF_PLL_PFDR_MFD(0x78); + MCF_PLL_PLLCR = 0; + MCF_PLL_PMDR = 0; + + /* Enable PLL and wait for lock */ + MCF_CCM_MISCCR &= ~MCF_CCM_MISCCR_LIMP; + while ((MCF_CCM_MISCCR & MCF_CCM_MISCCR_PLL_LOCK) == 0) ; + + /* From the Device Errata: + + "After exiting LIMP mode, the value of 0x40000000 should be written + to address 0xFC0B8080 before attempting to initialize the SDRAMC + or exit the SDRAM from self-refresh mode." + */ + *(vuint32 *) 0xfc0b8080 = 0x40000000; + + /* If we put the SDRAM into self-refresh mode earlier, restore mode now */ + if (MCF_SDRAMC_SDCR & MCF_SDRAMC_SDCR_REF) + MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_CKE; +} + +/********************************************************************* +* init_cache - Unified (Instruction and Data) Cache * +**********************************************************************/ +static void init_cache(void) +{ + /* ACR0: Cache accesses to 32 MB memory region at address $40000000 + CACR: Don't cache accesses to the rest of memory + */ + /* + * Cache is enabled in bspstart.c + */ +#if 0 + __asm__ ("move.l #0xa0000600,%d0"); + __asm__ ("movec %d0,%CACR"); +#endif + __asm__ ("move.l #0x4001c020,%d0"); + __asm__ ("movec %d0,%ACR0"); + __asm__ ("move.l #0x00000000,%d0"); + __asm__ ("movec %d0,%ACR1"); +} + +/********************************************************************* +* init_crossbar - Cross-Bar Switch (XBS) Module * +**********************************************************************/ +static void init_crossbar(void) +{ + /* XBS settings for FlexBus/SDRAM Controller slave: + Fixed priority (Core, LCD, eDMA, FEC, USB Host, USB OTG), park on ColdFire Core + */ + MCF_XBS_PRS1 = MCF_XBS_PRS_M6(0x5) | + MCF_XBS_PRS_M5(0x4) | + MCF_XBS_PRS_M4(0x1) | MCF_XBS_PRS_M2(0x3) | MCF_XBS_PRS_M1(0x2); + MCF_XBS_CRS1 = 0; + + /* XBS settings for SRAM Backdoor slave: + Fixed priority (Core, eDMA, FEC, LCD, USB Host, USB OTG), park on ColdFire Core + */ + MCF_XBS_PRS4 = MCF_XBS_PRS_M6(0x5) | + MCF_XBS_PRS_M5(0x4) | + MCF_XBS_PRS_M4(0x3) | MCF_XBS_PRS_M2(0x2) | MCF_XBS_PRS_M1(0x1); + MCF_XBS_CRS4 = 0; + + /* XBS settings for Cryptography Modules slave: + Fixed priority (Core, eDMA, FEC, LCD, USB Host, USB OTG), park on ColdFire Core + */ + MCF_XBS_PRS6 = MCF_XBS_PRS_M6(0x5) | + MCF_XBS_PRS_M5(0x4) | + MCF_XBS_PRS_M4(0x3) | MCF_XBS_PRS_M2(0x2) | MCF_XBS_PRS_M1(0x1); + MCF_XBS_CRS6 = 0; + + /* XBS settings for On-chip Peripherals slave: + Fixed priority (Core, eDMA, FEC, LCD, USB Host, USB OTG), park on ColdFire Core + */ + MCF_XBS_PRS7 = MCF_XBS_PRS_M6(0x5) | + MCF_XBS_PRS_M5(0x4) | + MCF_XBS_PRS_M4(0x3) | MCF_XBS_PRS_M2(0x2) | MCF_XBS_PRS_M1(0x1); + MCF_XBS_CRS7 = 0; +} + +/********************************************************************* +* init_chip_selects - Chip Select Module (FlexBus) * +**********************************************************************/ +void init_chip_selects(void) +{ + /* Chip Select 1 disabled (CSMR1[V] = 0) */ + MCF_FBCS1_CSMR = 0; + + /* Chip Select 2 disabled (CSMR2[V] = 0) */ + MCF_FBCS2_CSMR = 0; + + /* Chip Select 3 disabled (CSMR3[V] = 0) */ + MCF_FBCS3_CSMR = 0; + + /* Chip Select 4 disabled (CSMR4[V] = 0) */ + MCF_FBCS4_CSMR = 0; + + /* Chip Select 5 disabled (CSMR5[V] = 0) */ + MCF_FBCS5_CSMR = 0; + + /* Chip Select 0: 2 MB of Flash at base address $00000000 + Port size = 16 bits + Assert chip select on first rising clock edge after address is asserted + Generate internal transfer acknowledge after 7 wait states + Address is held for 1 clock at end of read and write cycles + */ + MCF_FBCS0_CSAR = 0; + MCF_FBCS0_CSCR = MCF_FBCS_CSCR_WS(0x7) | + (0x1 << 9) | MCF_FBCS_CSCR_AA | MCF_FBCS_CSCR_PS(0x2) | MCF_FBCS_CSCR_BEM; + MCF_FBCS0_CSMR = MCF_FBCS_CSMR_BAM(0x1f) | MCF_FBCS_CSMR_V; +} + +/********************************************************************* +* init_eport - Edge Port Module (EPORT) * +**********************************************************************/ +static void init_eport(void) +{ + /* Pins 1-7 configured as GPIO inputs */ + MCF_EPORT_EPPAR = 0; + MCF_EPORT_EPDDR = 0; + MCF_EPORT_EPIER = 0; +} + +/********************************************************************* +* init_flexcan - FlexCAN Module * +**********************************************************************/ +static void init_flexcan(void) +{ + /* FlexCAN controller disabled (CANMCR0[MDIS]=1) */ + MCF_CAN_IMASK = 0; + MCF_CAN_RXGMASK = MCF_CAN_RXGMASK_MI(0x1fffffff); + MCF_CAN_RX14MASK = MCF_CAN_RX14MASK_MI(0x1fffffff); + MCF_CAN_RX15MASK = MCF_CAN_RX15MASK_MI(0x1fffffff); + MCF_CAN_CANCTRL = 0; + MCF_CAN_CANMCR = MCF_CAN_CANMCR_MDIS | + MCF_CAN_CANMCR_FRZ | + MCF_CAN_CANMCR_HALT | MCF_CAN_CANMCR_SUPV | MCF_CAN_CANMCR_MAXMB(0xf); +} + +/********************************************************************* +* init_sdram_controller - SDRAM Controller * +**********************************************************************/ +void init_sdram_controller(void) +{ + /* Check to see if the SDRAM has already been initialized + by a run control tool and skip if so + */ + if (MCF_SDRAMC_SDCR & MCF_SDRAMC_SDCR_REF) + return; + + /* Ensure that there is a delay from processor reset of the time recommended in + the SDRAM data sheet (typically 100-200 microseconds) until the following + code so that the SDRAM is ready for commands... + */ + + /* SDRAM controller configured for Double-data rate (DDR) SDRAM + Bus width = 16 bits + SDRAM specification: + SDRAM clock frequency = 80.00 MHz + CASL = 2.5 + ACTV-to-read/write delay, tRCD = 20.0 nanoseconds + Write recovery time, tWR = 15.0 nanoseconds + Precharge comand to ACTV command, tRP = 20.0 nanoseconds + Auto refresh command period, tRFC = 75.0 nanoseconds + Average periodic refresh interval, tREFI = 7.8 microseconds + */ + + /* Memory block 0 enabled - 32 MBytes at address $40000000 + Block consists of 1 device x 256 MBits (13 rows x 9 columns x 4 banks) + */ + MCF_SDRAMC_SDCS0 = MCF_SDRAMC_SDCS_BASE(0x400) | MCF_SDRAMC_SDCS_CSSZ(0x18); + + /* Memory block 1 disabled */ + MCF_SDRAMC_SDCS1 = 0; + + /* Initialise SDCFG1 register with delay and timing values + SRD2RWP = 4, SWT2RWP = 3, RD_LAT = 7, ACT2RW = 2 + PRE2ACT = 2, REF2ACT = 6, WT_LAT = 3 + */ + MCF_SDRAMC_SDCFG1 = MCF_SDRAMC_SDCFG1_SRD2RW(0x4) | + MCF_SDRAMC_SDCFG1_SWT2RD(0x3) | + MCF_SDRAMC_SDCFG1_RDLAT(0x7) | + MCF_SDRAMC_SDCFG1_ACT2RW(0x2) | + MCF_SDRAMC_SDCFG1_PRE2ACT(0x2) | + MCF_SDRAMC_SDCFG1_REF2ACT(0x6) | MCF_SDRAMC_SDCFG1_WTLAT(0x3); + + /* Initialise SDCFG2 register with delay and timing values + BRD2RP = 5, BWT2RWP = 6, BRD2W = 6, BL = 7 + */ + MCF_SDRAMC_SDCFG2 = MCF_SDRAMC_SDCFG2_BRD2PRE(0x5) | + MCF_SDRAMC_SDCFG2_BWT2RW(0x6) | + MCF_SDRAMC_SDCFG2_BRD2WT(0x6) | MCF_SDRAMC_SDCFG2_BL(0x7); + + /* Issue a Precharge All command */ + MCF_SDRAMC_SDCR = MCF_SDRAMC_SDCR_MODE_EN | + MCF_SDRAMC_SDCR_CKE | + MCF_SDRAMC_SDCR_DDR | + MCF_SDRAMC_SDCR_MUX(0x1) | + MCF_SDRAMC_SDCR_RCNT(0x8) | MCF_SDRAMC_SDCR_PS_16 | MCF_SDRAMC_SDCR_IPALL; + + /* Write Extended Mode Register */ + MCF_SDRAMC_SDMR = MCF_SDRAMC_SDMR_BNKAD_LEMR | MCF_SDRAMC_SDMR_CMD; + + /* Write Mode Register and Reset DLL */ + MCF_SDRAMC_SDMR = MCF_SDRAMC_SDMR_BNKAD_LMR | + MCF_SDRAMC_SDMR_AD(0x163) | MCF_SDRAMC_SDMR_CMD; + + /* Insert code here to pause for DLL lock time specified by memory... */ + + /* Issue a second Precharge All command */ + MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_IPALL; + + /* Refresh sequence... + (check the number of refreshes required by the SDRAM manufacturer) + */ + MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_IREF; + MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_IREF; + + /* Write Mode Register and clear the Reset DLL bit */ + MCF_SDRAMC_SDMR = MCF_SDRAMC_SDMR_BNKAD_LMR | + MCF_SDRAMC_SDMR_AD(0x63) | MCF_SDRAMC_SDMR_CMD; + + /* Enable automatic refresh and lock SDMR */ + MCF_SDRAMC_SDCR &= ~MCF_SDRAMC_SDCR_MODE_EN; + MCF_SDRAMC_SDCR |= MCF_SDRAMC_SDCR_REF | + MCF_SDRAMC_SDCR_DQS_OE(0x8) | MCF_SDRAMC_SDCR_DQS_OE(0x4); + +} + +/********************************************************************* +* init_dma_timers - DMA Timers * +**********************************************************************/ +static void init_dma_timers(void) +{ + /* DMA Timer 0 disabled (DTMR0[RST] = 0) */ + MCF_DTIM0_DTMR = 0; + MCF_DTIM0_DTXMR = 0; + MCF_DTIM0_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); + + /* DMA Timer 1 disabled (DTMR1[RST] = 0) */ + MCF_DTIM1_DTMR = 0; + MCF_DTIM1_DTXMR = 0; + MCF_DTIM1_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); + + /* DMA Timer 2 disabled (DTMR2[RST] = 0) */ + MCF_DTIM2_DTMR = 0; + MCF_DTIM2_DTXMR = 0; + MCF_DTIM2_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); + + /* DMA Timer 3 disabled (DTMR3[RST] = 0) */ + MCF_DTIM3_DTMR = 0; + MCF_DTIM3_DTXMR = 0; + MCF_DTIM3_DTRR = MCF_DTIM_DTRR_REF(0xffffffff); +} + +/********************************************************************* +* init_interrupt_timers - Programmable Interrupt Timers (PIT) * +**********************************************************************/ +static void init_interrupt_timers(void) +{ + /* PIT0 disabled (PCSR0[EN]=0) */ + MCF_PIT0_PCSR = 0; + + /* PIT1 disabled (PCSR1[EN]=0) */ + MCF_PIT1_PCSR = 0; + + /* PIT2 disabled (PCSR2[EN]=0) */ + MCF_PIT2_PCSR = 0; + + /* PIT3 disabled (PCSR3[EN]=0) */ + MCF_PIT3_PCSR = 0; +} + +/********************************************************************* +* init_real_time_clock - Real-Time Clock (RTC) * +**********************************************************************/ +static void init_real_time_clock(void) +{ + /* Disable the RTC */ + MCF_RTC_CR = 0; +} + +/********************************************************************* +* init_watchdog_timers - Watchdog Timers * +**********************************************************************/ +static void init_watchdog_timers(void) +{ + /* Watchdog Timer disabled (WCR[EN]=0) + NOTE: WCR and WMR cannot be written again until after the + processor is reset. + */ + MCF_WTM_WCR = MCF_WTM_WCR_WAIT | MCF_WTM_WCR_DOZE | MCF_WTM_WCR_HALTED; + MCF_WTM_WMR = MCF_WTM_WMR_WM(0xffff); + + /* Core watchdog timer disabled */ + MCF_SCM_CWCR = MCF_SCM_CWCR_CWT(0x8); +} + +/********************************************************************* +* init_edma - eDMA Controller * +**********************************************************************/ +static void init_edma(void) +{ + /* Associate eDMA channels 9-12 with SSI signals */ + MCF_CCM_MISCCR &= ~MCF_CCM_MISCCR_TIM_DMA; + + /* Configured for round-robin arbitration mode */ + MCF_EDMA_CR = MCF_EDMA_CR_ERCA; + + /* All error interrupts are disabled */ + MCF_EDMA_EEI = 0; + + /* All DMA requests from peripherals are masked */ + MCF_EDMA_ERQ = 0; +} + +/********************************************************************* +* init_interrupt_controller - Interrupt Controller * +**********************************************************************/ +static void init_interrupt_controller(void) +{ + /* No interrupt sources configured */ + MCF_INTC1_ICR0 = 0; + MCF_INTC1_ICR1 = 0; + MCF_INTC1_ICR3 = 0; + MCF_INTC1_ICR4 = 0; + MCF_INTC1_ICR5 = 0; + MCF_INTC1_ICR6 = 0; + MCF_INTC1_ICR7 = 0; + MCF_INTC1_ICR8 = 0; + MCF_INTC1_ICR9 = 0; + MCF_INTC1_ICR10 = 0; + MCF_INTC1_ICR11 = 0; + MCF_INTC1_ICR12 = 0; + MCF_INTC1_ICR13 = 0; + MCF_INTC1_ICR14 = 0; + MCF_INTC1_ICR15 = 0; + MCF_INTC1_ICR16 = 0; + MCF_INTC1_ICR17 = 0; + MCF_INTC1_ICR18 = 0; + MCF_INTC1_ICR19 = 0; + MCF_INTC1_ICR40 = 0; + MCF_INTC1_ICR41 = 0; + MCF_INTC1_ICR42 = 0; + MCF_INTC1_ICR43 = 0; + MCF_INTC1_ICR44 = 0; + MCF_INTC1_ICR45 = 0; + MCF_INTC1_ICR46 = 0; + MCF_INTC1_ICR47 = 0; + MCF_INTC1_ICR48 = 0; + MCF_INTC1_ICR49 = 0; + MCF_INTC1_ICR50 = 0; + MCF_INTC1_ICR51 = 0; + MCF_INTC1_ICR52 = 0; + MCF_INTC1_ICR53 = 0; + MCF_INTC0_ICR1 = 0; + MCF_INTC0_ICR2 = 0; + MCF_INTC0_ICR3 = 0; + MCF_INTC0_ICR4 = 0; + MCF_INTC0_ICR5 = 0; + MCF_INTC0_ICR6 = 0; + MCF_INTC0_ICR7 = 0; + MCF_INTC0_ICR8 = 0; + MCF_INTC0_ICR9 = 0; + MCF_INTC0_ICR10 = 0; + MCF_INTC0_ICR11 = 0; + MCF_INTC0_ICR12 = 0; + MCF_INTC0_ICR13 = 0; + MCF_INTC0_ICR14 = 0; + MCF_INTC0_ICR15 = 0; + MCF_INTC0_ICR16 = 0; + MCF_INTC0_ICR17 = 0; + MCF_INTC0_ICR18 = 0; + MCF_INTC0_ICR19 = 0; + MCF_INTC0_ICR20 = 0; + MCF_INTC0_ICR21 = 0; + MCF_INTC0_ICR22 = 0; + MCF_INTC0_ICR23 = 0; + MCF_INTC0_ICR24 = 0; + MCF_INTC0_ICR25 = 0; + MCF_INTC0_ICR26 = 0; + MCF_INTC0_ICR27 = 0; + MCF_INTC0_ICR28 = 0; + MCF_INTC0_ICR30 = 0; + MCF_INTC0_ICR31 = 0; + MCF_INTC0_ICR32 = 0; + MCF_INTC0_ICR33 = 0; + MCF_INTC0_ICR34 = 0; + MCF_INTC0_ICR35 = 0; + MCF_INTC0_ICR36 = 0; + MCF_INTC0_ICR37 = 0; + MCF_INTC0_ICR38 = 0; + MCF_INTC0_ICR39 = 0; + MCF_INTC0_ICR40 = 0; + MCF_INTC0_ICR41 = 0; + MCF_INTC0_ICR42 = 0; + MCF_INTC0_ICR43 = 0; + MCF_INTC0_ICR44 = 0; + MCF_INTC0_ICR45 = 0; + MCF_INTC0_ICR46 = 0; + MCF_INTC0_ICR47 = 0; + MCF_INTC0_ICR48 = 0; + MCF_INTC0_ICR62 = 0; + MCF_INTC0_IMRH = 0xffffffff; + MCF_INTC0_IMRL = 0xffffffff; + MCF_INTC1_IMRH = 0xffffffff; + MCF_INTC1_IMRL = 0xffffffff; +} + +/********************************************************************* +* init_pin_assignments - Pin Assignment and General Purpose I/O * +**********************************************************************/ +static void init_pin_assignments(void) +{ + /* Pin assignments for port BUSCTL + Pin BUSCTL3 : External bus output enable, /OE + Pin BUSCTL2 : External bus transfer acknowledge, /TA + Pin BUSCTL1 : External bus read/write, R/W + Pin BUSCTL0 : External bus transfer start, /TS + */ + MCF_GPIO_PDDR_BUSCTL = 0; + MCF_GPIO_PAR_BUSCTL = MCF_GPIO_PAR_BUSCTL_PAR_OE | + MCF_GPIO_PAR_BUSCTL_PAR_TA | + MCF_GPIO_PAR_BUSCTL_PAR_RWB | MCF_GPIO_PAR_BUSCTL_PAR_TS(0x3); + + /* Pin assignments for port BE + Pin BE3 : External bus byte enable BW/BWE3 + Pin BE2 : External bus byte enable BW/BWE2 + Pin BE1 : External bus byte enable BW/BWE1 + Pin BE0 : External bus byte enable BW/BWE0 + */ + MCF_GPIO_PDDR_BE = 0; + MCF_GPIO_PAR_BE = MCF_GPIO_PAR_BE_PAR_BE3 | + MCF_GPIO_PAR_BE_PAR_BE2 | + MCF_GPIO_PAR_BE_PAR_BE1 | MCF_GPIO_PAR_BE_PAR_BE0; + + /* Pin assignments for port CS + Pin CS5 : Flex bus chip select /FB_CS5 + Pin CS4 : Flex bus chip select /FB_CS4 + Pin CS3 : Flex bus chip select /FB_CS3 + Pin CS2 : Flex bus chip select /FB_CS2 + Pin CS1 : Flex bus chip select /FB_CS1 + */ + MCF_GPIO_PDDR_CS = 0; + MCF_GPIO_PAR_CS = MCF_GPIO_PAR_CS_PAR_CS5 | + MCF_GPIO_PAR_CS_PAR_CS4 | + MCF_GPIO_PAR_CS_PAR_CS3 | + MCF_GPIO_PAR_CS_PAR_CS2 | MCF_GPIO_PAR_CS_PAR_CS1; + + /* Pin assignments for port FECI2C + Pin FECI2C3 : FEC management data clock, FEC_MDC + Pin FECI2C2 : FEC management data, FEC_MDIO + Pin FECI2C1 : GPIO input + Pin FECI2C0 : GPIO input + */ + MCF_GPIO_PDDR_FECI2C = 0; + MCF_GPIO_PAR_FECI2C = MCF_GPIO_PAR_FECI2C_PAR_MDC(0x3) | + MCF_GPIO_PAR_FECI2C_PAR_MDIO(0x3); + + /* Pin assignments for ports FECH and FECL + Pin FECH7 : FEC transmit clock, FEC_TXCLK + Pin FECH6 : FEC transmit enable, FEC_TXEN + Pin FECH5 : FEC transmit data 0, FEC_TXD0 + Pin FECH4 : FEC collision, FEC_COL + Pin FECH3 : FEC receive clock, FEC_RXCLK + Pin FECH2 : FEC receive data valid, FEC_RXDV + Pin FECH1 : FEC receive data 0, FEC_RXD0 + Pin FECH0 : FEC carrier receive sense, FEC_CRS + Pin FECL7 : FEC transmit data 3, FEC_TXD3 + Pin FECL6 : FEC transmit data 2, FEC_TXD2 + Pin FECL5 : FEC transmit data 1, FEC_TXD1 + Pin FECL4 : FEC transmit error, FEC_TXER + Pin FECL3 : FEC receive data 3, FEX_RXD3 + Pin FECL2 : FEC receive data 2, FEX_RXD2 + Pin FECL1 : FEC receive data 1, FEX_RXD1 + Pin FECL0 : FEC receive error, FEC_RXER + */ + MCF_GPIO_PDDR_FECH = 0; + MCF_GPIO_PDDR_FECL = 0; + MCF_GPIO_PAR_FEC = MCF_GPIO_PAR_FEC_PAR_FEC_7W(0x3) | + MCF_GPIO_PAR_FEC_PAR_FEC_MII(0x3); + + /* Pin assignments for port IRQ + Pins are all used for EdgePort GPIO/IRQ + */ + MCF_GPIO_PAR_IRQ = 0; + + /* Pin assignments for port LCDDATAH + Pins are all GPIO inputs + */ + MCF_GPIO_PDDR_LCDDATAH = 0; + MCF_GPIO_PAR_LCDDATA = 0; + + /* Pin assignments for port LCDDATAM + Port LCDDATAM pins are all GPIO inputs + */ + MCF_GPIO_PDDR_LCDDATAM = 0; + + /* Pin assignments for port LCDDATAL + Port LCDDATAL pins are all GPIO inputs + */ + MCF_GPIO_PDDR_LCDDATAL = 0; + + /* Pin assignments for port LCDCTLH + Pins are all GPIO inputs + */ + MCF_GPIO_PDDR_LCDCTLH = 0; + MCF_GPIO_PAR_LCDCTL = 0; + + /* Pin assignments for port LCDCTLL + Pins are all GPIO inputs + */ + MCF_GPIO_PDDR_LCDCTLL = 0; + + /* Pin assignments for port PWM + Pins are all GPIO inputs + */ + MCF_GPIO_PDDR_PWM = 0; + MCF_GPIO_PAR_PWM = 0; + + /* Pin assignments for port QSPI + Pins are all GPIO inputs + */ + MCF_GPIO_PDDR_QSPI = 0; + MCF_GPIO_PAR_QSPI = 0; + + /* Pin assignments for port SSI + Pins are all GPIO inputs + */ + MCF_GPIO_PDDR_SSI = 0; + MCF_GPIO_PAR_SSI = 0; + + /* Pin assignments for port TIMER + Pins are all GPIO outputs + */ + MCF_GPIO_PDDR_TIMER = MCF_GPIO_PDDR_TIMER_PDDR_TIMER3 | + MCF_GPIO_PDDR_TIMER_PDDR_TIMER2 | + MCF_GPIO_PDDR_TIMER_PDDR_TIMER1 | MCF_GPIO_PDDR_TIMER_PDDR_TIMER0; + MCF_GPIO_PAR_TIMER = 0; + + /* Pin assignments for port UART + Pin UART7 : UART 1 clear-to-send, /U1CTS + Pin UART6 : UART 1 request-to-send, /U1RTS + Pin UART5 : UART 1 transmit data, U1TXD + Pin UART4 : UART 1 receive data, U1RXD + Pin UART3 : UART 0 clear-to-send, /U0CTS + Pin UART2 : UART 0 request-to-send, /U0RTS + Pin UART1 : UART 0 transmit data, U0TXD + Pin UART0 : UART 0 receive data, U0RXD + */ + MCF_GPIO_PDDR_UART = 0; + MCF_GPIO_PAR_UART = MCF_GPIO_PAR_UART_PAR_UCTS1(0x3) | + MCF_GPIO_PAR_UART_PAR_URTS1(0x3) | + MCF_GPIO_PAR_UART_PAR_URXD1(0x3) | + MCF_GPIO_PAR_UART_PAR_UTXD1(0x3) | + MCF_GPIO_PAR_UART_PAR_UCTS0 | + MCF_GPIO_PAR_UART_PAR_URTS0 | + MCF_GPIO_PAR_UART_PAR_URXD0 | MCF_GPIO_PAR_UART_PAR_UTXD0; +} diff --git a/bsps/m68k/mcf5329/start/init5329.c b/bsps/m68k/mcf5329/start/init5329.c new file mode 100644 index 0000000000..8719514736 --- /dev/null +++ b/bsps/m68k/mcf5329/start/init5329.c @@ -0,0 +1,79 @@ +/* + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +extern void _wr_vbr(uint32_t); +extern void init_main(void); + +/* + * From linkcmds + */ + +extern uint8_t _INTERRUPT_VECTOR[]; + +extern uint8_t _clear_start[]; +extern uint8_t _clear_end[]; + +extern uint8_t _data_src_start[]; +extern uint8_t _data_dest_start[]; +extern uint8_t _data_dest_end[]; + +void Init5329(void) +{ + register uint32_t i; + register uint8_t *dbp, *sbp; + register uint32_t *dp, *sp; + + /* + * Initialize the hardware + */ + init_main(); + + /* + * Copy the vector table to RAM + */ + if (&_VBR != (void *) _INTERRUPT_VECTOR) { + sp = (uint32_t *) _INTERRUPT_VECTOR; + dp = (uint32_t *) &_VBR; + for (i = 0; i < 256; i++) { + *dp++ = *sp++; + } + } + + _wr_vbr((uint32_t) &_VBR); + + /* + * Move initialized data from ROM to RAM. + */ + if (_data_src_start != _data_dest_start) { + dbp = (uint8_t *) _data_dest_start; + sbp = (uint8_t *) _data_src_start; + i = _data_dest_end - _data_dest_start; + while (i--) + *dbp++ = *sbp++; + } + + /* + * Zero uninitialized data + */ + + if (_clear_start != _clear_end) { + sbp = _clear_start; + dbp = _clear_end; + i = dbp - sbp; + while (i--) + *sbp++ = 0; + } + + /* + * We have to call some kind of RTEMS function here! + */ + + boot_card(0); + for (;;) ; +} diff --git a/bsps/m68k/mcf5329/start/linkcmds b/bsps/m68k/mcf5329/start/linkcmds new file mode 100644 index 0000000000..1982a91f7b --- /dev/null +++ b/bsps/m68k/mcf5329/start/linkcmds @@ -0,0 +1,206 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Freescale ColdFire mcf52235 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE.e + */ + +/* + * Declare some sizes. + */ +_CoreSRamBase = DEFINED(RamBase) ? RamBase : 0x80000000; +_CoreSRamSize = DEFINED(RamSize) ? RamSize : 32K; + +RamBase = DEFINED(RamBase) ? RamBase : 0x40000000; +RamSize = DEFINED(RamSize) ? RamSize : 32M; + +_BootFlashBase = DEFINED(_FlashBase) ? _FlashBase : 0x00000000; +_BootFlashSize = DEFINED(_FlashBase) ? _FlashBase : 2M; + +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x400; + +_VBR = 0x40000000; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + core_sram : ORIGIN = 0x80000000, LENGTH = 32K + boot_flash : ORIGIN = 0x00000000, LENGTH = 2M + dram : ORIGIN = 0x40000000, LENGTH = 32M +} + +SECTIONS +{ + .ram_code : + { + *(.ram_code) + } > core_sram + + /* + * Text, data and bss segments + */ + .text 0x40000500 : { + + *(.text*) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } > dram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } > dram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } > dram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : + { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } > dram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : + { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (_end = .); + + _clear_end = .; + WorkAreaBase = .; + } > dram + + .start_stack : + { + /* + * Starting Stack + */ + . += _StackSize; + . = ALIGN (16); + PROVIDE(_StackInit = .); + } > core_sram + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + + PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/mcf5329/start/linkcmdsflash b/bsps/m68k/mcf5329/start/linkcmdsflash new file mode 100644 index 0000000000..af0cc4ee01 --- /dev/null +++ b/bsps/m68k/mcf5329/start/linkcmdsflash @@ -0,0 +1,202 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Freescale ColdFire mcf52235 + * + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE.e + */ + +/* + * Declare some sizes. + */ +_CoreSRamBase = DEFINED(RamBase) ? RamBase : 0x80000000; +_CoreSRamSize = DEFINED(RamSize) ? RamSize : 32K; + +RamBase = DEFINED(RamBase) ? RamBase : 0x40000000; +RamSize = DEFINED(RamSize) ? RamSize : 32M; + +_BootFlashBase = DEFINED(_FlashBase) ? _FlashBase : 0x00000000; +_BootFlashSize = DEFINED(_FlashBase) ? _FlashBase : 2M; + +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x400; + +_VBR = 0x40000000; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + core_sram : ORIGIN = 0x80000000, LENGTH = 32K + boot_flash : ORIGIN = 0x00000000, LENGTH = 2M + dram : ORIGIN = 0x40000000, LENGTH = 32M +} + +SECTIONS +{ + /* + * Text, data and bss segments + */ + .text : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + } > boot_flash + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } > boot_flash + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } > boot_flash + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data 0x40000500 : AT (_estuff) + { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } > dram + + _data_src_start = _estuff; + _data_src_end = _data_dest_start + SIZEOF(.data); + + .bss : + { + _clear_start = .; + *(.bss*) + *(COMMON) + . = ALIGN (16); + PROVIDE (_end = .); + + _clear_end = .; + WorkAreaBase = .; + } > dram + + .start_stack : + { + /* + * Starting Stack + */ + . += _StackSize; + . = ALIGN (16); + PROVIDE(_StackInit = .); + } > core_sram + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + + PROVIDE (end_of_all = .); +} diff --git a/bsps/m68k/mrm332/start/bsp_specs b/bsps/m68k/mrm332/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/mrm332/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/mrm332/start/linkcmds b/bsps/m68k/mrm332/start/linkcmds new file mode 100644 index 0000000000..1ee7117d6b --- /dev/null +++ b/bsps/m68k/mrm332/start/linkcmds @@ -0,0 +1,212 @@ +/* linkcmds + */ + +OUTPUT_ARCH(m68k) +ENTRY(start) +STARTUP(start.o) +__DYNAMIC = 0; + +/* + * ROM: + * +--------------------+ <- low memory + * | .text | + * | etext | + * | ctor list | the ctor and dtor lists are for + * | dtor list | C++ support + * | _endtext | + * | temporary .data | .data is moved to RAM by crt0 + * | | + * +--------------------+ <- high memory + * + * + * RAM: + * +--------------------+ <- low memory + * | .data | initialized data goes here + * | _sdata | + * | _edata | + * +--------------------+ + * | .bss | + * | __bss_start | start of bss, cleared by crt0 + * | _end | start of heap, used by sbrk() + * +--------------------+ + * | heap space | + * | _ENDHEAP | + * | stack space | + * | __stack | top of stack + * +--------------------+ <- high memory + */ + +/* + * Declare some sizes. + */ +RomBase = DEFINED(RomBase) ? RomBase : 0x90000; +RamBase = DEFINED(RamBase) ? RamBase : 0x03000; +RamSize = DEFINED(RamSize) ? RamSize : 0x7d000; +_RamEnd = RamBase + RamSize; + +MEMORY +{ + rom : ORIGIN = 0x90000, LENGTH = 0x70000 + ram : ORIGIN = 0x03000, LENGTH = 0x7d000 +} + +_copy_data_from_rom = 1; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0x0; +_StackSize = DEFINED(_StackSize) ? _StackSize : 0x2000; + + +/* + * + */ +SECTIONS +{ + .text : + { + . = .; + text_start = .; + _text_start = .; + *(.text*) + . = ALIGN (16); + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + PROVIDE (_etext = .); + _endtext = .; + __data_start_rom = .; + } > rom + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } > rom + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } > rom + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + .gcc_exc : + AT ( ADDR(.tdata) + SIZEOF( .tdata ) ) + { + *(.gcc_exc) + } > ram + .data : AT(__data_start_rom) + { + PROVIDE (_copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + } > ram + .shbss : + { + *(.shbss) + } > ram + .bss : + { + M68Kvec = .; + . += (256 * 4); + _clear_start = .; + *(.dynbss) + *(.bss* .gnu.linkonce.b.*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + . += _StackSize; + . = ALIGN (16); + _stack_init = .; + _clear_end = .; + + WorkAreaBase = .; + } > ram + .stab . (NOLOAD) : + { + [ .stab ] + } + .stabstr . (NOLOAD) : + { + [ .stabstr ] + } +} diff --git a/bsps/m68k/mrm332/start/start_c.c b/bsps/m68k/mrm332/start/start_c.c new file mode 100644 index 0000000000..060c96b004 --- /dev/null +++ b/bsps/m68k/mrm332/start/start_c.c @@ -0,0 +1,130 @@ +/** + * @file + * + * MRM332 C Start Up Code + */ + +/* + * COPYRIGHT (c) 2000. + * Matt Cross <profesor@gweep.net> + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + * + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <mrm332.h> +#include <rtems/m68k/sim.h> +#define __START_C__ + +/* + * This prototype really should have the noreturn attribute but + * that causes a warning. Not sure how to fix that. + */ +/* void dumby_start () __attribute__ ((noreturn)); */ +void start_c(void); + +void start_c(void) { + +#ifdef SET_EDIV +#define OPTIONAL_EDIV EDIV +#else +#define OPTIONAL_EDIV 0 +#endif + + /* Synthesizer Control Register */ + /* see section(s) 4.8 */ + /* end include in ram_init.S */ + *SYNCR = (unsigned short int) (SAM(MRM_W, 15, VCO) | SAM(0x0, 14, PRESCALE) + | SAM(MRM_Y, 8, COUNTER) | OPTIONAL_EDIV); + while (!(*SYNCR & SLOCK)) + ; /* protect from clock overshoot */ + /* include in ram_init.S */ + *SYNCR = (unsigned short int) (SAM(MRM_W, 15, VCO) | SAM(MRM_X, 14, + PRESCALE) | SAM(MRM_Y, 8, COUNTER) | OPTIONAL_EDIV); + + /* System Protection Control Register */ + /* !!! can only write to once after reset !!! */ + /* see section 3.8.4 of the SIM Reference Manual */ + *SYPCR = (unsigned char) (HME | BME); + + /* Periodic Interrupr Control Register */ + /* see section 3.8.2 of the SIM Reference Manual */ + *PICR = (unsigned short int) (SAM(0, 8, PIRQL) | SAM(MRM_PIV, 0, PIV)); + /* ^^^ zero disables interrupt, don't enable here or ram_init will + be wrong. It's enabled below. */ + + /* Periodic Interrupt Timer Register */ + /* see section 3.8.3 of the SIM Reference Manual */ + *PITR = (unsigned short int) (SAM(0x09, 0, PITM)); + /* 1.098mS interrupt, assuming 32.768 KHz input clock */ + + /* Port C Data */ + /* load values before enabled */ + *PORTC = (unsigned char) 0x0; + + /* Port E and F Data Register */ + /* see section 9 of the SIM Reference Manual */ + *PORTE0 = (unsigned char) 0; + *PORTF0 = (unsigned char) 0; + + /* Port E and F Data Direction Register */ + /* see section 9 of the SIM Reference Manual */ + *DDRE = (unsigned char) 0xff; + *DDRF = (unsigned char) 0xfd; + + /* Port E and F Pin Assignment Register. Set up Port E and F as I/O */ + /* see section 9 of the SIM Reference Manual */ + *PEPAR = (unsigned char) 0; + *PFPAR = (unsigned char) 0; + + /* end of SIM initalization code */ + /* end include in ram_init.S */ + + /* + * Initialize RAM by copying the .data section out of ROM (if + * needed) and "zero-ing" the .bss section. + */ + { + register char *src = _etext; + register char *dst = _copy_start; + + if (_copy_data_from_rom) { + /* ROM has data at end of text; copy it. */ + while (dst < _edata) + *dst++ = *src++; + } + /* Zero bss */ + for (dst = _clear_start; dst < end; dst++) { + *dst = 0; + } + } + + /* + * Initialize vector table. + */ + { + rtems_isr_entry *monitors_vector_table; + + m68k_get_vbr(monitors_vector_table); + + M68Kvec[4] = monitors_vector_table[4]; /* breakpoints vector */ + M68Kvec[9] = monitors_vector_table[9]; /* trace vector */ + M68Kvec[31] = monitors_vector_table[31]; /* level 7 interrupt */ + M68Kvec[47] = monitors_vector_table[47]; /* system call vector */ + M68Kvec[66] = monitors_vector_table[66]; /* user defined */ + + m68k_set_vbr(&M68Kvec); + } + + + /* + * Execute main with arguments argc and agrv. + */ + boot_card((void*)0); + reboot(); + +} diff --git a/bsps/m68k/mvme147/start/bsp_specs b/bsps/m68k/mvme147/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/mvme147/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/mvme147/start/bspclean.c b/bsps/m68k/mvme147/start/bspclean.c new file mode 100644 index 0000000000..6606b9a249 --- /dev/null +++ b/bsps/m68k/mvme147/start/bspclean.c @@ -0,0 +1,49 @@ +/* + * This routine returns control to 147Bug. + */ + +/* + * COPYRIGHT (c) 1989-2014. + * 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.org/license/LICENSE. + * + * MVME147 port for TNI - Telecom Bretagne + * by Dominique LE CAMPION (Dominique.LECAMPION@enst-bretagne.fr) + * May 1996 + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +extern void start(void); + +static rtems_isr bsp_return_to_monitor_trap( + rtems_vector_number vector +) +{ + register volatile void *start_addr; + + m68k_set_vbr( 0 ); /* restore 147Bug vectors */ + __asm__ volatile( "trap #15" ); /* trap to 147Bug */ + __asm__ volatile( ".short 0x63" ); /* return to 147Bug (.RETURN) */ + /* restart program */ + start_addr = start; + + __asm__ volatile ( "jmp %0@" : "=a" (start_addr) : "0" (start_addr) ); +} + +void bsp_fatal_extension( + rtems_fatal_source source, + bool always_set_to_false, + rtems_fatal_code error +) +{ + pcc->timer1_int_control = 0; /* Disable Timer 1 */ + pcc->timer2_int_control = 0; /* Disable Timer 2 */ + + M68Kvec[ 45 ] = bsp_return_to_monitor_trap; /* install handler */ + __asm__ volatile( "trap #13" ); /* ensures SUPV mode */ +} diff --git a/bsps/m68k/mvme147/start/bspstart.c b/bsps/m68k/mvme147/start/bspstart.c new file mode 100644 index 0000000000..cb5f84a075 --- /dev/null +++ b/bsps/m68k/mvme147/start/bspstart.c @@ -0,0 +1,45 @@ +/* + * This routine does the bulk of the system initialization. + */ + +/* + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + * + * MVME147 port for TNI - Telecom Bretagne + * by Dominique LE CAMPION (Dominique.LECAMPION@enst-bretagne.fr) + * May 1996 + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +void bsp_start( void ) +{ + rtems_isr_entry *monitors_vector_table; + int index; + + monitors_vector_table = (rtems_isr_entry *)0; /* 135Bug Vectors are at 0 */ + m68k_set_vbr( monitors_vector_table ); + + for ( index=2 ; index<=255 ; index++ ) + M68Kvec[ index ] = monitors_vector_table[ 32 ]; + + M68Kvec[ 2 ] = monitors_vector_table[ 2 ]; /* bus error vector */ + M68Kvec[ 4 ] = monitors_vector_table[ 4 ]; /* breakpoints vector */ + M68Kvec[ 9 ] = monitors_vector_table[ 9 ]; /* trace vector */ + M68Kvec[ 47 ] = monitors_vector_table[ 47 ]; /* system call vector */ + + m68k_set_vbr( &M68Kvec ); + + pcc->int_base_vector = PCC_BASE_VECTOR; /* Set the PCC int vectors base */ + + (*(uint8_t*)0xfffe2001) = 0x08; /* make VME access round-robin */ + + rtems_cache_enable_instruction(); + rtems_cache_enable_data(); +} diff --git a/bsps/m68k/mvme147/start/linkcmds b/bsps/m68k/mvme147/start/linkcmds new file mode 100644 index 0000000000..6603a438f1 --- /dev/null +++ b/bsps/m68k/mvme147/start/linkcmds @@ -0,0 +1,30 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Motorola MVME147 boards. + */ + +/* + * COPYRIGHT (c) 1989-2007,2016. + * 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.org/license/LICENSE. + * + * MVME147 port for TNI - Telecom Bretagne + * by Dominique LE CAMPION (Dominique.LECAMPION@enst-bretagne.fr) + * May 1996 + */ + +MEMORY +{ + bootrom_reserved : ORIGIN = 0x00000000, LENGTH = 0x5000 + ram : ORIGIN = 0x00005000, LENGTH = 4M - 0x5000 +} + +REGION_ALIAS ("REGION_TEXT", ram); +REGION_ALIAS ("REGION_TEXT_LOAD", ram); +REGION_ALIAS ("REGION_DATA", ram); +REGION_ALIAS ("REGION_DATA_LOAD", ram); + +INCLUDE linkcmds.base diff --git a/bsps/m68k/mvme147s/start/bsp_specs b/bsps/m68k/mvme147s/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/mvme147s/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/mvme147s/start/bspstart.c b/bsps/m68k/mvme147s/start/bspstart.c new file mode 100644 index 0000000000..497b644150 --- /dev/null +++ b/bsps/m68k/mvme147s/start/bspstart.c @@ -0,0 +1,108 @@ +/* + * This routine does the bulk of the system initialization. + */ + +/* + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + * + * MVME147 port for TNI - Telecom Bretagne + * by Dominique LE CAMPION (Dominique.LECAMPION@enst-bretagne.fr) + * May 1996 + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +void bsp_start( void ) +{ + rtems_isr_entry *monitors_vector_table; + int index; + uint8_t node_number; + + monitors_vector_table = (rtems_isr_entry *)0; /* 147Bug Vectors are at 0 */ + m68k_set_vbr( monitors_vector_table ); + + for ( index=2 ; index<=255 ; index++ ) + M68Kvec[ index ] = monitors_vector_table[ 32 ]; + + M68Kvec[ 2 ] = monitors_vector_table[ 2 ]; /* bus error vector */ + M68Kvec[ 4 ] = monitors_vector_table[ 4 ]; /* breakpoints vector */ + M68Kvec[ 9 ] = monitors_vector_table[ 9 ]; /* trace vector */ + M68Kvec[ 47 ] = monitors_vector_table[ 47 ]; /* system call vector */ + + m68k_set_vbr( &M68Kvec ); + + pcc->int_base_vector = PCC_BASE_VECTOR & 0xF0; + /* Set the PCC int vectors base */ + + /* VME shared memory configuration */ + /* Only the first node shares its top 128k DRAM */ + + vme_lcsr->utility_interrupt_vector = VME_BASE_VECTOR & 0xF8; + /* Set VMEchip base interrupt vector */ + vme_lcsr->utility_interrupt_mask |= 0x02; + /* Enable SIGLP interruption (see shm support) */ + pcc->general_purpose_control &= 0x10; + /* Enable VME master interruptions */ + + if (vme_lcsr->system_controller & 0x01) { + /* the board is system controller */ + vme_lcsr->system_controller = 0x08; + /* Make VME access round-robin */ + } + +#if defined(RTEMS_MULTIPROCESSING) + node_number = (uint8_t) + (rtems_configuration_get_user_multiprocessing_table()->node - 1) & 0xF; +#else + node_number = 1; +#endif + /* Get and store node ID, first node_number = 0 */ + vme_gcsr->board_identification = node_number; + + vme_lcsr->gcsr_base_address = node_number; + /* Setup the base address of this board's gcsr */ + vme_lcsr->timer_configuration = 0x6a; + /* Enable VME time outs, maximum periods */ + + if (node_number == 0) { + pcc->slave_base_address = 0x01; + /* Set local DRAM base address on the VME bus to the DRAM size */ + + vme_lcsr->vme_bus_requester = 0x80; + while (! (vme_lcsr->vme_bus_requester & 0x40)); + /* Get VMEbus mastership */ + vme_lcsr->slave_address_modifier = 0xfb; + /* Share everything */ + vme_lcsr->slave_configuration = 0x80; + /* Share local DRAM */ + vme_lcsr->vme_bus_requester = 0x0; + /* release bus */ + } else { + pcc->slave_base_address = 0; + /* Set local DRAM base address on the VME bus to 0 */ + + vme_lcsr->vme_bus_requester = 0x80; + while (! (vme_lcsr->vme_bus_requester & 0x40)); + /* Get VMEbus mastership */ + vme_lcsr->slave_address_modifier = 0x08; + /* Share only the short adress range */ + vme_lcsr->slave_configuration = 0; + /* Don't share local DRAM */ + vme_lcsr->vme_bus_requester = 0x0; + /* release bus */ + } + + vme_lcsr->master_address_modifier = 0; + /* Automatically set the address modifier */ + vme_lcsr->master_configuration = 1; + /* Disable D32 transfers : they don't work on my VMEbus rack */ + + rtems_cache_enable_instruction(); + rtems_cache_enable_data(); +} diff --git a/bsps/m68k/mvme147s/start/linkcmds b/bsps/m68k/mvme147s/start/linkcmds new file mode 100644 index 0000000000..01be6d93b2 --- /dev/null +++ b/bsps/m68k/mvme147s/start/linkcmds @@ -0,0 +1,30 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Motorola MVME147s boards. + */ + +/* + * COPYRIGHT (c) 1989-2007,2016. + * 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.org/license/LICENSE. + * + * MVME147 port for TNI - Telecom Bretagne + * by Dominique LE CAMPION (Dominique.LECAMPION@enst-bretagne.fr) + * May 1996 + */ + +MEMORY +{ + bootrom_reserved : ORIGIN = 0x00000000, LENGTH = 0x7000 + ram : ORIGIN = 0x00007000, LENGTH = 4M - 0x7000 +} + +REGION_ALIAS ("REGION_TEXT", ram); +REGION_ALIAS ("REGION_TEXT_LOAD", ram); +REGION_ALIAS ("REGION_DATA", ram); +REGION_ALIAS ("REGION_DATA_LOAD", ram); + +INCLUDE linkcmds.base diff --git a/bsps/m68k/mvme162/start/bsp_specs b/bsps/m68k/mvme162/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/mvme162/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/mvme162/start/bspclean.c b/bsps/m68k/mvme162/start/bspclean.c new file mode 100644 index 0000000000..dd91f96b1a --- /dev/null +++ b/bsps/m68k/mvme162/start/bspclean.c @@ -0,0 +1,47 @@ +/* + * This routine returns control to 162Bug. + */ + +/* + * COPYRIGHT (c) 1989-2014. + * 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.org/license/LICENSE. + * + * Modifications of respective RTEMS file: COPYRIGHT (c) 1994. + * EISCAT Scientific Association. M.Savitski + * + * This material is a part of the MVME162 Board Support Package + * for the RTEMS executive. Its licensing policies are those of the + * RTEMS above. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <rtems/zilog/z8036.h> +#include <page_table.h> + +static rtems_isr bsp_return_to_monitor_trap( + rtems_vector_number vector +) +{ + page_table_teardown(); + + lcsr->intr_ena = 0; /* disable interrupts */ + m68k_set_vbr(MOT_162BUG_VEC_ADDRESS); /* restore 162Bug vectors */ + + __asm__ volatile( "trap #15" ); /* trap to 162Bug */ + __asm__ volatile( ".short 0x63" ); /* return to 162Bug (.RETURN) */ +} + +void bsp_fatal_extension( + rtems_fatal_source source, + bool always_set_to_false, + rtems_fatal_code error +) +{ + M68Kvec[ 45 ] = bsp_return_to_monitor_trap; /* install handler */ + __asm__ volatile( "trap #13" ); /* ensures SUPV mode */ +} diff --git a/bsps/m68k/mvme162/start/bspstart.c b/bsps/m68k/mvme162/start/bspstart.c new file mode 100644 index 0000000000..29e56e35ea --- /dev/null +++ b/bsps/m68k/mvme162/start/bspstart.c @@ -0,0 +1,58 @@ +/* + * This routine does the bulk of the system initialization. + */ + +/* + * COPYRIGHT (c) 1989-1999. + * 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.org/license/LICENSE. + * + * Modifications of respective RTEMS file: COPYRIGHT (c) 1994. + * EISCAT Scientific Association. M.Savitski + * + * This material is a part of the MVME162 Board Support Package + * for the RTEMS executive. Its licensing policies are those of the + * RTEMS above. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <page_table.h> + +/* + * bsp_start + * + * This routine does the bulk of the system initialization. + */ +void bsp_start( void ) +{ + rtems_isr_entry *monitors_vector_table; + int index; + + monitors_vector_table = (rtems_isr_entry *)MOT_162BUG_VEC_ADDRESS; + m68k_set_vbr( monitors_vector_table ); + + for ( index=2 ; index<=255 ; index++ ) + M68Kvec[ index ] = monitors_vector_table[ 32 ]; + + M68Kvec[ 2 ] = monitors_vector_table[ 2 ]; /* bus error vector */ + M68Kvec[ 4 ] = monitors_vector_table[ 4 ]; /* breakpoints vector */ + M68Kvec[ 9 ] = monitors_vector_table[ 9 ]; /* trace vector */ + M68Kvec[ 47 ] = monitors_vector_table[ 47 ]; /* system call vector */ + + m68k_set_vbr( &M68Kvec ); + + /* + * You may wish to make the VME arbitration round-robin here, currently + * we leave it as it is. + */ + + /* set the Interrupt Base Vectors */ + + lcsr->vector_base = (VBR0 << 28) | (VBR1 << 24); + + page_table_init(); +} diff --git a/bsps/m68k/mvme162/start/linkcmds b/bsps/m68k/mvme162/start/linkcmds new file mode 100644 index 0000000000..fd77dcf147 --- /dev/null +++ b/bsps/m68k/mvme162/start/linkcmds @@ -0,0 +1,32 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Motorola MVME162 boards. + */ + +/* + * COPYRIGHT (c) 1989-2007,2016. + * 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.org/license/LICENSE. + * + * MVME147 port for TNI - Telecom Bretagne + * by Dominique LE CAMPION (Dominique.LECAMPION@enst-bretagne.fr) + * May 1996 + */ + +RamSize = DEFINED(RamSize) ? RamSize : 1M; + +MEMORY +{ + bootrom_reserved : ORIGIN = 0x00000000, LENGTH = 0x20000 + ram : ORIGIN = 0x00020000, LENGTH = RamSize - 0x20000 +} + +REGION_ALIAS ("REGION_TEXT", ram); +REGION_ALIAS ("REGION_TEXT_LOAD", ram); +REGION_ALIAS ("REGION_DATA", ram); +REGION_ALIAS ("REGION_DATA_LOAD", ram); + +INCLUDE linkcmds.base diff --git a/bsps/m68k/mvme162/start/page_table.c b/bsps/m68k/mvme162/start/page_table.c new file mode 100644 index 0000000000..3dbd05a56f --- /dev/null +++ b/bsps/m68k/mvme162/start/page_table.c @@ -0,0 +1,196 @@ +/* + * This file was submitted by Eric Vaitl <vaitl@viasat.com>. + * The manipulation of the page table has a very positive impact on + * the performance of the MVME162. + * + * The following history is included verbatim from the submitter. + * + * Revision 1.8 1995/11/18 00:07:25 vaitl + * Modified asm-statements to get rid of the register hard-codes. + * + * Revision 1.7 1995/10/27 21:00:32 vaitl + * Modified page table routines so application code can map + * VME space. + * + * Revision 1.6 1995/10/26 17:40:01 vaitl + * Two cache changes after reading the mvme162 users manual. + * + * 1) The users manual says that the MPU can act as a source for the + * VME2 chip, so I made the VME accessable memory copy-back instead + * of write through. I have't changed the comments yet. If this + * causes problems, I'll change it back. + * + * 2) The 162 book also says that IO space should be serialized as well as + * non-cacheable. I flipped the appropriate dttr0 and ittr0 registers. I + * don't think this is really necessary because we don't recover from any + * exceptions. If it slows down IO addresses too much, I'll change it back + * and see what happens. + * + * Revision 1.5 1995/10/25 19:32:38 vaitl + * Got it. Three problems: + * 1) Must cpusha instead of cinva. + * 2) On page descriptors the PDT field of 1 or 3 is resident. On pointer + * descriptors resident is 2 or 3. I was using 2 for everything. + * Changed it to 3 for everything. + * 3) Forgot to do a pflusha. + * + * Revision 1.4 1995/10/25 17:47:11 vaitl + * Still working on it. + * + * Revision 1.3 1995/10/25 17:16:05 vaitl + * Working on page table. Caching partially set up, but can't currently + * set tc register. + * + */ + +#include <string.h> +#include <page_table.h> + +/* All page table must fit between BASE_TABLE_ADDR and + MAX_TABLE_ADDR. */ + +#define BASE_TABLE_ADDR 0x10000 +#define MAX_TABLE_ADDR 0x20000 +#define ROOT_TABLE_SIZE 512 +#define POINTER_TABLE_SIZE 512 +#define PAGE_TABLE_SIZE 256 + +static unsigned long *root_table; +static unsigned long *next_avail; + +/* Returns a zeroed out table. */ +static unsigned long *table_alloc(int size){ + unsigned long *addr=next_avail; + if(((unsigned long)next_avail + size) > MAX_TABLE_ADDR){ + return 0; + } + memset((void *)addr,0, size); + next_avail =(unsigned long *)((unsigned long)next_avail + size); + return addr; +} + +/* + void page_table_init(); + + This should transparently map the first 4 Meg of ram. Caching is + turned off from 0x00000000 to 0x00020000 (this region is used by + 162Bug and contains the page tables). From 0x00020000 to 0x00400000 + we are using copy back caching. DTTR0 and ITTR0 are set up to + directly translate from 0x80000000-0xffffffff with caching turned + off and serialized. Addresses between 0x400000 and 0x80000000 are + illegal. +*/ +void page_table_init(){ + + /* put everything in a known state */ + page_table_teardown(); + + root_table=table_alloc(ROOT_TABLE_SIZE); + + /* First set up TTR. + base address = 0x80000000 + address mask = 0x7f + Ignore FC2 for match. + Noncachable. + Not write protected.*/ + __asm__ volatile ("movec %0,%%dtt0\n\ + movec %0,%%itt0" + :: "d" (0x807fc040)); + + /* Point urp and srp at root page table. */ + __asm__ volatile ("movec %0,%%urp\n\ + movec %0,%%srp" + :: "d" (BASE_TABLE_ADDR)); + + page_table_map((void *)0,0x20000, CACHE_NONE); + page_table_map((void *)0x20000,0x400000-0x20000,CACHE_COPYBACK); + + /* Turn on paging with a 4 k page size.*/ + __asm__ volatile ("movec %0,%%tc" + :: "d" (0x8000)); + + /* Turn on the cache. */ + __asm__ volatile ("movec %0,%%cacr" + :: "d" (0x80008000)); +} + +void page_table_teardown(){ + next_avail=(unsigned long *)BASE_TABLE_ADDR; + /* Turn off paging. Turn off the cache. Flush the cache. Tear down + the transparent translations. */ + __asm__ volatile ("movec %0,%%tc\n\ + movec %0,%%cacr\n\ + cpusha %%bc\n\ + movec %0,%%dtt0\n\ + movec %0,%%itt0\n\ + movec %0,%%dtt1\n\ + movec %0,%%itt1" + :: "d" (0) ); +} + +/* Identity maps addr to addr+size with caching cache_type. */ +int page_table_map(void *addr, unsigned long size, int cache_type){ + unsigned long *pointer_table; + unsigned long *page_table; + unsigned long root_index, pointer_index, page_index; + /* addr must be a multiple of 4k */ + if((unsigned long)addr & 0xfff){ + return PTM_BAD_ADDR; + } + /* size must also be a multiple of 4k */ + if(size & 0xfff){ + return PTM_BAD_SIZE; + } + /* check for valid cache type */ + if( (cache_type>CACHE_NONE) || (cache_type<CACHE_WRITE_THROUGH)){ + return PTM_BAD_CACHE; + } + + while(size){ + root_index=(unsigned long)addr; + root_index >>= 25; + root_index &= 0x7f; + + if(root_table[root_index]){ + pointer_table = + (unsigned long *) (root_table[root_index] & 0xfffffe00); + }else{ + if(!(pointer_table=table_alloc(POINTER_TABLE_SIZE))){ + return PTM_NO_TABLE_SPACE; + } + root_table[root_index]=((unsigned long)pointer_table) + 0x03; + } + + pointer_index=(unsigned long)addr; + pointer_index >>=18; + pointer_index &= 0x7f; + + if(pointer_table[pointer_index]){ + page_table = + (unsigned long *) (pointer_table[pointer_index] & + 0xffffff00); + }else{ + if(!(page_table=table_alloc(PAGE_TABLE_SIZE))){ + return PTM_NO_TABLE_SPACE; + } + pointer_table[pointer_index]= + ((unsigned long)page_table) + 0x03; + } + + page_index=(unsigned long)addr; + page_index >>=12; + page_index &= 0x3f; + + page_table[page_index] = + ((unsigned long) addr & 0xfffff000) + 0x03 + (cache_type << 5); + + size -= 4096; + addr = (void *) ((unsigned long)addr + 4096); + } + + /* Flush the ATC. Push and invalidate the cache. */ + __asm__ volatile ("pflusha\n\ + cpusha %bc"); + + return PTM_SUCCESS; +} diff --git a/bsps/m68k/mvme167/start/bsp_specs b/bsps/m68k/mvme167/start/bsp_specs new file mode 100644 index 0000000000..87638cc027 --- /dev/null +++ b/bsps/m68k/mvme167/start/bsp_specs @@ -0,0 +1,9 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} diff --git a/bsps/m68k/mvme167/start/bspclean.c b/bsps/m68k/mvme167/start/bspclean.c new file mode 100644 index 0000000000..2dd980fdb4 --- /dev/null +++ b/bsps/m68k/mvme167/start/bspclean.c @@ -0,0 +1,70 @@ +/** + * @file + * + * These routines return control to 167Bug after a normal exit from the + * application. + */ + +/* + * COPYRIGHT (c) 1989-2012. + * 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.org/license/LICENSE. + * + * Modifications of respective RTEMS files: + * Copyright (c) 1998, National Research Council of Canada + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <page_table.h> + +extern void start( void ); +extern void page_table_teardown( void ); + +/** + * @brief bsp_return_to_monitor_trap + * + * Switch the VBR back to ROM and make a .RETURN syscall to return control to + * 167 Bug. If 167Bug ever returns, restart the application. + */ +static void bsp_return_to_monitor_trap( void ) +{ + register volatile void *start_addr; + + page_table_teardown(); + + lcsr->intr_ena = 0; /* disable interrupts */ + m68k_set_vbr(0xFFE00000); /* restore 167Bug vectors */ + __asm__ volatile( "trap #15\n\t" /* trap to 167Bug */ + ".short 0x63" ); /* return to 167Bug (.RETURN) */ + + /* restart program */ + start_addr = start; + __asm__ volatile( "jmp %0@" : "=a" (start_addr) : "0" (start_addr) ); +} + +/* + * This code was copied from other MC680x0 MVME BSPs. + * Our guess is that someone was concerned about the CPU no longer being in + * supervisor mode when they got here. This function forces the CPU back to + * supervisor mode so the VBR may be changed. It places the address of the + * function that makes a 167Bug .RETURN syscall in the trap 13 entry in the + * exception vector, and then issues a trap 13 call. It is also possible that + * the code was copied from some other OS that does run tasks in user mode. + * In any case, it appears to be a bit of paranoia, and could lead to + * problems if 167Bug is invoked before we get to switch the VBR back to + * 167Bug because trap 13 is documented as being reserved for the internal + * use of the debugger. + */ +void bsp_fatal_extension( + rtems_fatal_source source, + bool always_set_to_false, + rtems_fatal_code error +) +{ + M68Kvec[ 45 ] = bsp_return_to_monitor_trap; + __asm__ volatile( "trap #13" ); +} diff --git a/bsps/m68k/mvme167/start/bspstart.c b/bsps/m68k/mvme167/start/bspstart.c new file mode 100644 index 0000000000..7ff6d2b118 --- /dev/null +++ b/bsps/m68k/mvme167/start/bspstart.c @@ -0,0 +1,80 @@ +/** + * @file + * + * Board-specific initialization code. Called from the generic boot_card() + * function defined in rtems/c/src/lib/libbsp/shared/main.c. That function + * does some of the board independent initialization. It is called from the + * generic MC680x0 entry point _start() defined in + * rtems/c/src/lib/start/m68k/start.s + * + * _start() has set up a stack, has zeroed the .bss section, has turned off + * interrupts, and placed the processor in the supervisor mode. boot_card() + * has left the processor in that state when bsp_start() was called. + * + * RUNS WITH ADDRESS TRANSLATION AND CACHING TURNED OFF! + * ASSUMES THAT THE VIRTUAL ADDRESSES WILL BE IDENTICAL TO THE PHYSICAL + * ADDRESSES. Software-controlled address translation would be required + * otherwise. + * + * ASSUMES THAT 167BUG IS PRESENT TO CATCH ANY EXCEPTIONS DURING + * INITIALIZATION. + */ + +/* + * COPYRIGHT (c) 1989-2012. + * 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.org/license/LICENSE. + * + * Modifications of respective RTEMS files: + * Copyright (c) 1998, National Research Council of Canada + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <page_table.h> + +void M68KFPSPInstallExceptionHandlers (void); + +void bsp_start( void ) +{ + void **rom_monitor_vector_table; + int index; + + /* + * 167Bug Vectors are at 0xFFE00000 + */ + rom_monitor_vector_table = (void **)0xFFE00000; + m68k_set_vbr( rom_monitor_vector_table ); + + /* + * Copy 167Bug Bus Error handler into our exception vector. All 167Bug + * exception vectors are the same and point to the generalized exception + * handler. The bus error handler is the one that Motorola says to copy + * (p. 2-13, Debugging Package for Motorola 68K CISC CPUs User's Manual + * 68KBUG/D1A3, October 1993). + */ + for ( index=2 ; index<=255 ; index++ ) + M68Kvec[ index ] = rom_monitor_vector_table[ 2 ]; + + /* Any exceptions during initialization should be trapped by 167Bug */ + m68k_set_vbr( &M68Kvec ); + + /* Install the 68040 FPSP here */ + M68KFPSPInstallExceptionHandlers(); + + /* + * You may wish to make the VME arbitration round-robin here, currently + * we leave it as it is. + */ + + /* Set the Interrupt Base Vectors */ + lcsr->vector_base = (VBR0 << 28) | (VBR1 << 24); + + /* + * Initialize address translation + */ + page_table_init(); +} diff --git a/bsps/m68k/mvme167/start/linkcmds b/bsps/m68k/mvme167/start/linkcmds new file mode 100644 index 0000000000..dc50449b29 --- /dev/null +++ b/bsps/m68k/mvme167/start/linkcmds @@ -0,0 +1,35 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Motorola MVME167 board. + * + * Copyright (c) 1999, National Research Council of Canada. + * Some of this material was copied from binutils-2.9.4 linker scripts, + * and is therefore likely to be copyrighted by the Free Software + * Foundation, even though explicit copyright notices did not appear in + * those files. + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + */ + +RamBase = DEFINED(RamBase) ? RamBase : 0x00800000; +RamSize = DEFINED(RamSize) ? RamSize : 4M; + +MEMORY +{ + /* The location of RAM is the address space is configurable. + This is where we put one board. The base address should be + passed as a parameter when building multiprocessor images + where each board resides at a different address. */ + ram : org = RamBase, l = RamSize + rom : org = 0xFF800000, l = 4M + sram : org = 0xFFE00000, l = 128K +} + +REGION_ALIAS ("REGION_TEXT", ram); +REGION_ALIAS ("REGION_TEXT_LOAD", ram); +REGION_ALIAS ("REGION_DATA", ram); +REGION_ALIAS ("REGION_DATA_LOAD", ram); + +INCLUDE linkcmds.base diff --git a/bsps/m68k/mvme167/start/page_table.c b/bsps/m68k/mvme167/start/page_table.c new file mode 100644 index 0000000000..da50e511b0 --- /dev/null +++ b/bsps/m68k/mvme167/start/page_table.c @@ -0,0 +1,149 @@ +/* page_table.c + * + * The code submitted by Eric Vaitl <vaitl@viasat.com> for the MVME162 appears + * to be for a uniprocessor implementation. The function that sets up the + * page tables, page_table_init(), is not data driven. For all processors, it + * sets up page tables to map virtual addresses from 0x20000 to 0x3FFFFF to + * physical addresses 0x20000 to 0x3FFFFF. This presumably maps a subset of + * a local 4 MB space, which is probably the amount of RAM on Eric Vailt's + * MVME162. + * + * It is possible to set up the various bus bridges in the MVME167s to create + * a flat physical address space across multiple boards, i.e., it is possible + * for each MVME167 in a multiprocessor system to access a given memory + * location using the same physical address, whether that location is in local + * or VME space. Addres translation can be set up so that each virtual address + * maps to its corresponding physical address, e.g. virtual address 0x12345678 + * is mapped to physical address 0x12345678. With this mapping, the MMU is + * only used to control the caching modes for the various regions of memory. + * Mapping the virtual addresses to their corresponding physical address makes + * it unnecessary to map addresses under software control during the + * initialization of RTEMS, before address translation is turned on. + * + * With the above approach, address translation may be set up either with the + * transparent address translation registers, or with page tables. If page + * tables are used, a more efficient use of page table space can be achieved + * by sharing the page tables between processors. The entire page table tree + * can be shared, or each processor can hold a private copy of the top nodes + * which point to leaf nodes stored on individual processors. + * + * In this port, only the transparent address translation registers are used. + * We map the entire virtual range from 0x0 to 0x7FFFFFFF to the identical + * physical range 0x0 to 0x7FFFFFFF. We rely on the hardware to signal bus + * errors if we address non-existent memory within this range. Our two + * MVME167s are configured to exist at physical addresses 0x00800000 to + * 0x00BFFFFF and 0x00C00000 to 0x00FFFFFF respectively. If jumper J1-4 is + * installed, memory and cache control can be done by providing parameters + * in NVRAM and jumpers J1-[5-7] are ignored. See the README for details. + * If J1-4 is removed, behaviour defaults to the following. We map the space + * from 0x0 to 0x7FFFFFFF as copyback, unless jumper J1-5 is removed, in which + * case we map as writethrough. If jumper J1-7 is removed, the data cache is + * NOT enabled. If jumper J1-6 is removed, the instruction cache is not enabled. + * + * Copyright (c) 1998, National Research Council of Canada + */ + +#include <bsp.h> +#include <page_table.h> /* Nothing in here for us */ + +/* + * page_table_init + * + * Map the virtual range 0x00000000--0x7FFFFFFF to the physical range + * 0x00000000--0x7FFFFFFF. Rely on the hardware to raise exceptions when + * addressing non-existent memory. Use only the transparent translation + * registers (for now). + * + * On all processors, the local virtual address range 0xFF000000--0xFFFFFFFF + * is mapped to the physical address range 0xFF000000--0xFFFFFFFF as + * caching disabled, serialized access. + * + * Output parameters: NONE + * + * Return values: NONE + */ +void page_table_init( void ) +{ + unsigned char j1; /* State of J1 jumpers */ + register unsigned long dtt0; /* Content of dtt0 */ + register unsigned long cacr; /* Content of cacr */ + + /* + * Logical base addr = 0x00 map starting at 0x00000000 + * Logical address mask = 0x7F map up to 0x7FFFFFFF + * E = 0b1 enable address translation + * S-Field = 0b1X ignore FC2 when matching + * U1, U0 = 0b00 user page attributes not used + * CM = 0b01 cachable, copyback + * W = 0b0 read/write access allowed + */ + dtt0 = 0x007FC020; + + cacr = 0x00000000; /* Data and instruction cache off */ + + /* Read the J1 header */ + j1 = (unsigned char)(lcsr->vector_base & 0xFF); + + if ( !(j1 & 0x10) ) { + /* Jumper J1-4 is on, configure from NVRAM */ + + if ( nvram->cache_mode & 0x01 ) + cacr |= 0x80000000; + + if ( nvram->cache_mode & 0x02 ) + cacr |= 0x00008000; + + if ( nvram->cache_mode ) + dtt0 = ((nvram->cache_mode & 0x0C) << 3) | (dtt0 & 0xFFFFFF9F); + } + else { + /* Configure according to other jumper settings */ + + if ( !(j1 & 0x80) ) + /* Jumper J1-7 if on, enable data caching */ + cacr |= 0x80000000; + + if ( !(j1 & 0x40) ) + /* Jumper J1-6 if on, enable instruction caching */ + cacr |= 0x00008000; + + if ( j1 & 0x20 ) + /* Jumper J1-5 is off, enable writethrough caching */ + dtt0 &= 0xFFFFFF9F; + } + + /* do it ! */ + __asm__ volatile("movec %0, %%tc\n\t" /* turn off paged address translation */ + "movec %0, %%cacr\n\t" /* disable both caches */ + "cinva %%bc\n\t" /* clear both caches */ + "movec %1,%%dtt0\n\t" /* block address translation on */ + "movec %1,%%itt0\n\t" + "movec %2,%%dtt1\n\t" + "movec %2,%%itt1\n\t" + "movec %3,%%cacr" /* data cache on */ + :: "d" (0), "d" (dtt0), "d" (0xFF00C040), "d" (cacr)); +} + +/* + * page_table_teardown + * + * Turn off paging. Turn off the cache. Flush the cache. Tear down + * the transparent translations. + * + * Input parameters: NONE + * + * Output parameters: NONE + * + * Return values: NONE + */ +void page_table_teardown( void ) +{ + __asm__ volatile ("movec %0,%%tc\n\t" + "movec %0,%%cacr\n\t" + "cpusha %%bc\n\t" + "movec %0,%%dtt0\n\t" + "movec %0,%%itt0\n\t" + "movec %0,%%dtt1\n\t" + "movec %0,%%itt1" + :: "d" (0) ); +} diff --git a/bsps/m68k/shared/start/linkcmds.base b/bsps/m68k/shared/start/linkcmds.base new file mode 100644 index 0000000000..56af70d1da --- /dev/null +++ b/bsps/m68k/shared/start/linkcmds.base @@ -0,0 +1,326 @@ +/* + * Copyright (c) 2008-2013 embedded brains GmbH. All rights reserved. + * + * embedded brains GmbH + * Dornierstr. 4 + * 82178 Puchheim + * Germany + * <rtems@embedded-brains.de> + * + * The license and distribution terms for this file may be + * found in the file LICENSE in this distribution or at + * http://www.rtems.org/license/LICENSE. + */ + +OUTPUT_FORMAT("elf32-m68k", "elf32-m68k", "elf32-m68k") + +OUTPUT_ARCH(m68k) + +ENTRY(start) +STARTUP(start.o) + +bsp_initstack_size = DEFINED (bsp_initstack_size) ? bsp_initstack_size : 2048; + +MEMORY { + UNEXPECTED_SECTIONS : ORIGIN = 0xffffffff, LENGTH = 0 +} + +SECTIONS { + .vector0 : ALIGN_WITH_INPUT { + bsp_vector0_begin = .; + KEEP (*(.vectors*)) + bsp_vector0_end = .; + } > REGION_TEXT AT > REGION_TEXT + bsp_vector0_size = bsp_vector0_end - bsp_vector0_begin; + + .text : ALIGN_WITH_INPUT { + *(.text.unlikely .text.*_unlikely) + *(.text .stub .text.* .gnu.linkonce.t.*) + /* .gnu.warning sections are handled specially by elf32.em. */ + *(.gnu.warning) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .init : ALIGN_WITH_INPUT { + KEEP (*(.init)) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .fini : ALIGN_WITH_INPUT { + KEEP (*(.fini)) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .rodata : ALIGN_WITH_INPUT { + *(.rodata .rodata.* .gnu.linkonce.r.*) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .rodata1 : ALIGN_WITH_INPUT { + *(.rodata1) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .eh_frame : ALIGN_WITH_INPUT { + KEEP (*(.eh_frame)) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .gcc_except_table : ALIGN_WITH_INPUT { + *(.gcc_except_table .gcc_except_table.*) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .tdata : ALIGN_WITH_INPUT { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } > REGION_TEXT AT > REGION_TEXT_LOAD + .tbss : ALIGN_WITH_INPUT { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } > REGION_TEXT AT > REGION_TEXT_LOAD + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + .preinit_array : ALIGN_WITH_INPUT { + PROVIDE_HIDDEN (__preinit_array_start = .); + KEEP (*(.preinit_array)) + PROVIDE_HIDDEN (__preinit_array_end = .); + } > REGION_TEXT AT > REGION_TEXT_LOAD + .init_array : ALIGN_WITH_INPUT { + PROVIDE_HIDDEN (__init_array_start = .); + KEEP (*(SORT(.init_array.*))) + KEEP (*(.init_array)) + PROVIDE_HIDDEN (__init_array_end = .); + } > REGION_TEXT AT > REGION_TEXT_LOAD + .fini_array : ALIGN_WITH_INPUT { + PROVIDE_HIDDEN (__fini_array_start = .); + KEEP (*(.fini_array)) + KEEP (*(SORT(.fini_array.*))) + PROVIDE_HIDDEN (__fini_array_end = .); + } > REGION_TEXT AT > REGION_TEXT_LOAD + .ctors : ALIGN_WITH_INPUT { + /* gcc uses crtbegin.o to find the start of + the constructors, so we make sure it is + first. Because this is a wildcard, it + doesn't matter if the user does not + actually link against crtbegin.o; the + linker won't look for a file to match a + wildcard. The wildcard also means that it + doesn't matter which directory crtbegin.o + is in. */ + KEEP (*crtbegin.o(.ctors)) + KEEP (*crtbegin?.o(.ctors)) + /* We don't want to include the .ctor section from + the crtend.o file until after the sorted ctors. + The .ctor section from the crtend file contains the + end of ctors marker and it must be last */ + KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .ctors)) + KEEP (*(SORT(.ctors.*))) + KEEP (*(.ctors)) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .dtors : ALIGN_WITH_INPUT { + KEEP (*crtbegin.o(.dtors)) + KEEP (*crtbegin?.o(.dtors)) + KEEP (*(EXCLUDE_FILE (*crtend.o *crtend?.o ) .dtors)) + KEEP (*(SORT(.dtors.*))) + KEEP (*(.dtors)) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .data.rel.ro : ALIGN_WITH_INPUT { + *(.data.rel.ro.local* .gnu.linkonce.d.rel.ro.local.*) + *(.data.rel.ro* .gnu.linkonce.d.rel.ro.*) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .jcr : ALIGN_WITH_INPUT { + KEEP (*(.jcr)) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .interp : ALIGN_WITH_INPUT { + *(.interp) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .note.gnu.build-id : ALIGN_WITH_INPUT { + *(.note.gnu.build-id) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .hash : ALIGN_WITH_INPUT { + *(.hash) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .gnu.hash : ALIGN_WITH_INPUT { + *(.gnu.hash) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .dynsym : ALIGN_WITH_INPUT { + *(.dynsym) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .dynstr : ALIGN_WITH_INPUT { + *(.dynstr) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .gnu.version : ALIGN_WITH_INPUT { + *(.gnu.version) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .gnu.version_d : ALIGN_WITH_INPUT { + *(.gnu.version_d) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .gnu.version_r : ALIGN_WITH_INPUT { + *(.gnu.version_r) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .rel.dyn : ALIGN_WITH_INPUT { + *(.rel.init) + *(.rel.text .rel.text.* .rel.gnu.linkonce.t.*) + *(.rel.fini) + *(.rel.rodata .rel.rodata.* .rel.gnu.linkonce.r.*) + *(.rel.data.rel.ro* .rel.gnu.linkonce.d.rel.ro.*) + *(.rel.data .rel.data.* .rel.gnu.linkonce.d.*) + *(.rel.tdata .rel.tdata.* .rel.gnu.linkonce.td.*) + *(.rel.tbss .rel.tbss.* .rel.gnu.linkonce.tb.*) + *(.rel.ctors) + *(.rel.dtors) + *(.rel.got) + *(.rel.bss .rel.bss.* .rel.gnu.linkonce.b.*) + PROVIDE_HIDDEN (__rel_iplt_start = .); + *(.rel.iplt) + PROVIDE_HIDDEN (__rel_iplt_end = .); + PROVIDE_HIDDEN (__rela_iplt_start = .); + PROVIDE_HIDDEN (__rela_iplt_end = .); + } > REGION_TEXT AT > REGION_TEXT_LOAD + .rela.dyn : ALIGN_WITH_INPUT { + *(.rela.init) + *(.rela.text .rela.text.* .rela.gnu.linkonce.t.*) + *(.rela.fini) + *(.rela.rodata .rela.rodata.* .rela.gnu.linkonce.r.*) + *(.rela.data .rela.data.* .rela.gnu.linkonce.d.*) + *(.rela.tdata .rela.tdata.* .rela.gnu.linkonce.td.*) + *(.rela.tbss .rela.tbss.* .rela.gnu.linkonce.tb.*) + *(.rela.ctors) + *(.rela.dtors) + *(.rela.got) + *(.rela.bss .rela.bss.* .rela.gnu.linkonce.b.*) + *(.rela.rtemsroset*) + *(.rela.rtemsrwset*) + PROVIDE_HIDDEN (__rel_iplt_start = .); + PROVIDE_HIDDEN (__rel_iplt_end = .); + PROVIDE_HIDDEN (__rela_iplt_start = .); + *(.rela.iplt) + PROVIDE_HIDDEN (__rela_iplt_end = .); + } > REGION_TEXT AT > REGION_TEXT_LOAD + .rel.plt : ALIGN_WITH_INPUT { + *(.rel.plt) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .rela.plt : ALIGN_WITH_INPUT { + *(.rela.plt) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .plt : ALIGN_WITH_INPUT { + *(.plt) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .iplt : ALIGN_WITH_INPUT { + *(.iplt) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .dynamic : ALIGN_WITH_INPUT { + *(.dynamic) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .got : ALIGN_WITH_INPUT { + *(.got.plt) *(.igot.plt) *(.got) *(.igot) + } > REGION_TEXT AT > REGION_TEXT_LOAD + .rtemsroset : ALIGN_WITH_INPUT { + /* Special FreeBSD linker set sections */ + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = .; + *(set_domain_*); + *(set_pseudo_*); + + KEEP (*(SORT(.rtemsroset.*))) + } > REGION_TEXT AT > REGION_TEXT_LOAD + + .vector1 : ALIGN_WITH_INPUT { + bsp_vector1_begin = .; + . = . + (ORIGIN (REGION_TEXT) == ORIGIN (REGION_DATA) ? 0 : bsp_vector0_size); + bsp_vector1_end = .; + } > REGION_DATA AT > REGION_DATA + bsp_vector1_size = bsp_vector1_end - bsp_vector1_begin; + + .initstack : ALIGN_WITH_INPUT { + bsp_initstack_begin = .; + . = . + bsp_initstack_size; + bsp_initstack_end = .; + } > REGION_DATA AT > REGION_DATA + + .data : ALIGN_WITH_INPUT { + bsp_section_data_begin = .; + *(.data .data.* .gnu.linkonce.d.*) + SORT(CONSTRUCTORS) + } > REGION_DATA AT > REGION_DATA_LOAD + .data1 : ALIGN_WITH_INPUT { + *(.data1) + } > REGION_DATA AT > REGION_DATA_LOAD + .rtemsrwset : ALIGN_WITH_INPUT { + KEEP (*(SORT(.rtemsrwset.*))) + bsp_section_data_end = .; + } > REGION_DATA AT > REGION_DATA_LOAD + bsp_section_data_size = bsp_section_data_end - bsp_section_data_begin; + bsp_section_data_load_begin = LOADADDR (.data); + bsp_section_data_load_end = bsp_section_data_load_begin + bsp_section_data_size; + + .bss : ALIGN_WITH_INPUT { + bsp_section_bss_begin = .; + *(.dynbss) + *(.bss .bss.* .gnu.linkonce.b.*) + *(COMMON) + bsp_section_bss_end = .; + } > REGION_DATA AT > REGION_DATA + bsp_section_bss_size = bsp_section_bss_end - bsp_section_bss_begin; + + .work : ALIGN_WITH_INPUT { + /* + * The work section will occupy the remaining REGION_DATA region and + * contains the RTEMS work space and heap. + */ + bsp_section_work_begin = .; + . += ORIGIN (REGION_DATA) + LENGTH (REGION_DATA) - ABSOLUTE (.); + bsp_section_work_end = .; + } > REGION_DATA AT > REGION_DATA + bsp_section_work_size = bsp_section_work_end - bsp_section_work_begin; + + /* FIXME */ + RamBase = ORIGIN (REGION_DATA); + RamSize = LENGTH (REGION_DATA); + WorkAreaBase = bsp_section_work_begin; + HeapSize = 0; + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + /* DWARF debug sections. + Symbols in the DWARF debugging sections are relative to the beginning + of the section so we begin them at 0. */ + /* DWARF 1 */ + .debug 0 : { *(.debug) } + .line 0 : { *(.line) } + /* GNU DWARF 1 extensions */ + .debug_srcinfo 0 : { *(.debug_srcinfo) } + .debug_sfnames 0 : { *(.debug_sfnames) } + /* DWARF 1.1 and DWARF 2 */ + .debug_aranges 0 : { *(.debug_aranges) } + .debug_pubnames 0 : { *(.debug_pubnames) } + /* DWARF 2 */ + .debug_info 0 : { *(.debug_info .gnu.linkonce.wi.*) } + .debug_abbrev 0 : { *(.debug_abbrev) } + .debug_line 0 : { *(.debug_line) } + .debug_frame 0 : { *(.debug_frame) } + .debug_str 0 : { *(.debug_str) } + .debug_loc 0 : { *(.debug_loc) } + .debug_macinfo 0 : { *(.debug_macinfo) } + /* SGI/MIPS DWARF 2 extensions */ + .debug_weaknames 0 : { *(.debug_weaknames) } + .debug_funcnames 0 : { *(.debug_funcnames) } + .debug_typenames 0 : { *(.debug_typenames) } + .debug_varnames 0 : { *(.debug_varnames) } + /* DWARF 3 */ + .debug_pubtypes 0 : { *(.debug_pubtypes) } + .debug_ranges 0 : { *(.debug_ranges) } + /* DWARF extension */ + .debug_macro 0 : { *(.debug_macro) } + /DISCARD/ : { *(.note.GNU-stack) *(.gnu_debuglink) *(.gnu.lto_*) } + + /* + * This is a RTEMS specific section to catch all unexpected input + * sections. In case you get an error like + * "section `.unexpected_sections' will not fit in region + * `UNEXPECTED_SECTIONS'" + * you have to figure out the offending input section and add it to the + * appropriate output section definition above. + */ + .unexpected_sections : { *(*) } > UNEXPECTED_SECTIONS +} diff --git a/bsps/m68k/uC5282/start/bsp_specs b/bsps/m68k/uC5282/start/bsp_specs new file mode 100644 index 0000000000..3a20757667 --- /dev/null +++ b/bsps/m68k/uC5282/start/bsp_specs @@ -0,0 +1,10 @@ +%rename endfile old_endfile +%rename startfile old_startfile + +*startfile: +%{!qrtems: %(old_startfile)} \ +%{!nostdlib: %{qrtems: crti.o%s crtbegin.o%s}} + +*endfile: +%{!qrtems: %(old_endfile)} %{qrtems: crtend.o%s crtn.o%s} + diff --git a/bsps/m68k/uC5282/start/bspclean.c b/bsps/m68k/uC5282/start/bspclean.c new file mode 100644 index 0000000000..a344efd7bb --- /dev/null +++ b/bsps/m68k/uC5282/start/bspclean.c @@ -0,0 +1,24 @@ +/* + * This routine returns control from RTEMS to the monitor. + * + * Author: W. Eric Norum <norume@aps.anl.gov> + * + * COPYRIGHT (c) 2005. + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> + +void bsp_fatal_extension( + rtems_fatal_source source, + bool always_set_to_false, + rtems_fatal_code error +) +{ + bsp_reset(); +} diff --git a/bsps/m68k/uC5282/start/bspreset.c b/bsps/m68k/uC5282/start/bspreset.c new file mode 100644 index 0000000000..b93fbb409f --- /dev/null +++ b/bsps/m68k/uC5282/start/bspreset.c @@ -0,0 +1,17 @@ +/* + * COPYRIGHT (c) 1989-2008. + * 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.org/license/LICENSE. + */ + +#include <rtems.h> +#include <bsp.h> +#include <bsp/bootcard.h> + +void bsp_reset(void) +{ + bsp_sysReset(0); +} diff --git a/bsps/m68k/uC5282/start/bspstart.c b/bsps/m68k/uC5282/start/bspstart.c new file mode 100644 index 0000000000..33ce737ceb --- /dev/null +++ b/bsps/m68k/uC5282/start/bspstart.c @@ -0,0 +1,673 @@ +/* + * This routine does the bulk of the system initialisation. + */ + +/* + * Author: W. Eric Norum <norume@aps.anl.gov> + * + * COPYRIGHT (c) 2005. + * 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.org/license/LICENSE. + */ + +#include <bsp.h> +#include <bsp/bootcard.h> +#include <rtems/error.h> +#include <errno.h> +#include <stdio.h> +#include <inttypes.h> +#include <mcf5282/mcf5282.h> + +/* + * Location of 'VME' access + */ +#define VME_ONE_BASE 0x30000000 +#define VME_TWO_BASE 0x31000000 + +/* + * Linker Script Defined Variables + */ +extern char RamSize[]; +extern char RamBase[]; +extern char _CPUClockSpeed[]; +extern char _PLLRefClockSpeed[]; + +uint32_t BSP_sys_clk_speed = (uint32_t)_CPUClockSpeed; +uint32_t BSP_pll_ref_clock = (uint32_t)_PLLRefClockSpeed; + +/* + * CPU-space access + * The NOP after writing the CACR is there to address the following issue as + * described in "Device Errata MCF5282DE", Rev. 1.7, 09/2004: + * + * 6 Possible Cache Corruption after Setting CACR[CINV] + * 6.1 Description + * The cache on the MCF5282 was enhanced to function as a unified data and + * instruction cache, an instruction cache, or an operand cache. The cache + * function and organization is controlled by the cache control register (CACR). + * The CINV (Bit 24 = cache invalidate) bit in the CACR causes a cache clear. + * If the cache is configured as a unified cache and the CINV bit is set, the + * scope of the cache clear is controlled by two other bits in the CACR, + * INVI (BIT 21 = CINV instruction cache only) and INVD (BIT 20 = CINV data + * cache only). These bits allow the entire cache, just the instruction + * portion of the cache, or just the data portion of the cache to be cleared. + * If a write to the CACR is performed to clear the cache (CINV = BIT 24 set) + * and only a partial clear will be done (INVI = BIT 21 or INVD = BIT 20 set), + * then cache corruption may occur. + * + * 6.2 Workaround + * All loads of the CACR that perform a cache clear operation (CINV = BIT 24) + * should be followed immediately by a NOP instruction. This avoids the cache + * corruption problem. + * DATECODES AFFECTED: All + * + * + * Buffered writes must be disabled as described in "MCF5282 Chip Errata", + * MCF5282DE, Rev. 6, 5/2009: + * SECF124: Buffered Write May Be Executed Twice + * Errata type: Silicon + * Affected component: Cache + * Description: If buffered writes are enabled using the CACR or ACR + * registers, the imprecise write transaction generated + * by a buffered write may be executed twice. + * Workaround: Do not enable buffered writes in the CACR or ACR registers: + * CACR[8] = DBWE (default buffered write enable) must be 0 + * ACRn[5] = BUFW (buffered write enable) must be 0 + * Fix plan: Currently, there are no plans to fix this. + */ +#define m68k_set_cacr_nop(_cacr) \ + __asm__ volatile ("movec %0,%%cacr\n\tnop" : : "d" (_cacr)) +#define m68k_set_cacr(_cacr) \ + __asm__ volatile ("movec %0,%%cacr" : : "d" (_cacr)) +#define m68k_set_acr0(_acr0) \ + __asm__ volatile ("movec %0,%%acr0" : : "d" (_acr0)) +#define m68k_set_acr1(_acr1) \ + __asm__ volatile ("movec %0,%%acr1" : : "d" (_acr1)) + +uint32_t mcf5282_acr0_mode = 0; +uint32_t mcf5282_acr1_mode = 0; + +extern void bsp_fake_syscall(int); + +/* + * The Arcturus boot ROM prints exception information improperly + * so use this default exception handler instead. This one also + * prints a call backtrace + */ +static void handler(int pc) +{ + int level; + static volatile int reent; + + rtems_interrupt_disable(level); + if (reent++) bsp_sysReset(0); + { + int *p = &pc; + int info = p[-1]; + int pc = p[0]; + int format = (info >> 28) & 0xF; + int faultStatus = ((info >> 24) & 0xC) | ((info >> 16) & 0x3); + int vector = (info >> 18) & 0xFF; + int statusRegister = info & 0xFFFF; + int *fp; + + printk("\n\nPC:%x SR:%x VEC:%x FORMAT:%x STATUS:%x\n", pc, + statusRegister, + vector, + format, + faultStatus); + fp = &p[-2]; + for(;;) { + int *nfp = (int *)*fp; + if ((nfp <= fp) + || ((char *)nfp >= RamSize) + || ((char *)(nfp[1]) >= RamSize)) + break; + printk("FP:%p -> %p PC:%x\n", fp, nfp, nfp[1]); + fp = nfp; + } + } + rtems_task_suspend(0); + rtems_panic("done"); +} + +void bsp_start( void ) +{ + int i; + const char *clk_speed_str; + uint32_t clk_speed, mfd, rfd; + uint8_t byte; + + /* + * Make sure UART TX is running - necessary for + * early printk to work. The firmware monitor + * usually enables this anyways but qemu doesn't! + */ + MCF5282_UART_UCR(CONSOLE_PORT) = MCF5282_UART_UCR_TX_ENABLED; + + /* + * Set up default exception handler + */ + for (i = 2 ; i < 256 ; i++) + if (i != (32+2)) /* Catch all but bootrom system calls */ + *((void (**)(int))(i * 4)) = handler; + + /* + * Invalidate the cache and disable it + */ + m68k_set_acr0(mcf5282_acr0_mode); + m68k_set_acr1(mcf5282_acr1_mode); + m68k_set_cacr_nop(MCF5XXX_CACR_CINV); + + /* + * Cache SDRAM + * Enable buffered writes + * As Device Errata SECF124 notes this may cause double writes, + * but that's not really a big problem and benchmarking tests have + * shown that buffered writes do gain some performance. + */ + mcf5282_acr0_mode = MCF5XXX_ACR_AB((uint32_t)RamBase) | + MCF5XXX_ACR_AM((uint32_t)RamSize-1) | + MCF5XXX_ACR_EN | + MCF5XXX_ACR_SM_IGNORE | + MCF5XXX_ACR_BWE; + m68k_set_acr0(mcf5282_acr0_mode); + + /* + * Qemu has no trap handler; install our fake syscall + * implementation if there is no existing handler. + */ + if ( 0 == *((void (**)(int))((32+2) * 4)) ) + *((void (**)(int))((32+2) * 4)) = bsp_fake_syscall; + + /* + * Read/write copy of cache registers + * Split instruction/data or instruction-only + * Allow CPUSHL to invalidate a cache line + * Disable buffered writes + * No burst transfers on non-cacheable accesses + * Default cache mode is *disabled* (cache only ACRx areas) + */ + mcf5xxx_initialize_cacr( + MCF5XXX_CACR_CENB | + #ifndef RTEMS_MCF5282_BSP_ENABLE_DATA_CACHE + MCF5XXX_CACR_DISD | + #endif + MCF5XXX_CACR_DCM + ); + + /* + * Set up CS* space (fake 'VME') + * Two A24/D16 spaces, supervisor data acces + */ + MCF5282_CS1_CSAR = MCF5282_CS_CSAR_BA(VME_ONE_BASE); + MCF5282_CS1_CSMR = MCF5282_CS_CSMR_BAM_16M | + MCF5282_CS_CSMR_CI | + MCF5282_CS_CSMR_SC | + MCF5282_CS_CSMR_UC | + MCF5282_CS_CSMR_UD | + MCF5282_CS_CSMR_V; + MCF5282_CS1_CSCR = MCF5282_CS_CSCR_PS_16; + MCF5282_CS2_CSAR = MCF5282_CS_CSAR_BA(VME_TWO_BASE); + MCF5282_CS2_CSMR = MCF5282_CS_CSMR_BAM_16M | + MCF5282_CS_CSMR_CI | + MCF5282_CS_CSMR_SC | + MCF5282_CS_CSMR_UC | + MCF5282_CS_CSMR_UD | + MCF5282_CS_CSMR_V; + MCF5282_CS2_CSCR = MCF5282_CS_CSCR_PS_16; + MCF5282_GPIO_PJPAR |= 0x06; + + /* + * Hopefully, the UART clock is still correctly set up + * so they can see the printk() output... + */ + clk_speed = 0; + printk("Trying to figure out the system clock\n"); + printk("Checking ENV variable SYS_CLOCK_SPEED:\n"); + if ( (clk_speed_str = bsp_getbenv("SYS_CLOCK_SPEED")) ) { + printk("Found: %s\n", clk_speed_str); + for ( clk_speed = 0, i=0; + clk_speed_str[i] >= '0' && clk_speed_str[i] <= '9'; + i++ ) { + clk_speed = 10*clk_speed + clk_speed_str[i] - '0'; + } + if ( 0 != clk_speed_str[i] ) { + printk("Not a decimal number; I'm not using this setting\n"); + clk_speed = 0; + } + } else { + printk("Not set.\n"); + } + + if ( 0 == clk_speed ) + clk_speed = BSP_sys_clk_speed; + + if ( 0 == clk_speed ) { + printk("Using some heuristics to determine clock speed...\n"); + byte = MCF5282_CLOCK_SYNSR; + if ( 0 == byte ) { + printk("SYNSR == 0; assuming QEMU at 66MHz\n"); + BSP_pll_ref_clock = 8250000; + mfd = ( 0 << 8 ) | ( 2 << 12 ); + } else { + if ( 0xf8 != byte ) { + printk("FATAL ERROR: Unexpected SYNSR contents (0x%02x), can't proceed\n", byte); + bsp_sysReset(0); + } + mfd = MCF5282_CLOCK_SYNCR; + } + printk("Assuming %" PRIu32 "Hz PLL ref. clock\n", BSP_pll_ref_clock); + rfd = (mfd >> 8) & 7; + mfd = (mfd >> 12) & 7; + /* Check against 'known' cases */ + if ( 0 != rfd || (2 != mfd && 3 != mfd) ) { + printk("WARNING: Pll divisor/multiplier has unknown value; \n"); + printk(" either your board is not 64MHz or 80Mhz or\n"); + printk(" it uses a PLL reference other than 8MHz.\n"); + printk(" I'll proceed anyways but you might have to\n"); + printk(" reset the board and set uCbootloader ENV\n"); + printk(" variable \"SYS_CLOCK_SPEED\".\n"); + } + mfd = 2 * (mfd + 2); + /* sysclk = pll_ref * 2 * (MFD + 2) / 2^(rfd) */ + printk( + "PLL multiplier: %" PRIu32", output divisor: %" PRIu32 "\n", + mfd, + rfd + ); + clk_speed = (BSP_pll_ref_clock * mfd) >> rfd; + } + + if ( 0 == clk_speed ) { + printk("FATAL ERROR: Unable to determine system clock speed\n"); + bsp_sysReset(0); + } else { + BSP_sys_clk_speed = clk_speed; + printk( + "System clock speed: %" PRIu32 "Hz\n", bsp_get_CPU_clock_speed()); + } +} + +uint32_t bsp_get_CPU_clock_speed(void) +{ + return( BSP_sys_clk_speed ); +} + +/* + * Interrupt controller allocation + */ +rtems_status_code +bsp_allocate_interrupt(int level, int priority) +{ + static char used[7]; + rtems_interrupt_level l; + rtems_status_code ret = RTEMS_RESOURCE_IN_USE; + + if ((level < 1) || (level > 7) || (priority < 0) || (priority > 7)) + return RTEMS_INVALID_NUMBER; + rtems_interrupt_disable(l); + if ((used[level-1] & (1 << priority)) == 0) { + used[level-1] |= (1 << priority); + ret = RTEMS_SUCCESSFUL; + } + rtems_interrupt_enable(l); + return ret; +} + +/* + * Arcturus bootloader system calls + */ +#define syscall_return(type, ret) \ +do { \ + if ((unsigned long)(ret) >= (unsigned long)(-64)) { \ + errno = -(ret); \ + ret = -1; \ + } \ + return (type)(ret); \ +} while (0) + +#define syscall_1(type,name,d1type,d1) \ +type bsp_##name(d1type d1); \ +type bsp_##name(d1type d1) \ +{ \ + long ret; \ + register long __d1 __asm__ ("%d1") = (long)d1; \ + __asm__ __volatile__ ("move.l %1,%%d0\n\t" \ + "trap #2\n\t" \ + "move.l %%d0,%0" \ + : "=g" (ret) \ + : "i" (SysCode_##name), "d" (__d1) \ + : "d0" ); \ + syscall_return(type,ret); \ +} + +#define syscall_2(type,name,d1type,d1,d2type,d2) \ +type bsp_##name(d1type d1, d2type d2); \ +type bsp_##name(d1type d1, d2type d2) \ +{ \ + long ret; \ + register long __d1 __asm__ ("%d1") = (long)d1; \ + register long __d2 __asm__ ("%d2") = (long)d2; \ + __asm__ __volatile__ ("move.l %1,%%d0\n\t" \ + "trap #2\n\t" \ + "move.l %%d0,%0" \ + : "=g" (ret) \ + : "i" (SysCode_##name), "d" (__d1),\ + "d" (__d2) \ + : "d0" ); \ + syscall_return(type,ret); \ +} + +#define syscall_3(type,name,d1type,d1,d2type,d2,d3type,d3) \ +type bsp_##name(d1type d1, d2type d2, d3type d3); \ +type bsp_##name(d1type d1, d2type d2, d3type d3) \ +{ \ + long ret; \ + register long __d1 __asm__ ("%d1") = (long)d1; \ + register long __d2 __asm__ ("%d2") = (long)d2; \ + register long __d3 __asm__ ("%d3") = (long)d3; \ + __asm__ __volatile__ ("move.l %1,%%d0\n\t" \ + "trap #2\n\t" \ + "move.l %%d0,%0" \ + : "=g" (ret) \ + : "i" (SysCode_##name), "d" (__d1),\ + "d" (__d2),\ + "d" (__d3) \ + : "d0" ); \ + syscall_return(type,ret); \ +} + +#define SysCode_sysReset 0 /* system reset */ +#define SysCode_program 5 /* program flash memory */ +#define SysCode_gethwaddr 12 /* get hardware address */ +#define SysCode_getbenv 14 /* get bootloader environment variable */ +#define SysCode_setbenv 15 /* set bootloader environment variable */ +#define SysCode_flash_erase_range 19 /* erase a section of flash */ +#define SysCode_flash_write_range 20 /* write a section of flash */ +syscall_1(int, sysReset, int, flags) +syscall_1(unsigned const char *, gethwaddr, int, a) +syscall_1(const char *, getbenv, const char *, a) +syscall_1(int, setbenv, const char *, a) +syscall_2(int, program, bsp_mnode_t *, chain, int, flags) +syscall_3(int, flash_erase_range, volatile unsigned short *, flashptr, int, start, int, end); +syscall_3(int, flash_write_range, volatile unsigned short *, flashptr, bsp_mnode_t *, chain, int, offset); + +/* Provide a dummy-implementation of these syscalls + * for qemu (which lacks the firmware). + */ + +#define __STR(x) #x +#define __STRSTR(x) __STR(x) +#define ERRVAL __STRSTR(EACCES) + +/* reset-control register */ +#define RCR "__IPSBAR + 0x110000" + +__asm__ ( + "bsp_fake_syscall: \n" + " cmpl #0, %d0 \n" /* sysreset */ + " bne 1f \n" + " moveb #0x80, %d0 \n" + " moveb %d0, "RCR" \n" /* reset-controller */ + /* should never get here - but we'd return -EACCESS if we do */ + "1: \n" + " cmpl #12, %d0 \n" /* gethwaddr */ + " beq 2f \n" + " cmpl #14, %d0 \n" /* getbenv */ + " beq 2f \n" + " movel #-"ERRVAL", %d0 \n" /* return -EACCESS */ + " rte \n" + "2: \n" + " movel #0, %d0 \n" /* return NULL */ + " rte \n" +); + + +/* + * 'Extended BSP' routines + * Should move to cpukit/score/cpu/m68k/cpu.c someday. + */ + +rtems_status_code bspExtInit(void) { return RTEMS_SUCCESSFUL; } +int BSP_enableVME_int_lvl(unsigned int level) { return 0; } +int BSP_disableVME_int_lvl(unsigned int level) { return 0; } + +/* + * 'VME' interrupt support + * Interrupt vectors 192-255 are set aside for use by external logic which + * drives IRQ1*. The actual interrupt source is read from the external + * logic at FPGA_IRQ_INFO. The most-significant bit of the least-significant + * byte read from this location is set as long as the external logic has + * interrupts to be serviced. The least-significant six bits indicate the + * interrupt source within the external logic and are used to select the + * specified interupt handler. + */ +#define NVECTOR 256 +#define FPGA_VECTOR (64+1) /* IRQ1* pin connected to external FPGA */ +#define FPGA_IRQ_INFO *((vuint16 *)(0x31000000 + 0xfffffe)) + +static struct handlerTab { + BSP_VME_ISR_t func; + void *arg; +} handlerTab[NVECTOR]; + +BSP_VME_ISR_t +BSP_getVME_isr(unsigned long vector, void **pusrArg) +{ + if (vector >= NVECTOR) + return (BSP_VME_ISR_t)NULL; + if (pusrArg) + *pusrArg = handlerTab[vector].arg; + return handlerTab[vector].func; +} + +static rtems_isr +fpga_trampoline (rtems_vector_number v) +{ + /* + * Handle FPGA interrupts until all have been consumed + */ + int loopcount = 0; + while (((v = FPGA_IRQ_INFO) & 0x80) != 0) { + v = 192 + (v & 0x3f); + if (++loopcount >= 50) { + rtems_interrupt_level level; + rtems_interrupt_disable(level); + printk( + "\nTOO MANY FPGA INTERRUPTS (LAST WAS 0x%lx) -- " + "DISABLING ALL FPGA INTERRUPTS.\n", + v & 0x3f + ); + MCF5282_INTC0_IMRL |= MCF5282_INTC_IMRL_INT1; + rtems_interrupt_enable(level); + return; + } + if (handlerTab[v].func) { + (*handlerTab[v].func)(handlerTab[v].arg, (unsigned long)v); + } + else { + rtems_interrupt_level level; + rtems_vector_number nv; + rtems_interrupt_disable(level); + printk("\nSPURIOUS FPGA INTERRUPT (0x%lx).\n", v & 0x3f); + if ((((nv = FPGA_IRQ_INFO) & 0x80) != 0) + && ((nv & 0x3f) == (v & 0x3f))) { + printk("DISABLING ALL FPGA INTERRUPTS.\n"); + MCF5282_INTC0_IMRL |= MCF5282_INTC_IMRL_INT1; + } + rtems_interrupt_enable(level); + return; + } + } +} + +static rtems_isr +trampoline (rtems_vector_number v) +{ + if (handlerTab[v].func) + (*handlerTab[v].func)(handlerTab[v].arg, (unsigned long)v); +} + +static void +enable_irq(unsigned source) +{ +rtems_interrupt_level level; + rtems_interrupt_disable(level); + if (source >= 32) + MCF5282_INTC0_IMRH &= ~(1 << (source - 32)); + else + MCF5282_INTC0_IMRL &= ~((1 << source) | + MCF5282_INTC_IMRL_MASKALL); + rtems_interrupt_enable(level); +} + +static int +init_intc0_bit(unsigned long vector) +{ +rtems_interrupt_level level; + + /* + * Find an unused level/priority if this is an on-chip (INTC0) + * source and this is the first time the source is being used. + * Interrupt sources 1 through 7 are fixed level/priority + */ + + if ((vector >= 65) && (vector <= 127)) { + int l, p; + int source = vector - 64; + static unsigned char installed[8]; + + rtems_interrupt_disable(level); + if (installed[source/8] & (1 << (source % 8))) { + rtems_interrupt_enable(level); + return 0; + } + installed[source/8] |= (1 << (source % 8)); + rtems_interrupt_enable(level); + for (l = 1 ; l < 7 ; l++) { + for (p = 0 ; p < 8 ; p++) { + if ((source < 8) + || (bsp_allocate_interrupt(l,p) == RTEMS_SUCCESSFUL)) { + if (source < 8) + MCF5282_EPORT_EPIER |= 1 << source; + else + *(&MCF5282_INTC0_ICR1 + (source - 1)) = + MCF5282_INTC_ICR_IL(l) | + MCF5282_INTC_ICR_IP(p); + enable_irq(source); + return 0; + } + } + } + return -1; + } + return 0; +} + +int +BSP_installVME_isr(unsigned long vector, BSP_VME_ISR_t handler, void *usrArg) +{ + rtems_isr_entry old_handler; + rtems_interrupt_level level; + + /* + * Register the handler information + */ + if (vector >= NVECTOR) + return -1; + handlerTab[vector].func = handler; + handlerTab[vector].arg = usrArg; + + /* + * If this is an external FPGA ('VME') vector set up the real IRQ. + */ + if ((vector >= 192) && (vector <= 255)) { + int i; + static volatile int setupDone; + rtems_interrupt_disable(level); + if (setupDone) { + rtems_interrupt_enable(level); + return 0; + } + setupDone = 1; + rtems_interrupt_catch(fpga_trampoline, FPGA_VECTOR, &old_handler); + i = init_intc0_bit(FPGA_VECTOR); + rtems_interrupt_enable(level); + return i; + } + + /* + * Make the connection between the interrupt and the local handler + */ + rtems_interrupt_catch(trampoline, vector, &old_handler); + + return init_intc0_bit(vector); +} + +int +BSP_removeVME_isr(unsigned long vector, BSP_VME_ISR_t handler, void *usrArg) +{ + if (vector >= NVECTOR) + return -1; + if ((handlerTab[vector].func != handler) + || (handlerTab[vector].arg != usrArg)) + return -1; + handlerTab[vector].func = (BSP_VME_ISR_t)NULL; + return 0; +} + +int +BSP_vme2local_adrs(unsigned am, unsigned long vmeaddr, unsigned long *plocaladdr) +{ + unsigned long offset; + + switch (am) { + default: return -1; + case VME_AM_SUP_SHORT_IO: offset = 0x31FF0000; break; /* A16/D16 */ + case VME_AM_STD_SUP_DATA: offset = 0x30000000; break; /* A24/D16 */ + case VME_AM_EXT_SUP_DATA: offset = 0x31000000; break; /* A32/D32 */ + } + *plocaladdr = vmeaddr + offset; + return 0; +} + +void +bsp_reset_cause(char *buf, size_t capacity) +{ + int bit, rsr; + size_t i; + const char *cp; + + if (buf == NULL) + return; + if (capacity) + buf[0] = '\0'; + rsr = MCF5282_RESET_RSR; + for (i = 0, bit = 0x80 ; bit != 0 ; bit >>= 1) { + if (rsr & bit) { + switch (bit) { + case MCF5282_RESET_RSR_LVD: cp = "Low voltage"; break; + case MCF5282_RESET_RSR_SOFT: cp = "Software reset"; break; + case MCF5282_RESET_RSR_WDR: cp = "Watchdog reset"; break; + case MCF5282_RESET_RSR_POR: cp = "Power-on reset"; break; + case MCF5282_RESET_RSR_EXT: cp = "External reset"; break; + case MCF5282_RESET_RSR_LOC: cp = "Loss of clock"; break; + case MCF5282_RESET_RSR_LOL: cp = "Loss of lock"; break; + default: cp = "??"; break; + } + i += snprintf(buf+i, capacity-i, cp); + if (i >= capacity) + break; + rsr &= ~bit; + if (rsr == 0) + break; + i += snprintf(buf+i, capacity-i, ", "); + if (i >= capacity) + break; + } + } +} diff --git a/bsps/m68k/uC5282/start/init5282.c b/bsps/m68k/uC5282/start/init5282.c new file mode 100644 index 0000000000..201ee58c8e --- /dev/null +++ b/bsps/m68k/uC5282/start/init5282.c @@ -0,0 +1,44 @@ +/* + * This is where the real hardware setup is done. A minimal stack + * has been provided by the start.S code. No normal C or RTEMS + * functions can be called from here. + * + * This routine is pretty simple for the uC5282 because all the hard + * work has been done by the bootstrap dBUG code. + */ + +/* + * Author: W. Eric Norum <norume@aps.anl.gov> + * + * COPYRIGHT (c) 2005. + * 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.org/license/LICENSE. + */ + +#include <rtems.h> +#include <bsp.h> + +#define m68k_set_cacr(_cacr) __asm__ volatile ("movec %0,%%cacr" : : "d" (_cacr)) +#define m68k_set_acr0(_acr0) __asm__ volatile ("movec %0,%%acr0" : : "d" (_acr0)) +#define m68k_set_acr1(_acr1) __asm__ volatile ("movec %0,%%acr1" : : "d" (_acr1)) + +/* + * This method is implemented in start.S. + */ +extern void CopyDataClearBSSAndStart (void); + +/* + * This method cannot be static because it is called from start.S. + */ +void Init5282 (void); + +void Init5282 (void) +{ + /* + * Copy data, clear BSS and call boot_card() + */ + CopyDataClearBSSAndStart (); +} diff --git a/bsps/m68k/uC5282/start/linkcmds b/bsps/m68k/uC5282/start/linkcmds new file mode 100644 index 0000000000..a3b84294e3 --- /dev/null +++ b/bsps/m68k/uC5282/start/linkcmds @@ -0,0 +1,243 @@ +/* + * This file contains directives for the GNU linker which are specific + * to the Arcturus uC DIMM ColdFire 5282 + * + * Author: W. Eric Norum <norume@aps.anl.gov> + * + * COPYRIGHT (c) 2005-2007. + * 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.org/license/LICENSE. + */ + +/* + * Declare some locations and sizes. + */ +RamBase = DEFINED(RamBase) ? RamBase : 0x0; +RamSize = DEFINED(RamSize) ? RamSize : 16M; +HeapSize = DEFINED(HeapSize) ? HeapSize : 0; +_FlashBase = DEFINED(_FlashBase) ? _FlashBase : 0x10000000; +_FlashSize = DEFINED(_FlashSize) ? _FlashSize : 4M ; + +/* + * Location of downloaded (from TFTP or flash) file + */ +_DownloadLocation = 0x40000; + +/* + * System clock speed + * + * If autodetection of the system clock pased on the PLL ref. clock + * (AFAIK 8MHz for both 64MHz and 80MHz boards) doesn't work then + * you can: + * - define (nonzero) system clock speed from app- linkflags (or here) + * - use a uCbootloader env. var: SYS_CLOCK_SPEED to define it. + * You can also redefine the PLL reference clock speed from linkflags + * or here... + */ +_CPUClockSpeed = DEFINED(_CPUClockSpeed) ? _CPUClockSpeed : 0 ; +_PLLRefClockSpeed = DEFINED(_PLLRefClockSpeed) ? _PLLRefClockSpeed : 8000000; + +/* + * Location of on-chip devices + */ +__IPSBAR = DEFINED(__IPSBAR) ? __IPSBAR : 0x40000000 ; +__SRAMBASE = DEFINED(__SRAMBASE) ? __SRAMBASE : 0x20000000 ; +_VBR = 0x0; + +ENTRY(start) +STARTUP(start.o) + +MEMORY +{ + ram : ORIGIN = 0, LENGTH = 16M + sram : ORIGIN = 0x20000000, LENGTH = 64k +} + +SECTIONS +{ + + _header_offset = 0; + + /* + * Text, data and bss segments + */ + .text _DownloadLocation : { + + *(.text*) + *(.ram_code) + + /* + * C++ constructors/destructors + */ + *(.gnu.linkonce.t.*) + + /* + * Initialization and finalization code. + * + * Various files can provide initialization and finalization + * functions. crtbegin.o and crtend.o are two instances. The + * body of these functions are in .init and .fini sections. We + * accumulate the bodies here, and prepend function prologues + * from crti.o and function epilogues from crtn.o. crti.o must + * be linked first; crtn.o must be linked last. Because these + * are wildcards, it doesn't matter if the user does not + * actually link against crti.o and crtn.o; the linker won't + * look for a file to match a wildcard. The wildcard also + * means that it doesn't matter which directory crti.o and + * crtn.o are in. + */ + PROVIDE (_init = .); + *crti.o(.init) + *(.init) + *crtn.o(.init) + PROVIDE (_fini = .); + *crti.o(.fini) + *(.fini) + *crtn.o(.fini) + + /* + * Special FreeBSD sysctl sections. + */ + . = ALIGN (16); + __start_set_sysctl_set = .; + *(set_sysctl_*); + __stop_set_sysctl_set = ABSOLUTE(.); + *(set_domain_*); + *(set_pseudo_*); + + /* + * C++ constructors/destructors + * + * gcc uses crtbegin.o to find the start of the constructors + * and destructors so we make sure it is first. Because this + * is a wildcard, it doesn't matter if the user does not + * actually link against crtbegin.o; the linker won't look for + * a file to match a wildcard. The wildcard also means that + * it doesn't matter which directory crtbegin.o is in. The + * constructor and destructor list are terminated in + * crtend.o. The same comments apply to it. + */ + . = ALIGN (16); + *crtbegin.o(.ctors) + *(.ctors) + *crtend.o(.ctors) + *crtbegin.o(.dtors) + *(.dtors) + *crtend.o(.dtors) + + /* + * Exception frame info + */ + . = ALIGN (16); + *(.eh_frame) + + /* + * Read-only data + */ + . = ALIGN (16); + _rodata_start = . ; + *(.rodata*) + KEEP (*(SORT(.rtemsroset.*))) + *(.gnu.linkonce.r*) + + . = ALIGN (16); + + *(.console_gdb_xfer) + *(.bootstrap_data) + . = ALIGN(16); + _estuff = .; + PROVIDE (_etext = .); + } >ram + + .tdata : { + _TLS_Data_begin = .; + *(.tdata .tdata.* .gnu.linkonce.td.*) + _TLS_Data_end = .; + } > ram + + .tbss : { + _TLS_BSS_begin = .; + *(.tbss .tbss.* .gnu.linkonce.tb.*) *(.tcommon) + _TLS_BSS_end = .; + } > ram + + _TLS_Data_size = _TLS_Data_end - _TLS_Data_begin; + _TLS_Data_begin = _TLS_Data_size != 0 ? _TLS_Data_begin : _TLS_BSS_begin; + _TLS_Data_end = _TLS_Data_size != 0 ? _TLS_Data_end : _TLS_BSS_begin; + _TLS_BSS_size = _TLS_BSS_end - _TLS_BSS_begin; + _TLS_Size = _TLS_BSS_end - _TLS_Data_begin; + _TLS_Alignment = MAX (ALIGNOF (.tdata), ALIGNOF (.tbss)); + + .data : { + PROVIDE( _data_dest_start = . ); + PROVIDE( _copy_start = .); + *(.data*) + KEEP (*(SORT(.rtemsrwset.*))) + *(.gnu.linkonce.d*) + *(.gcc_except_table*) + *(.jcr) + . = ALIGN (16); + PROVIDE (_edata = .); + PROVIDE (_copy_end = .); + PROVIDE (_data_dest_end = . ); + } >ram + + _data_src_start = LOADADDR(.data); + _data_src_end = _data_src_start + SIZEOF(.data); + + .bss : { + _clear_start = .; + *(.bss*) + *(.gnu.linkonce.b.*) + *(COMMON) + . = ALIGN (16); + PROVIDE (end = .); + _clear_end = .; + WorkAreaBase = .; + } >ram + + /* Stabs debugging sections. */ + .stab 0 : { *(.stab) } + .stabstr 0 : { *(.stabstr) } + .stab.excl 0 : { *(.stab.excl) } + .stab.exclstr 0 : { *(.stab.exclstr) } + .stab.index 0 : { *(.stab.index) } + .stab.indexstr 0 : { *(.stab.indexstr) } + .comment 0 : { *(.comment) } + + /* DWARF debug sections. + Symbols in the DWARF debugging sections are relative to the beginning + of the section so we begin them at 0. */ + /* DWARF 1 */ + .debug 0 : { *(.debug) } + .line 0 : { *(.line) } + + /* GNU DWARF 1 extensions */ + .debug_srcinfo 0 : { *(.debug_srcinfo) } + .debug_sfnames 0 : { *(.debug_sfnames) } + + /* DWARF 1.1 and DWARF 2 */ + .debug_aranges 0 : { *(.debug_aranges) } + .debug_pubnames 0 : { *(.debug_pubnames) } + + /* DWARF 2 */ + .debug_info 0 : { *(.debug_info) } + .debug_abbrev 0 : { *(.debug_abbrev) } + .debug_line 0 : { *(.debug_line) } + .debug_frame 0 : { *(.debug_frame) } + .debug_str 0 : { *(.debug_str) } + .debug_loc 0 : { *(.debug_loc) } + .debug_macinfo 0 : { *(.debug_macinfo) } + + /* SGI/MIPS DWARF 2 extensions */ + .debug_weaknames 0 : { *(.debug_weaknames) } + .debug_funcnames 0 : { *(.debug_funcnames) } + .debug_typenames 0 : { *(.debug_typenames) } + .debug_varnames 0 : { *(.debug_varnames) } + /* These must appear regardless of . */ + +PROVIDE (end_of_all = .); +} |