📄 stboot.c
字号:
/*****************************************************************************
File Name : stboot.c
Description : System Boot
This library is responsible for performing OS20/OS21
(ST20, ST40, ST200 devices) specific and backend processor
initialization.
Copyright (C) 1999-2005 STMicroelectronics
History :
8/99 First attempt
07/09/99 Addition of SDRAM initialization code for 5510
Toolset IO mutex functions now compile-time defined for
different toolset versions
13/09/99 API revised - dcache type changed
Partition initialization removed - now responsibility of
application
New API functions GetBackendInfo() and GetRevision().
14/09/99 Split boot setup into modules; sdram.c, cache.c and
stboot.c.
20/09/99 Addition of sdram init. params to API.
Removed local definition of SDRAM_FREQUENCY.
Removed ``repeated'' config. of audio clock interface in
MPEGInit() routine. This is now done in sdram.c via
ConfigurePLL().
21/12/99 Patch release to address PLL already initialized problem
if SDRAM is initialized in .cfg files.
08/08/00 Addition of EPLD and FPGA initialization for sti7015.
03/10/00 Move initialisation into 7015 target directory.
14/12/00 Remove not backend initialisation (FPGA & EPLD).
Add InitSDRAM7015 after BackendInit7015.
10/09/04 Added support for STi7710 and ST20 C1 timer. Added support for
use with OS21.
19/11/04 Added support for STi5105.
10/02/05 Added support for STi7100, STm5700.
20/04/05 Added support for STi5301, STm8010.
12/05/05 Changed ST200 specific dcache handling.
25/10/05 Added support for STi7109.
18/11/05 Added support for STi5188.
10/01/06 Added support for STx5525.
13/04/06 Added support for STx5107.
*****************************************************************************/
/* Includes --------------------------------------------------------------- */
/* override makefile forcing of 70xx addresses; this file needs the frontend
ones instead (INTERRUPT_...) */
#undef REMOVE_GENERIC_ADDRESSES
#ifdef ST_OS20
#include <device.h>
#endif
#include "stlite.h" /* STLite includes */
#include "stbootcache.h"
#ifdef ST_OS20
#include "debug.h"
#endif
#ifdef ST_OS21
#include "os21debug.h"
#ifdef ARCHITECTURE_ST200
#include <machine/sysconf.h>
#include <machine/rtrecord.h>
#include <machine/bsp.h>
#include <sys/bitfields.h>
#include <machine/ctrlreg.h>
#endif
#endif
#include "stdevice.h" /* Device includes */
#include "stboot.h" /* STAPI includes */
#include "stcommon.h"
#include "stsys.h"
#ifdef ARCHITECTURE_ST20 /* Local includes */
#include "sdram.h"
#include "be_init.h"
#if defined(ST_7015) || defined (ST_7020)
#include "be_7015.h" /* specific 7015/7020 backend init */
#endif
#endif /*#ifdef ARCHITECTURE_ST20*/
/* Private types/constants ------------------------------------------------ */
#ifdef ARCHITECTURE_ST20
/* The setup of mutual exclusion for the debug library depends on the compiler
version. For V1.7+:
- the mutual exclusion callback has a 2nd parameter, which is a pointer to
user data (pre-V1.7, the function had only 1 parameter).
- the callback function has no static link, & should be marked as
#pragma ST_nolink. */
#if (__ICC_VERSION_NUMBER__ < 50700)
#define OLD_MUTEX_FN
#endif
#ifndef OLD_MUTEX_FN
typedef struct
{
int *mutex_data_sl;
void *mutex_data_user;
} mutex_data_t;
#endif
/* Interrupt control structure */
typedef struct
{
char *stack_base;
size_t stack_size;
interrupt_flags_t flags;
} local_interrupt_control_t;
/* The chip-specific header file may override this definition to modify
* the trigger mode used for the various interrupt levels on the ILC.
* The default behaviour is specified here as 'high_level' and will
* be used otherwise.
*/
#ifndef INTERRUPT_TRIGGER_MODE
/* Workaround for STi5510 silicon */
#if defined(ST_5510)
#define INTERRUPT_TRIGGER_MODE(level) (((level==VIDEO_INTERRUPT_LEVEL) \
|| (level==AUDIO_INTERRUPT_LEVEL)) \
&& ((device_id().st.revision) == 0) \
&& ((device_id().st.device_code) == 0xCD) \
? interrupt_trigger_mode_falling : \
interrupt_trigger_mode_high_level)
#elif defined(mb295) || defined(mb290)
#define INTERRUPT_TRIGGER_MODE(level) ((level == EXTERNAL_1_INTERRUPT_LEVEL) \
? interrupt_trigger_mode_low_level : \
interrupt_trigger_mode_high_level)
#elif defined(ST_7020) /* db573 7020 STEM board */
#define INTERRUPT_TRIGGER_MODE(level) ((level == EXTERNAL_0_INTERRUPT_LEVEL) \
? interrupt_trigger_mode_low_level : \
interrupt_trigger_mode_high_level)
#elif defined(mb395)
#define INTERRUPT_TRIGGER_MODE(level) ((level == ATA_INTERRUPT_LEVEL) \
? interrupt_trigger_mode_low_level : \
interrupt_trigger_mode_high_level)
#else
#define INTERRUPT_TRIGGER_MODE(level) interrupt_trigger_mode_high_level
#endif
#endif /* INTERRUPT_TRIGGER_MODE */
/* Default interrupt level stack size */
#if defined (STBOOT_DEFAULT_ISR_STACK_SIZE)
#define DEFAULT_STACK_SIZE STBOOT_DEFAULT_ISR_STACK_SIZE
#else
#define DEFAULT_STACK_SIZE 1024
#endif
/* DeviceType for STi5512 Revs F & G */
#define DEVICE_5512_F 0x06
#define DEVICE_5512_G 0x07
/* Private variables ------------------------------------------------------ */
#if (OS20_VERSION_MAJOR < 2) || ((OS20_VERSION_MAJOR == 2) && (OS20_VERSION_MINOR <= 8))
/* This semaphore ensures mutual exclusion during debug output */
static semaphore_t mutex_sem;
#endif
/* Interrupt setup */
static char interrupt_level_0_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_1_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_2_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_3_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_4_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_5_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_6_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_7_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_8_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_9_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_10_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_11_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_12_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_13_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_14_stack[ DEFAULT_STACK_SIZE ];
static char interrupt_level_15_stack[ DEFAULT_STACK_SIZE ];
static local_interrupt_control_t interrupt_control[] =
{
{ interrupt_level_0_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_1_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_2_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_3_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_4_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_5_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_6_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_7_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_8_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_9_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_10_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_11_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_12_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_13_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_14_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority },
{ interrupt_level_15_stack, DEFAULT_STACK_SIZE, interrupt_flags_low_priority }
};
#endif /*#ifdef ARCHITECTURE_ST20*/
/* STBOOT revision number */
static const ST_Revision_t Revision = "STBOOT-REL_2.18.0";
/* Private macros --------------------------------------------------------- */
#define InitialiseStack(_base_, _size_) { \
unsigned int _i_; for (_i_=0;_i_<_size_ / sizeof(int);_i_++) \
((unsigned int*)_base_)[_i_] = 0xaaaaaaaa;\
}
/* Private function prototypes -------------------------------------------- */
#ifdef ARCHITECTURE_ST20
static ST_ErrorCode_t InitInterrupts(const STBOOT_InitParams_t *InitParams_p);
#if (OS20_VERSION_MAJOR < 2) || ((OS20_VERSION_MAJOR == 2) && (OS20_VERSION_MINOR <= 8))
/* The following routines prevent pre-emption of debug message output */
static void init_debugop_protection(void);
#ifdef OLD_MUTEX_FN
static long int mutex_fn (debugmutexop op);
#else
static long int mutex_fn (debugmutexop op, void *dummy);
static long int mutex_wrapper (debugmutexop op, mutex_data_t* mutex_data);
#pragma ST_nolink(mutex_wrapper)
#endif
#endif /* (OS20_VERSION_MAJOR < 2) || ((OS20_VERSION_MAJOR == 2) && (OS20_VERSION_MINOR <= 8))*/
#endif /*#ifdef ARCHITECTURE_ST20*/
/* API functions ---------------------------------------------------------- */
/*****************************************************************************
Name: STBOOT_Init()
Description:
Initializes system caches, SDRAM and the OS kernel.
Parameters:
DeviceName, device name associated with the boot.
InitParams_p, the initialization parameters.
Return Value:
ST_NO_ERROR No Errors during operation.
STBOOT_ERROR_KERNEL_INIT Error Initialising the Kernel.
STBOOT_ERROR_KERNEL_START Error Starting the Kernel.
STBOOT_ERROR_INTERRUPT_INIT Error Initilising Interrupts.
STBOOT_ERROR_INTERRUPT_ENABLE Error Enabling Interrupts.
STBOOT_ERROR_UNKNOWN_BACKEND The backend type is not recognized.
STBOOT_ERROR_BACKEND_MISMATCH The backend type does not match.
STBOOT_ERROR_INVALID_DCACHE Invalid dcache map.
STBOOT_ERROR_SDRAM_INIT Failed to setup SDRAM.
STBOOT_ERROR_BSP_FAILURE Error from toolset BSP.
See Also:
STBOOT_Term()
*****************************************************************************/
ST_ErrorCode_t STBOOT_Init( const ST_DeviceName_t DeviceName,
const STBOOT_InitParams_t *InitParams_p )
{
ST_ErrorCode_t ErrorCode = ST_NO_ERROR;
/************************ FOR OS20 ******************************/
#ifdef ST_OS20
#ifdef ST_5100
S8 Error = 0;
#endif
#if defined(PROCESSOR_C1)
int c1_timer_initialize(void);
#endif
#if !defined(ST_5100)
/* Initialize instruction cache before starting kernel */
stboot_InitICache( (CacheReg_t *)InitParams_p->CacheBaseAddress,
InitParams_p->ICacheEnabled );
/* Initialize data cache */
if ( stboot_InitDCache( (CacheReg_t *)InitParams_p->CacheBaseAddress,
InitParams_p->DCacheMap ) )
{
return STBOOT_ERROR_INVALID_DCACHE;
}
stboot_LockCaches( (CacheReg_t *)InitParams_p->CacheBaseAddress );
#endif
#if !defined (OS20_RUNTIME)
/* Initialize the kernel */
if (kernel_initialize() != 0)
{
return STBOOT_ERROR_KERNEL_INIT;
}
else if (kernel_start() != 0) /* Start the kernel */
{
return STBOOT_ERROR_KERNEL_START;
}
#endif
#if defined(ST_5100) /*cache config for 5100 only, due to dcache bug*/
Error = cache_init_controller((void *)InitParams_p->CacheBaseAddress, cache_map_c2_c200);
if(Error != 0)
{
return STBOOT_ERROR_BSP_FAILURE;
}
if(InitParams_p->ICacheEnabled)
{
#ifdef STBOOT_LMI_TOP_REGION_ICACHE_ENABLE
Error = cache_config_instruction ((void *)0x00000000, (void *)0xffffffff, cache_config_enable);
#else
Error = cache_config_instruction ((void *)0xC0000000, (void *)0xC07FFFFF, cache_config_enable);
Error |= cache_config_instruction ((void *)0x40000000, (void *)0x7FFFFFFF, cache_config_enable);
#endif
if(Error != 0)
{
return STBOOT_ERROR_BSP_FAILURE;
}
Error = cache_enable_instruction(); /*typically cache should be enabled AFTER an invalidate call. OS20 takes care of this when using this call*/
if(Error != 0)
{
return STBOOT_ERROR_BSP_FAILURE;
}
}
if ( stboot_InitDCache( (CacheReg_t *)InitParams_p->CacheBaseAddress, InitParams_p->DCacheMap ) )
{
return STBOOT_ERROR_INVALID_DCACHE;
}
#endif
/* Initialize interrupts and ILC */
ErrorCode = InitInterrupts(InitParams_p);
if(ErrorCode != ST_NO_ERROR)
{
return ErrorCode;
}
#if defined(PROCESSOR_C1)
c1_timer_initialize(); /*present in file st_c1_timer.c*/
#endif
#if (OS20_VERSION_MAJOR < 2) || ((OS20_VERSION_MAJOR == 2) && (OS20_VERSION_MINOR <= 8))
/* Debug output semaphore protection */
init_debugop_protection();
#endif
#ifndef mb295
/* Initialize 55xx MPEG backend */
ErrorCode = stboot_BackendInit(NULL);
if ( ErrorCode != ST_NO_ERROR )
{
return ErrorCode;
}
#if !defined(ST_5514) && !defined(ST_5516) && !defined(ST_5517) && !defined(ST_5528) && !defined(ST_5100) && !defined(ST_5101) && !defined(ST_7710) && !defined(ST_5105) && !defined(ST_5700) && !defined(ST_5188) && !defined(ST_5107) /* [ */ /* SMI is initialized in the cfg file */
/* Initialise SMI SDRAM if size is non zero */
switch( InitParams_p->MemorySize )
{
case STBOOT_DRAM_MEMORY_SIZE_0:
/* No initialization required */
/* This is not an error */
break;
case STBOOT_DRAM_MEMORY_SIZE_16_MBIT:
case STBOOT_DRAM_MEMORY_SIZE_32_MBIT:
case STBOOT_DRAM_MEMORY_SIZE_64_MBIT:
if(stboot_InitSDRAM(InitParams_p->SDRAMFrequency,
InitParams_p->MemorySize) )
{
return STBOOT_ERROR_SDRAM_INIT;
}
break;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -