📄 rtl8139.c
字号:
TmpAdapter->NextAdapter = TmpAdapter->NextAdapter->NextAdapter;
}
NdisFreeMemory(Adapter, sizeof(RTL8139_ADAPTER), 0);
return;
}
*/
NDIS_STATUS
RTL8139Reset(
OUT PBOOLEAN AddressingReset,
IN NDIS_HANDLE MiniportAdapterContext
)
/*++
功能描述:
RTL8139Reset函数发出请求将硬件资源进行重置。同时软件资源也被重置。
参数:
AddressingReset - 判断适配器是否重新载入分配的地址
MiniportAdapterContext - 指向网卡对象数据结构的指针
返回值:
返回操作后的状态
--*/
{
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
PRTL8139_ADAPTER adapter = (PRTL8139_ADAPTER)MiniportAdapterContext;
DbgPrint("Rtl8139Reset \n");
while(adapter->FreeRxPkt != 0x40);
while(adapter->FreeTxDesc != NUM_OF_DESC);
NdisRawWritePortUshort(adapter->ioaddr + IntrMask, 0);
NdisRawWritePortUchar(adapter->ioaddr + ChipCmd, 0);
ResetNIC(adapter);
StartDevice(adapter);
adapter->read_ptr = 0;
adapter->FreeRxPkt = 0x40;
adapter->cur_rx = 0;
adapter->dirty_rx = 0;
adapter->FreeTxDesc = NUM_OF_DESC;
adapter->cur_tx = 0;
adapter->dirty_tx = 0;
return Status;
}
/*{
PRTL8139_ADAPTER Adapter = (PRTL8139_ADAPTER)MiniportAdapterContext;
UINT i;
Adapter->NextBufToFill = 0;
Adapter->NextBufToXmit = 0;
Adapter->CurBufXmitting = (XMIT_BUF)-1;
Adapter->FirstPacket = NULL;
Adapter->LastPacket = NULL;
for (i=0; i<Adapter->NumBuffers; i++) {
Adapter->BufferStatus[i] = EMPTY;
}
Adapter->NicInterruptMask = IMR_RCV | IMR_XMIT | IMR_XMIT_ERR | IMR_OVERFLOW;
return (CardReset(Adapter) ? NDIS_STATUS_SUCCESS : NDIS_STATUS_FAILURE);
}*/
NDIS_STATUS
RTL8139QueryInformation
/*++
功能描述:
RTL8139QueryInformation函数对与网卡设备有关的OID值的对象进行查询
参数:
MiniportAdapterContext -指向网卡对象的指针
Oid - 要查询的NDIS_OID值
InformationBuffer - 指向存放查询结果的缓冲区的指针
InformationBufferLength - 指向存放查询结果的缓冲区的大小
BytesWritten -写入存放查询结果的缓冲区的字节数
BytesNeeded - 若缓冲区不够大,所需再分配的空间
返回值:
操作后的状态
--*/
(
IN NDIS_HANDLE Context,
IN NDIS_OID Oid,
IN PVOID inbuf,
IN ULONG buf_size,
OUT PULONG BytesWritten,
OUT PULONG BytesNeeded
)
{
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
UINT i;
PRTL8139_ADAPTER adapter = (PRTL8139_ADAPTER)Context;
static NDIS_OID OID_LIST[] =
{
// 所有的OID
OID_GEN_SUPPORTED_LIST,// 0x00010101
OID_GEN_HARDWARE_STATUS,// 0x00010102
OID_GEN_MEDIA_SUPPORTED,// 0x00010103
OID_GEN_MEDIA_IN_USE,// 0x00010104
OID_GEN_MAXIMUM_LOOKAHEAD,// 0x00010105
OID_GEN_MAXIMUM_FRAME_SIZE,// 0x00010106
OID_GEN_LINK_SPEED,// 0x00010107
OID_GEN_TRANSMIT_BUFFER_SPACE,// 0x00010108
OID_GEN_RECEIVE_BUFFER_SPACE,// 0x00010109
OID_GEN_TRANSMIT_BLOCK_SIZE,// 0x0001010A
OID_GEN_RECEIVE_BLOCK_SIZE,// 0x0001010B
OID_GEN_VENDOR_ID,// 0x0001010C
OID_GEN_VENDOR_DESCRIPTION,// 0x0001010D
OID_GEN_CURRENT_PACKET_FILTER,// 0x0001010E
OID_GEN_CURRENT_LOOKAHEAD,// 0x0001010F
OID_GEN_DRIVER_VERSION,// 0x00010110
OID_GEN_MAXIMUM_TOTAL_SIZE,// 0x00010111
OID_GEN_PROTOCOL_OPTIONS,// 0x00010112
OID_GEN_MAC_OPTIONS,// 0x00010113
OID_GEN_MEDIA_CONNECT_STATUS,// 0x00010114
OID_GEN_MAXIMUM_SEND_PACKETS,// 0x00010115
OID_GEN_VENDOR_DRIVER_VERSION,// 0x00010116
OID_GEN_SUPPORTED_GUIDS,// 0x00010117
OID_GEN_NETWORK_LAYER_ADDRESSES,// 0x00010118
OID_GEN_TRANSPORT_HEADER_OFFSET,// 0x00010119
// 802.3 Objects (Ethernet)
OID_802_3_PERMANENT_ADDRESS,// 0x01010101
OID_802_3_CURRENT_ADDRESS,// 0x01010102
OID_802_3_MULTICAST_LIST,// 0x01010103
OID_802_3_MAXIMUM_LIST_SIZE,// 0x01010104
OID_802_3_MAC_OPTIONS,// 0x01010105
NDIS_802_3_MAC_OPTION_PRIORITY,// 0x00000001
OID_802_3_RCV_ERROR_ALIGNMENT,// 0x01020101
OID_802_3_XMIT_ONE_COLLISION,// 0x01020102
OID_802_3_XMIT_MORE_COLLISIONS,// 0x01020103
OID_802_3_XMIT_DEFERRED,// 0x01020201
OID_802_3_XMIT_MAX_COLLISIONS,// 0x01020202
OID_802_3_RCV_OVERRUN,// 0x01020203
OID_802_3_XMIT_UNDERRUN,// 0x01020204
OID_802_3_XMIT_HEARTBEAT_FAILURE,// 0x01020205
OID_802_3_XMIT_TIMES_CRS_LOST,// 0x01020206
OID_802_3_XMIT_LATE_COLLISIONS,// 0x01020207
// 用户定义
USER_OID_REV_BYTE,// 0x02000000
USER_OID_XMIT_BYTE ,// 0x02000001
OID_GEN_XMIT_OK,// 0x00020101
OID_GEN_RCV_OK,// 0x00020102
OID_GEN_XMIT_ERROR,// 0x00020103
OID_GEN_RCV_ERROR,// 0x00020104
OID_GEN_RCV_NO_BUFFER,// 0x00020105
};
*BytesWritten = 4;
switch (Oid){
case USER_OID_REV_BYTE:
*((PULONG)inbuf) = adapter->rev_byte;
break;
case USER_OID_XMIT_BYTE:
*((PULONG)inbuf) = adapter->xmit_byte;
break;
case OID_GEN_SUPPORTED_LIST:
if(buf_size < sizeof(OID_LIST)){
*BytesNeeded = sizeof(OID_LIST);
Status = NDIS_STATUS_INVALID_LENGTH;
}else{
NdisMoveMemory(inbuf, OID_LIST, sizeof(OID_LIST));
*BytesWritten = sizeof(OID_LIST);
}
break;
case OID_GEN_CURRENT_PACKET_FILTER:
if(buf_size >= 4){
*(PULONG)inbuf = adapter->PacketFilter;
*BytesWritten = 4;
}else
*BytesNeeded = 4;
break;
case OID_GEN_MAC_OPTIONS:
*((PULONG)inbuf) = (ULONG)(NDIS_MAC_OPTION_TRANSFERS_NOT_PEND |
NDIS_MAC_OPTION_COPY_LOOKAHEAD_DATA |
NDIS_MAC_OPTION_NO_LOOPBACK
);
break;
case OID_GEN_HARDWARE_STATUS:
*((NDIS_HARDWARE_STATUS*)inbuf) = NdisHardwareStatusReady;
break;
case OID_GEN_MEDIA_SUPPORTED:
case OID_GEN_MEDIA_IN_USE:
*((NDIS_MEDIUM*)inbuf) = (NDIS_MEDIUM)(NdisMedium802_3);
break;
case OID_GEN_MAXIMUM_LOOKAHEAD:
case OID_GEN_CURRENT_LOOKAHEAD:
case OID_GEN_MAXIMUM_FRAME_SIZE:
*((PULONG)inbuf) = MAX_ETHERNET_FRAME_SIZE - MAC_HEADER_SIZE;
break;
case OID_GEN_MAXIMUM_TOTAL_SIZE:
case OID_GEN_TRANSMIT_BLOCK_SIZE:
case OID_GEN_RECEIVE_BLOCK_SIZE:
*((PULONG)inbuf) = (ULONG)MAX_ETHERNET_FRAME_SIZE;
break;
case OID_GEN_LINK_SPEED:
*((PULONG)inbuf) = 1000000;
break;
case OID_GEN_TRANSMIT_BUFFER_SPACE:
DbgPrint("data=%x, len=%x\n", inbuf, buf_size);
*((PULONG)inbuf) = (ULONG) MAX_ETHERNET_FRAME_SIZE * 4;
break;
case OID_GEN_RECEIVE_BUFFER_SPACE:
*((PULONG)inbuf) = (ULONG)RING_BUF_SIZE;
break;
case OID_GEN_VENDOR_ID:
*((PULONG)inbuf) = *(PULONG)adapter->NetworkAddress;
break;
case OID_GEN_VENDOR_DESCRIPTION:
*((PULONG)inbuf) = (ULONG)'0900';
break;
case OID_GEN_DRIVER_VERSION:
*((PULONG)inbuf) = (USHORT)0x0201;
break;
case OID_GEN_MAXIMUM_SEND_PACKETS:
*((PULONG)inbuf) = (ULONG) NUM_OF_DESC;
break;
case OID_GEN_MEDIA_CONNECT_STATUS:
*((PULONG)inbuf) = (ULONG)NdisMediaStateConnected;
break;
//
// 802.3 对象 (以太网)
//
case OID_802_3_PERMANENT_ADDRESS:// 0x01010101
NdisMoveMemory(inbuf, adapter->NetworkAddress, 6);
*BytesWritten = 6;
break;
case OID_802_3_CURRENT_ADDRESS:// 0x01010102
NdisMoveMemory(inbuf, adapter->NetworkAddress, 6);
*BytesWritten = 6;
break;
case OID_802_3_MULTICAST_LIST:// 0x01010103
if (buf_size < 8)
return (NDIS_STATUS_INVALID_LENGTH);
else
NdisMoveMemory(inbuf, adapter->mc_filter, buf_size);
break;
case OID_802_3_MAXIMUM_LIST_SIZE:// 0x01010104
*((PULONG)inbuf) = (ULONG)MULTICAST_FILTER_LIMIT;
break;
case OID_802_3_MAC_OPTIONS:// 0x01010105
Status = NDIS_STATUS_NOT_SUPPORTED;
break;
case NDIS_802_3_MAC_OPTION_PRIORITY:// 0x00000001
Status = NDIS_STATUS_NOT_SUPPORTED;
break;
case OID_802_3_RCV_ERROR_ALIGNMENT:// 0x01020101
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_ONE_COLLISION:// 0x01020102
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_MORE_COLLISIONS:// 0x01020103
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_DEFERRED:// 0x01020201
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_MAX_COLLISIONS:// 0x01020202
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_RCV_OVERRUN:// 0x01020203
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_UNDERRUN:// 0x01020204
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_HEARTBEAT_FAILURE:// 0x01020205
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_TIMES_CRS_LOST:// 0x01020206
*((PULONG)inbuf) = (ULONG)0;
break;
case OID_802_3_XMIT_LATE_COLLISIONS:// 0x01020207
*((PULONG)inbuf) = (ULONG)0;
break;
//
// Required statistics
//
case OID_GEN_XMIT_OK:// 0x00020101
*((PULONG)inbuf) = adapter->XMIT_OK;
break;
case OID_GEN_RCV_OK:// 0x00020102
*((PULONG)inbuf) = adapter->RCV_OK;
break;
case OID_GEN_XMIT_ERROR:// 0x00020103
*((PULONG)inbuf) = adapter->XMIT_ERR;
break;
case OID_GEN_RCV_ERROR:// 0x00020104
*((PULONG)inbuf) = adapter->RCV_ERR;
break;
case OID_GEN_RCV_NO_BUFFER:// 0x00020105
*((PULONG)inbuf) = adapter->RCV_NO_BUFFER;
break;
default:
break;
}
return (Status);
}
extern
NDIS_STATUS
RTL8139SetInformation(
IN NDIS_HANDLE MiniportAdapterContext,
IN NDIS_OID Oid,
IN PVOID InformationBuffer,
IN ULONG InformationBufferLength,
OUT PULONG BytesRead,
OUT PULONG BytesNeeded
)
/*
功能描述:
RTL8139SetInformation 对一个单独的OID对象进行操作
参数:
MiniportAdapterContext - 指向网卡对象的指针
InformationBuffer - 为设置信息而建立的缓冲区。
InformationBufferLength - 缓冲区长度
BytesRead - 如果调用正确,返回设置的OID的长度.
BytesNeeded - 如果信息缓冲区长度不够,返回还需要的字节数。
返回值:
NDIS_STATUS_SUCCESS 成功
NDIS_STATUS_PENDING 需要加长缓冲区的长度
NDIS_STATUS_INVALID_LENGTH 非法的长度值(如 0)
NDIS_STATUS_INVALID_OID 非法的OID值(不在OID列表中)
*/
{
NDIS_STATUS Status = NDIS_STATUS_SUCCESS;
UINT i;
PRTL8139_ADAPTER adapter = (PRTL8139_ADAPTER)MiniportAdapterContext;
switch(Oid){
case OID_802_3_MULTICAST_LIST:
if ( InformationBufferLength > 8)
return (NDIS_STATUS_INVALID_LENGTH);
else
NdisMoveMemory(adapter->mc_filter, InformationBuffer, InformationBufferLength);
break;
case OID_GEN_CURRENT_PACKET_FILTER:
if (InformationBufferLength!= 4)
return (NDIS_STATUS_INVALID_LENGTH);
adapter->PacketFilter = *(PULONG)InformationBuffer;
*BytesRead = InformationBufferLength;
break;
case OID_GEN_CURRENT_LOOKAHEAD:
if (InformationBufferLength!= 4)
return (NDIS_STATUS_INVALID_LENGTH);
*BytesRead = 4;
break;
default:
Status = NDIS_STATUS_INVALID_OID;
break;
}
return Status;
}
NDIS_STATUS
DispatchSetPacketFilter(
IN PRTL8139_ADAPTER Adapter
)
/*++
功能描述:
为数据包加上必要的包头,即填充包头
参数:
Adapter - 指向adapter对象的区域的指针
返回值:
终了状态 (总是NDIS_STATUS_SUCCESS).
注意事项:
如果是广播包的话,全填1。网卡的模式要设置成混杂模式。
其他类型的数据包取决于它所对应绑定网卡的协议。
--*/
{
//
// 判断应该加什么内容
//
if
(
Adapter->PacketFilter & (NDIS_PACKET_TYPE_ALL_MULTICAST |
NDIS_PACKET_TYPE_PROMISCUOUS)
)
{
//
// 需要“全广播”
//
CardSetAllMulticast(Adapter); // fills it with 1's
}
else
{
//
// 不再需要“全广播”
//
DispatchSetMulticastAddressList(Adapter);
}
//
// 如果任何一个协议中需要广播包,RCR中的广播位应处于“1”的状态
//.
//
if
(
Adapter->PacketFilter & (NDIS_PACKET_TYPE_ALL_MULTICAST |
NDIS_PACKET_TYPE_MULTICAST |
NDIS_PACKET_TYPE_PROMISCUOUS)
)
{
Adapter->NicReceiveConfig |= RCR_MULTICAST;
}
else
{
Adapter->NicReceiveConfig &= ~RCR_MULTICAST;
}
//
// 如果任何一个协议是混杂模式,RCR中的混杂位应处于“1”的状态
//
if (Adapter->PacketFilter & NDIS_PACKET_TYPE_PROMISCUOUS)
{
Adapter->NicReceiveConfig |= RCR_ALL_PHYS;
}
else
{
Adapter->NicReceiveConfig &= ~RCR_ALL_PHYS;
}
if
(
Adapter->PacketFilter & (NDIS_PACKET_TYPE_BROADCAST |
NDIS_PACKET_TYPE_PROMISCUOUS)
)
{
Adapter->NicReceiveConfig |= RCR_BROADCAST;
}
else
{
Adapter->NicReceiveConfig &= ~RCR_BROADCAST;
}
CardSetReceiveConfig(Adapter);
return(NDIS_STATUS_SUCCESS);
}
NDIS_STATUS
DispatchSetMulticastAddressList(
IN PRTL8139_ADAPTER Adapter
)
/*++
功能描述:
设置多播列表
参数:
Adapter - 指向网卡数据块的指针
返回值:
NDIS_STATUS_SUCESS
--*/
{
CardFillMulticastRegs(Adapter);
CardCopyMulticastRegs(Adapter);
return NDIS_STATUS_SUCCESS;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -