Popisovače paketů a rozšíření
V NetAdapterCx popisovače paketů jsou malé, kompaktní a rozšiřitelné struktury, které popisují síťový paket. Každý paket vyžaduje následující:
- Jedna základní charakteristika
- Jeden nebo více popisovačů fragmentů
- Nula nebo více rozšíření paketů
Základní popisovač paketu je struktura NET_PACKET. Obsahuje pouze nejzákladnější metadata použitelná pro všechny pakety, například rozložení rámování daného paketu a index prvního popisovače fragmentu paketu.
Každý paket musí mít také jeden nebo více popisovačů fragmentůnebo struktury NET_FRAGMENT, které popisují umístění v systémové paměti, kde se nacházejí data paketů.
rozšíření jsou volitelná a obsahují metadata pro jednotlivé pakety nebo fragmenty pro konkrétní funkce scénáře. Například rozšíření paketů mohou uchovávat informace pro kontrolní součet, vyvázání při velkém odesílání (LSO) a sloučení segmentů při přijetí (RSC), nebo mohou obsahovat podrobnosti specifické pro aplikaci. Rozšíření fragmentů můžou obsahovat informace o virtuálních adresách, informace o logické adrese DMA nebo jiné informace o fragmentu.
Společně tyto popisovače a rozšíření obsahují všechna metadata o síťovém paketu. Tady jsou dva příklady popisu paketu. První obrázek ukazuje scénář, ve kterém je celý paket uložený uvnitř jednoho fragmentu paměti, a offload kontrolního součtu je aktivováno.
Druhý obrázek znázorňuje paket rozprostřený přes dva fragmenty paměti, s aktivovaným RSC a offloadem kontrolního součtu.
Úložiště a přístup popisovače paketů
Popisovače paketů a popisovače fragmentů jsou uloženy v NET_RING strukturách. Klientský ovladač síťové karty přistupuje ke síťovým kruhům (net rings) a provádí s nimi operace prostřednictvím rozhraní Net Ring Iterator, které umožňuje ovladači spolupracovat s NetAdapterCx pro odesílání síťových dat do hardwaru a navracení zpracovaných dat zpět do operačního systému.
Další informace o síťových kroužcích a rozhraní Net Ring Iterátor viz Úvod do síťových kroužků.
Rozšiřitelnost popisovače paketů
Rozšiřitelnost je základní funkcí popisovače paketů NetAdapterCx, která tvoří základ pro škálovatelnost a výkon popisovače. Za běhu operační systém přiděluje všechny popisovače paketů pro každou frontu paketů v souvislém bloku spolu s případnými rozšířeními. Každý blok rozšíření je bezprostředně za popisovačem jádra, jak je znázorněno na následujícím obrázku:
Ovladače klientských síťových adaptérů nesmí natvrdo nastavovat posun k žádnému bloku rozšíření. Místo toho se musí během spuštění programu dotazovat na offset k jakémukoliv konkrétnímu rozšíření. Ovladač může například dotazovat posun k rozšíření B a získat zpět 70 bajtů, jak je znázorněno na následujícím obrázku.
Jakmile se vytvoří fronta paketů a její popisovače, systém zaručuje, že všechny jejich posuny rozšíření zůstanou konstantní, takže ovladače nemusí často znovu dotazovat tyto posuny. Vzhledem k tomu, že systém v době inicializace fronty paketů předem přiděluje všechna rozšíření, není potřeba přidělit bloky za běhu, prohledávat seznam pro konkrétní popisovač nebo ukládat ukazatele na každé rozšíření paketů.
Možnosti správy verzí popisovače paketů
Základní popisovač paketů NetAdapterCx lze snadno rozšířit v budoucích verzích přidáním nových polí na konec, například na následujícím obrázku:
Novější klientské ovladače, které znají pole V2, k nim mají přístup, zatímco starší ovladače využívající pouze verzi V1 používají posuny rozšíření, aby přeskočily pole V2 a měly přístup k polím, kterým rozumí. Kromě toho může být každé rozšíření verzováno stejným způsobem, jak ukazuje následující obrázek.
Klientský ovladač, který rozumí novému rozšíření, ho může používat. Ostatní klientské ovladače mohou ignorovat nová pole. To umožňuje nezávislé verze různých částí popisovače paketů.
Popisovače paketů a výkon cesty k datům
Funkce rozšiřitelnosti popsaná dříve poskytuje výhody, které pomáhají klientským ovladačům splňovat požadavky na výkon síťových adaptérů, které mají maximální kapacitu stovek gigabitů za sekundu s tisíci front:
- Popisovače paketů jsou co nejkomprimnější, aby se zlepšily přístupy do mezipaměti procesoru, protože funkce a rozšíření, které se nepoužívají, zabírají 0 bajtů místa v popisovačích.
- Neexistuje žádné dereferencování ukazatele, pouze aritmetika posunů, protože rozšíření jsou v rámci, což nejen šetří místo, ale také pomáhá při zásahu do mezipaměti procesoru.
- Rozšíření se přidělují při vytváření fronty, takže ovladače nemusí přidělovat a uvolňovat paměť v aktivní datové cestě nebo řešit seznamy kontextových bloků.
Použití rozšíření paketů
Důležitý
Klientské ovladače jsou v současné době omezeny na předem existující rozšíření paketů definovaná operačním systémem.
Registrace rozšíření paketů
Prvním krokem při práci s rozšířeními paketů v klientském ovladači síťové karty je deklarování podporovaných hardwarových snižování zátěže. Když oznamujete podporu pro odlehčení zátěže, jako jsou kontrolní součet a LSO, NetAdapterCx automaticky zaregistruje přidružená rozšíření paketů vaším jménem.
Příklad kódu reklamního snižování zátěže hardwaru naleznete v tématu Úvod k hardwarovým snižování zátěže.
Dotazování na posuny rozšíření paketů pro fronty datové cesty
Po registraci rozšíření paketů deklarováním podpory hardwarového offloadu budete potřebovat offsety rozšíření pro přístup k jednotlivým rozšířením při zpracování paketů. Aby se snížila zátěž ovladače a zlepšil se jeho výkon, můžete během funkce zpětného volání EvtNetAdapterCreateTx(Rx)Queue zjistit posuny pro vaše rozšíření a uložit informace o těchto posunech do kontextu fronty.
Příklad dotazování posunů rozšíření a jejich uložení do kontextu fronty najdete v tématu Přenos a příjem front.
Získání rozšíření paketů v době běhu
Jakmile uložíte posuny rozšíření v kontextu fronty, můžete je použít kdykoliv, když potřebujete informace v rozšíření. Můžete například volat metodu NetExtensionGetPacketChecksum při programování popisovačů hardwaru pro frontu přenosu:
// Get the extension offset from the device context
PMY_TX_QUEUE_CONTEXT queueContext = GetMyTxQueueContext(txQueue);
NET_EXTENSION checksumExtension = queueContext->ChecksumExtension;
// Get the checksum info for this packet
NET_PACKET_CHECKSUM* checksumInfo = NetExtensionGetPacketChecksum(checksumExtension, packetIndex);
// Do work with the checksum info
if (packet->Layout.Layer3Type == NET_PACKET_LAYER3_TYPE_IPV4_NO_OPTIONS ||
packet->Layout.Layer3Type == NET_PACKET_LAYER3_TYPE_IPV4_WITH_OPTIONS ||
packet->Layout.Layer3Type == NET_PACKET_LAYER3_TYPE_IPV4_UNSPECIFIED_OPTIONS)
{
if(checksumInfo->Layer4 == NET_PACKET_TX_CHECKSUM_REQUIRED)
{
...
}
}
...
Předdefinované rozšiřující konstanty paketů a pomocné metody
NetAdapterCx poskytuje definice známých konstant rozšíření paketů.
Konstanta | Definice |
---|---|
NET_PACKET_EXTENSION_INVALID_OFFSET | Chrání před neplatnými velikostmi offsetu. |
NET_PACKET_EXTENSION_CHECKSUM_NAME NET_PACKET_EXTENSION_CHECKSUM_VERSION_1 | Název a verze rozšíření pro kontrolní součet. |
NET_PACKET_EXTENSION_LSO_NAME NET_PACKET_EXTENSION_LSO_VERSION_1 | Název a verze rozšíření paketů pro velké offload odesílání (LSO). |
NET_PACKET_EXTENSION_RSC_NAME NET_PACKET_EXTENSION_RSC_VERSION_1 | Název a verze rozšíření paketů pro sloučování přijímaných segmentů (RSC). |
NetAdapterCx navíc poskytuje pomocné metody, které fungují jako obálky kolem metody NetExtensionGetData. Každá z těchto metod vrátí ukazatel na odpovídající typ struktury.
Metoda | Struktura |
---|---|
NetExtensionGetPacketChecksum | NET_PACKET_CHECKSUM |
NetExtensionGetGso | NET_PACKET_GSO |
NetExtensionGetPacketRsc | NET_PACKET_RSC |
Použití rozšíření fragmentů
Důležitý
Klientské ovladače jsou v současné době omezené na předem existující rozšíření fragmentu definovaná operačním systémem.
Registrace rozšíření fragmentů
NetAdapterCx automaticky zaregistruje většinu rozšíření fragmentů interpretací vyjádřených schopností ovladače. Pokud například ovladač vyjadřuje podporu DMA, architektura automaticky přidá rozšíření NET_FRAGMENT_LOGICAL_ADDRESS, které je nezbytné pro programování DMA.
Dotazování na posuny rozšíření fragmentů pro fronty datové cesty
Pokud chcete získat přístup k rozšířením fragmentů, můžete následovat stejný postup pro přístup k rozšířením paketů popsaná v dotazování offsetů rozšíření paketů pro datové cesty.
Předdefinované rozšiřující konstanty fragmentu
NetAdapterCx poskytuje definice známých konstant rozšíření fragmentů.
Konstanta | Definice |
---|---|
NET_FRAGMENT_EXTENSION_DATA_BUFFER_NAME NET_FRAGMENT_EXTENSION_DATA_BUFFER_VERSION_1 | Název a verze rozšíření pro fragment vyrovnávací paměti dat. |
NET_FRAGMENT_EXTENSION_LOGICAL_ADDRESS_NAME NET_FRAGMENT_EXTENSION_LOGICAL_ADDRESS_VERSION_1 | Název a verze rozšíření fragmentu logické adresy. |
NET_FRAGMENT_EXTENSION_MDL_NAME NET_FRAGMENT_EXTENSION_MDL_VERSION_1 | Název a verze rozšíření fragmentu MDL. |
NET_FRAGMENT_EXTENSION_RETURN_CONTEXT_NAME NET_FRAGMENT_EXTENSION_RETURN_CONTEXT_VERSION_1 | Název a verze rozšíření fragmentu návratového kontextu. |
NET_FRAGMENT_EXTENSION_VIRTUAL_ADDRESS_NAME NET_FRAGMENT_EXTENSION_VIRTUAL_ADDRESS_VERSION_1 | Název a verze rozšíření fragmentu virtuální adresy. |