📄 fec.c
字号:
FECEnetAutoNego(pEthernet);
} while( FALSE );
if (ConfigHandle)
{
NdisCloseConfiguration(ConfigHandle);
}
if (Status == NDIS_STATUS_SUCCESS)
{
DEBUGMSG(ZONE_INIT, (TEXT("FECInitialize: Initialize succeeded\n")));
}
else
{
if(gpFECReg != NULL)
{
NdisMDeregisterIoPortRange( pEthernet->ndisAdapterHandle,
(ULONG)CSP_BASE_REG_PA_FEC,
sizeof(CSP_FEC_REGS),
(PVOID)gpFECReg);
gpFECReg = NULL;
}
if (pEthernet)
NdisFreeMemory(pEthernet, sizeof(FEC_t), 0);
}
return Status;
}
//------------------------------------------------------------------------------
//
// Function: FECHalt
//
// FECHalt is a required function that de-allocates resources when the FEC
// adapter is removed and halts the network adapter.
//
// Parameters:
// MiniportAdapterContext
// [in] Specifies the handle to a FEC allocated context area in
// which the FEC driver maintains FEC adapter state,
// set up by FECInitialize.
//
// Return Value:
// None.
//
//------------------------------------------------------------------------------
#pragma NDIS_PAGABLE_FUNCTION(FECHalt)
void FECHalt(IN NDIS_HANDLE MiniportAdapterContext)
{
pFEC_t pEthernet = ((pFEC_t)(MiniportAdapterContext));
DEBUGMSG(ZONE_FUNCTION, (TEXT("FEC: +FECHalt\r\n")));
pEthernet->CurrentState = NdisHardwareStatusClosing;
NdisMDeregisterAdapterShutdownHandler(pEthernet->ndisAdapterHandle);
NdisMDeregisterInterrupt(&(pEthernet->interruptObj));
pEthernet->CurrentState = NdisHardwareStatusNotReady;
if(gpFECReg != NULL)
{
NdisMDeregisterIoPortRange( pEthernet->ndisAdapterHandle,
(ULONG)CSP_BASE_REG_PA_FEC,
sizeof(CSP_FEC_REGS),
(PVOID)gpFECReg);
gpFECReg = NULL;
}
FECEnetDeinit(pEthernet);
NdisFreeMemory( (PVOID)pEthernet, (UINT)sizeof(FEC_t), 0);
DEBUGMSG(ZONE_FUNCTION, (TEXT("FEC: -FECHalt\r\n")));
return;
}
//------------------------------------------------------------------------------
//
// Function: FECQueryInformation
//
// FECQueryInformation is a required function that returns information about
// the capabilities and status of the FEC driver. The NDIS library makes one
// or more calls to FECQueryInformation just after FECInitialize function
// returns NDIS_STATUS_SUCCESS.
//
// Parameters:
// MiniportAdapterContext
// [in] Specifies the handle to the driver allocated context area in
// which the driver maintains FEC adapter state, set up by
// FECInitialize
//
// Oid
// [in] Specifies the system-defined OID_XXX code designating the golbal
// query operation this function should carry out
//
// InformationBuffer
// [in] Points to a buffer in which FECQueryInformation should return
// the OID-specific information
//
// InformationBufferLength
// [in] Specifies the number of bytes at InformationBuffer
//
// BytesWritten
// [out] Points to a variable that FECQueryInformation sets to the number
// of bytes it is returning at InformationBuffer
//
// BytesNeeded
// [out] Points to a variable that FECQueryInformation sets to the number
// of additional bytes it needs to satisfy the request if
// InformationBufferLength is less than Oid requires
//
// Return Values:
// returns NDIS_STATUS_SUCCESS if FECQueryInformation returned the requested
// information at InformationBuffer and set the variable at BytesWritten to
// the amount of information it returned
//
// returns NDIS_STATUS_INVALID_OID if the requested Oid is not supported
//
// returns NDIS_STATUS_INVALID_LENGTH if The InformationBufferLength does
// not match the length required by the given Oid
//
//------------------------------------------------------------------------------
NDIS_STATUS FECQueryInformation(
IN NDIS_HANDLE MiniportAdapterContext,
IN NDIS_OID Oid,
IN PVOID InformationBuffer,
IN ULONG InformationBufferLength,
OUT PULONG BytesWritten,
OUT PULONG BytesNeeded
)
{
NDIS_STATUS result = NDIS_STATUS_SUCCESS;
UINT BytesLeft = InformationBufferLength;
PUCHAR InfoBuffer = (PUCHAR)(InformationBuffer);
// These variables hold the results of query
ULONG GenericULong;
USHORT GenericUShort;
UCHAR GenericArray[6];
UINT MoveBytes = sizeof(ULONG);
PVOID MoveSource = (PVOID)(&GenericULong);
pFEC_t pEthernet = ((pFEC_t)(MiniportAdapterContext));
DEBUGMSG(ZONE_FUNCTION, (TEXT("FEC: +FECQueryInformation\r\n")));
// Make sure that int is 4 bytes. Else GenericULong must change
// to something of size 4
ASSERT(sizeof(ULONG) == 4);
// Switch on request type
switch(Oid)
{
case OID_GEN_VENDOR_DRIVER_VERSION:
GenericULong = (FEC_NDIS_MAJOR_VERSION << 16) + FEC_NDIS_MINOR_VERSION;
break;
case OID_GEN_SUPPORTED_LIST:
MoveSource = (PVOID)(FECSupportedOids);
MoveBytes = sizeof(FECSupportedOids);
break;
case OID_GEN_HARDWARE_STATUS:
GenericULong = pEthernet->CurrentState;
break;
case OID_GEN_MEDIA_SUPPORTED:
case OID_GEN_MEDIA_IN_USE:
GenericULong = NdisMedium802_3;
break;
case OID_GEN_MEDIA_CONNECT_STATUS:
GenericULong = pEthernet->MediaState;
break;
case OID_GEN_MAXIMUM_LOOKAHEAD:
GenericULong = (PKT_MAXBUF_SIZE - ETHER_HDR_SIZE - PKT_CRC_SIZE);
break;
case OID_GEN_MAXIMUM_FRAME_SIZE:
GenericULong = (PKT_MAXBUF_SIZE - ETHER_HDR_SIZE - PKT_CRC_SIZE);
break;
case OID_GEN_MAXIMUM_TOTAL_SIZE:
GenericULong = (PKT_MAXBUF_SIZE - PKT_CRC_SIZE);
break;
case OID_GEN_MAC_OPTIONS:
GenericULong = (ULONG)(
NDIS_MAC_OPTION_TRANSFERS_NOT_PEND |
NDIS_MAC_OPTION_RECEIVE_SERIALIZED |
NDIS_MAC_OPTION_NO_LOOPBACK
);
break;
case OID_GEN_LINK_SPEED:
if(pEthernet->SpeedMode == TRUE)
GenericULong = 1000000; // 100 Mbps in 100 bps units
else
GenericULong = 100000; // 10 Mbps in 100 bps units
break;
case OID_GEN_TRANSMIT_BUFFER_SPACE:
GenericULong = MAXIMUM_TRANSMIT_PACKET * PKT_MAXBUF_SIZE;
break;
case OID_GEN_RECEIVE_BUFFER_SPACE:
GenericULong = PKT_MAXBUF_SIZE;
break;
case OID_GEN_TRANSMIT_BLOCK_SIZE:
GenericULong = PKT_MAXBUF_SIZE;
break;
case OID_GEN_RECEIVE_BLOCK_SIZE:
GenericULong = PKT_MAXBUF_SIZE;
break;
case OID_GEN_VENDOR_DESCRIPTION:
MoveSource = (PVOID)"Freescale Fast Ethernet Adapter";
MoveBytes = 32;
break;
case OID_GEN_VENDOR_ID:
NdisMoveMemory((PVOID)&GenericULong,
&(pEthernet->FecMacAddress),
(ULONG)ETHER_ADDR_SIZE);
GenericULong &= 0xFFFFFF00;
GenericULong |= 0x01;
MoveSource = (PVOID)(&GenericULong);
MoveBytes = sizeof(GenericULong);
break;
case OID_GEN_DRIVER_VERSION:
GenericUShort = ((USHORT)FEC_NDIS_MAJOR_VERSION << 8) |
FEC_NDIS_MINOR_VERSION;
MoveSource = (PVOID)(&GenericUShort);
MoveBytes = sizeof(GenericUShort);
break;
case OID_GEN_CURRENT_PACKET_FILTER:
GenericULong = (ULONG)(pEthernet->PacketFilter);
break;
case OID_GEN_CURRENT_LOOKAHEAD:
GenericULong = (ULONG)(pEthernet->CurrentLookAhead);
break;
case OID_GEN_XMIT_OK:
GenericULong = (UINT)(pEthernet->TxdStatus.FramesXmitGood);
break;
case OID_GEN_RCV_OK:
GenericULong = (UINT)(pEthernet->RcvStatus.FrameRcvGood);
break;
case OID_GEN_XMIT_ERROR:
GenericULong = (UINT)(pEthernet->TxdStatus.FramesXmitBad);
break;
case OID_GEN_RCV_ERROR:
GenericULong = (UINT)(pEthernet->RcvStatus.FrameRcvErrors);
break;
case OID_GEN_RCV_NO_BUFFER:
GenericULong = 0;
break;
case OID_GEN_MAXIMUM_SEND_PACKETS:
GenericULong = (UINT)MAXIMUM_TRANSMIT_PACKET;
break;
case OID_802_3_PERMANENT_ADDRESS:
case OID_802_3_CURRENT_ADDRESS:
NdisMoveMemory((PCHAR)GenericArray,
pEthernet->FecMacAddress,
(ULONG)ETHER_ADDR_SIZE);
MoveSource = (PVOID)(GenericArray);
MoveBytes = sizeof(pEthernet->FecMacAddress);
break;
case OID_802_3_MULTICAST_LIST:
MoveSource = (PVOID)(pEthernet->McastList);
MoveBytes = pEthernet->NumMulticastAddressesInUse * ETHER_ADDR_SIZE;
break;
case OID_802_3_MAXIMUM_LIST_SIZE:
GenericULong = MCAST_LIST_SIZE;
break;
case OID_802_3_RCV_ERROR_ALIGNMENT:
GenericULong = (UINT)(pEthernet->RcvStatus.FrameRcvAllignmentErrors);
break;
case OID_802_3_XMIT_ONE_COLLISION:
case OID_802_3_XMIT_MORE_COLLISIONS:
case OID_802_3_XMIT_MAX_COLLISIONS:
GenericULong = (UINT)(pEthernet->TxdStatus.FramesXmitCollisionErrors);
break;
case OID_802_3_RCV_OVERRUN:
GenericULong = (UINT)(pEthernet->RcvStatus.FrameRcvOverrunErrors);
break;
case OID_802_3_XMIT_UNDERRUN:
GenericULong = (UINT)(pEthernet->TxdStatus.FramesXmitUnderrunErrors);
break;
default:
result = NDIS_STATUS_INVALID_OID;
break;
}
if (result == NDIS_STATUS_SUCCESS)
{
if (MoveBytes > BytesLeft)
{
// Not enough room in InformationBuffer
*BytesNeeded = MoveBytes;
result = NDIS_STATUS_INVALID_LENGTH;
}
else
{
// Store result
NdisMoveMemory(InfoBuffer, MoveSource, MoveBytes);
*BytesWritten = MoveBytes;
}
}
DEBUGMSG(ZONE_FUNCTION, (TEXT("FEC: -FECQueryInformation\r\n")));
return result;
}
//------------------------------------------------------------------------------
//
// Function: FECReset
//
// This function is a required funtion that issues a hardware reset to the
// network adapter and/or resets the driver's software state. If FECCheckForHang
// returns TRUE, this function will be called to reset the FEC adapter.
//
// Parameters:
// AddressingReset
// [out] Points to a variable that FECReset sets to TRUE if the NDIS
// library call FECSetInformation to restore addressing
// information to the current values.
//
// MiniportAdapterContext
// [in] Specifies the handle to the driver allocated context area in
// which the driver maintains FEC adapter state, set up by
// FECInitialize.
//
// Return Value:
// Return NDIS_STATUS_SUCCESS always.
//
//------------------------------------------------------------------------------
NDIS_STATUS FECReset(
OUT PBOOLEAN AddressingReset,
IN NDIS_HANDLE MiniportAdapterContext
)
{
PNDIS_PACKET pNdisPacket;
pFEC_t pEthernet = ((pFEC_t)(MiniportAdapterContext));
DEBUGMSG(ZONE_FUNCTION, (TEXT("FEC: +FECReset\r\n")));
pEthernet->CurrentState = NdisHardwareStatusReset;
// Disable interrupts
FECDisableInterrupt(MiniportAdapterContext);
pEthernet->TransmitInProgress = FALSE;
pEthernet->StartTx = FALSE;
//
// Remove the packet from the queue.
//
EnterCriticalSection (&gFECBufCs);
pNdisPacket = pEthernet->HeadPacket;
while(pNdisPacket != NULL)
{
pEthernet->HeadPacket = RESERVED(pNdisPacket)->Next;
if (pNdisPacket == pEthernet->TailPacket)
{
pEthernet->TailPacket = NULL;
}
NdisMSendComplete(pEthernet->ndisAdapterHandle, pNdisPacket, NDIS_STATUS_SUCCESS);
pNdisPacket = pEthernet->HeadPacket;
}
LeaveCriticalSection (&gFECBufCs);
// issues the hardware reset for FEC adapter
FECEnetReset(MiniportAdapterContext, FALSE);
*AddressingReset = TRUE;
pEthernet->CurrentState = NdisHardwareStatusReady;
// enable interrupts
FECEnableInterrupt(MiniportAdapterContext);
DEBUGMSG(ZONE_FUNCTION, (TEXT("FEC: -FECReset\r\n")));
return NDIS_STATUS_SUCCESS;
}
//------------------------------------------------------------------------------
//
// Function: FECSend
//
// This function is responsible for sending the packet to the FEC and start the
// sending process.
//
// Parameters:
// MiniportAdapterContext
// [in] Specifies the handle to the driver allocated context area in
// which the driver maintains FEC adapter state, set up by
// FECInitialize
//
// Packet
// [in] Points to a packet descriptor specifying the data to be transmitted
//
// SendFlags
// [in] Specifies the packet flags, if any, set by the protocol
//
// Return Value:
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -