Fixed bug in ne2000 driver, re: copying ethernet frame header when only

payload should be copied in MiniportTransferData.

Changed tcpip to not consider the ethernet header anywhere above
ProtocolReceive.

svn path=/trunk/; revision=11650
This commit is contained in:
Art Yerkes 2004-11-14 10:13:17 +00:00
parent 62e00f3e2f
commit 11070b8093
4 changed files with 52 additions and 45 deletions

View file

@ -140,8 +140,21 @@ typedef struct _PACKET_HEADER {
UCHAR Status; /* See RSR_* constants */
UCHAR NextPacket; /* Pointer to next packet in chain */
USHORT PacketLength; /* Length of packet including this header */
} PACKET_HEADER, PPACKET_HEADER;
} PACKET_HEADER, *PPACKET_HEADER;
#define IEEE_802_ADDR_LENGTH 6
/* Ethernet frame header */
typedef struct _ETH_HEADER {
UCHAR Destination[IEEE_802_ADDR_LENGTH];
UCHAR Source[IEEE_802_ADDR_LENGTH];
USHORT PayloadType;
} ETH_HEADER, *PETH_HEADER;
typedef struct _DISCARD_HEADER {
PACKET_HEADER HWHeader;
ETH_HEADER EthernetHeader;
} DISCARD_HEADER, *PDISCARD_HEADER;
#define NICDisableInterrupts(Adapter) { \
NDIS_DbgPrint(MAX_TRACE, ("NICDisableInterrupts()\n")); \

View file

@ -764,14 +764,16 @@ NDIS_STATUS STDCALL MiniportTransferData(
NdisQueryPacket(Packet, NULL, NULL, &DstBuffer, NULL);
NdisQueryBuffer(DstBuffer, (PVOID)&DstData, &DstSize);
SrcData = Adapter->PacketOffset + sizeof(PACKET_HEADER) + ByteOffset;
if (ByteOffset + sizeof(PACKET_HEADER) + BytesToTransfer > Adapter->PacketHeader.PacketLength)
BytesToTransfer = Adapter->PacketHeader.PacketLength- sizeof(PACKET_HEADER) - ByteOffset;
SrcData = Adapter->PacketOffset + sizeof(DISCARD_HEADER) + ByteOffset;
if (ByteOffset + sizeof(DISCARD_HEADER) + BytesToTransfer >
Adapter->PacketHeader.PacketLength)
BytesToTransfer = Adapter->PacketHeader.PacketLength -
sizeof(DISCARD_HEADER) - ByteOffset;
/* Start copying the data */
BytesCopied = 0;
for (;;) {
BytesToCopy = (DstSize < BytesToTransfer)? DstSize : BytesToTransfer;
BytesToCopy = (DstSize < BytesToTransfer) ? DstSize : BytesToTransfer;
if (SrcData + BytesToCopy > RecvStop)
BytesToCopy = (RecvStop - SrcData);

View file

@ -227,10 +227,8 @@ VOID STDCALL LanReceiveWorker( PVOID Context ) {
/*OskitDumpBuffer( IPPacket.Header, IPPacket.TotalSize );*/
PacketType = ((PETH_HEADER)IPPacket.Header)->EType;
IPPacket.Header = ((PCHAR)IPPacket.Header) + sizeof(ETH_HEADER);
IPPacket.Position = sizeof(ETH_HEADER);
IPPacket.TotalSize -= sizeof(ETH_HEADER);
PacketType = PC(IPPacket.NdisPacket)->PacketType;
IPPacket.Position = 0;
TI_DbgPrint
(DEBUG_DATALINK,
@ -358,13 +356,14 @@ NDIS_STATUS STDCALL ProtocolReceive(
TI_DbgPrint(DEBUG_DATALINK, ("Adapter: %x (MTU %d)\n",
Adapter, Adapter->MTU));
//TcpipAcquireSpinLockAtDpcLevel(&Adapter->Lock);
NdisStatus = AllocatePacketWithBuffer( &NdisPacket, NULL, Adapter->MTU );
NdisStatus = AllocatePacketWithBuffer( &NdisPacket, NULL,
PacketSize + HeaderBufferSize );
if( NdisStatus != NDIS_STATUS_SUCCESS ) {
//TcpipReleaseSpinLockFromDpcLevel(&Adapter->Lock);
return NDIS_STATUS_NOT_ACCEPTED;
}
PC(NdisPacket)->PacketType = PacketType;
TI_DbgPrint(DEBUG_DATALINK, ("pretransfer LookaheadBufferSize %d packsize %d\n",LookaheadBufferSize,PacketSize));
GetDataPtr( NdisPacket, 0, &BufferData, &temp );
@ -372,42 +371,35 @@ NDIS_STATUS STDCALL ProtocolReceive(
IPPacket.NdisPacket = NdisPacket;
IPPacket.Position = 0;
if ((LookaheadBufferSize + HeaderBufferSize) < PacketSize)
if (LookaheadBufferSize == PacketSize)
{
TI_DbgPrint(DEBUG_DATALINK, ("pretransfer LookaheadBufferSize %d packsize %d bufferdata %x\n",LookaheadBufferSize,PacketSize, BufferData));
/* The following is this way because we want a nice, whole packet
* in NdisPacket, including ethernet header (which this code assumes)
* is in there. We are indeed retransferring some bytes. Eventually,
* I will change the downstream functions to take the payload only.
*
* Below: Count the ethernet header size, but don't count the crc */
NdisTransferData(&NdisStatus,
Adapter->NdisHandle,
MacReceiveContext,
0,
PacketSize + sizeof(ETH_HEADER) - sizeof(ULONG),
NdisPacket,
&BytesTransferred);
} else {
TI_DbgPrint(DEBUG_DATALINK, ("copy\n"));
NdisStatus = NDIS_STATUS_SUCCESS;
BytesTransferred = PacketSize;
RtlCopyMemory(BufferData,
HeaderBuffer,
HeaderBufferSize);
RtlCopyMemory(BufferData + HeaderBufferSize,
LookaheadBuffer, LookaheadBufferSize);
/* Optimized code path for packets that are fully contained in
* the lookahead buffer. */
NdisCopyLookaheadData(BufferData,
LookaheadBuffer,
LookaheadBufferSize,
Adapter->MacOptions);
}
else
{
if (NdisStatus == NDIS_STATUS_SUCCESS)
{
NdisTransferData(&NdisStatus, Adapter->NdisHandle,
MacReceiveContext, 0, PacketSize,
NdisPacket, &BytesTransferred);
}
else
{
BytesTransferred = 0;
}
}
TI_DbgPrint(DEBUG_DATALINK, ("Calling complete\n"));
/* Release the packet descriptor */
//TcpipReleaseSpinLockFromDpcLevel(&Adapter->Lock);
if (NdisStatus != NDIS_STATUS_PENDING)
ProtocolTransferDataComplete(BindingContext,
NdisPacket,
NdisStatus,
PacketSize + HeaderBufferSize);
PacketSize);
TI_DbgPrint(DEBUG_DATALINK, ("leaving\n"));

View file

@ -96,11 +96,11 @@ typedef struct _IP_PACKET {
/* Packet context */
typedef struct _PACKET_CONTEXT {
PACKET_COMPLETION_ROUTINE Complete; /* Transport level completion handler */
PACKET_COMPLETION_ROUTINE DLComplete; /* Data link level completion handler
* Also used to link to next packet
* in a queue */
PVOID Context; /* Context information for handler */
PACKET_COMPLETION_ROUTINE DLComplete; /* Data link level completion handler. Also
used to link to next packet in a queue */
UINT DLOffset; /* Offset where data (IP header) starts */
UINT PacketType; /* Type of packet */
} PACKET_CONTEXT, *PPACKET_CONTEXT;
/* The ProtocolReserved field is structured as a PACKET_CONTEXT */