|
|
NDIS_PACKET Discussion
| ||||||||||||||
| MiniportReserved - An eight-byte area that "miniports" can use for their own purposes. | |
| ProtocolReserved - A variable-sized area (at least 16 bytes in length) that "protocols" can use for their own purposes. |
Use of these fields can significantly simplify the management of packet descriptors. The fields can be used to save private information about a packet descriptor or be used to queue a packet descriptor in a linked list.
There is one additional reserved area of interest:
| WrapperReserved - An eight-byte area reserved exclusively for use by the NDIS wrapper. |
Although use of the WrapperReserved area is propritary to the NDIS wrapper, it is probable that it is used by NDIS to keep information specific to the binding on which a packet is sent or received.
The requirement that "NDIS Intermediate drivers must repackage each incoming packet in a fresh packet descriptor before it passes the transfer request down to an underlying driver or up to a higher-level driver" is actually to insure that a unique WrapperReserved area is available for the NDIS wrapper; it actually doesn't matter whether the MiniportReserved or ProtocolReserved areas are used.
Neither Miniports nor Protocols should alter the contents of the WrapperReserved area.
The basic rules for "ownership" of NDIS_PACKET reserved members are simple and consistent.
If a protocol driver allocates a packet descriptor (to be sent "down the stack" for transmission), then:
If a miniport driver allocates a packet descriptor (to be indicated "up the stack" for reception), then:
On 32-bit systems, PROTOCOL_RESERVED_SIZE_IN_PACKET equals 16 bytes. On 64-bit systems, PROTOCOL_RESERVED_SIZE_IN_PACKET equals 32 bytes.
Case 4.) above identifies a requirement that a miniport driver must allocate at least a minimum ProtocolReservedSize of PROTOCOL_RESERVED_SIZE_IN_PACKET (defined in NDIS.H) when allocating a pool of NDIS packet descriptors to be used in making receive indications (i.e., packet descriptors that will be passed to NdisMIndicateReceive).
Failure to allocate the minimum ProtocolReservedSize for packet descriptors to be used in making receive indications will result in bizarre behaviors.
The introduction of NDIS Intermediate (IM) drivers complicates the use of the NDIS_PACKET reserved fields somewhat. A NDIS IM driver includes both upper-edge miniport functionality and lower-edge protocol functionality.
Actually, the rules remain the same if you look at each "edge" of a NDIS IM individually.
There are four cases that must be considered in understanding the use of NDIS_PACKET reserved fields in an NDIS IM driver:
| Packets Being Sent |
| Packets Being Received |
The "upper-edge" of a NDIS IM driver looks like a miniport driver. Your NDIS IM driver is functioning as a miniport driver when the SendHandler or SendPacketsHandler functions are called.
Within these "miniport" functions it is easy to understand that:
The essential point to understand at this critical point is that the "ownership" of both of these reserved fields is already established.
Even if you don't elect to use the MiniportReserved area in the packet descriptor that was given to you, the miniport edge of your NDIS IM driver owns it - and it can't be "given away". Similarly, the higher-level protocol "owns" the ProtocolReserved area of the packet descriptor - and you can't use it.
Since your miniport edge "owns" the MiniportReserved area of the packet descriptor, it can use it for whatever purpose you wish. You could, for example, use it to queue the packet being sent for deferred processing.
The "lower-edge" of a NDIS IM driver looks like a protocol driver. Your NDIS IM driver is functioning as a protocol driver when it is calls at the NdisSend or NdisSendPackets.
A protocol must allocate a new packet descriptor in order to call NdisSend or NdisSendPackets.
Concerning the new packet descriptor allocated by your NDIS IM protocol edge:
At this point you must fill your NDIS_PACKET with packet data to be sent.
There are two basic cases:
Spontaneous Packet Send (Completely New Packet)
In this case your NDIS IM behaves exactly as an ordinary NDIS protocol driver. Virtual memory is allocated and filled with packet data, a NDIS_BUFFER is allocated to describe the packet data virtual memory and the completely new NDIS_PACKET is sent.
Passthru Of Packet From Higher-Level Protocol (Re-Wraping A Packet)
We have already allocated the required new NDIS_PACKET.
In this case we can simply "re-wrap" the packet that was passed to us from the higher-level protocol in the "fresh" packet descriptor. We do this by setting the Private.Head and Private.Tail members of our fresh packet descriptor to the values of the packet descriptor that was passed to us from above.
The "re-wrapping" techniques allows the NDIS IM to pass the original packet data on down to be sent without requiring it to be copied. At the same time, the "fresh" packet descriptor provides new and separate NDIS_PACKET reserved fields that are required to support the send operation.
The "lower-edge" of a NDIS IM driver looks like a protocol driver. Your NDIS IM driver is functioning as a protocol driver when it is called at the ReceiveHandler or ReceivePacketHandler are called.
Within these "protocol" functions it is easy to understand that:
The essential point to understand at this critical point is that the "ownership" of both of these reserved fields is already established.
Even if you don't elect to use the ProtocolReserved area in the packet descriptor that was given to you, the protocol edge of your NDIS IM driver owns it - and it can't be "given away". Similarly, the lower-level miniport "owns" the MiniportReserved area of the packet descriptor - and you can't use it.
Since your protocol edge "owns" the ProtocolReserved area of the packet descriptor, it can use it for whatever purpose you wish. You could, for example, use it to queue the packet being received for deferred processing.
The "upper-edge" of a NDIS IM driver looks like a miniport driver. Your NDIS IM driver is functioning as a miniport driver when it calls NdisMIndicateReceivePacket.
A miniport must allocate a new packet descriptor in order to call NdisMIndicatReceivePacket.
Concerning the new packet descriptor allocated by your NDIS IM miniport edge:
At this point you must fill your NDIS_PACKET with packet data to be indicated upwards as if it was received from the network.
There are two basic cases:
Spontaneous Packet Receive (Completely New Packet)
In this case your NDIS IM behaves exactly as an ordinary NDIS miniport driver. Virtual memory is allocated and filled with packet data, a NDIS_BUFFER is allocated to describe the packet data virtual memory and the completely new NDIS_PACKET is indicated upwards by calling NdisMIndicateReceivePacket.
Passthru Of Packet From Lower-Level Miniport (Re-Wraping A Packet)
We have already allocated the required new NDIS_PACKET.
In this case we can simply "re-wrap" the packet that was passed to us from the lower-level miniport in the "fresh" packet descriptor. We do this by setting the Private.Head and Private.Tail members of our fresh packet descriptor to the values of the packet descriptor that was passed to us from below.
The "re-wrapping" techniques allows the NDIS IM to pass the original packet data on upwards to appear as received without requiring it to be copied. At the same time, the "fresh" packet descriptor provides new and separate NDIS_PACKET reserved fields that are required to support the receive operation.
|
Topic Status |
|
| December 29, 2002 | Reviewed and moved to NDIS.com. |
![]()
|
PCAUSA Home
· Privacy Statement ·
Products · Ordering · Support ·
Utilities ·
Resources
|