https://git.reactos.org/?p=reactos.git;a=commitdiff;h=3f97671319509df175dd57...
commit 3f97671319509df175dd5702d670aaa2ff8ea99a Author: Dmitry Borisov di.sean@protonmail.com AuthorDate: Tue Dec 14 04:57:33 2021 +0600 Commit: GitHub noreply@github.com CommitDate: Tue Dec 14 01:57:33 2021 +0300
[E1000] Minor improvements (#3904)
- Add support for 64-bit counters (Intel gigabit NICs) - Properly handle OIDs - Check that the packet filter is not 0 - Performance increase --- drivers/network/dd/e1000/CMakeLists.txt | 3 +- drivers/network/dd/e1000/hardware.c | 107 +-------------------- drivers/network/dd/e1000/info.c | 158 +++++++++++++++++++++----------- drivers/network/dd/e1000/interrupt.c | 29 ++++-- drivers/network/dd/e1000/ndis.c | 45 +-------- drivers/network/dd/e1000/nic.h | 93 ++++++++++++------- drivers/network/dd/e1000/send.c | 85 +++++++++++++++++ 7 files changed, 274 insertions(+), 246 deletions(-)
diff --git a/drivers/network/dd/e1000/CMakeLists.txt b/drivers/network/dd/e1000/CMakeLists.txt index 8bb4aa25ccf..cd67a525a9d 100644 --- a/drivers/network/dd/e1000/CMakeLists.txt +++ b/drivers/network/dd/e1000/CMakeLists.txt @@ -12,7 +12,8 @@ list(APPEND SOURCE nic.h e1000hw.h debug.c - debug.h) + debug.h + send.c)
add_library(e1000 MODULE ${SOURCE} e1000.rc) add_pch(e1000 nic.h SOURCE) diff --git a/drivers/network/dd/e1000/hardware.c b/drivers/network/dd/e1000/hardware.c index aa5fc26896b..c0c41ce9403 100644 --- a/drivers/network/dd/e1000/hardware.c +++ b/drivers/network/dd/e1000/hardware.c @@ -53,32 +53,6 @@ static USHORT SupportedDevices[] = 0x10B5, // Intel 82546GB Quad Copper KSP3 };
- -static ULONG E1000WriteFlush(IN PE1000_ADAPTER Adapter) -{ - volatile ULONG Value; - - NdisReadRegisterUlong(Adapter->IoBase + E1000_REG_STATUS, &Value); - return Value; -} - -VOID NTAPI E1000WriteUlong(IN PE1000_ADAPTER Adapter, IN ULONG Address, IN ULONG Value) -{ - NdisWriteRegisterUlong((PULONG)(Adapter->IoBase + Address), Value); -} - -VOID NTAPI E1000ReadUlong(IN PE1000_ADAPTER Adapter, IN ULONG Address, OUT PULONG Value) -{ - NdisReadRegisterUlong((PULONG)(Adapter->IoBase + Address), Value); -} - -static VOID E1000WriteIoUlong(IN PE1000_ADAPTER Adapter, IN ULONG Address, IN ULONG Value) -{ - NdisRawWritePortUlong((PULONG)(Adapter->IoPort), Address); - E1000WriteFlush(Adapter); - NdisRawWritePortUlong((PULONG)(Adapter->IoPort + 4), Value); -} - static ULONG PacketFilterToMask(ULONG PacketFilter) { ULONG FilterMask = 0; @@ -145,16 +119,11 @@ static BOOLEAN E1000ReadMdic(IN PE1000_ADAPTER Adapter, IN ULONG Address, USHORT ULONG Mdic; UINT n;
- if (Address > MAX_PHY_REG_ADDRESS) - { - NDIS_DbgPrint(MIN_TRACE, ("PHY Address %d is invalid\n", Address)); - return 1; - } + ASSERT(Address <= MAX_PHY_REG_ADDRESS)
Mdic = (Address << E1000_MDIC_REGADD_SHIFT); Mdic |= (E1000_MDIC_PHYADD_GIGABIT << E1000_MDIC_PHYADD_SHIFT); Mdic |= E1000_MDIC_OP_READ; - E1000WriteUlong(Adapter, E1000_REG_MDIC, Mdic);
for (n = 0; n < MAX_PHY_READ_ATTEMPTS; n++) @@ -725,6 +694,7 @@ NICUpdateMulticastList( UINT n; NDIS_DbgPrint(MAX_TRACE, ("Called.\n"));
+ // FIXME: Use 'Adapter->MulticastListSize'? Check the datasheet for (n = 0; n < MAXIMUM_MULTICAST_ADDRESSES; ++n) { ULONG Ral = *(ULONG *)Adapter->MulticastList[n].MacAddress; @@ -763,46 +733,6 @@ NICApplyPacketFilter( return NDIS_STATUS_SUCCESS; }
-NDIS_STATUS -NTAPI -NICApplyInterruptMask( - IN PE1000_ADAPTER Adapter) -{ - NDIS_DbgPrint(MAX_TRACE, ("Called.\n")); - - E1000WriteUlong(Adapter, E1000_REG_IMS, Adapter->InterruptMask /*| 0x1F6DC*/); - return NDIS_STATUS_SUCCESS; -} - -NDIS_STATUS -NTAPI -NICDisableInterrupts( - IN PE1000_ADAPTER Adapter) -{ - NDIS_DbgPrint(MAX_TRACE, ("Called.\n")); - - E1000WriteUlong(Adapter, E1000_REG_IMC, ~0); - return NDIS_STATUS_SUCCESS; -} - -ULONG -NTAPI -NICInterruptRecognized( - IN PE1000_ADAPTER Adapter, - OUT PBOOLEAN InterruptRecognized) -{ - ULONG Value; - - /* Reading the interrupt acknowledges them */ - E1000ReadUlong(Adapter, E1000_REG_ICR, &Value); - - *InterruptRecognized = (Value & Adapter->InterruptMask) != 0; - - NDIS_DbgPrint(MAX_TRACE, ("NICInterruptRecognized(0x%x, 0x%x).\n", Value, *InterruptRecognized)); - - return (Value & Adapter->InterruptMask); -} - VOID NTAPI NICUpdateLinkStatus( @@ -819,36 +749,3 @@ NICUpdateLinkStatus( SpeedIndex = (DeviceStatus & E1000_STATUS_SPEEDMASK) >> E1000_STATUS_SPEEDSHIFT; Adapter->LinkSpeedMbps = SpeedValues[SpeedIndex]; } - -NDIS_STATUS -NTAPI -NICTransmitPacket( - IN PE1000_ADAPTER Adapter, - IN PHYSICAL_ADDRESS PhysicalAddress, - IN ULONG Length) -{ - volatile PE1000_TRANSMIT_DESCRIPTOR TransmitDescriptor; - - NDIS_DbgPrint(MAX_TRACE, ("Called.\n")); - - TransmitDescriptor = Adapter->TransmitDescriptors + Adapter->CurrentTxDesc; - TransmitDescriptor->Address = PhysicalAddress.QuadPart; - TransmitDescriptor->Length = Length; - TransmitDescriptor->ChecksumOffset = 0; - TransmitDescriptor->Command = E1000_TDESC_CMD_RS | E1000_TDESC_CMD_IFCS | E1000_TDESC_CMD_EOP | E1000_TDESC_CMD_IDE; - TransmitDescriptor->Status = 0; - TransmitDescriptor->ChecksumStartField = 0; - TransmitDescriptor->Special = 0; - - Adapter->CurrentTxDesc = (Adapter->CurrentTxDesc + 1) % NUM_TRANSMIT_DESCRIPTORS; - - E1000WriteUlong(Adapter, E1000_REG_TDT, Adapter->CurrentTxDesc); - - if (Adapter->CurrentTxDesc == Adapter->LastTxDesc) - { - NDIS_DbgPrint(MID_TRACE, ("All TX descriptors are full now\n")); - Adapter->TxFull = TRUE; - } - - return NDIS_STATUS_SUCCESS; -} diff --git a/drivers/network/dd/e1000/info.c b/drivers/network/dd/e1000/info.c index 42b7fe8f2c8..9a5b632d56c 100644 --- a/drivers/network/dd/e1000/info.c +++ b/drivers/network/dd/e1000/info.c @@ -10,7 +10,7 @@
#include <debug.h>
-static ULONG SupportedOidList[] = +static NDIS_OID SupportedOidList[] = { OID_GEN_SUPPORTED_LIST, OID_GEN_CURRENT_PACKET_FILTER, @@ -37,14 +37,36 @@ static ULONG SupportedOidList[] = OID_802_3_PERMANENT_ADDRESS, OID_802_3_CURRENT_ADDRESS, OID_802_3_MAXIMUM_LIST_SIZE, + /* Statistics */ OID_GEN_XMIT_OK, OID_GEN_RCV_OK, OID_GEN_XMIT_ERROR, OID_GEN_RCV_ERROR, OID_GEN_RCV_NO_BUFFER, + + OID_PNP_CAPABILITIES, };
+static +ULONG64 +NICQueryStatisticCounter( + _In_ PE1000_ADAPTER Adapter, + _In_ NDIS_OID Oid) +{ + /* TODO */ + return 0; +} + +static +NDIS_STATUS +NICFillPowerManagementCapabilities( + _In_ PE1000_ADAPTER Adapter, + _Out_ PNDIS_PNP_CAPABILITIES Capabilities) +{ + /* TODO */ + return NDIS_STATUS_NOT_SUPPORTED; +}
NDIS_STATUS NTAPI @@ -57,13 +79,20 @@ MiniportQueryInformation( OUT PULONG BytesNeeded) { PE1000_ADAPTER Adapter = (PE1000_ADAPTER)MiniportAdapterContext; - ULONG genericUlong; ULONG copyLength; PVOID copySource; NDIS_STATUS status; + union _GENERIC_INFORMATION + { + USHORT Ushort; + ULONG Ulong; + ULONG64 Ulong64; + NDIS_MEDIUM Medium; + NDIS_PNP_CAPABILITIES PmCapabilities; + } GenericInfo;
status = NDIS_STATUS_SUCCESS; - copySource = &genericUlong; + copySource = &GenericInfo; copyLength = sizeof(ULONG);
switch (Oid) @@ -74,20 +103,19 @@ MiniportQueryInformation( break;
case OID_GEN_CURRENT_PACKET_FILTER: - genericUlong = Adapter->PacketFilter; + GenericInfo.Ulong = Adapter->PacketFilter; break;
case OID_GEN_HARDWARE_STATUS: UNIMPLEMENTED_DBGBREAK(); - genericUlong = (ULONG)NdisHardwareStatusReady; //FIXME + GenericInfo.Ulong = (ULONG)NdisHardwareStatusReady; //FIXME break;
case OID_GEN_MEDIA_SUPPORTED: case OID_GEN_MEDIA_IN_USE: { - static const NDIS_MEDIUM medium = NdisMedium802_3; - copySource = (PVOID)&medium; - copyLength = sizeof(medium); + GenericInfo.Medium = NdisMedium802_3; + copyLength = sizeof(NDIS_MEDIUM); break; }
@@ -96,31 +124,36 @@ MiniportQueryInformation( case OID_GEN_CURRENT_LOOKAHEAD: case OID_GEN_MAXIMUM_LOOKAHEAD: case OID_GEN_MAXIMUM_FRAME_SIZE: - genericUlong = MAXIMUM_FRAME_SIZE - sizeof(ETH_HEADER); + GenericInfo.Ulong = MAXIMUM_FRAME_SIZE - sizeof(ETH_HEADER); + break; + + case OID_802_3_MULTICAST_LIST: + copySource = Adapter->MulticastList; + copyLength = Adapter->MulticastListSize * IEEE_802_ADDR_LENGTH; break;
case OID_802_3_MAXIMUM_LIST_SIZE: - genericUlong = MAXIMUM_MULTICAST_ADDRESSES; + GenericInfo.Ulong = MAXIMUM_MULTICAST_ADDRESSES; break;
case OID_GEN_LINK_SPEED: - genericUlong = Adapter->LinkSpeedMbps * 10000; + GenericInfo.Ulong = Adapter->LinkSpeedMbps * 10000; break;
case OID_GEN_TRANSMIT_BUFFER_SPACE: - genericUlong = MAXIMUM_FRAME_SIZE; + GenericInfo.Ulong = MAXIMUM_FRAME_SIZE; break;
case OID_GEN_RECEIVE_BUFFER_SPACE: - genericUlong = RECEIVE_BUFFER_SIZE; + GenericInfo.Ulong = RECEIVE_BUFFER_SIZE; break;
case OID_GEN_VENDOR_ID: /* The 3 bytes of the MAC address is the vendor ID */ - genericUlong = 0; - genericUlong |= (Adapter->PermanentMacAddress[0] << 16); - genericUlong |= (Adapter->PermanentMacAddress[1] << 8); - genericUlong |= (Adapter->PermanentMacAddress[2] & 0xFF); + GenericInfo.Ulong = 0; + GenericInfo.Ulong |= (Adapter->PermanentMacAddress[0] << 16); + GenericInfo.Ulong |= (Adapter->PermanentMacAddress[1] << 8); + GenericInfo.Ulong |= (Adapter->PermanentMacAddress[2] & 0xFF); break;
case OID_GEN_VENDOR_DESCRIPTION: @@ -132,38 +165,35 @@ MiniportQueryInformation( }
case OID_GEN_VENDOR_DRIVER_VERSION: - genericUlong = DRIVER_VERSION; + GenericInfo.Ulong = DRIVER_VERSION; break;
case OID_GEN_DRIVER_VERSION: { - static const USHORT driverVersion = - (NDIS_MINIPORT_MAJOR_VERSION << 8) + NDIS_MINIPORT_MINOR_VERSION; - copySource = (PVOID)&driverVersion; - copyLength = sizeof(driverVersion); + copyLength = sizeof(USHORT); + GenericInfo.Ushort = (NDIS_MINIPORT_MAJOR_VERSION << 8) + NDIS_MINIPORT_MINOR_VERSION; break; }
case OID_GEN_MAXIMUM_TOTAL_SIZE: - genericUlong = MAXIMUM_FRAME_SIZE; + GenericInfo.Ulong = MAXIMUM_FRAME_SIZE; break;
case OID_GEN_MAXIMUM_SEND_PACKETS: - genericUlong = 1; + GenericInfo.Ulong = 1; break;
case OID_GEN_MAC_OPTIONS: - genericUlong = NDIS_MAC_OPTION_RECEIVE_SERIALIZED | + GenericInfo.Ulong = NDIS_MAC_OPTION_RECEIVE_SERIALIZED | NDIS_MAC_OPTION_COPY_LOOKAHEAD_DATA | NDIS_MAC_OPTION_TRANSFERS_NOT_PEND | NDIS_MAC_OPTION_NO_LOOPBACK; break;
case OID_GEN_MEDIA_CONNECT_STATUS: - genericUlong = Adapter->MediaState; + GenericInfo.Ulong = Adapter->MediaState; break;
- case OID_802_3_CURRENT_ADDRESS: copySource = Adapter->MulticastList[0].MacAddress; copyLength = IEEE_802_ADDR_LENGTH; @@ -175,20 +205,39 @@ MiniportQueryInformation( break;
case OID_GEN_XMIT_OK: - genericUlong = 0; - break; case OID_GEN_RCV_OK: - genericUlong = 0; - break; case OID_GEN_XMIT_ERROR: - genericUlong = 0; - break; case OID_GEN_RCV_ERROR: - genericUlong = 0; - break; case OID_GEN_RCV_NO_BUFFER: - genericUlong = 0; + { + GenericInfo.Ulong64 = NICQueryStatisticCounter(Adapter, Oid); + + *BytesNeeded = sizeof(ULONG64); + if (InformationBufferLength >= sizeof(ULONG64)) + { + *BytesWritten = sizeof(ULONG64); + NdisMoveMemory(InformationBuffer, copySource, sizeof(ULONG64)); + } + else if (InformationBufferLength >= sizeof(ULONG)) + { + *BytesWritten = sizeof(ULONG); + NdisMoveMemory(InformationBuffer, copySource, sizeof(ULONG)); + } + else + { + *BytesWritten = 0; + return NDIS_STATUS_BUFFER_TOO_SHORT; + } + return NDIS_STATUS_SUCCESS; + } + + case OID_PNP_CAPABILITIES: + { + copyLength = sizeof(NDIS_PNP_CAPABILITIES); + + status = NICFillPowerManagementCapabilities(Adapter, &GenericInfo.PmCapabilities); break; + }
default: NDIS_DbgPrint(MIN_TRACE, ("Unknown OID 0x%x(%s)\n", Oid, Oid2Str(Oid))); @@ -202,7 +251,7 @@ MiniportQueryInformation( { *BytesNeeded = copyLength; *BytesWritten = 0; - status = NDIS_STATUS_INVALID_LENGTH; + status = NDIS_STATUS_BUFFER_TOO_SHORT; } else { @@ -217,13 +266,8 @@ MiniportQueryInformation( *BytesNeeded = 0; }
- /* XMIT_ERROR and RCV_ERROR are really noisy, so do not log those. */ - if (Oid != OID_GEN_XMIT_ERROR && Oid != OID_GEN_RCV_ERROR) - { - NDIS_DbgPrint(MAX_TRACE, ("Query OID 0x%x(%s): Completed with status 0x%x (%d, %d)\n", - Oid, Oid2Str(Oid), status, *BytesWritten, *BytesNeeded)); - } - + NDIS_DbgPrint(MAX_TRACE, ("Query OID 0x%x(%s): Completed with status 0x%x (%d, %d)\n", + Oid, Oid2Str(Oid), status, *BytesWritten, *BytesNeeded)); return status; }
@@ -257,12 +301,12 @@ MiniportSetInformation( NdisMoveMemory(&genericUlong, InformationBuffer, sizeof(ULONG));
if (genericUlong & - (NDIS_PACKET_TYPE_SOURCE_ROUTING | - NDIS_PACKET_TYPE_SMT | - NDIS_PACKET_TYPE_ALL_LOCAL | - NDIS_PACKET_TYPE_GROUP | - NDIS_PACKET_TYPE_ALL_FUNCTIONAL | - NDIS_PACKET_TYPE_FUNCTIONAL)) + ~(NDIS_PACKET_TYPE_DIRECTED | + NDIS_PACKET_TYPE_MULTICAST | + NDIS_PACKET_TYPE_ALL_MULTICAST | + NDIS_PACKET_TYPE_BROADCAST | + NDIS_PACKET_TYPE_PROMISCUOUS | + NDIS_PACKET_TYPE_MAC_FRAME)) { *BytesRead = sizeof(ULONG); *BytesNeeded = sizeof(ULONG); @@ -270,6 +314,11 @@ MiniportSetInformation( break; }
+ if (Adapter->PacketFilter == genericUlong) + { + break; + } + Adapter->PacketFilter = genericUlong;
status = NICApplyPacketFilter(Adapter); @@ -312,15 +361,18 @@ MiniportSetInformation( break; }
- if (InformationBufferLength / 6 > MAXIMUM_MULTICAST_ADDRESSES) + if (InformationBufferLength > sizeof(Adapter->MulticastList)) { - *BytesNeeded = MAXIMUM_MULTICAST_ADDRESSES * IEEE_802_ADDR_LENGTH; + *BytesNeeded = sizeof(Adapter->MulticastList); *BytesRead = 0; - status = NDIS_STATUS_INVALID_LENGTH; + status = NDIS_STATUS_MULTICAST_FULL; break; }
NdisMoveMemory(Adapter->MulticastList, InformationBuffer, InformationBufferLength); + + Adapter->MulticastListSize = InformationBufferLength / IEEE_802_ADDR_LENGTH; + NICUpdateMulticastList(Adapter); break;
diff --git a/drivers/network/dd/e1000/interrupt.c b/drivers/network/dd/e1000/interrupt.c index e3f1b83da98..e4ab64d353f 100644 --- a/drivers/network/dd/e1000/interrupt.c +++ b/drivers/network/dd/e1000/interrupt.c @@ -21,18 +21,24 @@ MiniportISR( ULONG Value; PE1000_ADAPTER Adapter = (PE1000_ADAPTER)MiniportAdapterContext;
- Value = NICInterruptRecognized(Adapter, InterruptRecognized); - InterlockedOr(&Adapter->InterruptPending, Value); + /* Reading the interrupt acknowledges them */ + E1000ReadUlong(Adapter, E1000_REG_ICR, &Value);
- if (!(*InterruptRecognized)) + Value &= Adapter->InterruptMask; + _InterlockedOr(&Adapter->InterruptPending, Value); + + if (Value) + { + *InterruptRecognized = TRUE; + /* Mark the events pending service */ + *QueueMiniportHandleInterrupt = TRUE; + } + else { /* This is not ours. */ + *InterruptRecognized = FALSE; *QueueMiniportHandleInterrupt = FALSE; - return; } - - /* Mark the events pending service */ - *QueueMiniportHandleInterrupt = TRUE; }
VOID @@ -46,7 +52,7 @@ MiniportHandleInterrupt(
NDIS_DbgPrint(MAX_TRACE, ("Called.\n"));
- InterruptPending = InterlockedExchange(&Adapter->InterruptPending, 0); + InterruptPending = _InterlockedExchange(&Adapter->InterruptPending, 0);
/* Link State Changed */ @@ -101,6 +107,12 @@ MiniportHandleInterrupt( NDIS_DbgPrint(MIN_TRACE, ("Unrecognized ReceiveDescriptor status flag: %u\n", ReceiveDescriptor->Status)); }
+ /* Make sure the receive indications are enabled */ + if (!Adapter->PacketFilter) + { + goto NextReceiveDescriptor; + } + if (ReceiveDescriptor->Length != 0 && ReceiveDescriptor->Address != 0) { EthHeader = (PETH_HEADER)(Adapter->ReceiveBuffer + BufferOffset); @@ -120,6 +132,7 @@ MiniportHandleInterrupt( NDIS_DbgPrint(MIN_TRACE, ("Got a NULL descriptor")); }
+NextReceiveDescriptor: /* Give the descriptor back */ ReceiveDescriptor->Status = 0;
diff --git a/drivers/network/dd/e1000/ndis.c b/drivers/network/dd/e1000/ndis.c index d6074cb5a2c..fedbd8ec4bb 100644 --- a/drivers/network/dd/e1000/ndis.c +++ b/drivers/network/dd/e1000/ndis.c @@ -23,44 +23,6 @@ MiniportReset( return NDIS_STATUS_FAILURE; }
-NDIS_STATUS -NTAPI -MiniportSend( - IN NDIS_HANDLE MiniportAdapterContext, - IN PNDIS_PACKET Packet, - IN UINT Flags) -{ - PE1000_ADAPTER Adapter = (PE1000_ADAPTER)MiniportAdapterContext; - PSCATTER_GATHER_LIST sgList = NDIS_PER_PACKET_INFO_FROM_PACKET(Packet, ScatterGatherListPacketInfo); - ULONG TransmitLength; - PHYSICAL_ADDRESS TransmitBuffer; - NDIS_STATUS Status; - - ASSERT(sgList != NULL); - ASSERT(sgList->NumberOfElements == 1); - ASSERT((sgList->Elements[0].Address.LowPart & 3) == 0); - ASSERT(sgList->Elements[0].Length <= MAXIMUM_FRAME_SIZE); - - if (Adapter->TxFull) - { - NDIS_DbgPrint(MIN_TRACE, ("All TX descriptors are full\n")); - return NDIS_STATUS_RESOURCES; - } - - TransmitLength = sgList->Elements[0].Length; - TransmitBuffer = sgList->Elements[0].Address; - Adapter->TransmitPackets[Adapter->CurrentTxDesc] = Packet; - - Status = NICTransmitPacket(Adapter, TransmitBuffer, TransmitLength); - if (Status != NDIS_STATUS_SUCCESS) - { - NDIS_DbgPrint(MIN_TRACE, ("Transmit packet failed\n")); - return Status; - } - - return NDIS_STATUS_PENDING; -} - VOID NTAPI MiniportHalt( @@ -264,12 +226,7 @@ MiniportInitialize(
/* Enable interrupts on the NIC */ Adapter->InterruptMask = DEFAULT_INTERRUPT_MASK; - Status = NICApplyInterruptMask(Adapter); - if (Status != NDIS_STATUS_SUCCESS) - { - NDIS_DbgPrint(MIN_TRACE, ("Unable to apply interrupt mask (0x%x)\n", Status)); - goto Cleanup; - } + NICApplyInterruptMask(Adapter);
/* Turn on TX and RX now */ Status = NICEnableTxRx(Adapter); diff --git a/drivers/network/dd/e1000/nic.h b/drivers/network/dd/e1000/nic.h index c1bd82997fc..32b1c888b7f 100644 --- a/drivers/network/dd/e1000/nic.h +++ b/drivers/network/dd/e1000/nic.h @@ -26,6 +26,11 @@
typedef struct _E1000_ADAPTER { + /* NIC Memory */ + volatile PUCHAR IoBase; + NDIS_PHYSICAL_ADDRESS IoAddress; + ULONG IoLength; + // NDIS_SPIN_LOCK AdapterLock;
NDIS_HANDLE AdapterHandle; @@ -35,9 +40,11 @@ typedef struct _E1000_ADAPTER USHORT SubsystemVendorID;
UCHAR PermanentMacAddress[IEEE_802_ADDR_LENGTH]; + struct { UCHAR MacAddress[IEEE_802_ADDR_LENGTH]; } MulticastList[MAXIMUM_MULTICAST_ADDRESSES]; + ULONG MulticastListSize;
ULONG LinkSpeedMbps; ULONG MediaState; @@ -48,11 +55,6 @@ typedef struct _E1000_ADAPTER ULONG IoPortLength; volatile PUCHAR IoPort;
- /* NIC Memory */ - NDIS_PHYSICAL_ADDRESS IoAddress; - ULONG IoLength; - volatile PUCHAR IoBase; - /* Interrupt */ ULONG InterruptVector; ULONG InterruptLevel; @@ -63,7 +65,9 @@ typedef struct _E1000_ADAPTER BOOLEAN InterruptRegistered;
LONG InterruptMask; - LONG InterruptPending; + + _Interlocked_ + volatile LONG InterruptPending;
/* Transmit */ @@ -156,22 +160,6 @@ NTAPI NICApplyPacketFilter( IN PE1000_ADAPTER Adapter);
-NDIS_STATUS -NTAPI -NICApplyInterruptMask( - IN PE1000_ADAPTER Adapter); - -NDIS_STATUS -NTAPI -NICDisableInterrupts( - IN PE1000_ADAPTER Adapter); - -ULONG -NTAPI -NICInterruptRecognized( - IN PE1000_ADAPTER Adapter, - OUT PBOOLEAN InterruptRecognized); - VOID NTAPI NICUpdateLinkStatus( @@ -179,10 +167,10 @@ NICUpdateLinkStatus(
NDIS_STATUS NTAPI -NICTransmitPacket( - IN PE1000_ADAPTER Adapter, - IN PHYSICAL_ADDRESS PhysicalAddress, - IN ULONG Length); +MiniportSend( + _In_ NDIS_HANDLE MiniportAdapterContext, + _In_ PNDIS_PACKET Packet, + _In_ UINT Flags);
NDIS_STATUS NTAPI @@ -216,19 +204,54 @@ NTAPI MiniportHandleInterrupt( IN NDIS_HANDLE MiniportAdapterContext);
- +FORCEINLINE VOID -NTAPI E1000ReadUlong( - IN PE1000_ADAPTER Adapter, - IN ULONG Address, - OUT PULONG Value); + _In_ PE1000_ADAPTER Adapter, + _In_ ULONG Address, + _Out_ PULONG Value) +{ + NdisReadRegisterUlong((PULONG)(Adapter->IoBase + Address), Value); +}
+FORCEINLINE VOID -NTAPI E1000WriteUlong( - IN PE1000_ADAPTER Adapter, - IN ULONG Address, - IN ULONG Value); + _In_ PE1000_ADAPTER Adapter, + _In_ ULONG Address, + _In_ ULONG Value) +{ + NdisWriteRegisterUlong((PULONG)(Adapter->IoBase + Address), Value); +} + +FORCEINLINE +VOID +E1000WriteIoUlong( + _In_ PE1000_ADAPTER Adapter, + _In_ ULONG Address, + _In_ ULONG Value) +{ + volatile ULONG Dummy; + + NdisRawWritePortUlong((PULONG)(Adapter->IoPort), Address); + NdisReadRegisterUlong(Adapter->IoBase + E1000_REG_STATUS, &Dummy); + NdisRawWritePortUlong((PULONG)(Adapter->IoPort + 4), Value); +} + +FORCEINLINE +VOID +NICApplyInterruptMask( + _In_ PE1000_ADAPTER Adapter) +{ + E1000WriteUlong(Adapter, E1000_REG_IMS, Adapter->InterruptMask /*| 0x1F6DC*/); +} + +FORCEINLINE +VOID +NICDisableInterrupts( + _In_ PE1000_ADAPTER Adapter) +{ + E1000WriteUlong(Adapter, E1000_REG_IMC, ~0); +}
#endif /* _E1000_PCH_ */ diff --git a/drivers/network/dd/e1000/send.c b/drivers/network/dd/e1000/send.c new file mode 100644 index 00000000000..990e8b313d2 --- /dev/null +++ b/drivers/network/dd/e1000/send.c @@ -0,0 +1,85 @@ +/* + * PROJECT: ReactOS Intel PRO/1000 Driver + * LICENSE: GPL-2.0-or-later (https://spdx.org/licenses/GPL-2.0-or-later.html) + * PURPOSE: Sending packets + * COPYRIGHT: Copyright 2018 Mark Jansen mark.jansen@reactos.org + * Copyright 2019 Victor Perevertkin victor.perevertkin@reactos.org + */ + +#include "nic.h" + +#include <debug.h> + +static +NDIS_STATUS +NICTransmitPacket( + _In_ PE1000_ADAPTER Adapter, + _In_ PHYSICAL_ADDRESS PhysicalAddress, + _In_ ULONG Length) +{ + volatile PE1000_TRANSMIT_DESCRIPTOR TransmitDescriptor; + + NDIS_DbgPrint(MAX_TRACE, ("Called.\n")); + + TransmitDescriptor = Adapter->TransmitDescriptors + Adapter->CurrentTxDesc; + TransmitDescriptor->Address = PhysicalAddress.QuadPart; + TransmitDescriptor->Length = Length; + TransmitDescriptor->ChecksumOffset = 0; + TransmitDescriptor->Command = E1000_TDESC_CMD_RS | E1000_TDESC_CMD_IFCS | + E1000_TDESC_CMD_EOP | E1000_TDESC_CMD_IDE; + TransmitDescriptor->Status = 0; + TransmitDescriptor->ChecksumStartField = 0; + TransmitDescriptor->Special = 0; + + Adapter->CurrentTxDesc = (Adapter->CurrentTxDesc + 1) % NUM_TRANSMIT_DESCRIPTORS; + + E1000WriteUlong(Adapter, E1000_REG_TDT, Adapter->CurrentTxDesc); + + if (Adapter->CurrentTxDesc == Adapter->LastTxDesc) + { + NDIS_DbgPrint(MID_TRACE, ("All TX descriptors are full now\n")); + Adapter->TxFull = TRUE; + } + + return NDIS_STATUS_SUCCESS; +} + +NDIS_STATUS +NTAPI +MiniportSend( + _In_ NDIS_HANDLE MiniportAdapterContext, + _In_ PNDIS_PACKET Packet, + _In_ UINT Flags) +{ + PE1000_ADAPTER Adapter = (PE1000_ADAPTER)MiniportAdapterContext; + PSCATTER_GATHER_LIST sgList; + ULONG TransmitLength; + PHYSICAL_ADDRESS TransmitBuffer; + NDIS_STATUS Status; + + sgList = NDIS_PER_PACKET_INFO_FROM_PACKET(Packet, ScatterGatherListPacketInfo); + + ASSERT(sgList != NULL); + ASSERT(sgList->NumberOfElements == 1); + ASSERT((sgList->Elements[0].Address.LowPart & 3) == 0); + ASSERT(sgList->Elements[0].Length <= MAXIMUM_FRAME_SIZE); + + if (Adapter->TxFull) + { + NDIS_DbgPrint(MIN_TRACE, ("All TX descriptors are full\n")); + return NDIS_STATUS_RESOURCES; + } + + TransmitLength = sgList->Elements[0].Length; + TransmitBuffer = sgList->Elements[0].Address; + Adapter->TransmitPackets[Adapter->CurrentTxDesc] = Packet; + + Status = NICTransmitPacket(Adapter, TransmitBuffer, TransmitLength); + if (Status != NDIS_STATUS_SUCCESS) + { + NDIS_DbgPrint(MIN_TRACE, ("Transmit packet failed\n")); + return Status; + } + + return NDIS_STATUS_PENDING; +}