Deskriptor dan ekstensi paket
Di NetAdapterCx, deskriptor paket adalah struktur kecil, ringkas, dan dapat diperluas runtime yang menggambarkan paket jaringan. Setiap paket memerlukan hal-hal berikut:
- Satu deskriptor inti
- Satu atau beberapa deskriptor fragmen
- Ekstensi paket nol atau lebih
Deskriptor inti paket adalah struktur NET_PACKET. Ini hanya berisi metadata paling dasar yang berlaku untuk semua paket, seperti tata letak pembingkaian paket tertentu dan indeks ke deskriptor fragmen pertama paket.
Setiap paket juga harus memiliki satu atau beberapa deskriptor fragmen, atau struktur NET_FRAGMENT , yang menjelaskan lokasi dalam memori sistem tempat data paket berada.
Ekstensi bersifat opsional dan tahan metadata per paket atau per fragmen untuk fitur khusus skenario. Misalnya, ekstensi paket dapat menahan informasi offload untuk checksum, offload pengiriman besar (LSO), dan menerima segmen coalescence (RSC), atau mereka dapat menyimpan detail khusus aplikasi. Ekstensi fragmen dapat menyimpan informasi alamat virtual, informasi alamat DMA logis, atau informasi lain untuk fragmen.
Bersama-sama, deskriptor dan ekstensi ini menyimpan semua metadata tentang paket jaringan. Berikut adalah dua contoh bagaimana mereka menggambarkan paket. Gambar pertama menunjukkan skenario di mana seluruh paket disimpan di dalam fragmen memori tunggal dan offload checksum telah diaktifkan.
Gambar kedua menunjukkan paket yang disimpan di dua fragmen memori, dengan offload RSC dan checksum diaktifkan.
Penyimpanan dan akses deskriptor paket
Deskriptor paket dan deskriptor fragmen keduanya disimpan dalam struktur NET_RING . Driver klien NIC mengakses cincin bersih dan melakukan operasi pada mereka dengan memanggil ke Net Ring Iterator Interface, yang memungkinkan driver untuk bekerja dengan NetAdapterCx untuk memposting data jaringan ke perangkat keras dan menguras data yang diselesaikan kembali ke OS.
Untuk informasi selengkapnya tentang cincin net dan Antarmuka Iterator Cincin Bersih, lihat Pengantar cincin bersih.
Ekstensibilitas deskriptor paket
Ekstensibilitas adalah fitur inti dari deskriptor paket NetAdapterCx, membentuk fondasi untuk kemampuan dan performa versi deskriptor. Pada runtime, sistem operasi mengalokasikan semua deskriptor paket untuk setiap antrean paket dalam blok yang berdekatan, bersama dengan ekstensi yang tersedia. Setiap blok ekstensi berada tepat di belakang deskriptor inti, seperti yang ditunjukkan pada gambar berikut:
Driver klien NIC tidak diizinkan untuk melakukan hardcode offset ke blok ekstensi apa pun. Sebaliknya, mereka harus meminta pada runtime untuk offset ke ekstensi tertentu. Misalnya, driver mungkin mengkueri offset ke Ekstensi B dan mendapatkan kembali 70 byte seperti pada gambar berikut:
Setelah antrean paket dan deskriptornya dibuat, semua offset ekstensi mereka dijamin oleh sistem menjadi konstan, sehingga driver tidak perlu sering mengkueri ulang offset. Selain itu, karena semua ekstensi telah dialokasikan sebelumnya oleh sistem dalam blok pada saat antrean paket diinisialisasi, tidak perlu alokasi runtime blok, mencari daftar untuk deskriptor tertentu, atau harus menyimpan pointer ke setiap ekstensi paket.
Kemampuan versi deskriptor paket
Deskriptor paket inti NetAdapterCx dapat dengan mudah diperluas dalam rilis mendatang dengan menambahkan bidang baru ke akhir, seperti pada gambar berikut:
Driver klien yang lebih baru yang tahu tentang bidang V2 dapat mengaksesnya, sementara driver khusus V1 yang lebih lama akan menggunakan offset ekstensi untuk melewati bidang V2 sehingga mereka dapat mengakses bidang yang mereka pahami. Selain itu, setiap ekstensi dapat diberi versi dengan cara yang sama, seperti yang ditunjukkan oleh gambar berikut:
Driver klien yang memahami ekstensi baru dapat menggunakannya. Driver klien lain dapat melewati bidang baru. Ini memungkinkan berbagai bagian deskriptor paket untuk diversikan secara independen.
Deskriptor paket dan performa jalur data
Fitur ekstensibilitas yang diuraikan sebelumnya memberikan manfaat untuk membantu driver klien memenuhi persyaratan performa NIC yang mampu mencapai ratusan gigabit per detik, dengan ribuan antrean:
- Deskriptor paket disimpan sepadat mungkin untuk meningkatkan hit cache CPU, karena fitur dan ekstensi yang tidak digunakan menempati 0 byte ruang dalam deskriptor.
- Tidak ada dereferensi pointer, hanya offset aritmetika karena ekstensi sejalan, yang tidak hanya menghemat ruang tetapi juga membantu dengan hit cache CPU.
- Ekstensi dialokasikan pada waktu pembuatan antrean, sehingga driver tidak perlu mengalokasikan dan membatalkan alokasi memori di jalur data aktif atau menangani daftar blok konteks yang terlihat.
Menggunakan ekstensi paket
Penting
Saat ini, driver klien terbatas pada ekstensi paket yang sudah ada sebelumnya yang ditentukan oleh sistem operasi.
Mendaftarkan ekstensi paket
Langkah pertama dalam bekerja dengan ekstensi paket di driver klien NIC Anda adalah mendeklarasikan offload perangkat keras yang didukung. Saat Anda mengiklankan dukungan untuk offload seperti checksum dan LSO, NetAdapterCx secara otomatis mendaftarkan ekstensi paket terkait atas nama Anda.
Untuk contoh kode offload perangkat keras iklan, lihat Pengantar offload perangkat keras.
Mengkueri offset ekstensi paket untuk antrean jalur data
Setelah mendaftarkan ekstensi paket dengan mendeklarasikan dukungan offload perangkat keras, Anda memerlukan offset ekstensi untuk mengakses masing-masing paket saat memproses paket Anda. Untuk mengurangi panggilan keluar dari driver dan meningkatkan performa, Anda dapat mengkueri offset untuk ekstensi Anda selama fungsi panggilan balik EvtNetAdapterCreateTx(Rx)Queue dan menyimpan informasi offset dalam konteks antrean Anda.
Untuk contoh mengkueri offset ekstensi dan menyimpannya dalam konteks antrean, lihat Mengirimkan dan menerima antrean.
Mendapatkan ekstensi paket saat runtime
Setelah menyimpan offset ekstensi dalam konteks antrean, Anda dapat menggunakannya kapan saja Anda memerlukan informasi dalam ekstensi. Misalnya, Anda dapat memanggil metode NetExtensionGetPacketChecksum saat Anda memprogram deskriptor ke perangkat keras untuk antrean transmisi:
// 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)
{
...
}
}
...
Konstanta ekstensi paket dan metode pembantu yang telah ditentukan sebelumnya
NetAdapterCx menyediakan definisi untuk konstanta ekstensi paket yang diketahui.
Terus-menerus | Definisi |
---|---|
NET_PACKET_EXTENSION_INVALID_OFFSET | Menjaga dari ukuran offset yang tidak valid. |
NET_PACKET_EXTENSION_CHECKSUM_NAME NET_PACKET_EXTENSION_CHECKSUM_VERSION_1 | Nama dan versi ekstensi paket checksum. |
NET_PACKET_EXTENSION_LSO_NAME NET_PACKET_EXTENSION_LSO_VERSION_1 | Nama dan versi ekstensi paket send offload (LSO) besar. |
NET_PACKET_EXTENSION_RSC_NAME NET_PACKET_EXTENSION_RSC_VERSION_1 | Nama dan versi ekstensi paket receive segment coalescence (RSC). |
Selain itu, NetAdapterCx menyediakan metode pembantu yang bertindak sebagai pembungkus di sekitar metode NetExtensionGetData . Masing-masing metode ini mengembalikan penunjuk ke jenis struktur yang sesuai.
Metode | Struktur |
---|---|
NetExtensionGetPacketChecksum | NET_PACKET_CHECKSUM |
NetExtensionGetGso | NET_PACKET_GSO |
NetExtensionGetPacketRsc | NET_PACKET_RSC |
Menggunakan ekstensi fragmen
Penting
Saat ini, driver klien terbatas pada ekstensi fragmen yang sudah ada sebelumnya yang ditentukan oleh sistem operasi.
Mendaftarkan ekstensi fragmen
NetAdapterCx secara otomatis mendaftarkan sebagian besar ekstensi fragmen dengan menginterpretasikan kemampuan yang diekspresikan driver. Misalnya, jika driver menyatakan mendukung DMA, kerangka kerja akan secara otomatis menambahkan ekstensi NET_FRAGMENT_LOGICAL_ADDRESS yang diperlukan untuk pemrograman DMA.
Mengkueri offset ekstensi fragmen untuk antrean jalur data
Untuk mengakses ekstensi fragmen, Anda dapat mengikuti proses yang sama untuk mengakses ekstensi paket yang diuraikan dalam Mengkueri offset ekstensi paket untuk antrean jalur data.
Konstanta ekstensi fragmen yang telah ditentukan sebelumnya
NetAdapterCx menyediakan definisi untuk konstanta ekstensi fragmen yang diketahui.
Terus-menerus | Definisi |
---|---|
NET_FRAGMENT_EXTENSION_DATA_BUFFER_NAME NET_FRAGMENT_EXTENSION_DATA_BUFFER_VERSION_1 | Nama dan versi ekstensi fragmen buffer data. |
NET_FRAGMENT_EXTENSION_LOGICAL_ADDRESS_NAME NET_FRAGMENT_EXTENSION_LOGICAL_ADDRESS_VERSION_1 | Nama dan versi ekstensi fragmen alamat logis. |
NET_FRAGMENT_EXTENSION_MDL_NAME NET_FRAGMENT_EXTENSION_MDL_VERSION_1 | Nama dan versi ekstensi fragmen MDL. |
NET_FRAGMENT_EXTENSION_RETURN_CONTEXT_NAME NET_FRAGMENT_EXTENSION_RETURN_CONTEXT_VERSION_1 | Nama dan versi ekstensi fragmen konteks pengembalian. |
NET_FRAGMENT_EXTENSION_VIRTUAL_ADDRESS_NAME NET_FRAGMENT_EXTENSION_VIRTUAL_ADDRESS_VERSION_1 | Nama dan versi ekstensi fragmen alamat virtual. |