2386 lines
65 KiB
C
2386 lines
65 KiB
C
//
|
||
// Pcimac.c - Main file for pcimac miniport wan driver
|
||
//
|
||
//
|
||
//
|
||
//
|
||
#include <ndis.h>
|
||
#include <ndiswan.h>
|
||
#include <mytypes.h>
|
||
#include <mydefs.h>
|
||
#include <opcodes.h>
|
||
#include <disp.h>
|
||
#include <adapter.h>
|
||
#include <util.h>
|
||
#include <idd.h>
|
||
#include <mtl.h>
|
||
#include <cm.h>
|
||
#include <tapioid.h>
|
||
#include <res.h>
|
||
#include <trc.h>
|
||
#include <io.h>
|
||
|
||
#include <ansihelp.h>
|
||
|
||
|
||
/* driver global vars */
|
||
DRIVER_BLOCK Pcimac;
|
||
|
||
ULONG DigiDebugLevel = ( DIGIERRORS | DIGIBUGCHECK | DIGIINIT );
|
||
|
||
ULONG DigiDontLoadDriver = FALSE;
|
||
|
||
USHORT MCAIOAddressTable[] = { 0x108, 0x118,
|
||
0x128, 0x208,
|
||
0x228, 0x308,
|
||
0x328, 0 };
|
||
|
||
#if !BINARY_COMPATIBLE
|
||
/* store location for prev. ioctl handler */
|
||
NTSTATUS (*PrevIoctl)(DEVICE_OBJECT* DeviceObject, IRP* Irp) = NULL;
|
||
#endif
|
||
|
||
/* forward for external name manager */
|
||
VOID BindName(ADAPTER *Adapter, BOOL create);
|
||
|
||
//VOID RegistryInit (VOID);
|
||
//VOID NdisTapiRequest(PNDIS_STATUS, NDIS_HANDLE, PNDIS_REQUEST);
|
||
|
||
ULONG
|
||
GetBaseConfigParams(
|
||
CONFIGPARAM *ConfigParam,
|
||
CHAR *Key
|
||
);
|
||
|
||
|
||
ULONG
|
||
GetLineConfigParams(
|
||
CONFIGPARAM *ConfigParam,
|
||
ULONG LineNumber,
|
||
CHAR *Key
|
||
);
|
||
|
||
ULONG
|
||
GetLTermConfigParams(
|
||
CONFIGPARAM *ConfigParam,
|
||
ULONG LineNumber,
|
||
ULONG LTermNumber,
|
||
CHAR *Key
|
||
);
|
||
|
||
VOID
|
||
IdpGetEaddrFromNvram(
|
||
IDD *idd,
|
||
CM *cm,
|
||
USHORT Line,
|
||
USHORT LineIndex
|
||
);
|
||
|
||
VOID
|
||
AdpGetEaddrFromNvram(
|
||
IDD *idd,
|
||
CM *cm,
|
||
USHORT Line,
|
||
USHORT LineIndex
|
||
);
|
||
|
||
|
||
NTSTATUS PcimacInitMCA( NDIS_HANDLE AdapterHandle,
|
||
PULONG BaseIO,
|
||
PULONG BaseMemory,
|
||
ULONG SlotNumber );
|
||
|
||
|
||
NTSTATUS DriverEntry( IN PDRIVER_OBJECT DriverObject,
|
||
IN PUNICODE_STRING RegistryPath );
|
||
|
||
/* driver entry point */
|
||
#pragma NDIS_INIT_FUNCTION( DriverEntry )
|
||
NTSTATUS DriverEntry( PDRIVER_OBJECT DriverObject,
|
||
PUNICODE_STRING RegistryPath )
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
Entry point for loading driver.
|
||
|
||
Arguments:
|
||
|
||
DriverObject - Pointer to this drivers object.
|
||
|
||
RegistryPath - Pointer to a unicode string which points to this
|
||
drivers registry entry.
|
||
|
||
Return Value:
|
||
|
||
STATUS_SUCCESS - If the driver was successfully loaded, otherwise,
|
||
a value which indicates why it wasn't able to load.
|
||
|
||
|
||
--*/
|
||
{
|
||
ULONG RetVal, n, m;
|
||
|
||
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
|
||
|
||
NDIS_HANDLE NdisWrapperHandle;
|
||
|
||
NDIS_MINIPORT_CHARACTERISTICS MiniportChars;
|
||
|
||
PWCHAR path;
|
||
ULONG DebugLevel;
|
||
ULONG zero = 0;
|
||
ULONG shouldBreak = 0;
|
||
#if !BINARY_COMPATIBLE
|
||
ULONG defaultMemPrintFlags=MEM_PRINT_FLAG_FILE;
|
||
|
||
RTL_QUERY_REGISTRY_TABLE paramTable[5];
|
||
|
||
//
|
||
// First, read the registry to determine some initial information.
|
||
//
|
||
DigiInitMem( 'irbD' );
|
||
|
||
if( path = DigiAllocMem( PagedPool,
|
||
RegistryPath->Length+sizeof(WCHAR) ))
|
||
{
|
||
RtlZeroMemory( ¶mTable[0], sizeof(paramTable) );
|
||
RtlZeroMemory( path, RegistryPath->Length+sizeof(WCHAR) );
|
||
RtlMoveMemory( path, RegistryPath->Buffer, RegistryPath->Length );
|
||
|
||
paramTable[0].Flags = RTL_QUERY_REGISTRY_DIRECT;
|
||
paramTable[0].Name = L"DigiBreakOnEntry";
|
||
paramTable[0].EntryContext = &shouldBreak;
|
||
paramTable[0].DefaultType = REG_DWORD;
|
||
paramTable[0].DefaultData = &zero;
|
||
paramTable[0].DefaultLength = sizeof(ULONG);
|
||
|
||
paramTable[1].Flags = RTL_QUERY_REGISTRY_DIRECT;
|
||
paramTable[1].Name = L"DigiDebugLevel";
|
||
paramTable[1].EntryContext = &DebugLevel;
|
||
paramTable[1].DefaultType = REG_DWORD;
|
||
paramTable[1].DefaultData = &DigiDebugLevel;
|
||
paramTable[1].DefaultLength = sizeof(ULONG);
|
||
|
||
paramTable[2].Flags = RTL_QUERY_REGISTRY_DIRECT;
|
||
paramTable[2].Name = L"DigiPrintFlags";
|
||
paramTable[2].EntryContext = &DigiPrintFlags;
|
||
paramTable[2].DefaultType = REG_DWORD;
|
||
paramTable[2].DefaultData = &defaultMemPrintFlags;
|
||
paramTable[2].DefaultLength = sizeof(ULONG);
|
||
|
||
if( !NT_SUCCESS(RtlQueryRegistryValues(
|
||
RTL_REGISTRY_ABSOLUTE | RTL_REGISTRY_OPTIONAL,
|
||
path,
|
||
¶mTable[0],
|
||
NULL, NULL )))
|
||
{
|
||
// No, don't break on entry if there isn't anything to over-
|
||
// ride.
|
||
shouldBreak = 0;
|
||
|
||
// Set debug level to what ever was compiled into the driver.
|
||
DebugLevel = DigiDebugLevel;
|
||
}
|
||
|
||
}
|
||
|
||
DigiDebugLevel = DebugLevel;
|
||
|
||
if( shouldBreak )
|
||
{
|
||
DbgBreakPoint();
|
||
}
|
||
|
||
if( DigiDontLoadDriver )
|
||
return( STATUS_CANCELLED );
|
||
|
||
MemPrintPreInitSettings( "\\SystemRoot\\digibri.log",
|
||
(65536 * 8) );
|
||
|
||
MemPrintInitialize();
|
||
|
||
#endif
|
||
|
||
NdisZeroMemory(&Pcimac, sizeof(DRIVER_BLOCK));
|
||
|
||
/* initialize ndis wrapper */
|
||
NdisMInitializeWrapper(&NdisWrapperHandle, DriverObject, RegistryPath, NULL);
|
||
|
||
/* initialize debug support */
|
||
D_LOG(DIGIINIT, ("PCIMAC WanMiniport NT Driver, Copyright Digi Intl. Inc, 1992-1994\n"));
|
||
D_LOG(DIGIINIT, ("DriverObject: 0x%x\n", DriverObject));
|
||
D_LOG(DIGIINIT, ("RegisteryPath: 0x%x\n", RegistryPath));
|
||
D_LOG(DIGIINIT, ("WrapperHandle: 0x%x\n", NdisWrapperHandle));
|
||
|
||
Pcimac.NdisWrapperHandle = NdisWrapperHandle;
|
||
|
||
NdisAllocateSpinLock (&Pcimac.lock);
|
||
|
||
/* initialize classes */
|
||
if ((RetVal = idd_init()) != IDD_E_SUCC)
|
||
goto exit_idd_error;
|
||
|
||
if ((RetVal = cm_init()) != CM_E_SUCC)
|
||
goto exit_cm_error;
|
||
|
||
if ((RetVal = res_init()) != RES_E_SUCC)
|
||
goto exit_res_error;
|
||
|
||
NdisZeroMemory(&MiniportChars,
|
||
sizeof(NDIS_MINIPORT_CHARACTERISTICS));
|
||
|
||
MiniportChars.MajorNdisVersion = NDIS_MAJOR_VER;
|
||
MiniportChars.MinorNdisVersion = NDIS_MINOR_VER;
|
||
MiniportChars.Reserved = NDIS_USE_WAN_WRAPPER;
|
||
MiniportChars.CheckForHangHandler = PcimacCheckForHang;
|
||
MiniportChars.DisableInterruptHandler = NULL;
|
||
MiniportChars.EnableInterruptHandler = NULL;
|
||
MiniportChars.HaltHandler = PcimacHalt;
|
||
MiniportChars.HandleInterruptHandler = NULL;
|
||
MiniportChars.InitializeHandler = PcimacInitialize;
|
||
MiniportChars.ISRHandler = NULL;
|
||
MiniportChars.QueryInformationHandler = PcimacSetQueryInfo;
|
||
MiniportChars.ReconfigureHandler = PcimacReconfigure;
|
||
MiniportChars.ResetHandler = PcimacReset;
|
||
MiniportChars.WanSendHandler = PcimacSend;
|
||
MiniportChars.SetInformationHandler = PcimacSetQueryInfo;
|
||
MiniportChars.WanTransferDataHandler = NULL;
|
||
|
||
NdisMRegisterMiniport (NdisWrapperHandle,
|
||
(PNDIS_MINIPORT_CHARACTERISTICS)&MiniportChars,
|
||
sizeof(MiniportChars));
|
||
|
||
if (!EnumAdaptersInSystem())
|
||
goto exit_event_error;
|
||
|
||
/* initialize ioctl filter */
|
||
#if !BINARY_COMPATIBLE
|
||
PrevIoctl = DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL];
|
||
DriverObject->MajorFunction[IRP_MJ_DEVICE_CONTROL] = PcimacIoctl;
|
||
#endif
|
||
|
||
//
|
||
// get an adapter to create a binding I/O name binding to
|
||
//
|
||
for( n = 0; n < MAX_ADAPTERS_IN_SYSTEM; n++ )
|
||
{
|
||
ADAPTER *Adapter = Pcimac.AdapterTbl[n];
|
||
|
||
if (Adapter)
|
||
{
|
||
/* create external name binding */
|
||
BindName(Adapter, TRUE);
|
||
break;
|
||
}
|
||
}
|
||
|
||
//
|
||
// turn off the trace on all idd's in the system
|
||
//
|
||
for (n = 0; n < MAX_ADAPTERS_IN_SYSTEM; n++)
|
||
{
|
||
ADAPTER *Adapter = Pcimac.AdapterTbl[n];
|
||
IDD_MSG msg;
|
||
|
||
if (Adapter)
|
||
{
|
||
for (m = 0; m < MAX_IDD_PER_ADAPTER; m++)
|
||
{
|
||
IDD *idd = Adapter->IddTbl[m];
|
||
|
||
if (idd)
|
||
{
|
||
/* issue idd command to stop trace */
|
||
NdisZeroMemory(&msg, sizeof(msg));
|
||
msg.opcode = CMD_TRC_OFF;
|
||
idd_send_msg(idd, &msg, IDD_PORT_CMD_TX, NULL, NULL);
|
||
}
|
||
}
|
||
}
|
||
}
|
||
|
||
D_LOG(D_EXIT, ("DriverEntry: exit success!\n"));
|
||
|
||
/* if successful here, done */
|
||
return(STATUS_SUCCESS);
|
||
|
||
exit_event_error:
|
||
D_LOG(D_ALWAYS, ("EventError!\n"));
|
||
res_term();
|
||
|
||
exit_res_error:
|
||
D_LOG(D_ALWAYS, ("ResError!\n"));
|
||
cm_term();
|
||
|
||
exit_cm_error:
|
||
exit_idd_error:
|
||
D_LOG(D_ALWAYS, ("CmIddError!\n"));
|
||
|
||
NdisFreeSpinLock(&Pcimac.lock);
|
||
|
||
NdisTerminateWrapper(Pcimac.NdisWrapperHandle, NULL);
|
||
|
||
#if !BINARY_COMPATIBLE
|
||
if( path )
|
||
{
|
||
DigiFreeMem(path);
|
||
}
|
||
|
||
MemPrintQuit();
|
||
#endif
|
||
|
||
return(NDIS_STATUS_FAILURE);
|
||
}
|
||
|
||
BOOLEAN
|
||
PcimacCheckForHang(
|
||
NDIS_HANDLE AdapterContext
|
||
)
|
||
{
|
||
ULONG n, IdpCounter = 0;
|
||
ADAPTER *Adapter = (ADAPTER *)AdapterContext;
|
||
BOOLEAN ReturnStatus = FALSE;
|
||
|
||
D_LOG(D_ENTRY, ("PcimacCheckForHang: Adapter: 0x%lx\n", AdapterContext));
|
||
|
||
//
|
||
// for all idd's that belong to this adpater
|
||
//
|
||
for (n = 0; Adapter->IddTbl[n] && n < MAX_IDD_PER_ADAPTER; n++)
|
||
{
|
||
IDD *idd = Adapter->IddTbl[n];
|
||
|
||
//
|
||
// see if this idd is dead
|
||
//
|
||
if (!idd || idd->state == IDD_S_SHUTDOWN)
|
||
continue;
|
||
|
||
IdpCounter++;
|
||
}
|
||
|
||
//
|
||
// if there are no idps alive on this adapter tell the wrapper
|
||
//
|
||
if (!IdpCounter)
|
||
ReturnStatus = TRUE;
|
||
|
||
D_LOG(D_ALWAYS, ("PcimacCheckForHang: ReturnStatus: %d\n", ReturnStatus));
|
||
|
||
return(ReturnStatus);
|
||
}
|
||
|
||
VOID
|
||
PcimacHalt(
|
||
NDIS_HANDLE AdapterContext
|
||
)
|
||
{
|
||
ULONG n;
|
||
ADAPTER *Adapter = (ADAPTER*)AdapterContext;
|
||
|
||
D_LOG(D_ENTRY, ("PcimacHalt: Adapter: 0x%lx\n", AdapterContext));
|
||
DbgPrint("PcimacHalt: Adapter: 0x%lx\n", AdapterContext);
|
||
|
||
//
|
||
// destroy cm objects
|
||
//
|
||
for (n = 0; n < MAX_CM_PER_ADAPTER; n++)
|
||
{
|
||
CM *cm = Adapter->CmTbl[n];
|
||
|
||
Adapter->CmTbl[n] = NULL;
|
||
|
||
if (cm)
|
||
cm_destroy(cm);
|
||
}
|
||
|
||
//
|
||
// destroy mtl objects
|
||
//
|
||
for (n = 0; n < MAX_MTL_PER_ADAPTER; n++)
|
||
{
|
||
MTL *mtl = Adapter->MtlTbl[n];
|
||
|
||
Adapter->MtlTbl[n] = NULL;
|
||
|
||
if (mtl)
|
||
mtl_destroy(mtl);
|
||
}
|
||
|
||
//
|
||
// destroy idd objects
|
||
//
|
||
for (n = 0; n < MAX_IDD_PER_ADAPTER; n++)
|
||
{
|
||
IDD *idd = (IDD*)Adapter->IddTbl[n];
|
||
|
||
Adapter->IddTbl[n] = NULL;
|
||
|
||
if (idd)
|
||
idd_destroy(idd);
|
||
}
|
||
|
||
/* delete external name binding */
|
||
BindName(Adapter, FALSE);
|
||
|
||
//
|
||
// deregister adapter
|
||
//
|
||
AdapterDestroy(Adapter);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(PcimacInitialize)
|
||
|
||
NDIS_STATUS PcimacInitialize( PNDIS_STATUS OpenErrorStatus,
|
||
PUINT SelectMediumIndex,
|
||
PNDIS_MEDIUM MediumArray,
|
||
UINT MediumArraySize,
|
||
NDIS_HANDLE AdapterHandle,
|
||
NDIS_HANDLE WrapperConfigurationContext )
|
||
{
|
||
ADAPTER *Adapter;
|
||
USHORT BoardType, NumberOfLines, NumberOfLTerms, BoardNumber;
|
||
ULONG BaseMem, BaseIO, n, m, l, IddStarted = 0;
|
||
PVOID VBaseMem, VBaseIO;
|
||
ANSI_STRING AnsiStr;
|
||
NDIS_STRING NdisStr;
|
||
CHAR DefName[128];
|
||
NDIS_STATUS RetVal = NDIS_STATUS_SUCCESS;
|
||
CONFIGPARAM ConfigParam;
|
||
NDIS_INTERFACE_TYPE NdisInterfaceType = NdisInterfaceIsa;
|
||
NDIS_PHYSICAL_ADDRESS MemPhyAddr;
|
||
NDIS_PHYSICAL_ADDRESS HighestAcceptableMax = NDIS_PHYSICAL_ADDRESS_CONST(-1, -1);
|
||
|
||
D_LOG(D_ENTRY, ("PcimacInitialize: AdapterHandle: 0x%x\n", AdapterHandle));
|
||
|
||
for (n = 0; n < MediumArraySize; n++)
|
||
if (MediumArray[n] == NdisMediumWan)
|
||
break;
|
||
|
||
if (n == MediumArraySize)
|
||
return(NDIS_STATUS_UNSUPPORTED_MEDIA);
|
||
|
||
*SelectMediumIndex = n;
|
||
|
||
//
|
||
// allocate control block for this adapter
|
||
//
|
||
NdisAllocateMemory((PVOID*)&Adapter,
|
||
sizeof(ADAPTER),
|
||
0,
|
||
HighestAcceptableMax);
|
||
if ( !Adapter)
|
||
{
|
||
D_LOG(D_ALWAYS, ("PcimacInitiailize: Adapter memory allocate failed!\n"));
|
||
return (NDIS_STATUS_ADAPTER_NOT_FOUND);
|
||
}
|
||
D_LOG(D_ALWAYS, ("PcimacInitialize: Allocated an Adapter: 0x%lx\n", Adapter));
|
||
NdisZeroMemory(Adapter, sizeof(ADAPTER));
|
||
|
||
//
|
||
// store adapter in global structure
|
||
//
|
||
for (n = 0; n < MAX_ADAPTERS_IN_SYSTEM; n++)
|
||
{
|
||
if (!Pcimac.AdapterTbl[n])
|
||
{
|
||
Pcimac.AdapterTbl[n] = Adapter;
|
||
Pcimac.NumberOfAdaptersInSystem++;
|
||
BoardNumber = (USHORT)n;
|
||
break;
|
||
}
|
||
}
|
||
|
||
//
|
||
// if no room destroy and leave
|
||
//
|
||
if (n >= MAX_ADAPTERS_IN_SYSTEM)
|
||
{
|
||
D_LOG(D_ALWAYS, ("PcimacInitialize: No room in Adapter Table\n"));
|
||
NdisFreeMemory(Adapter, sizeof(ADAPTER), 0);
|
||
return (NDIS_STATUS_ADAPTER_NOT_FOUND);
|
||
}
|
||
|
||
//
|
||
// set in driver access lock
|
||
//
|
||
// NdisAllocateSpinLock (&Adapter->InDriverLock);
|
||
|
||
|
||
//
|
||
// store adapter handle
|
||
//
|
||
Adapter->Handle = AdapterHandle;
|
||
|
||
//
|
||
// initialize adapter specific timers
|
||
//
|
||
NdisMInitializeTimer(&Adapter->IddPollTimer, Adapter->Handle, IddPollFunction, Adapter);
|
||
NdisMSetTimer(&Adapter->IddPollTimer, IDD_POLL_T);
|
||
|
||
NdisMInitializeTimer(&Adapter->MtlPollTimer, Adapter->Handle, MtlPollFunction, Adapter);
|
||
NdisMSetTimer(&Adapter->MtlPollTimer, MTL_POLL_T);
|
||
|
||
NdisMInitializeTimer(&Adapter->CmPollTimer, Adapter->Handle, CmPollFunction, Adapter);
|
||
NdisMSetTimer(&Adapter->CmPollTimer, CM_POLL_T);
|
||
|
||
ConfigParam.AdapterHandle = AdapterHandle;
|
||
|
||
//
|
||
// Open registry
|
||
//
|
||
NdisOpenConfiguration(&RetVal, &ConfigParam.ConfigHandle, WrapperConfigurationContext);
|
||
|
||
if (RetVal != NDIS_STATUS_SUCCESS)
|
||
{
|
||
D_LOG(D_ALWAYS, ("PcimacInitialize: Error Opening Config: RetVal: 0x%x\n", RetVal));
|
||
NdisWriteErrorLogEntry (AdapterHandle,
|
||
NDIS_ERROR_CODE_MISSING_CONFIGURATION_PARAMETER,
|
||
1,
|
||
0);
|
||
goto InitErrorExit;
|
||
}
|
||
|
||
//
|
||
// read registry board type
|
||
//
|
||
ConfigParam.StringLen = sizeof(ConfigParam.String);
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetBaseConfigParams(&ConfigParam, PCIMAC_KEY_BOARDTYPE))
|
||
goto InitErrorExit;
|
||
|
||
if (!__strncmp(ConfigParam.String, "PCIMAC4", 7))
|
||
BoardType = IDD_BT_PCIMAC4;
|
||
else if (!__strncmp(ConfigParam.String, "PCIMAC - ISA", 12))
|
||
BoardType = IDD_BT_PCIMAC;
|
||
else if (!__strncmp(ConfigParam.String, "PCIMAC - MC", 11))
|
||
{
|
||
NdisInterfaceType = NdisInterfaceMca;
|
||
BoardType = IDD_BT_MCIMAC;
|
||
}
|
||
else if (!__strncmp(ConfigParam.String, "DATAFIRE - ISA1U", 16))
|
||
BoardType = IDD_BT_DATAFIREU;
|
||
else if (!__strncmp(ConfigParam.String, "DATAFIRE - ISA1ST", 17))
|
||
BoardType = IDD_BT_DATAFIREST;
|
||
else if (!__strncmp(ConfigParam.String, "DATAFIRE - ISA4ST", 17))
|
||
BoardType = IDD_BT_DATAFIRE4ST;
|
||
else
|
||
{
|
||
D_LOG(D_ALWAYS, ("PcimacInitialize: Invalid BoardType: %s\n", ConfigParam.String));
|
||
goto InitErrorExit;
|
||
}
|
||
|
||
//
|
||
// save board type
|
||
//
|
||
Adapter->BoardType = BoardType;
|
||
|
||
//
|
||
// set miniport attributes (only isa for now)
|
||
//
|
||
NdisMSetAttributes( AdapterHandle, Adapter, FALSE, NdisInterfaceType );
|
||
|
||
//
|
||
// read registry base io
|
||
//
|
||
ConfigParam.StringLen = 0;
|
||
ConfigParam.ParamType = NdisParameterInteger;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetBaseConfigParams(&ConfigParam,PCIMAC_KEY_BASEIO))
|
||
goto InitErrorExit;
|
||
|
||
BaseIO = ConfigParam.Value;
|
||
|
||
if( NdisInterfaceType != NdisInterfaceMca )
|
||
{
|
||
//
|
||
// save base I/O for this adapter
|
||
//
|
||
Adapter->BaseIO = BaseIO;
|
||
|
||
}
|
||
else
|
||
{
|
||
//
|
||
// Must be a MCA adapter.
|
||
//
|
||
// Note, BaseIO should be the slot number for this adapter instance.
|
||
//
|
||
RetVal = PcimacInitMCA( AdapterHandle,
|
||
&Adapter->BaseIO,
|
||
&Adapter->BaseMem,
|
||
BaseIO );
|
||
|
||
BaseMem = Adapter->BaseMem;
|
||
BaseIO = Adapter->BaseIO;
|
||
|
||
if( RetVal != NDIS_STATUS_SUCCESS )
|
||
goto InitErrorExit;
|
||
|
||
}
|
||
|
||
//
|
||
// register I/O range
|
||
//
|
||
RetVal = NdisMRegisterIoPortRange(&VBaseIO,
|
||
AdapterHandle,
|
||
BaseIO,
|
||
8);
|
||
|
||
if (RetVal != NDIS_STATUS_SUCCESS)
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_BAD_IO_BASE_ADDRESS,
|
||
0);
|
||
goto InitErrorExit;
|
||
}
|
||
|
||
Adapter->VBaseIO = VBaseIO;
|
||
|
||
if( (BoardType != IDD_BT_DATAFIREU) &&
|
||
(BoardType != IDD_BT_DATAFIREST) &&
|
||
(BoardType != IDD_BT_DATAFIRE4ST) )
|
||
{
|
||
//
|
||
// This is a PCIMAC family of adapters
|
||
//
|
||
//
|
||
// read registry base mem
|
||
//
|
||
|
||
if( NdisInterfaceType != NdisInterfaceMca )
|
||
{
|
||
ConfigParam.StringLen = 0;
|
||
ConfigParam.ParamType = NdisParameterInteger;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if( !GetBaseConfigParams(&ConfigParam, PCIMAC_KEY_BASEMEM) )
|
||
goto InitErrorExit;
|
||
|
||
BaseMem = ConfigParam.Value;
|
||
|
||
//
|
||
// save base memory for this adapter
|
||
//
|
||
Adapter->BaseMem = BaseMem;
|
||
|
||
}
|
||
|
||
//
|
||
// since our adapters can share the same base memory we need to
|
||
// see if we have already mapped this memory range. if we have already
|
||
// mapped the memory once then save that previous value
|
||
//
|
||
for (n = 0; n < MAX_ADAPTERS_IN_SYSTEM; n++)
|
||
{
|
||
ADAPTER *PreviousAdapter = Pcimac.AdapterTbl[n];
|
||
|
||
//
|
||
// if this is a valid adapter, this is not the current adapter, and
|
||
// this adapter has the same shared memory address as the current
|
||
// adapter, then use this adapters mapped memory for the current
|
||
// adpaters mapped memory
|
||
//
|
||
if (PreviousAdapter &&
|
||
(PreviousAdapter != Adapter) &&
|
||
(PreviousAdapter->BaseMem == Adapter->BaseMem))
|
||
{
|
||
VBaseMem = PreviousAdapter->VBaseMem;
|
||
break;
|
||
}
|
||
}
|
||
|
||
//
|
||
// if we did not find a previous adapter with this memory range
|
||
// we need to map this memory range
|
||
//
|
||
if (n >= MAX_ADAPTERS_IN_SYSTEM)
|
||
{
|
||
//
|
||
// map our physical memory into virtual memory
|
||
//
|
||
NdisSetPhysicalAddressHigh(MemPhyAddr, 0);
|
||
NdisSetPhysicalAddressLow(MemPhyAddr, BaseMem);
|
||
|
||
RetVal = NdisMMapIoSpace(&VBaseMem,
|
||
AdapterHandle,
|
||
MemPhyAddr,
|
||
0x4000);
|
||
|
||
if (RetVal != NDIS_STATUS_SUCCESS)
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_RESOURCE_CONFLICT,
|
||
0);
|
||
goto InitErrorExit;
|
||
}
|
||
|
||
Adapter->VBaseMem = VBaseMem;
|
||
}
|
||
}
|
||
|
||
//
|
||
// read registry name
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = sizeof(Adapter->Name);
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetBaseConfigParams(&ConfigParam, PCIMAC_KEY_BOARDNAME))
|
||
goto InitErrorExit;
|
||
|
||
NdisMoveMemory( Adapter->Name,
|
||
ConfigParam.String,
|
||
ConfigParam.StringLen );
|
||
//
|
||
// read the number of lines for this board
|
||
//
|
||
ConfigParam.StringLen = 0;
|
||
ConfigParam.ParamType = NdisParameterInteger;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetBaseConfigParams(&ConfigParam, PCIMAC_KEY_NUMLINES))
|
||
NumberOfLines = (BoardType == IDD_BT_PCIMAC4) ? 4 : 1;
|
||
else
|
||
NumberOfLines = (USHORT)ConfigParam.Value;
|
||
|
||
//
|
||
// for number of lines
|
||
//
|
||
for (n = 0; n < NumberOfLines; n++)
|
||
{
|
||
IDD *idd;
|
||
|
||
//
|
||
// Create idd object
|
||
//
|
||
if (idd_create(&idd, BoardType) != IDD_E_SUCC)
|
||
{
|
||
NdisWriteErrorLogEntry (AdapterHandle,
|
||
NDIS_ERROR_CODE_OUT_OF_RESOURCES,
|
||
0);
|
||
|
||
goto InitErrorExit;
|
||
}
|
||
|
||
//
|
||
// store idd in idd table
|
||
//
|
||
for (l = 0; l < MAX_IDD_PER_ADAPTER; l++)
|
||
{
|
||
if (!Adapter->IddTbl[l])
|
||
{
|
||
Adapter->IddTbl[l] = idd;
|
||
break;
|
||
}
|
||
}
|
||
|
||
Adapter->NumberOfIddOnAdapter++;
|
||
|
||
//
|
||
// set idd physical base i/o and memory
|
||
//
|
||
idd->phw.base_io = BaseIO;
|
||
idd->phw.base_mem = BaseMem;
|
||
|
||
//
|
||
// set idd virtual base i/o and memory
|
||
//
|
||
idd->vhw.vbase_io = (ULONG)VBaseIO;
|
||
idd->vhw.vmem = VBaseMem;
|
||
|
||
//
|
||
// create an i/o resource manager for this idd
|
||
//
|
||
idd->res_io = res_create(RES_CLASS_IO, (ULONG)BaseIO);
|
||
|
||
//
|
||
// create a memory resource manager for this idd
|
||
//
|
||
idd->res_mem = res_create(RES_CLASS_MEM, (ULONG)BaseMem);
|
||
res_set_data(idd->res_mem, (ULONG)VBaseMem);
|
||
|
||
//
|
||
// save adapter handle
|
||
//
|
||
idd->adapter_handle = AdapterHandle;
|
||
|
||
//
|
||
// save the board number of this idd
|
||
//
|
||
idd->bnumber = BoardNumber;
|
||
|
||
//
|
||
// save the line number of this idd
|
||
//
|
||
// idd->bline = (USHORT)NumberOfLines - 1 - n;
|
||
idd->bline = (USHORT)n;
|
||
|
||
//
|
||
// save the board type that this idd belongs to
|
||
//
|
||
idd->btype = BoardType;
|
||
|
||
if(idd->CheckIO(idd))
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_BAD_IO_BASE_ADDRESS,
|
||
0);
|
||
goto InitErrorExit;
|
||
}
|
||
|
||
//
|
||
// read registry line name
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = sizeof(idd->name);
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetLineConfigParams(&ConfigParam, n, PCIMAC_KEY_LINENAME))
|
||
goto InitErrorExit;
|
||
|
||
sprintf(idd->name, "%s-%s", Adapter->Name, ConfigParam.String);
|
||
|
||
// NdisMoveMemory(idd->name,
|
||
// ConfigParam.String,
|
||
// ConfigParam.StringLen);
|
||
|
||
//
|
||
// read registry idp file name
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = sizeof(idd->phw.idp_bin);
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetLineConfigParams(&ConfigParam, n, PCIMAC_KEY_IDPFILENAME))
|
||
goto InitErrorExit;
|
||
|
||
NdisMoveMemory(idd->phw.idp_bin,
|
||
ConfigParam.String,
|
||
ConfigParam.StringLen);
|
||
|
||
|
||
//
|
||
// Try to open idp bin file
|
||
//
|
||
RtlInitAnsiString(&AnsiStr, idd->phw.idp_bin);
|
||
|
||
//
|
||
// allocate buffer and turn ansi to unicode
|
||
//
|
||
RtlAnsiStringToUnicodeString(&NdisStr, &AnsiStr, TRUE);
|
||
|
||
NdisOpenFile(&RetVal,
|
||
&idd->phw.fbin,
|
||
&idd->phw.fbin_len,
|
||
&NdisStr,
|
||
HighestAcceptableMax);
|
||
|
||
//
|
||
// free up unicode string buffer
|
||
//
|
||
RtlFreeUnicodeString(&NdisStr);
|
||
|
||
if (RetVal != NDIS_STATUS_SUCCESS)
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_UNSUPPORTED_CONFIGURATION,
|
||
0);
|
||
goto InitErrorExit;
|
||
}
|
||
|
||
//
|
||
// read registry switch style
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = 128;
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetLineConfigParams(&ConfigParam, n, PCIMAC_KEY_SWITCHSTYLE))
|
||
goto InitErrorExit;
|
||
|
||
//
|
||
// added to support the new switch styles
|
||
//
|
||
CmSetSwitchStyle(ConfigParam.String);
|
||
|
||
idd_add_def(idd, "q931.style", ConfigParam.String);
|
||
|
||
//
|
||
// read registry terminal management
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = 128;
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetLineConfigParams(&ConfigParam, n,
|
||
PCIMAC_KEY_TERMINALMANAGEMENT))
|
||
goto InitErrorExit;
|
||
|
||
idd_add_def(idd, "q931.tm", ConfigParam.String);
|
||
|
||
//
|
||
// read WaitForL3 value
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = 128;
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = FALSE;
|
||
if (!GetLineConfigParams(&ConfigParam, n,
|
||
PCIMAC_KEY_WAITFORL3))
|
||
strcpy(ConfigParam.String, "5");
|
||
|
||
idd_add_def(idd, "q931.wait_l3", ConfigParam.String);
|
||
|
||
//
|
||
// read registry logical terminals
|
||
//
|
||
ConfigParam.StringLen = 0;
|
||
ConfigParam.ParamType = NdisParameterInteger;
|
||
ConfigParam.MustBePresent = TRUE;
|
||
if (!GetLineConfigParams(&ConfigParam, n, PCIMAC_KEY_NUMLTERMS))
|
||
goto InitErrorExit;
|
||
|
||
NumberOfLTerms = (USHORT)ConfigParam.Value;
|
||
|
||
if (NumberOfLTerms > 1)
|
||
idd_add_def(idd, "dual_q931", "any");
|
||
|
||
//
|
||
// store number of lterms that this idd has
|
||
//
|
||
idd->CallInfo.NumLTerms = NumberOfLTerms;
|
||
|
||
//
|
||
// for each logical terminal
|
||
//
|
||
for (l = 0; l < NumberOfLTerms; l++)
|
||
{
|
||
//
|
||
// read registry tei
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = 128;
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = FALSE;
|
||
if (!GetLTermConfigParams(&ConfigParam, n, l, PCIMAC_KEY_TEI))
|
||
__strcpy(ConfigParam.String, "127");
|
||
|
||
NdisZeroMemory(DefName, sizeof(DefName));
|
||
sprintf(DefName, "q931.%d.tei", l);
|
||
idd_add_def(idd, DefName, ConfigParam.String);
|
||
|
||
//
|
||
// read registry spid
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = 128;
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = FALSE;
|
||
if (GetLTermConfigParams(&ConfigParam, n, l, PCIMAC_KEY_SPID))
|
||
{
|
||
CHAR TempVal[64];
|
||
ULONG i, j;
|
||
|
||
//
|
||
// remove any non digits except # & *
|
||
//
|
||
NdisZeroMemory(TempVal, sizeof(TempVal));
|
||
|
||
for (i = 0, j = 0; i < ConfigParam.StringLen; i++)
|
||
{
|
||
if ((ConfigParam.String[i] >= '0' && ConfigParam.String[i] <= '9') ||
|
||
ConfigParam.String[i] == '*' ||
|
||
ConfigParam.String[i] == '#')
|
||
{
|
||
TempVal[j++] = ConfigParam.String[i];
|
||
}
|
||
}
|
||
|
||
NdisZeroMemory(DefName, sizeof(DefName));
|
||
sprintf(DefName, "q931.%d.spid", l);
|
||
idd_add_def(idd, DefName, TempVal);
|
||
idd_add_def(idd, "q931.multipoint", "any");
|
||
}
|
||
|
||
//
|
||
// read registry address
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = 128;
|
||
ConfigParam.ParamType = NdisParameterString;
|
||
ConfigParam.MustBePresent = FALSE;
|
||
if (GetLTermConfigParams(&ConfigParam, n, l, PCIMAC_KEY_ADDRESS))
|
||
{
|
||
CHAR TempVal[64];
|
||
ULONG i, j;
|
||
|
||
//
|
||
// remove any non digits except # & *
|
||
//
|
||
NdisZeroMemory(TempVal, sizeof(TempVal));
|
||
|
||
for (i = 0, j = 0; i < ConfigParam.StringLen; i++)
|
||
{
|
||
if ((ConfigParam.String[i] >= '0' && ConfigParam.String[i] <= '9') ||
|
||
ConfigParam.String[i] == '*' ||
|
||
ConfigParam.String[i] == '#')
|
||
{
|
||
TempVal[j++] = ConfigParam.String[i];
|
||
}
|
||
}
|
||
|
||
NdisZeroMemory(DefName, sizeof(DefName));
|
||
sprintf(DefName, "q931.%d.addr", l);
|
||
idd_add_def(idd, DefName, TempVal);
|
||
}
|
||
|
||
//
|
||
// add code to read generic multistring at the lterm level
|
||
// Key is "LTermDefinitions" these will be added to
|
||
// the enviornment database
|
||
// each string will look like "name=value\0" should
|
||
// remove "=" and replace with '\0'
|
||
//
|
||
}
|
||
|
||
//
|
||
// add code to read generic multistring at the board level
|
||
// Key is "GenericDefines"
|
||
// each string will look like "name=value\0" should
|
||
// remove "=" and replace with '\0'
|
||
//
|
||
NdisZeroMemory(ConfigParam.String, sizeof(ConfigParam.String));
|
||
ConfigParam.StringLen = sizeof(ConfigParam.String);
|
||
ConfigParam.ParamType = NdisParameterMultiString;
|
||
ConfigParam.MustBePresent = FALSE;
|
||
if (GetBaseConfigParams(&ConfigParam, PCIMAC_KEY_GENERICDEFINES))
|
||
{
|
||
CHAR Name[50] = {0};
|
||
CHAR Value[50] = {0};
|
||
CHAR *StringPointer = ConfigParam.String;
|
||
|
||
while (__strlen(StringPointer))
|
||
{
|
||
//
|
||
// copy the name part of the generic define
|
||
//
|
||
__strcpy(Name, StringPointer);
|
||
|
||
D_LOG(D_ALWAYS, ("PcimacInitialize: GenericDefines: Name: %s\n", Name));
|
||
//
|
||
// push pointer over the name
|
||
//
|
||
StringPointer += __strlen(StringPointer);
|
||
|
||
//
|
||
// get over the null character
|
||
//
|
||
StringPointer += 1;
|
||
|
||
//
|
||
// copy the value part of the generic define
|
||
//
|
||
__strcpy(Value, StringPointer);
|
||
D_LOG(D_ALWAYS, ("PcimacInitialize: GenericDefines: Value: %s\n", Value));
|
||
|
||
idd_add_def(idd, Name, Value);
|
||
|
||
//
|
||
// push pointer over the value
|
||
//
|
||
StringPointer += __strlen(StringPointer);
|
||
|
||
//
|
||
// get over the null character
|
||
//
|
||
StringPointer += 1;
|
||
}
|
||
}
|
||
|
||
//
|
||
// startup idd
|
||
//
|
||
if (idd_startup(idd) != IDD_E_SUCC)
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_HARDWARE_FAILURE,
|
||
2,
|
||
(ULONG)idd->bnumber,
|
||
(ULONG)idd->bline);
|
||
idd_destroy(idd);
|
||
for (m = 0; m < MAX_IDD_PER_ADAPTER; m++)
|
||
if (Adapter->IddTbl[m] == idd)
|
||
Adapter->IddTbl[m] = NULL;
|
||
|
||
Adapter->NumberOfIddOnAdapter--;
|
||
continue;
|
||
}
|
||
|
||
//
|
||
// register handlers for idd
|
||
//
|
||
cm_register_idd(idd);
|
||
|
||
IddStarted++;
|
||
}
|
||
|
||
if (!IddStarted)
|
||
goto InitErrorExit;
|
||
|
||
|
||
for (n = 0; n < IddStarted; n++)
|
||
{
|
||
CM *cm;
|
||
MTL *mtl;
|
||
IDD *idd;
|
||
|
||
idd = Adapter->IddTbl[n];
|
||
|
||
//
|
||
// build two cm's and two mtl's per line
|
||
//
|
||
for (l = 0; l < 2; l++)
|
||
{
|
||
ULONG m;
|
||
|
||
//
|
||
// Allocate memory for cm object
|
||
//
|
||
if (cm_create(&cm, AdapterHandle) != CM_E_SUCC)
|
||
goto InitErrorExit;
|
||
|
||
for (m = 0; m < MAX_CM_PER_ADAPTER; m++)
|
||
{
|
||
if (!Adapter->CmTbl[m])
|
||
{
|
||
Adapter->CmTbl[m] = cm;
|
||
break;
|
||
}
|
||
}
|
||
|
||
//
|
||
// back pointer to adapter structure
|
||
//
|
||
cm->Adapter = Adapter;
|
||
|
||
//
|
||
// pointer to idd that belongs to this cm
|
||
//
|
||
cm->idd = idd;
|
||
|
||
//
|
||
// name cm object format: AdapterName-LineName-chan#
|
||
//
|
||
sprintf(cm->name,"%s-%d", idd->name, l);
|
||
|
||
//
|
||
// set local address, format: NetCard#-idd#-chan#
|
||
//
|
||
#if !BINARY_COMPATIBLE
|
||
sprintf( cm->LocalAddress, "%d-%d-%d",
|
||
atoi( &Adapter->Name[6] ),
|
||
(idd->bline * 2) + l,
|
||
0 );
|
||
#else
|
||
sprintf(cm->LocalAddress, "1-%d-%d", (idd->bline * 2) + l, 0);
|
||
#endif
|
||
|
||
//
|
||
// get ethernet addresses for this cm
|
||
//
|
||
if( (idd->btype == IDD_BT_DATAFIREU) ||
|
||
(idd->btype == IDD_BT_DATAFIREST) ||
|
||
(idd->btype == IDD_BT_DATAFIRE4ST) )
|
||
AdpGetEaddrFromNvram(idd, cm, (USHORT)n, (USHORT)l);
|
||
else
|
||
IdpGetEaddrFromNvram(idd, cm, (USHORT)n, (USHORT)l);
|
||
|
||
//
|
||
// Allocate memory for mtl object
|
||
//
|
||
if (mtl_create(&mtl, AdapterHandle) != MTL_E_SUCC)
|
||
goto InitErrorExit;
|
||
|
||
for (m = 0; m < MAX_MTL_PER_ADAPTER; m++)
|
||
{
|
||
if (!Adapter->MtlTbl[m])
|
||
{
|
||
Adapter->MtlTbl[m] = mtl;
|
||
break;
|
||
}
|
||
}
|
||
|
||
//
|
||
// back pointer to adapter structure
|
||
//
|
||
mtl->Adapter = Adapter;
|
||
|
||
//
|
||
// link between cm and mtl
|
||
//
|
||
cm->mtl = mtl;
|
||
mtl->cm = cm;
|
||
}
|
||
}
|
||
|
||
NdisCloseConfiguration(ConfigParam.ConfigHandle);
|
||
|
||
NdisMRegisterAdapterShutdownHandler(
|
||
AdapterHandle,
|
||
Adapter,
|
||
(PVOID)PcimacHalt
|
||
);
|
||
|
||
return (NDIS_STATUS_SUCCESS);
|
||
|
||
InitErrorExit:
|
||
NdisCloseConfiguration(ConfigParam.ConfigHandle);
|
||
|
||
//
|
||
// clean up all idd's allocated
|
||
//
|
||
for (l = 0; l < MAX_IDD_PER_ADAPTER; l++)
|
||
{
|
||
IDD *idd = Adapter->IddTbl[l];
|
||
|
||
//
|
||
// if memory has been mapped release
|
||
//
|
||
if (idd)
|
||
{
|
||
idd_destroy(idd);
|
||
Adapter->IddTbl[l] = NULL;
|
||
}
|
||
}
|
||
|
||
//
|
||
// clean up all cm's allocated
|
||
//
|
||
for (l = 0; l < MAX_CM_PER_ADAPTER; l++)
|
||
{
|
||
CM *cm = Adapter->CmTbl[l];
|
||
|
||
if (cm)
|
||
{
|
||
cm_destroy(cm);
|
||
Adapter->CmTbl[l] = NULL;
|
||
}
|
||
}
|
||
|
||
//
|
||
// clean up all mtl's allocated
|
||
//
|
||
for (l = 0; l < MAX_MTL_PER_ADAPTER; l++)
|
||
{
|
||
MTL *mtl = Adapter->MtlTbl[l];
|
||
|
||
if (mtl)
|
||
{
|
||
mtl_destroy(mtl);
|
||
Adapter->MtlTbl[l] = NULL;
|
||
}
|
||
}
|
||
|
||
//
|
||
// clean up adapter block allocated
|
||
//
|
||
AdapterDestroy(Adapter);
|
||
|
||
return (NDIS_STATUS_ADAPTER_NOT_FOUND);
|
||
} // end PcimacInitialize
|
||
|
||
NDIS_STATUS
|
||
PcimacSetQueryInfo(
|
||
NDIS_HANDLE AdapterContext,
|
||
NDIS_OID Oid,
|
||
PVOID InfoBuffer,
|
||
ULONG InfoBufferLen,
|
||
PULONG BytesReadWritten,
|
||
PULONG BytesNeeded
|
||
)
|
||
{
|
||
ULONG OidType;
|
||
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
|
||
|
||
D_LOG(D_ENTRY, ("PcimacSetQueryInfo: Adapter: 0x%lx, Oid: 0x%x\n", AdapterContext, Oid));
|
||
|
||
//
|
||
// get oid type
|
||
//
|
||
OidType = Oid & 0xFF000000;
|
||
|
||
switch (OidType)
|
||
{
|
||
case OID_WAN_INFO:
|
||
Status = WanOidProc(AdapterContext,
|
||
Oid,
|
||
InfoBuffer,
|
||
InfoBufferLen,
|
||
BytesReadWritten,
|
||
BytesNeeded);
|
||
break;
|
||
|
||
case OID_TAPI_INFO:
|
||
Status = TapiOidProc(AdapterContext,
|
||
Oid,
|
||
InfoBuffer,
|
||
InfoBufferLen,
|
||
BytesReadWritten,
|
||
BytesNeeded);
|
||
break;
|
||
|
||
|
||
case OID_GEN_INFO:
|
||
case OID_8023_INFO:
|
||
Status = LanOidProc(AdapterContext,
|
||
Oid,
|
||
InfoBuffer,
|
||
InfoBufferLen,
|
||
BytesReadWritten,
|
||
BytesNeeded);
|
||
break;
|
||
|
||
default:
|
||
Status = NDIS_STATUS_INVALID_OID;
|
||
break;
|
||
}
|
||
|
||
D_LOG(D_EXIT, ("PcimacSetQueryInfo: Status: 0x%x, BytesReadWritten: %d, BytesNeeded: %d\n", Status, *BytesReadWritten, *BytesNeeded));
|
||
return(Status);
|
||
}
|
||
|
||
NDIS_STATUS
|
||
PcimacReconfigure(
|
||
PNDIS_STATUS OpenErrorStatus,
|
||
NDIS_HANDLE AdapterContext,
|
||
NDIS_HANDLE WrapperConfigurationContext
|
||
)
|
||
{
|
||
D_LOG(D_ENTRY, ("PcimacReconfigure: Adapter: 0x%lx\n", AdapterContext));
|
||
//
|
||
// not supported for now
|
||
//
|
||
return(NDIS_STATUS_FAILURE);
|
||
}
|
||
|
||
NDIS_STATUS
|
||
PcimacReset(
|
||
PBOOLEAN AddressingReset,
|
||
NDIS_HANDLE AdapterContext
|
||
)
|
||
{
|
||
D_LOG(D_ENTRY, ("PcimacReset: Adapter: 0x%lx\n", AdapterContext));
|
||
|
||
return(NDIS_STATUS_HARD_ERRORS);
|
||
}
|
||
|
||
NDIS_STATUS
|
||
PcimacSend(
|
||
NDIS_HANDLE MacBindingHandle,
|
||
NDIS_HANDLE LinkContext,
|
||
PNDIS_WAN_PACKET WanPacket
|
||
)
|
||
{
|
||
MTL *mtl = (MTL*)LinkContext;
|
||
|
||
D_LOG(D_ENTRY, ("PcimacSend: Link: 0x%lx\n", mtl));
|
||
|
||
/* send packet */
|
||
mtl__tx_packet(mtl, WanPacket);
|
||
|
||
return(NDIS_STATUS_PENDING);
|
||
}
|
||
|
||
/* create/delete external name binding */
|
||
VOID
|
||
BindName(ADAPTER *Adapter, BOOL create)
|
||
{
|
||
#if !BINARY_COMPATIBLE
|
||
|
||
#define LINKNAME "\\DosDevices\\PCIMAC0"
|
||
UNICODE_STRING linkname, devname;
|
||
NTSTATUS stat;
|
||
CHAR name[128];
|
||
ANSI_STRING aname;
|
||
ANSI_STRING lname;
|
||
|
||
if (Adapter)
|
||
sprintf(name,"\\Device\\%s",Adapter->Name);
|
||
|
||
if ( !name )
|
||
sprintf(name,"\\Device\\Pcimac69");
|
||
|
||
D_LOG(D_ENTRY, ("BindName: LinkName: %s, NdisName: %s\n", LINKNAME, name));
|
||
|
||
/* convert to unicode string */
|
||
RtlInitAnsiString(&lname, LINKNAME);
|
||
stat = RtlAnsiStringToUnicodeString(&linkname, &lname, TRUE);
|
||
|
||
/* convert to unicode string */
|
||
RtlInitAnsiString(&aname, name);
|
||
stat = RtlAnsiStringToUnicodeString(&devname, &aname, TRUE);
|
||
|
||
/* create? */
|
||
if ( create )
|
||
{
|
||
UNICODE_STRING AtlasVName, AtlasVEntry;
|
||
|
||
RtlInitAnsiString( &aname, "DigiBRI" );
|
||
RtlAnsiStringToUnicodeString( &AtlasVName, &aname, TRUE );
|
||
|
||
RtlInitAnsiString( &aname, "DgBRIAtlas" );
|
||
RtlAnsiStringToUnicodeString( &AtlasVEntry, &aname, TRUE );
|
||
|
||
stat = DigiRegisterAtlasName( &devname,
|
||
&AtlasVName,
|
||
&AtlasVEntry );
|
||
|
||
if( NT_ERROR(stat) )
|
||
stat = IoCreateSymbolicLink (&linkname, &devname);
|
||
|
||
RtlFreeUnicodeString( &AtlasVName );
|
||
RtlFreeUnicodeString( &AtlasVEntry );
|
||
}
|
||
else /* delete */
|
||
stat = IoDeleteSymbolicLink (&linkname);
|
||
|
||
D_LOG(D_ENTRY, ("BindName: Operation: 0x%x, stat: 0x%x\n", create, stat));
|
||
|
||
RtlFreeUnicodeString(&devname);
|
||
RtlFreeUnicodeString(&linkname);
|
||
|
||
#endif
|
||
|
||
}
|
||
|
||
//
|
||
// Function commented out for change in how RAS picks up tapi name and address info
|
||
// This will help make the driver more portable.
|
||
//
|
||
//#pragma NDIS_INIT_FUNCTION(RegistryInit)
|
||
//
|
||
//VOID
|
||
//RegistryInit(VOID)
|
||
//{
|
||
// UNICODE_STRING AddressUnicodeString;
|
||
// UNICODE_STRING UnicodeString;
|
||
// ANSI_STRING AnsiString;
|
||
// PWCHAR AddressBuffer;
|
||
// NDIS_PHYSICAL_ADDRESS HighestAcceptableMax = NDIS_PHYSICAL_ADDRESS_CONST(-1, -1);
|
||
// ULONG l, m;
|
||
//
|
||
// NdisAllocateMemory((PVOID)&AddressBuffer,
|
||
// 1024,
|
||
// 0,
|
||
// HighestAcceptableMax);
|
||
//
|
||
// if (!AddressBuffer)
|
||
// {
|
||
// D_LOG(D_ALWAYS, ("RegistryInit: Memory Allocation Failed!\n"));
|
||
// return;
|
||
// }
|
||
//
|
||
// AddressUnicodeString.MaximumLength = 1024;
|
||
// AddressUnicodeString.Length = 0;
|
||
// NdisZeroMemory(AddressBuffer, 1024);
|
||
// AddressUnicodeString.Buffer = AddressBuffer;
|
||
//
|
||
// //
|
||
// // create tapi devices key
|
||
// //
|
||
// RtlCreateRegistryKey (RTL_REGISTRY_DEVICEMAP, L"Tapi Devices");
|
||
//
|
||
// //
|
||
// // create pcimac service provider key
|
||
// //
|
||
// RtlCreateRegistryKey (RTL_REGISTRY_DEVICEMAP, L"Tapi Devices\\PCIMAC");
|
||
//
|
||
// //
|
||
// // write media type - isdn for us
|
||
// //
|
||
// RtlInitAnsiString(&AnsiString, "ISDN");
|
||
//
|
||
// RtlAnsiStringToUnicodeString(&UnicodeString, &AnsiString, TRUE);
|
||
//
|
||
// RtlWriteRegistryValue(RTL_REGISTRY_DEVICEMAP,
|
||
// L"Tapi Devices\\PCIMAC",
|
||
// L"Media Type",
|
||
// REG_SZ,
|
||
// UnicodeString.Buffer,
|
||
// UnicodeString.Length);
|
||
//
|
||
// RtlFreeUnicodeString(&UnicodeString);
|
||
//
|
||
// for (l = 0; l < MAX_ADAPTERS_IN_SYSTEM; l++)
|
||
// {
|
||
// ADAPTER *Adapter = (ADAPTER*)Pcimac.AdapterTbl[l];
|
||
//
|
||
// if (Adapter)
|
||
// {
|
||
// for (m = 0; m < MAX_CM_PER_ADAPTER; m++)
|
||
// {
|
||
// CM *cm = Adapter->CmTbl[m];
|
||
//
|
||
// if (cm)
|
||
// {
|
||
// RtlInitAnsiString(&AnsiString, cm->LocalAddress);
|
||
//
|
||
// RtlAnsiStringToUnicodeString(&UnicodeString, &AnsiString, TRUE);
|
||
//
|
||
// RtlAppendUnicodeStringToString(&AddressUnicodeString, &UnicodeString);
|
||
//
|
||
// AddressUnicodeString.Buffer[AddressUnicodeString.Length + 1] = '\0';
|
||
// AddressUnicodeString.Length += 2;
|
||
//
|
||
// RtlFreeUnicodeString(&UnicodeString);
|
||
// }
|
||
// }
|
||
// }
|
||
// }
|
||
//
|
||
// //
|
||
// // write value
|
||
// //
|
||
// RtlWriteRegistryValue(RTL_REGISTRY_DEVICEMAP,
|
||
// L"Tapi Devices\\PCIMAC",
|
||
// L"Address",
|
||
// REG_MULTI_SZ,
|
||
// AddressUnicodeString.Buffer,
|
||
// AddressUnicodeString.Length);
|
||
//
|
||
// NdisFreeMemory(AddressBuffer, 1024, 0);
|
||
//}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(GetBaseConfigParams)
|
||
|
||
ULONG
|
||
GetBaseConfigParams(
|
||
CONFIGPARAM *RetParam,
|
||
CHAR *Key
|
||
)
|
||
{
|
||
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
|
||
NDIS_STRING KeyWord;
|
||
ANSI_STRING AnsiKey;
|
||
ULONG n;
|
||
PNDIS_CONFIGURATION_PARAMETER ConfigParam;
|
||
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: Key: %s\n", Key));
|
||
//
|
||
// turn passed in key to an ansi string
|
||
//
|
||
RtlInitAnsiString(&AnsiKey, Key);
|
||
|
||
//
|
||
// allocate buffer and turn ansi to unicode
|
||
//
|
||
RtlAnsiStringToUnicodeString(&KeyWord, &AnsiKey, TRUE);
|
||
|
||
NdisReadConfiguration(&Status,
|
||
&ConfigParam,
|
||
RetParam->ConfigHandle,
|
||
&KeyWord,
|
||
RetParam->ParamType);
|
||
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: Status: 0x%x\n", Status));
|
||
//
|
||
// free up unicode string buffer
|
||
//
|
||
RtlFreeUnicodeString(&KeyWord);
|
||
|
||
if (Status != NDIS_STATUS_SUCCESS)
|
||
{
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: Error Reading Config: RetVal: 0x%x\n", Status));
|
||
if (RetParam->MustBePresent)
|
||
NdisWriteErrorLogEntry (RetParam->AdapterHandle,
|
||
NDIS_ERROR_CODE_MISSING_CONFIGURATION_PARAMETER,
|
||
0);
|
||
return(0);
|
||
}
|
||
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: StringLength: %d\n", ConfigParam->ParameterData.StringData.Length));
|
||
switch (ConfigParam->ParameterType)
|
||
{
|
||
case NdisParameterString:
|
||
{
|
||
#if !BINARY_COMPATIBLE
|
||
ANSI_STRING AnsiRet;
|
||
|
||
RtlUnicodeStringToAnsiString(&AnsiRet, &ConfigParam->ParameterData.StringData, TRUE);
|
||
__strncpy(RetParam->String, AnsiRet.Buffer, AnsiRet.Length);
|
||
RetParam->StringLen = AnsiRet.Length;
|
||
RtlFreeAnsiString(&AnsiRet);
|
||
#else
|
||
RetParam->StringLen = __strlen((PUCHAR)ConfigParam->ParameterData.StringData.Buffer);
|
||
__strncpy(RetParam->String, (PUCHAR) ConfigParam->ParameterData.StringData.Buffer, RetParam->StringLen);
|
||
#endif
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: String: %s, Length: %d\n", RetParam->String, RetParam->StringLen));
|
||
|
||
break;
|
||
}
|
||
case NdisParameterMultiString:
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: String: %s, Length: %d\n", RetParam->String, RetParam->StringLen));
|
||
|
||
#if !BINARY_COMPATIBLE
|
||
for (n = 0; n < RetParam->StringLen && n < ConfigParam->ParameterData.StringData.Length; n++)
|
||
RetParam->String[n] = (CHAR)ConfigParam->ParameterData.StringData.Buffer[n];
|
||
|
||
RetParam->StringLen = n/2;
|
||
|
||
#else
|
||
// Ansi
|
||
for (n = 0; n < RetParam->StringLen && n < ConfigParam->ParameterData.StringData.Length; n++)
|
||
RetParam->String[n] = ((PUCHAR)ConfigParam->ParameterData.StringData.Buffer)[n];
|
||
|
||
RetParam->StringLen = n;
|
||
|
||
#endif
|
||
for (n = 0; n < RetParam->StringLen; n++)
|
||
if (!__strnicmp((CHAR*)&RetParam->String[n], (CHAR*)"=", 1))
|
||
RetParam->String[n] = '\0';
|
||
break;
|
||
|
||
case NdisParameterInteger:
|
||
case NdisParameterHexInteger:
|
||
RetParam->Value = ConfigParam->ParameterData.IntegerData;
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: Integer: 0x%x\n", RetParam->Value));
|
||
break;
|
||
|
||
default:
|
||
return(0);
|
||
}
|
||
return(1);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(GetLineConfigParams)
|
||
|
||
ULONG
|
||
GetLineConfigParams(
|
||
CONFIGPARAM *RetParam,
|
||
ULONG LineNumber,
|
||
CHAR *Key
|
||
)
|
||
{
|
||
ULONG n;
|
||
CHAR LinePath[64];
|
||
NDIS_STRING KeyWord;
|
||
ANSI_STRING AnsiKey;
|
||
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
|
||
PNDIS_CONFIGURATION_PARAMETER ConfigParam;
|
||
|
||
sprintf(LinePath,
|
||
"%s%d.%s",
|
||
PCIMAC_KEY_LINE,
|
||
LineNumber,
|
||
Key);
|
||
|
||
D_LOG(D_ALWAYS, ("GetLineConfigParams: LineNumber: %d, Key: %s\n", LineNumber, Key));
|
||
//
|
||
// turn passed in key to an ansi string
|
||
//
|
||
RtlInitAnsiString(&AnsiKey, LinePath);
|
||
|
||
//
|
||
// allocate buffer and turn ansi to unicode
|
||
//
|
||
RtlAnsiStringToUnicodeString(&KeyWord, &AnsiKey, TRUE);
|
||
|
||
NdisReadConfiguration(&Status,
|
||
&ConfigParam,
|
||
RetParam->ConfigHandle,
|
||
&KeyWord,
|
||
RetParam->ParamType);
|
||
|
||
//
|
||
// free up unicode string buffer
|
||
//
|
||
RtlFreeUnicodeString(&KeyWord);
|
||
|
||
if (Status != NDIS_STATUS_SUCCESS)
|
||
{
|
||
D_LOG(D_ALWAYS, ("GetLineConfigParams: Error Reading Config: RetVal: 0x%x\n", Status));
|
||
if (RetParam->MustBePresent)
|
||
NdisWriteErrorLogEntry (RetParam->AdapterHandle,
|
||
NDIS_ERROR_CODE_MISSING_CONFIGURATION_PARAMETER,
|
||
0);
|
||
return(0);
|
||
}
|
||
|
||
switch (ConfigParam->ParameterType)
|
||
{
|
||
case NdisParameterString:
|
||
{
|
||
#if !BINARY_COMPATIBLE
|
||
ANSI_STRING AnsiRet;
|
||
|
||
RtlUnicodeStringToAnsiString(&AnsiRet, &ConfigParam->ParameterData.StringData, TRUE);
|
||
__strncpy(RetParam->String, AnsiRet.Buffer, AnsiRet.Length);
|
||
RetParam->StringLen = AnsiRet.Length;
|
||
RtlFreeAnsiString(&AnsiRet);
|
||
#else
|
||
RetParam->StringLen = __strlen((PUCHAR)ConfigParam->ParameterData.StringData.Buffer);
|
||
__strncpy(RetParam->String, (PUCHAR) ConfigParam->ParameterData.StringData.Buffer, RetParam->StringLen);
|
||
#endif
|
||
|
||
D_LOG(D_ALWAYS, ("GetLineConfigParams: String: %s, Length: %d\n", RetParam->String, RetParam->StringLen));
|
||
break;
|
||
}
|
||
|
||
case NdisParameterMultiString:
|
||
for (n = 0; n < RetParam->StringLen && n < ConfigParam->ParameterData.StringData.Length; n++)
|
||
RetParam->String[n] = (CHAR)ConfigParam->ParameterData.StringData.Buffer[n];
|
||
|
||
RetParam->StringLen = n/2;
|
||
|
||
for (n = 0; n < RetParam->StringLen; n++)
|
||
if (!__strnicmp((CHAR*)&RetParam->String[n], (CHAR*)"=", 1))
|
||
RetParam->String[n] = '\0';
|
||
D_LOG(D_ALWAYS, ("GetBaseConfigParams: String: %s, Length: %d\n", RetParam->String, RetParam->StringLen));
|
||
break;
|
||
|
||
case NdisParameterInteger:
|
||
case NdisParameterHexInteger:
|
||
RetParam->Value = ConfigParam->ParameterData.IntegerData;
|
||
D_LOG(D_ALWAYS, ("GetLineConfigParams: Integer: 0x%x\n", RetParam->Value));
|
||
break;
|
||
|
||
default:
|
||
return(0);
|
||
}
|
||
return(1);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(GetLTermConfigParams)
|
||
|
||
ULONG
|
||
GetLTermConfigParams(
|
||
CONFIGPARAM *RetParam,
|
||
ULONG LineNumber,
|
||
ULONG LTermNumber,
|
||
CHAR *Key
|
||
)
|
||
{
|
||
ULONG n;
|
||
CHAR LTermPath[64];
|
||
NDIS_STRING KeyWord;
|
||
ANSI_STRING AnsiKey;
|
||
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
|
||
PNDIS_CONFIGURATION_PARAMETER ConfigParam;
|
||
|
||
D_LOG(D_ALWAYS, ("GetLTermConfigParams: LineNumber: %d, LTerm: %d, Key: %s\n", LineNumber, LTermNumber, Key));
|
||
|
||
sprintf(LTermPath,
|
||
"%s%d.%s%d.%s",
|
||
PCIMAC_KEY_LINE,
|
||
LineNumber,
|
||
PCIMAC_KEY_LTERM,
|
||
LTermNumber,
|
||
Key);
|
||
|
||
//
|
||
// turn passed in key to an ansi string
|
||
//
|
||
RtlInitAnsiString(&AnsiKey, LTermPath);
|
||
|
||
//
|
||
// allocate buffer and turn ansi to unicode
|
||
//
|
||
RtlAnsiStringToUnicodeString(&KeyWord, &AnsiKey, TRUE);
|
||
|
||
NdisReadConfiguration(&Status,
|
||
&ConfigParam,
|
||
RetParam->ConfigHandle,
|
||
&KeyWord,
|
||
RetParam->ParamType);
|
||
|
||
//
|
||
// free up unicode string buffer
|
||
//
|
||
RtlFreeUnicodeString(&KeyWord);
|
||
|
||
if (Status != NDIS_STATUS_SUCCESS)
|
||
{
|
||
D_LOG(D_ALWAYS, ("GetLTermConfigParams: Error Reading Config: RetVal: 0x%x\n", Status));
|
||
if (RetParam->MustBePresent)
|
||
NdisWriteErrorLogEntry (RetParam->AdapterHandle,
|
||
NDIS_ERROR_CODE_MISSING_CONFIGURATION_PARAMETER,
|
||
0);
|
||
return(0);
|
||
}
|
||
|
||
switch (ConfigParam->ParameterType)
|
||
{
|
||
case NdisParameterString:
|
||
{
|
||
#if !BINARY_COMPATIBLE
|
||
ANSI_STRING AnsiRet;
|
||
|
||
RtlUnicodeStringToAnsiString(&AnsiRet, &ConfigParam->ParameterData.StringData, TRUE);
|
||
__strncpy(RetParam->String, AnsiRet.Buffer, AnsiRet.Length);
|
||
RetParam->StringLen = AnsiRet.Length;
|
||
RtlFreeAnsiString(&AnsiRet);
|
||
#else
|
||
RetParam->StringLen = __strlen((PUCHAR)ConfigParam->ParameterData.StringData.Buffer);
|
||
__strncpy(RetParam->String, (PUCHAR) ConfigParam->ParameterData.StringData.Buffer, RetParam->StringLen);
|
||
#endif
|
||
D_LOG(D_ALWAYS, ("GetLTermConfigParams: String: %s, Length: %d\n", RetParam->String, RetParam->StringLen));
|
||
break;
|
||
}
|
||
|
||
case NdisParameterMultiString:
|
||
for (n = 0; n < RetParam->StringLen && n < ConfigParam->ParameterData.StringData.Length; n++)
|
||
RetParam->String[n] = (CHAR)ConfigParam->ParameterData.StringData.Buffer[n];
|
||
|
||
RetParam->StringLen = n/2;
|
||
|
||
for (n = 0; n < RetParam->StringLen; n++)
|
||
if (!__strnicmp((CHAR*)&RetParam->String[n], (CHAR*)"=", 1))
|
||
RetParam->String[n] = '\0';
|
||
D_LOG(D_ALWAYS, ("GetLTermConfigParams: String: %s, Length: %d\n", RetParam->String, RetParam->StringLen));
|
||
break;
|
||
|
||
case NdisParameterInteger:
|
||
case NdisParameterHexInteger:
|
||
RetParam->Value = ConfigParam->ParameterData.IntegerData;
|
||
D_LOG(D_ALWAYS, ("GetLTermConfigParams: Integer: 0x%x\n", RetParam->Value));
|
||
break;
|
||
|
||
default:
|
||
return(0);
|
||
}
|
||
return(1);
|
||
}
|
||
|
||
VOID
|
||
SetInDriverFlag (
|
||
ADAPTER *Adapter
|
||
)
|
||
{
|
||
NdisAcquireSpinLock(&Pcimac.lock);
|
||
|
||
Pcimac.InDriverFlag = 1;
|
||
|
||
Pcimac.CurrentAdapter = Adapter;
|
||
|
||
Pcimac.NextAdapterToPoll++;
|
||
|
||
if (Pcimac.NextAdapterToPoll == Pcimac.NumberOfAdaptersInSystem)
|
||
Pcimac.NextAdapterToPoll = 0;
|
||
|
||
NdisReleaseSpinLock(&Pcimac.lock);
|
||
}
|
||
|
||
VOID
|
||
ClearInDriverFlag (
|
||
ADAPTER *Adapter
|
||
)
|
||
{
|
||
NdisAcquireSpinLock(&Pcimac.lock);
|
||
|
||
Pcimac.InDriverFlag = 0;
|
||
|
||
NdisReleaseSpinLock(&Pcimac.lock);
|
||
}
|
||
|
||
ULONG
|
||
CheckInDriverFlag (
|
||
ADAPTER *Adapter
|
||
)
|
||
{
|
||
ADAPTER *CurrentAdapter;
|
||
INT RetVal = 0;
|
||
|
||
NdisAcquireSpinLock(&Pcimac.lock);
|
||
|
||
//
|
||
// get the current in driver adapter
|
||
//
|
||
CurrentAdapter = (ADAPTER*)Pcimac.CurrentAdapter;
|
||
|
||
//
|
||
// if someone is in the driver and they are using the same
|
||
// shared memory window as the new prospective user send them
|
||
// away unhappy
|
||
//
|
||
if (Pcimac.InDriverFlag && CurrentAdapter && (Adapter->VBaseMem == CurrentAdapter->VBaseMem))
|
||
RetVal = 1;
|
||
|
||
NdisReleaseSpinLock(&Pcimac.lock);
|
||
|
||
return(RetVal);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(IdpGetEaddrFromNvram)
|
||
|
||
/*
|
||
* get ethernet address(s) out on nvram & register
|
||
*
|
||
* note that line number inside board (bline) argument was added here.
|
||
* for each idd installed, this function is called to add two ethernet
|
||
* addresses associated with it (it's two B channels - or it's capability to
|
||
* handle two connections). All ethernet address are derived from the
|
||
* single address stored starting at nvram address 8. since the manufecturer
|
||
* code is the first 3 bytes, we must not modify these bytes. therefor,
|
||
* addresses are generated by indexing the 4'th byte by bline*2 (need two
|
||
* address - remember?).
|
||
*/
|
||
VOID
|
||
IdpGetEaddrFromNvram(
|
||
IDD *idd,
|
||
CM *cm,
|
||
USHORT Line,
|
||
USHORT LineIndex
|
||
)
|
||
{
|
||
UCHAR eaddr[6];
|
||
USHORT nvval;
|
||
|
||
/* extract original stored ethernet address */
|
||
idd_get_nvram(idd, (USHORT)(8), &nvval);
|
||
eaddr[0] = LOBYTE(nvval);
|
||
eaddr[1] = HIBYTE(nvval);
|
||
idd_get_nvram(idd, (USHORT)(9), &nvval);
|
||
eaddr[2] = LOBYTE(nvval);
|
||
eaddr[3] = HIBYTE(nvval);
|
||
idd_get_nvram(idd, (USHORT)(10), &nvval);
|
||
eaddr[4] = LOBYTE(nvval);
|
||
eaddr[5] = HIBYTE(nvval);
|
||
|
||
/* create derived address and store it */
|
||
eaddr[3] += (Line * 2) + LineIndex;
|
||
|
||
NdisMoveMemory(cm->SrcAddr, eaddr, sizeof(cm->SrcAddr));
|
||
} // end IdpGetEaddrFromNvram
|
||
|
||
#pragma NDIS_INIT_FUNCTION(AdpGetEaddrFromNvram)
|
||
|
||
/*
|
||
* get ethernet address(s) out on nvram & register
|
||
*
|
||
* note that line number inside board (bline) argument was added here.
|
||
* for each idd installed, this function is called to add two ethernet
|
||
* addresses associated with it (it's two B channels - or it's capability to
|
||
* handle two connections). All ethernet address are derived from the
|
||
* single address stored starting at nvram address 8. since the manufecturer
|
||
* code is the first 3 bytes, we must not modify these bytes. therefor,
|
||
* addresses are generated by indexing the 4'th byte by bline*2 (need two
|
||
* address - remember?).
|
||
*/
|
||
VOID
|
||
AdpGetEaddrFromNvram(
|
||
IDD *idd,
|
||
CM *cm,
|
||
USHORT Line,
|
||
USHORT LineIndex
|
||
)
|
||
{
|
||
UCHAR eaddr[6];
|
||
USHORT nvval;
|
||
|
||
//
|
||
// the MAC address lines at offset 0x950 in the onboard memory
|
||
// this is NVRAM_WINDOW 0x940 + 0x10
|
||
//
|
||
idd_get_nvram(idd, (USHORT)(0x10), &nvval);
|
||
eaddr[0] = LOBYTE(nvval);
|
||
eaddr[1] = HIBYTE(nvval);
|
||
idd_get_nvram(idd, (USHORT)(0x12), &nvval);
|
||
eaddr[2] = LOBYTE(nvval);
|
||
eaddr[3] = HIBYTE(nvval);
|
||
idd_get_nvram(idd, (USHORT)(0x14), &nvval);
|
||
eaddr[4] = LOBYTE(nvval);
|
||
eaddr[5] = HIBYTE(nvval);
|
||
|
||
/* create derived address and store it */
|
||
eaddr[3] += (Line * 2) + LineIndex;
|
||
|
||
NdisMoveMemory(cm->SrcAddr, eaddr, sizeof(cm->SrcAddr));
|
||
} // end AdpGetEaddrFromNvram
|
||
|
||
#ifdef OLD
|
||
ULONG
|
||
EnumAdaptersInSystem()
|
||
{
|
||
ULONG n, NumAdapters = 0;
|
||
|
||
for (n = 0; n < MAX_ADAPTERS_IN_SYSTEM; n++)
|
||
{
|
||
if (Pcimac.AdapterTbl[n])
|
||
NumAdapters++;
|
||
}
|
||
return(NumAdapters);
|
||
}
|
||
#endif
|
||
|
||
ULONG
|
||
EnumAdaptersInSystem()
|
||
{
|
||
ULONG NumAdapters;
|
||
|
||
NdisAcquireSpinLock(&Pcimac.lock);
|
||
|
||
NumAdapters = Pcimac.NumberOfAdaptersInSystem;
|
||
|
||
NdisReleaseSpinLock(&Pcimac.lock);
|
||
|
||
return(NumAdapters);
|
||
}
|
||
|
||
ADAPTER*
|
||
GetAdapterByIndex(
|
||
ULONG Index
|
||
)
|
||
{
|
||
ADAPTER *Adapter;
|
||
|
||
NdisAcquireSpinLock(&Pcimac.lock);
|
||
|
||
Adapter = Pcimac.AdapterTbl[Index];
|
||
|
||
NdisReleaseSpinLock(&Pcimac.lock);
|
||
|
||
return(Adapter);
|
||
}
|
||
|
||
INT
|
||
IoEnumAdapter(VOID *cmd_1)
|
||
{
|
||
IO_CMD *cmd = (IO_CMD*)cmd_1;
|
||
ULONG n, m, NumberOfAdapters;
|
||
|
||
NumberOfAdapters = cmd->val.enum_adapters.num = (USHORT)EnumAdaptersInSystem();
|
||
|
||
for (n = 0, m = 0; n < NumberOfAdapters; n++)
|
||
{
|
||
ADAPTER *Adapter = GetAdapterByIndex(n);
|
||
|
||
if (Adapter)
|
||
{
|
||
cmd->val.enum_adapters.BaseIO[m] = Adapter->BaseIO;
|
||
cmd->val.enum_adapters.BaseMem[m] = Adapter->BaseMem;
|
||
cmd->val.enum_adapters.BoardType[m] = Adapter->BoardType;
|
||
NdisMoveMemory (&cmd->val.enum_adapters.Name[m], Adapter->Name, sizeof(cmd->val.enum_adapters.Name[n]));
|
||
cmd->val.enum_adapters.tbl[m] = Adapter;
|
||
m++;
|
||
}
|
||
}
|
||
|
||
return(0);
|
||
}
|
||
|
||
VOID
|
||
AdapterDestroy(
|
||
ADAPTER *Adapter
|
||
)
|
||
{
|
||
ULONG n;
|
||
|
||
for (n = 0; n < MAX_ADAPTERS_IN_SYSTEM; n++)
|
||
{
|
||
if (Adapter == Pcimac.AdapterTbl[n])
|
||
break;
|
||
}
|
||
|
||
if (n == MAX_ADAPTERS_IN_SYSTEM)
|
||
return;
|
||
|
||
//
|
||
// stop idd timers
|
||
//
|
||
StopTimers(Adapter);
|
||
|
||
Pcimac.AdapterTbl[n] = NULL;
|
||
|
||
Pcimac.NumberOfAdaptersInSystem--;
|
||
|
||
//
|
||
// if we have successfully mapped our base i/o then we need to release
|
||
//
|
||
if (Adapter->VBaseIO)
|
||
{
|
||
//
|
||
// deregister adapters I/O and memory
|
||
//
|
||
NdisMDeregisterIoPortRange((NDIS_HANDLE)Adapter->Handle,
|
||
Adapter->BaseIO,
|
||
8,
|
||
Adapter->VBaseIO);
|
||
}
|
||
|
||
//
|
||
// if we have successfully mapped our base memory then we need to release
|
||
//
|
||
if (Adapter->VBaseMem)
|
||
{
|
||
NdisMUnmapIoSpace((NDIS_HANDLE)Adapter->Handle,
|
||
Adapter->VBaseMem,
|
||
0x4000);
|
||
}
|
||
|
||
// NdisFreeSpinLock(&Adapter->lock);
|
||
|
||
NdisFreeMemory(Adapter, sizeof(ADAPTER), 0);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(StartTimers)
|
||
|
||
VOID
|
||
StartTimers(
|
||
ADAPTER *Adapter
|
||
)
|
||
{
|
||
NdisMSetTimer(&Adapter->IddPollTimer, IDD_POLL_T);
|
||
NdisMSetTimer(&Adapter->MtlPollTimer, MTL_POLL_T);
|
||
NdisMSetTimer(&Adapter->CmPollTimer, CM_POLL_T);
|
||
}
|
||
|
||
VOID
|
||
StopTimers(
|
||
ADAPTER *Adapter
|
||
)
|
||
{
|
||
BOOLEAN TimerCanceled;
|
||
|
||
NdisMCancelTimer(&Adapter->IddPollTimer, &TimerCanceled);
|
||
NdisMCancelTimer(&Adapter->MtlPollTimer, &TimerCanceled);
|
||
NdisMCancelTimer(&Adapter->CmPollTimer, &TimerCanceled);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(IdpCheckIO)
|
||
|
||
ULONG
|
||
IdpCheckIO(IDD *idd)
|
||
{
|
||
ULONG ReturnValue = 1;
|
||
|
||
//
|
||
// check for board at this I/O address
|
||
//
|
||
if (idd->btype == IDD_BT_PCIMAC || idd->btype == IDD_BT_PCIMAC4)
|
||
{
|
||
UCHAR BoardID;
|
||
|
||
BoardID = (idd->InFromPort(idd, 5) & 0x0F);
|
||
|
||
if ( ((idd->btype == IDD_BT_PCIMAC) && (BoardID == 0x02)) ||
|
||
((idd->btype == IDD_BT_PCIMAC4) && (BoardID == 0x04)))
|
||
ReturnValue = 0;
|
||
}
|
||
else if( idd->btype == IDD_BT_MCIMAC )
|
||
ReturnValue = 0;
|
||
|
||
return(ReturnValue);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(AdpCheckIO)
|
||
|
||
ULONG
|
||
AdpCheckIO(IDD *idd)
|
||
{
|
||
UCHAR BoardId = idd->InFromPort(idd, ADP_REG_ID);
|
||
|
||
D_LOG(D_ENTRY, ("AdpCheckIO: entry, idd: 0x%lx BoardType: %d\n", idd, idd->btype));
|
||
|
||
D_LOG(D_ALWAYS, ("AdpCheckIO: ADP_REG_ID: %d\n", BoardId));
|
||
|
||
switch( idd->btype )
|
||
{
|
||
case IDD_BT_DATAFIREU:
|
||
case IDD_BT_DATAFIREST:
|
||
if (BoardId != ADP_BT_ADP1)
|
||
return(1);
|
||
break;
|
||
|
||
case IDD_BT_DATAFIRE4ST:
|
||
if (BoardId != ADP_BT_ADP4)
|
||
return(1);
|
||
break;
|
||
}
|
||
|
||
return( 0 );
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(IdpCheckMem)
|
||
|
||
ULONG
|
||
IdpCheckMem(IDD *idd)
|
||
{
|
||
return(0);
|
||
}
|
||
|
||
#pragma NDIS_INIT_FUNCTION(AdpCheckMem)
|
||
|
||
ULONG
|
||
AdpCheckMem(IDD *idd)
|
||
{
|
||
return(0);
|
||
|
||
}
|
||
|
||
|
||
NTSTATUS PcimacInitMCA( NDIS_HANDLE AdapterHandle,
|
||
PULONG BaseIO,
|
||
PULONG BaseMemory,
|
||
ULONG SlotNumber )
|
||
/*++
|
||
|
||
Routine Description:
|
||
|
||
This routine will be called if it is determined the type of bus
|
||
is MCA. We verify that the controller is actually a DigiBoard
|
||
PCIMAC controller, read the POS to determine the I/O address and
|
||
Memory Mapped address, so the initialization process can continue.
|
||
|
||
Arguments:
|
||
|
||
AdapterHandle - Handle passed in the initialization routine. Required
|
||
so mapping of POS I/O ports can take place.
|
||
|
||
BaseIO - Pointer where the adapters base I/O address is passed back.
|
||
|
||
BaseMemory - Pointer where the adapters base memory address is passed back.
|
||
|
||
SlotNumber - Number indicating what slot this MCA adapter should be in.
|
||
|
||
Return Value:
|
||
|
||
STATUS_SUCCESS - If we were able to complete successfully
|
||
|
||
?? - We were not able to get the information required to continue.
|
||
|
||
--*/
|
||
{
|
||
#define PcimacPOSID 0x7F9E
|
||
#define MCA_BASE_POS_IO_PORT 0x96
|
||
#define MCA_INFO_POS_IO_PORT 0x100
|
||
|
||
#define MCA_IO_PORT_MASK 0x0070
|
||
|
||
USHORT ActualPosId, POSConfig;
|
||
USHORT IOPortOffset;
|
||
ULONG MemoryAddress;
|
||
|
||
PVOID VirtualPOSBaseAddress; // Virtual address
|
||
PVOID VirtualPOSInfoAddress; // Virtual address
|
||
|
||
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
|
||
UCHAR OneByte;
|
||
|
||
//
|
||
// We need to read the POS Adapter ID and make sure the controller
|
||
// is one of ours. Use the Slot number and the POS ID we
|
||
// installed during configuration from the registry.
|
||
//
|
||
|
||
DigiDump( DIGIINIT, ("Pcimac: PcimacPOSID: 0x%x\n",
|
||
PcimacPOSID) );
|
||
|
||
DigiDump( DIGIINIT, ("--------- SlotNumber: 0x%x\n",
|
||
SlotNumber) );
|
||
|
||
*BaseIO = 0;
|
||
*BaseMemory = 0;
|
||
|
||
Status = NdisMRegisterIoPortRange( &VirtualPOSBaseAddress,
|
||
AdapterHandle,
|
||
MCA_BASE_POS_IO_PORT,
|
||
1 );
|
||
|
||
if( Status != NDIS_STATUS_SUCCESS )
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_BAD_IO_BASE_ADDRESS,
|
||
0);
|
||
goto PcimacInitMCAExit;
|
||
}
|
||
|
||
Status = NdisMRegisterIoPortRange( &VirtualPOSInfoAddress,
|
||
AdapterHandle,
|
||
MCA_INFO_POS_IO_PORT,
|
||
1 );
|
||
|
||
if( Status != NDIS_STATUS_SUCCESS )
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_BAD_IO_BASE_ADDRESS,
|
||
0);
|
||
goto PcimacInitMCAExit;
|
||
}
|
||
|
||
|
||
// Enable the POS information for the slot we are interested in.
|
||
NdisRawWritePortUchar( VirtualPOSBaseAddress, (UCHAR)(SlotNumber + 7) );
|
||
|
||
NdisRawReadPortUchar( (PVOID)((ULONG)VirtualPOSInfoAddress + 1),
|
||
(PUCHAR)&OneByte );
|
||
ActualPosId = ((USHORT)OneByte << 8);
|
||
NdisRawReadPortUchar( VirtualPOSInfoAddress, (PUCHAR)&OneByte );
|
||
ActualPosId |= OneByte;
|
||
|
||
DigiDump( DIGIINIT, ("POS Adapter ID = 0x%hx\n", ActualPosId) );
|
||
|
||
if( ActualPosId != PcimacPOSID )
|
||
{
|
||
NdisWriteErrorLogEntry(AdapterHandle,
|
||
NDIS_ERROR_CODE_ADAPTER_NOT_FOUND,
|
||
0);
|
||
Status = NDIS_STATUS_ADAPTER_NOT_FOUND;
|
||
goto PcimacInitMCAError2;
|
||
}
|
||
|
||
//
|
||
// Clear the VPD.
|
||
//
|
||
NdisRawWritePortUchar( (ULONG)VirtualPOSInfoAddress + 6, 0 );
|
||
|
||
NdisRawReadPortUchar( (ULONG)VirtualPOSInfoAddress + 4,
|
||
(PUCHAR)&OneByte );
|
||
MemoryAddress = ((ULONG)OneByte << 22);
|
||
NdisRawReadPortUchar( (ULONG)VirtualPOSInfoAddress + 3,
|
||
(PUCHAR)&OneByte );
|
||
MemoryAddress |= ((ULONG)OneByte << 14);
|
||
|
||
NdisRawReadPortUchar( (ULONG)VirtualPOSInfoAddress + 2,
|
||
(PUCHAR)&OneByte );
|
||
POSConfig = OneByte;
|
||
|
||
IOPortOffset = (POSConfig & MCA_IO_PORT_MASK) >> 4;
|
||
|
||
DigiDump( DIGIINIT, ("POS config read = 0x%hx\n"
|
||
" IOPortOffset = 0x%hx, MemoryAddress = 0x%x,"
|
||
" IOPort = 0x%hx\n",
|
||
POSConfig, IOPortOffset, MemoryAddress,
|
||
MCAIOAddressTable[IOPortOffset]) );
|
||
|
||
*BaseIO = MCAIOAddressTable[IOPortOffset];
|
||
|
||
*BaseMemory = MemoryAddress;
|
||
|
||
// Disable the POS information.
|
||
NdisRawWritePortUchar( VirtualPOSBaseAddress, 0 );
|
||
|
||
//
|
||
// Unmap the POS register
|
||
//
|
||
|
||
PcimacInitMCAError2:;
|
||
|
||
NdisMDeregisterIoPortRange( AdapterHandle,
|
||
MCA_INFO_POS_IO_PORT,
|
||
1,
|
||
VirtualPOSInfoAddress );
|
||
|
||
NdisMDeregisterIoPortRange( AdapterHandle,
|
||
MCA_BASE_POS_IO_PORT,
|
||
1,
|
||
VirtualPOSBaseAddress );
|
||
|
||
PcimacInitMCAExit:;
|
||
|
||
return( Status );
|
||
} // end PcimacInitMCA
|
||
|
||
|
||
|