NDIS Loopback Discussion

 

Introduction

Under certain conditions packets that are sent a NDIS protocol by calling NdisSend or NdisSendPackets are "looped back" to the sender's ProtocolReceive or ProtocolReceivePacket handlers where they appear as if they were received from the network.

Having a loopback facility greatly simplifies some aspects of network protocol implementation.

One example concerns MAC-level broadcast packets. When a broadcast packet is sent all hosts on the local network (including the sending host) should receive the broadcast. NDIS loopback can be used loop the broadcast packet back to the local host where it is "received" as if it was actually from the network.

From the perspective of the NDIS protocol sending a packet, loopback is simply an operation that is performed sometime between the point that NdisSend or NdisSendPackets is called to send packets and the point that the send is completed.

There are several factors that control loopback behavior as observed by the sending NDIS protocol:

bulletProtocol's NDIS Packet Filter Setting
bullet

Set with OID_GEN_CURRENT_PACKET_FILTER
 

bulletSend Packet's Characteristics
bulletPacket Destination Link Address
bulletPacket Descriptor Flags
bulletNDIS_FLAGS_DONT_LOOPBACK (Windows XP and higher)
bulletNDIS_FLAGS_SKIP_LOOPBACK_WIN2K (Windows 2000 only)
 
bulletReceive (looped-back) Packet's Characteristics
bulletPacket Descriptor Flags
bulletNDIS_FLAGS_IS_LOOPBACK_PACKET (??)

 

There are other factors that influence loopback the loopback implementation and and behavior to a limited extent. These include:

bulletProtocol's Options
bulletSet with OID_GEN_PROTOCOL_OPTIONS
bulletNDIS_PROT_OPTION_NO_LOOPBACK
 
bulletMiniport's Options
bulletQuerried with OID_GEN_MAC_OPTIONS
bulletNDIS_MAC_OPTION_NO_LOOPBACK

 

Protocol's NDIS Packet Filter Setting

The two primary factors that influence NDIS loopback are:

bulletProtocol's NDIS packet Filter Setting
bulletSend Packet's Characteristics

The protocol's NDIS packet filter is set when it makes a NdisRequest call to set information on OID_GEN_CURRENT_PACKET_FILTER. The packet filter specifies the types of net packets for which a protocol receives indications from a NIC driver. The "type of net packet" is really a filter on the receive packet's destination link address. For example:

bulletDirected Packet - A packet whose destination link address is the same as the link address of the NIC that the packet is received on.
bulletBroadcast Packet - A packet whose destination link address specifies that it should be delivered to all nodes on the network..
bulletPromiscuous Packet - Any packet, regardless of destination link address.

The protocol can specify a bit combination of these NDIS packet types:

bulletNDIS_PACKET_TYPE_DIRECTED
bulletNDIS_PACKET_TYPE_MULTICAST
bulletNDIS_PACKET_TYPE_ALL_MULTICAST
bulletNDIS_PACKET_TYPE_BROADCAST
bulletNDIS_PACKET_TYPE_SOURCE_ROUTING
bulletNDIS_PACKET_TYPE_PROMISCUOUS
bulletNDIS_PACKET_TYPE_SMT
bulletNDIS_PACKET_TYPE_ALL_LOCAL
bulletNDIS_PACKET_TYPE_GROUP
bulletNDIS_PACKET_TYPE_ALL_FUNCTIONAL
bulletNDIS_PACKET_TYPE_FUNCTIONAL
bulletNDIS_PACKET_TYPE_MAC_FRAME

The DDK documentation provides more complete descriptions of the NDIS packet type values.

 

Send Packet's Characteristic

As part of the NdisSend and NdisSendPackets operation NDIS examines each packet sent to decide whether it should be looped back to the sending protocol. The loopback decision is made just before the packet is returned to the protocol's ProtocolSendComplete handler.

The loopback decision is made on the basis of two characteristics of the packet being sent:

Packet Destination Link Address
The packet's destination link address and the protocol's NDIS packet filter bits are used to determine whether the packet should be looped back. For example, if the destination link address is the broadcast address and the NDIS_PACKET_TYPE_BROADCAST filter bit is set, then the packet should be looped back.

Similarly, if the promiscuous bit is set, then the packet should be looped back regardless of the destination address.

Packet Descriptor Flags (Windows 2000 and higher ONLY)
On Windows 2000 and higher a protocol can set information in the send packet descriptor Flags field to tell NDIS not to loopback the packet at all. This is effectively an override of the packet destination logic mentioned above.

The Flags used to inhibit loopback is the NDIS_FLAGS_DONT_LOOPBACK flag, defined in NDIS.H in the Windows 2000 and higher DDK.

However, the NDIS_FLAGS_DONT_LOOPBACK flag does not work correctly on Windows 2000.

 

On Windows 2000 (only) it is necessary to OR the undocumented value 0x400 with the NDIS_FLAGS_DONT_LOOPBACK flag to inhibit loopback of a send packet. This value is used in the Windows 2000 DDK MUX driver sample, where it is defined as:

#define NDIS_FLAGS_SKIP_LOOPBACK_W2K    0x400

Only use NDIS_FLAGS_SKIP_LOOPBACK_W2K on Windows 2000. It is reserved and may have other meanings on other platforms.

Please do review the details of using these flags by examining the Windows XP DDK MUX driver sample.

Unfortunately there are no similar loopback-inhibit flags on Windows 9X/ME or Windows NT 4.0. On those platforms there is no NDIS mechanism to inhibit loopback. One approach that may work in some designs is to filter received packets based on their source link address. If the received packet's source link address is the same as that of the NIC the packet is being received on, then the packet is a loopback packet.

 

Receive (looped-back) Packet's Characteristics

The NDIS header file defines this interesting NDIS_PACKET Flag:

NDIS_FLAGS_IS_LOOPBACK_PACKET

Although the intended use of this flag is not difficult to infer, the actual use is not documented in the DDK Help file. Microsoft has provided this information concerning this flag:

The NDIS_FLAGS_IS_LOOPBACK_PACKET flag is reserved for Microsoft internal use and its usage may change in the future.

 

Protocol's Options


Set with OID_GEN_PROTOCOL_OPTIONS. The value NDIS_PROT_OPTION_NO_LOOPBACK simply informs NDIS that the protocol does not require packets to be looped back. This is advisory only, and does not command NDIS not to loopback packets.

NDIS_PROT_OPTION_NO_LOOPBACK does not command NDIS not to loopback packets. Instead, it simply advises NDIS that the protocol is not interested in loopback packets.

 

Miniport's Options


Reported  when a miniport is queried for OID_GEN_MAC_OPTIONS. The value NDIS_MAC_OPTION_NO_LOOPBACK informs NDIS that the miniport does not have any loopback mechanism of its own. If this option bit is set, then NDIS will implement loopback within the NDIS wrapper.

In most cases physical miniports will report the NDIS_MAC_OPTION_NO_LOOPBACK option and let NDIS perform the send packet loopback.

 

Handling Miniport Options in a NDIS Intermediate Driver

If you are writing a NDIS IM driver then you will probably need to add code to deal with loopback packets. The code that you will need to add will depend on the functionality that you implement in your NDIS IM driver. In addition, there are runtime-dependent NDIS version differences in how you handle loopback in a NDIS IM driver.

The goal of the NDIS IM driver loopback handling is to insure that higher-level protocols bound to the miniport edge of your driver see sane loopback behavior. Here are some things to consider:

bulletNecessary packets are looped back - Some higher-level protocols depend on proper loopback behavior. For example, failing to loop back UDP broadcasts can cause problems.
bulletDuplicated loopback packets - Can confuse some components, such as network monitors.

The Windows XP Passthru NDIS IM driver filters completion OID_GEN_MAC_OPTIONS query to insure that the NDIS_MAC_OPTION_NO_LOOPBACK bit is NOT set. This effectively tells NDIS that the NDIS IM driver's miniport section actually has its own loopback mechanism. This is not really the case, but it works for PassThru because the lower-level miniport will perform the loopback.

The strategy of modifying the no-loopback MAC option bit in a NDIS IM driver should only be used on Windows XP and higher (NOT on Windows 2000).  Click here for additional information.

For modifying NDIS IM drivers the trivial loopback process used in PassThru may not be correct. If instead, it may be more appropriate to set the NDIS_MAC_OPTION_NO_LOOPBACK, causing NDIS to loopback packet from the IM miniport edge, and also block packets looped back from the lower miniport.

 

Loopback Quirks

There are some "quirks" associated with NDIS loopback:

Differences Between Loopback Behavior between Windows XP and prior Windows versions
According to Microsoft:
 
"If a network driver interface specification (NDIS) protocol driver sends a packet down the networking stack that is self-directed (that is, the media access control [MAC] destination address is directed at itself), the behavior of other protocol drivers varies among versions of Microsoft Windows".
 

For more information see Microsoft Knowledge Base Article - 813542.

 

Loopback of Runt Packets May Not Be Padded
When a packet is sent on a physical miniport (lowest-level) the loopback packet is the packet that was originally passed to the miniport - not the actual packet as it was sent "on the wire".

If the packet that was sent was a runt packet, then the loopback packet may not appear to be padded to the required minimum packet length. This does not mean that the packet on the wire wasn't padded correctly; padding is usually performed in the adapter hardware.

 

Loopback Packets May Not Appear To Have Correct Checksum

This behavior may be observed when sending on an adapter that supports NDIS Task Offload. In that case, the adapter hardware will generate the correct checksum on the wire. However, the looped-back packet will not reflect the hardware-generated checksum.

 

Loopback Packets Out Of Order

Software loopback is performed as part of send completion processing, and send completion processing may be deferred in favor of processing packet reception.

One artifact of this is that is a request-response scenario the response may actually be received before the loopback of the request that initiated the response.

 

Network Monitors May Not See Sent Packets If NDIS IM Driver Installed

If you examine the Microsoft PassThru NDIS IM driver sample you will see that in the PtRequestComplete routine in protocol.c it clears the NDIS_MAC_OPTION_NO_LOOPBACK bit in the lower-level miniport's response to the OID_GEN_MAC_OPTIONS query. Clearing this bit effectively tells NDIS that the PassThru miniport will perform it's own loopback of packets that are sent.

Of course, PassThru actually does NOT perform loopback of packets as they are sent. Neither does the lower-level miniport. As a result, when PassThru is installed there is no loopback of sent packets and network monitors (or "sniffers") that are based on using a NDIS protocol driver to collect packets will not see packets that are send.

Sorry...

 

 

Topic Status

January 24, 2004 Added comment that modifying the no-loopback MAC option bit in a NDIS IM driver is only for Windows XP and higher.
January 6, 2004 Added link to MS KB Article "Change in how self-directed loopback packets are processed".
April 15, 2003 Added comment about network monitors.
February 7, 2003 Added Loopback Quirks. Some modifications based on MS feedback.
February 6, 2003 Initial release.

 

 

PCAUSA Home · Privacy Statement · Products · Ordering · Support · Utilities · Resources
Mailing Lists  · PCAUSA Newsletter · PCAUSA Discussion List
Rawether for Windows, Rawether .NET, WinDis 32 and NDIS Press are trademarks of Printing Communications Assoc., Inc. (PCAUSA)
Microsoft, MS, Windows, Windows Vista, Windows 95, Windows 98, Windows Millennium, Windows 2000, and Win32 are registered trademarks and Visual C++ and Windows NT are trademarks of the Microsoft Corporation.
Copyright © 1996-2010 Printing Communications Assoc., Inc. (PCAUSA)
Last modified: January 17, 2010