📄 lan91c111_miniport.c
字号:
/*
*
* Copyright (c) Standard MicroSystems Corporation. All Rights Reserved.
*
* LAN91C111 Driver for Windows CE .NET
*
* Revision History
*_______________________________________________________________________________
* Author Date Version Description
*_______________________________________________________________________________
* Pramod Bhardwaj 6/18/2002 0.1 Beta Release
* Pramod Bhardwaj 7/15/2002 1.0 Release
*_______________________________________________________________________________
*
*
*Description:
* Functions exposed to the NDIS wrapper, ie., MiniportXXX functions.
*
*
*/
#define NDIS_MINIPORT_DRIVER
#define NDIS50_MINIPORT
#include <Ndis.h>
#include <LAN91C111_Adapter.h>
#include <LAN91C111_Proto.h>
extern NDIS_STATUS CopyInfo (UCHAR *, UCHAR *, UINT, UINT, UINT *, UINT *);
extern void BackOut (MINIPORT_ADAPTER *Adapter);
extern BOOLEAN AdapterReset(MINIPORT_ADAPTER *);
/*
Function Name : AllocateTxBuffer
Description :
This function allocates a buffer for transmission. This called by
the miniportsend function.
Parameters :
MINIPORT_ADAPTER *Adapter - Pointer to the adapter structure
MINIPORT_PACKET **Packet - Pointer to the packet !!
Return Value :
TRUE - if allocation was succesful, else FLASE
*/
BOOLEAN AllocateTxBuffer(MINIPORT_ADAPTER *Adapter, MINIPORT_PACKET **Packet)
{
MINIPORT_PACKET *CurrentPacket;
UINT AllocateOk;
USHORT AllocSts;
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111==> Do Allocate\r\n")));
if((Adapter->IsAllocateActive) || (!Adapter->AllocPending.First) /*|| (Adapter->XmitPending >= Adapter->MaxXmits)*/)
{
DEBUGMSG(ZONE_INIT, (TEXT("Adapter->IsAllocateActive %d\r\n"),Adapter->IsAllocateActive));
DEBUGMSG(ZONE_INIT, (TEXT("Adapter->AllocPending.First %d\r\n"),Adapter->AllocPending.First));
DEBUGMSG(ZONE_INIT, (TEXT("Adapter->XmitPending %d\r\n"), Adapter->XmitPending));
DEBUGMSG(ZONE_INIT, (TEXT("Adapter->MaxXmits %d\r\n"), Adapter->MaxXmits));
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111 : Do Allocate Failed !!\r\n")));
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111 <== Do Allocate\r\n")));
return(FALSE);
}
Adapter->AllocateFlag =
Adapter->IsAllocateActive = TRUE;
Adapter->XmitPending++;
CurrentPacket = Adapter->AllocPending.First;
//Set the MMU Alloc Command
NdisRawWritePortUshort(Adapter->IOBase + BANK_SELECT,2);
NdisRawWritePortUshort(Adapter->IOBase + BANK2_MMU_CMD, (USHORT)CMD_ALLOC);
AllocateOk = MMU_WAIT;
while(AllocateOk)
{
NdisRawReadPortUshort(Adapter->IOBase + BANK2_INT_STS, (PUSHORT) &AllocSts);
if(AllocSts & INT_ALLOC)
break;
AllocateOk--;
}
if(AllocateOk)
{
USHORT TempWord;
*Packet = CurrentPacket;
NdisRawReadPortUshort( Adapter->IOBase + BANK2_PNR,(PUSHORT) &TempWord );
CurrentPacket->PacketNumber = HIBYTE(TempWord);
DequePacket(Adapter->AllocPending, CurrentPacket);
Adapter->IsAllocateActive = Adapter->AllocateFlag = FALSE;
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111 <== Do Allocate\r\n")));
return TRUE;
}
else
{
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111: Do Allocate Failed\r\n")));
Adapter->IsAllocateActive = FALSE;
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111 <== Do Allocate\r\n")));
return FALSE;
}
}
/*
Function Name : AdapterWrite
Description :
This function write the contents of the packet to the chip's internal
buffer. The packet has to be allocated before calling this function
Parameters :
MINIPORT_ADAPTER *Adapter - Pointer to the adapter structure
MINIPORT_PACKET *Packet - Pointer to the packet structure,
this contains the packet descriptors and
the allocated packet number.
Return Value :
void
*/
VOID AdapterWrite (MINIPORT_ADAPTER *Adapter,
MINIPORT_PACKET *Packet)
{
UINT IOBase,
DataPort,
TotalRange,
BufferRange;
UCHAR *BufferData;
BOOLEAN WriteContinue = TRUE;
NDIS_BUFFER *CurrentBuffer,
*NextBuffer;
NDIS_PACKET *NdisPacket;
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111:==> Adapter Write\r\n")));
if(!Adapter->IsWriteActive)
{
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111: Adapter is not busy\r\n")));
Adapter->IsWriteActive = TRUE;
//Attach to tail of appropriate write queue.
QuePacket(Adapter->AckPending, Packet);
}
else
// Write routine is already executing. When the current write is completed, this one will be processed.
{
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111: Adapter is busy\r\n")));
QuePacket(Adapter->WritePending, Packet);
return;
}
IOBase = Adapter->IOBase;
DataPort = IOBase + BANK2_DATA1;
//Write the Packet to the 91C111
while(WriteContinue)
{
NdisPacket = CONTAINING_RECORD(Packet,NDIS_PACKET,MiniportReserved[0]);
//Write the Packet number, that we got from the allocation
NdisRawWritePortUshort(Adapter->IOBase + BANK_SELECT,2);
NdisRawWritePortUchar(IOBase + BANK2_PNR, Packet->PacketNumber);
NdisRawWritePortUshort(IOBase + BANK2_PTR, (USHORT) PTR_AUTO);
// Output packet preamble.
NdisQueryPacket(NdisPacket,
(PUINT) 0,
(PUINT) 0,
(PNDIS_BUFFER *) &CurrentBuffer,
(PUINT) &TotalRange);
//Start writing the Packet to the memory
//First Write 0 - This is placeholder for the Status word in the memory
NdisRawWritePortUshort(DataPort, (USHORT) 0);
//Next write the byte count + frame overhead
NdisRawWritePortUshort(DataPort, (USHORT)(TotalRange + FRAME_OVERHEAD));
//Now write the Data
while (CurrentBuffer)
{
NdisQueryBuffer(CurrentBuffer,(PVOID *) &BufferData,(PUINT) &BufferRange);
NdisRawWritePortBufferUshort(DataPort, BufferData, BufferRange>>1);
if (BufferRange & 0x1)
NdisRawWritePortUchar(DataPort, BufferData[BufferRange-1]);
NdisGetNextBuffer(CurrentBuffer,(PNDIS_BUFFER *) &NextBuffer);
CurrentBuffer = NextBuffer;
}
//Lastly write the ControlByte and Odd byte if needed..
if (TotalRange & 1)
NdisRawWritePortUchar( DataPort, (UCHAR) ( CTL_BYTE_ODD | CTL_BYTE_CRC ) );
else
NdisRawWritePortUshort( DataPort, (USHORT) ( CTL_BYTE_CRC << 8 ) );
//Now enque the packet for transmission..
NdisRawWritePortUshort( IOBase + BANK2_MMU_CMD, (USHORT) CMD_ENQ_TX );
//Check if more packets to be transmitted.
if(!Adapter->WritePending.First)
{
WriteContinue =
Adapter->IsWriteActive = FALSE;
}
else
{
DequePacket(Adapter->WritePending, Packet);
QuePacket(Adapter->AckPending, Packet);
}
}
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111:<== Adapter Write\r\n")));
}
/*
Function Name : LAN91C111-MiniportHalt
Description :
MiniportHalt is a required function that de-allocates resources
when the network adapter is removed and halts the network adapter
Parameters :
NDIS_HANDLE AdapterContext - Specifies the handle to a
miniport-allocated context area
Return Value :
VOID
*/
VOID LAN91C111_MiniportHalt (NDIS_HANDLE AdapterContext)
{
PMINIPORT_ADAPTER Adapter = (MINIPORT_ADAPTER *) AdapterContext;
BackOut(Adapter);
return;
}
/*
Function Name : LAN91C111_MiniportQueryInformation
Description : This function is a required function
that returns information about the capabilities
and status of the driver and/or its network adapter.
Parameters :
NDIS_HANDLE AdapterContext - Handle to the adapter structure
NDIS_OID Oid - OID code designation the query operation that the driver should carr out
PVOID InformationBuffer - pointer to the buffer in which the driver return the value
ULONG InformationBufferLength - lenght of the buffer
PULONG BytesWritten - number of bytes the driver is returning
PULONG BytesNeeded - additional bytes, if needed, to satisfy the query.
Return Value :
NDIS_STATUS Status
*/
NDIS_STATUS LAN91C111_MiniportQueryInformation(
NDIS_HANDLE AdapterContext,
NDIS_OID Oid,
PVOID InformationBuffer,
ULONG InformationBufferLength,
PULONG BytesWritten,
PULONG BytesNeeded
)
{
MINIPORT_ADAPTER *Adapter = (MINIPORT_ADAPTER *) AdapterContext;
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
NDIS_OID ReturnData;
void *Source = &ReturnData;
UINT BytesToMove = sizeof(NDIS_OID);
DEBUGMSG(ZONE_INIT, (TEXT("LAN91C111 ==> MiniportQuery Information OID=%x, "), Oid));
switch(Oid)
{
case OID_GEN_SUPPORTED_LIST:
DEBUGMSG(ZONE_INIT, (TEXT("OID_GEN_SUPPORTED_LIST\r\n")));
Source = (void *) &GlobalObjects;
BytesToMove = sizeof(GlobalObjects);
break;
case OID_GEN_MEDIA_SUPPORTED:
DEBUGMSG(ZONE_INIT, (TEXT("OID_GEN_MEDIA_SUPPORTED\r\n")));
ReturnData = NdisMedium802_3;
break;
case OID_GEN_MEDIA_IN_USE:
DEBUGMSG(ZONE_INIT, (TEXT("OID_GEN_MEDIA_IN_USE\r\n")));
ReturnData = NdisMedium802_3;
break;
case OID_GEN_MAXIMUM_LOOKAHEAD:
DEBUGMSG(ZONE_INIT, (TEXT("OID_GEN_MAXIMUM_LOOKAHEAD\r\n")));
ReturnData = MAX_LOOKAHEAD_SIZE;
break;
case OID_GEN_MAXIMUM_FRAME_SIZE:
DEBUGMSG(ZONE_INIT, (TEXT("OID_GEN_MAXIMUM_FRAME_SIZE\r\n")));
ReturnData = MAX_FRAME_DATA_SIZE;
break;
case OID_GEN_LINK_SPEED:
DEBUGMSG(ZONE_INIT, (TEXT("OID_GEN_LINK_SPEED\r\n")));
ReturnData = Adapter->Speed;
break;
case OID_GEN_TRANSMIT_BUFFER_SPACE:
DEBUGMSG(ZONE_INIT, (TEXT("OID_GEN_TRANSMIT_BUFFER_SPACE\r\n")));
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -