⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 syslib.c

📁 VxWorks下 Spruce的BSP源代码
💻 C
📖 第 1 页 / 共 2 页
字号:
     * run-time update of the MMU entry for main RAM     */    sysPhysMemDesc[1].len = (UINT)(sysPhysMemTop () - RAM_LOW_ADRS);#endif	/* INCLUDE_MMU */#ifdef INCLUDE_PCI              /* PCI initialization */    pciIntLibInit();    pciConfigLibInit(PCI_MECHANISM_1, PCICFGADR, PCICFGDATA, (int)NULL);    sysPciInit();#endif#ifdef INCLUDE_NETWORK    sysNetHwInit();             /* network interface */#endif#ifdef INCLUDE_SERIAL    sysSerialHwInit();          /* serial devices */#endif    }/********************************************************************************* sysHwInit2 - initialize additional system hardware** This routine connects system interrupt vectors and configures any* required features not configured by sysHwInit. It is called from usrRoot()* in usrConfig.c after the multitasking kernel has started.** RETURNS: N/A*/void sysHwInit2    (    void    )    {    static int  initialized;       /* must protect against double call! */    if (!initialized)        {        initialized = TRUE;	/* connect external interrupt handler */	excIntConnect ((VOIDFUNCPTR *) _EXC_OFF_INTR, sysCPC700IntHandler);#ifdef INCLUDE_NETWORK        sysNetHwInit2 ();       /* network interface */#endif#ifdef INCLUDE_SERIAL        sysSerialHwInit2 ();    /* connect serial interrupts */#endif        /*         * L2 Cache setup         */#if     defined(INCLUDE_CACHE_SUPPORT) && defined(INCLUDE_CACHE_L2)        sysL2CacheInit();#  ifdef USER_L2_CACHE_ENABLE        sysL2CacheEnable();#  endif#endif /*(INCLUDE_CACHE_SUPPORT) && (INCLUDE_CACHE_L2)*/        }    }/********************************************************************************* sysPhysMemTop - get the address of the top of physical memory** This routine returns the address of the first missing byte of memory,* which indicates the top of memory.** Normally, the user specifies the amount of physical memory with the* macro LOCAL_MEM_SIZE in config.h.  BSPs that support run-time* memory sizing do so only if the macro LOCAL_MEM_AUTOSIZE is defined.* If not defined, then LOCAL_MEM_SIZE is assumed to be, and must be, the* true size of physical memory.** NOTE: Do no adjust LOCAL_MEM_SIZE to reserve memory for application* use.  See sysMemTop() for more information on reserving memory.** RETURNS: The address of the top of physical memory.** SEE ALSO: sysMemTop()*/char * sysPhysMemTop    (    void    )    {    static char * physTop = NULL;#ifdef LOCAL_MEM_AUTOSIZE    int memSize;#endif    if (physTop == NULL)        {#ifdef LOCAL_MEM_AUTOSIZE        /*         * Look at the CPC700 memory controller configuration to determine the         * the total amount of SDRAM installed.  SDRAM bank 1 is always         * used on Spruce, and the starting address is always 0x00000000.         * Read MB1EA and add 1MB to it to get the size of bank 1.         * If the SDRAM DIMM is double sided, the bit in MBEN for bank 2 will         * be set.  If this is true just double the total SDRAM size.         */        sysOutLong(MEMCFGADR, MB1EA);        memSize = sysInLong(MEMCFGDATA);        memSize += 0x100000;                         /* add 1MB */        sysOutLong(MEMCFGADR, MBEN);        if (sysInLong(MEMCFGDATA) & MBEN_BANK2)            memSize = memSize * 2;                 /* SDRAM bank 2 is enabled */        physTop = (char *)memSize;#else        /* Don't do autosizing, if size is given */        physTop = (char *)(LOCAL_MEM_LOCAL_ADRS + LOCAL_MEM_SIZE);#endif /* LOCAL_MEM_AUTOSIZE */        }    return physTop;    }/********************************************************************************* sysMemTop - get the address of the top of VxWorks memory** This routine returns a pointer to the first byte of memory not* controlled or used by VxWorks.** The user can reserve memory space by defining the macro USER_RESERVED_MEM* in config.h.  This routine returns the address of the reserved memory* area.  The value of USER_RESERVED_MEM is in bytes.** RETURNS: The address of the top of VxWorks memory.*/char * sysMemTop    (    void    )    {    static char * memTop = NULL;    if (memTop == NULL)        {        memTop = sysPhysMemTop () - USER_RESERVED_MEM;        }    return memTop;    }/********************************************************************************* sysToMonitor - transfer control to the ROM monitor** This routine transfers control to the ROM monitor.  Normally, it is called* only by reboot()--which services ^X--and by bus errors at interrupt level.* However, in some circumstances, the user may wish to introduce a* <startType> to enable special boot ROM facilities.** The entry point for a warm boot is defined by the macro ROM_WARM_ADRS* in config.h.  We do an absolute jump to this address to enter the* ROM code.** RETURNS: Does not return.*/STATUS sysToMonitor    (    int startType    /* parameter passed to ROM to tell it how to boot */    )    {    FUNCPTR pRom = (FUNCPTR) (ROM_WARM_ADRS);    intLock ();                 /* disable interrupts */    cacheDisable (0);           /* Disable the Instruction Cache */    cacheDisable (1);           /* Disable the Data Cache */    sysHwInit ();               /* disable all sub systems to a quiet state */    vxMsrSet (0);               /* Clear the MSR */    (*pRom) (startType);        /* jump to romInit.s */    return (OK);                /* in case we continue from ROM monitor */    }/******************************************************************************** sysProcNumGet - get the processor number** This routine returns the processor number for the CPU board, which is* set with sysProcNumSet().** RETURNS: The processor number for the CPU board.** SEE ALSO: sysProcNumSet()*/int sysProcNumGet    (    void    )    {    return (sysProcNum);    }/******************************************************************************** sysProcNumSet - set the processor number** This routine sets the processor number for the CPU board.  Processor numbers* should be unique on a single backplane.** For bus systems, it is assumes that processor 0 is the bus master and* exports its memory to the bus.** RETURNS: N/A** SEE ALSO: sysProcNumGet()*/void sysProcNumSet    (    int procNum                 /* processor number */    )    {    sysProcNum = procNum;    }/********************************************************************************* sysCpuCheck - confirm the CPU type** This routine validates the cpu type.  If the wrong cpu type is discovered* a message is printed using the serial channel in polled mode.** RETURNS: N/A.*/void sysCpuCheck (void)    {#if     (CPU == PPC604)    int msgSize;    int msgIx;    SIO_CHAN * pSioChan;        /* serial I/O channel */    /*     * Check for a valid CPU type;  If one is found, just return.     * 603 kernels run OK on 604's, but 604 kernels need to check.     * Also prevent recursive loop with sysHwInit() and sysToMonitor().     */    if (sysInCpuCheck                       ||        (CPU_TYPE == CPU_TYPE_740_750)      ||        (CPU_TYPE == CPU_TYPE_740L_750L)    ||        (CPU_TYPE == CPU_TYPE_740L_750L_2)  ||        (CPU_TYPE == CPU_TYPE_740L_750L_3)  ||        (CPU_TYPE == CPU_TYPE_750CX)        ||        (CPU_TYPE == CPU_TYPE_750FX)        ||        (CPU_TYPE == CPU_TYPE_750FX_7K)     ||	(((CPU_TYPE >> 16) & 0xfff0) == CPU_FAMILY_750FX))        {        return;        }    sysInCpuCheck = TRUE;    /*     * Invalid CPU type; print error message and terminate.     * Check size of wrongCpuPvr[] above if changing this.     */    sprintf(wrongCpuPvr, "[PVR=%08x]!\r\n", vxPvrGet());    sysSerialHwInit ();    pSioChan = sysSerialChanGet (0);    sioIoctl (pSioChan, SIO_MODE_SET, (void *) SIO_MODE_POLL);    msgSize = strlen (wrongCpuMsg);    for (msgIx = 0; msgIx < msgSize; msgIx++)        {        while (sioPollOutput (pSioChan, wrongCpuMsg[msgIx]) == EAGAIN);        }    /*     * Include the final NULL byte here, in case sysToMonitor() shuts     * down the I/O before the last-written byte actually makes it     * onto the line.  (Such disappearances have been observed.)     */    msgSize = strlen (wrongCpuPvr) + 1;    for (msgIx = 0; msgIx < msgSize; msgIx++)        {        while (sioPollOutput (pSioChan, wrongCpuPvr[msgIx]) == EAGAIN);        }    sysToMonitor (BOOT_NO_AUTOBOOT);#endif /* CPU == PPC604 */    }/********************************************************************************* sysGetBusSpd - gets the speed of the 6xx/7xx bus** This routine uses the FPGA on the Spruce board to determine the speed at* which the Processor bus is operating.* If the FPGA reg says the Spruce board is using an external clock source,* we will assume it is an 83.33MHz source for faster rated CPC700s.* Otherwise, check to see if the bus speed is 66.66MHz or 60MHz.** RETURNS: N/A.*/int sysGetBusSpd    (    void    )    {    UCHAR  fpga_reg;    UINT32 cpu_bus_freq;    fpga_reg = sysInByte(FPGA_REG_A);    if (fpga_reg & UART_CLK_EXT)            cpu_bus_freq = 83333333;    /* 83MHz */    else        {        if (fpga_reg & UART_CLK_33)            cpu_bus_freq = 66666666;    /* 66MHz */        else            cpu_bus_freq = 60000000;    /* 60MHz */        }    return(cpu_bus_freq);    }/********************************************************************************* sysLocalDelay - delay of <ms_delay> milliseconds used before kernel is up*** RETURNS: N/A.*/void sysLocalDelay    (    UINT32 ms_delay    )    {    UINT32 timebase_freq;    UINT32 start_upper;    UINT32 start_lower;    UINT32 end_upper;    UINT32 end_lower;    UINT32 upper;    UINT32 lower;    UINT32 delay;    int timesup = 0;    /*     *  get the frequency that the timebase operates at     */    timebase_freq = sysGetBusSpd() / 4;    /*     *  Read the timebase twice to start     */    vxTimeBaseGet (&start_upper, &start_lower);    vxTimeBaseGet (&end_upper, &end_lower);    while (timesup == 0)        {        /*         * Determine if the delay has been long enough         */        upper = end_upper - start_upper;        if (start_lower > end_lower)            upper--;        lower=end_lower - start_lower;        delay =  1000 * upper * (0xFFFFFFFF / timebase_freq);        delay += lower / (timebase_freq / 1000);        if (delay > ms_delay)            {            timesup = 1;            }            else            {            vxTimeBaseGet (&end_upper, &end_lower);            }        }    return;    }void sysDelay(void) ;void sysMsDelay(UINT delay) ;/******************************************************************************** sysDelay - delay for approximately one millisecond** Delay for approximately one milli-second.** RETURNS: N/A*/void sysDelay (void)    {    sysLocalDelay(1);#if 0    sysMsDelay(1) ;#endif    }#if 1/******************************************************************************** sysMsDelay - delay for the specified amount of time (MS)** This routine will delay for the specified amount of time by counting* decrementer ticks.** This routine is not dependent on a particular rollover value for* the decrementer, it should work no matter what the rollover* value is.** A small amount of count may be lost at the rollover point resulting in* the sysMsDelay() causing a slightly longer delay than requested.** This routine will produce incorrect results if the delay time requested* requires a count larger than 0xffffffff to hold the decrementer* elapsed tick count.  For a System Bus Speed of 67 MHZ this amounts to* about 258 seconds.** RETURNS: N/A*//* ZZZZZZZZZZZZ */#define DELTA(a,b) (abs((int)a - (int)b))void sysMsDelay    (    UINT        delay                   /* length of time in MS to delay */    )    {    register UINT oldval;               /* decrementer value */    register UINT newval;               /* decrementer value */    register UINT totalDelta;           /* Dec. delta for entire delay period */    register UINT decElapsed;           /* cumulative decrementer ticks */    /*     * Calculate delta of decrementer ticks for desired elapsed time.     * The macro DEC_CLOCK_FREQ MUST REFLECT THE PROPER 6xx BUS SPEED.     */    totalDelta = ((DEC_CLOCK_FREQ / 4) / 1000) * delay;    /*     * Now keep grabbing decrementer value and incrementing "decElapsed" until     * we hit the desired delay value.  Compensate for the fact that we may     * read the decrementer at 0xffffffff before the interrupt service     * routine has a chance to set in the rollover value.     */    decElapsed = 0;    oldval = vxDecGet ();    while (decElapsed < totalDelta)        {        newval = vxDecGet ();        if ( DELTA(oldval,newval) < 1000 )            decElapsed += DELTA(oldval,newval);  /* no rollover */        else            if (newval > oldval)                decElapsed += abs((int)oldval);  /* rollover */        oldval = newval;        }    }#endif

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -