📄 sysend.c
字号:
/* sysEnd.c - system configuration module for END devices */
/* Copyright 1984-1999 Wind River Systems, Inc. */
/* Copyright 1999-2000 Motorola, Inc., All Rights Reserved */
/*
modification history
--------------------
01a,24apr00,rhk Created (from version 01c of mv5100/sysEnd.c).
*/
/*
DESCRIPTION
This is the WRS-supplied configuration module for the VxWorks
END drivers. It performs the dynamic parameterization
specific to the End drivers. This technique of 'just-in-time'
parameterization allows driver parameter values to be declared as
any other defined constants rather than as static strings.
*/
#if (defined(INCLUDE_NETWORK) && defined (INCLUDE_END))
/* includes */
#include "vxWorks.h"
#include "stdio.h"
#include "stdlib.h"
#include "string.h"
#include "end.h"
#include "config.h"
#include "./pci/pciAutoConfigLib.h"
#include "drv/pci/pciConfigLib.h"
/* defines */
#ifdef INCLUDE_SECONDARY_ENET
#define NUM_END_DEVICES 2
#else
#define NUM_END_DEVICES 1
#endif /* INCLUDE_SECONDARY_ENET */
/* forward declarations */
/* locals */
typedef struct endInfo
{
PCI_ID pciId;
UINT32 bar0Csr;
UINT32 bar1Csr;
UINT8 irqnum;
UINT8 irqvec;
} endInfoType;
LOCAL endInfoType endDevices[NUM_END_DEVICES];
LOCAL char dbgMsg[100];
LOCAL initUnit = 0; /* initialization unit - not sent by end interface */
/* imports */
IMPORT END_OBJ* i82559DrvEndLoad (char *);
IMPORT void sysDebugMsg (char * str, UINT32 recovery);
/******************************************************************************
*
* sysEndLoad - create load string and load the END devices.
*
* This routine loads the END devices with initial parameters.
*
* RETURNS: pointer to END object or ERROR.
*
* SEE ALSO: driver xxxEndLoad() functions.
*/
END_OBJ * sysEndLoad
(
char * pParamStr, /* ptr to initialization parameter string */
void * unused /* unused optional argument */
)
{
/*
* The End driver END_LOAD_STRING should be:
* The format of the parameter string is:
*
* "<device_addr>:<PCI_addr>:<ivec>:<ilevel>:<num_rds>:<num_tds>:
* <mem_base>:<mem_size>:<user_flags>"
*
* Note that unit number is prepended in muxDevLoad, so we
* don't put it here!
*/
char * cp;
char paramStr [END_INIT_STR_MAX]; /* end.h */
END_OBJ * pEnd = (END_OBJ *)NULL;
UINT32 unit = 0;
char unitString[3];
/* read PCI configuration and initialize endDevices[] */
sysPciInit ();
if (strlen (pParamStr) == 0)
{
/*
* muxDevLoad() calls us twice. If the string is
* zero length, then this is the first time through
* this routine, so we just return.
*/
switch (endDevices[initUnit].pciId.devVend)
{
case PCI_ID_LN_I82559:
case PCI_ID_LN_I82559ER:
pEnd = i82559DrvEndLoad (pParamStr);
break;
default:
sprintf(dbgMsg, "Unknown End device %x unit %d\r\n",
endDevices[initUnit].pciId.devVend, initUnit);
/*sysDebugMsg(dbgMsg, 0);*/
return ((END_OBJ *)NULL);
}
initUnit++;
/* never go past the end of the list */
if (initUnit == NUM_END_DEVICES)
initUnit = 0;
}
else
{
/*
* On the second pass though here, we actually create
* the initialization parameter string on the fly.
* Note that we will be handed our unit number on the
* second pass through and we need to preserve that information.
* So we use the unit number handed from the input string.
*/
cp = strcpy (paramStr, pParamStr); /* cp points to paramStr */
unitString[0] = paramStr[0];
unitString[1] = '\0';
unit = atoi(unitString);
/* Now, we advance cp, by finding the end the string */
cp += strlen (paramStr);
/* finish off the initialization parameter string */
switch (endDevices[unit].pciId.devVend)
{
case PCI_ID_LN_I82559:
case PCI_ID_LN_I82559ER:
sprintf (cp, "%d:%d:0x%x:0x%x:0x%x:0x%x:0x%x:0x%x:0x%x:0x%x",
unit,
0,
endDevices[unit].pciId.loc.bus,
endDevices[unit].pciId.loc.device,
endDevices[unit].pciId.loc.function,
endDevices[unit].irqvec,/*PCI_82559_INT_VEC,*/
endDevices[unit].irqnum,/*PCI_82559_INT_VEC,*/
endDevices[unit].bar1Csr, /* device io base */
(UINT) PCI_SLV_MEM_BUS, /* pciMemBase */
0); /* user flags */
if ((pEnd = i82559DrvEndLoad (paramStr)) == (END_OBJ *)ERROR)
{
sprintf(dbgMsg, "Failed i82559DrvEndLoad.\r\n");
/*sysDebugMsg(dbgMsg, 0);*/
return ((END_OBJ *)NULL);
}
break;
default:
sprintf(dbgMsg, "Unknown End device %x unit %d\r\n",
endDevices[unit].pciId.devVend, unit);
/*sysDebugMsg(dbgMsg, 0);*/
return ((END_OBJ *)NULL);
}
}
return (pEnd);
}
/*******************************************************************************
*
* sysPciInit - prepare LAN adapters for initialization
*
* This routine finds the PCI device, and maps its memory and IO address.
*
* RETURNS: N/A
*/
STATUS sysPciInit (void)
{
UINT32 pciBus;
UINT32 unit = 0;
endDevices[0].pciId.loc.device = PCI_IDSEL_PRI_LAN;
/* limit search to bus 0 */
pciBus = 0;
#ifdef INCLUDE_SECONDARY_ENET
for (;unit < NUM_END_DEVICES; unit++)
{
if (unit)
endDevices[unit].pciId.loc.device = PCI_IDSEL_SEC_LAN;
#endif /* INCLUDE_SECONDARY_ENET */
endDevices[unit].pciId.loc.bus = pciBus;
pciConfigInLong (pciBus, endDevices[unit].pciId.loc.device,
0, PCI_CFG_VENDOR_ID,
&(endDevices[unit].pciId.devVend));
/* get memory base address, IO base address, and interrupt line */
pciConfigInLong (endDevices[unit].pciId.loc.bus,
endDevices[unit].pciId.loc.device,
endDevices[unit].pciId.loc.function,
PCI_CFG_BASE_ADDRESS_0, &(endDevices[unit].bar0Csr));
pciConfigInLong (endDevices[unit].pciId.loc.bus,
endDevices[unit].pciId.loc.device,
endDevices[unit].pciId.loc.function,
PCI_CFG_BASE_ADDRESS_1, &(endDevices[unit].bar1Csr));
pciConfigInByte (endDevices[unit].pciId.loc.bus,
endDevices[unit].pciId.loc.device,
endDevices[unit].pciId.loc.function,
PCI_CFG_DEV_INT_LINE, &(endDevices[unit].irqvec));
endDevices[unit].irqnum = endDevices[unit].irqvec;
switch (endDevices[unit].pciId.devVend)
{
case PCI_ID_LN_I82559:
case PCI_ID_LN_I82559ER:
/* convert Memory base addresses from PCI space to CPU space */
endDevices[unit].bar0Csr = TRANSLATE(
(endDevices[unit].bar0Csr &
PCI_MEMBASE_MASK),
PCI_MSTR_MEMIO_BUS,
PCI_MSTR_MEMIO_LOCAL);
/* convert I/O base addresses from PCI space to CPU space */
endDevices[unit].bar1Csr = TRANSLATE(
(endDevices[unit].bar1Csr &
PCI_IOBASE_MASK),
PCI_MSTR_IO_BUS,PCI_MSTR_IO_LOCAL);
break;
#ifdef INCLUDE_DEC_END
case PCI_ID_LN_DEC21040:
case PCI_ID_LN_DEC21140:
case PCI_ID_LN_DEC21143:
/* convert I/O and Memory base from PCI space to CPU space */
endDevices[unit].bar0Csr = TRANSLATE(
(endDevices[unit].bar0Csr &
PCI_IOBASE_MASK),
PCI_MSTR_IO_BUS,PCI_MSTR_IO_LOCAL);
endDevices[unit].bar1Csr = TRANSLATE(
(endDevices[unit].bar1Csr &
PCI_MEMBASE_MASK),
PCI_MSTR_MEMIO_BUS,
PCI_MSTR_MEMIO_LOCAL);
if (endDevices[unit].pciId.devVend == PCI_ID_LN_DEC21143)
{
/* disable sleep mode */
pciConfigOutByte (endDevices[unit].pciId.loc.bus,
endDevices[unit].pciId.loc.device,
endDevices[unit].pciId.loc.function,
PCI_CFG_MODE,
SLEEP_MODE_DIS);
pciConfigOutLong (endDevices[unit].pciId.loc.bus,
endDevices[unit].pciId.loc.device,
endDevices[unit].pciId.loc.function,
PCI_CFG_21143_DA, 0 );
}
break;
#endif /* INCLUDE_DEC_END */
default:
sprintf(dbgMsg, "Unknown End device %x unit %d\r\n",
endDevices[unit].pciId.devVend, unit);
/*sysDebugMsg(dbgMsg, 0);*/
break;
}
#ifdef INCLUDE_SECONDARY_ENET
}
#endif /* INCLUDE_SECONDARY_ENET */
return (OK);
}
/*******************************************************************************
*
* sysDec21x40EnetAddrGet - gets the ethernet address from the ROM register
*
* This routine returns ERROR. It is legacy and should never be called.
*
* RETURNS: ERROR
*/
STATUS sysDec21x40EnetAddrGet
(
)
{
return (ERROR);
}
#endif /* defined(INCLUDE_NETWORK) && defined (INCLUDE_END) */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -