TCP bağlantısı için maksimum paket boyutu


197

TCP bağlantısı için maksimum paket boyutu nedir veya maksimum paket boyutunu nasıl alabilirim?


24
TCP akış tabanlıdır. Bireysel paketler için endişelenmenizin özel bir nedeni var mı?
Matti Virkkunen

27
Altındaki katmanlar paket tabanlı olduğu için ... Tipik Uygulama -> Katman 1 - Ethernet PHY, Katman 2 - Ethernet MAC (MAC Paket Tanımı, Katman 3 - İnternet Protokolü (IP Paket Tanımı), Katman 4 - TCP (İletim Kontrol Protokolü) ) -

2
'TCP paketi' diye bir şey yoktur. Uzunluğu 32 bitlik bir sözcükle tanımlanan TCP segmentleri vardır ve uzunlukları 16 bit olarak tanımlanan IP paketlerinin içinde veya arasında bulunur. Tüm bunları içeren Ethernet çerçeveleri de vardır. Bunlardan hangilerini soruyorsun? Her halükarda TCP kullanıyorsanız hiçbir şekilde endişelenmenize gerek yoktur: TCP ve IP sizin için her şeyin peşinde.
Lorne Marquis

Yanıtlar:


178

TCP paket boyutu üzerindeki mutlak sınırlama 64K'dır (65535 bayt), ancak pratik olarak bu, göreceğiniz herhangi bir paketin boyutundan çok daha büyüktür, çünkü alt katmanların (örn. Ethernet) daha düşük paket boyutları vardır.

Örneğin, Ethernet için MTU (Maksimum İletim Birimi) 1500 bayttır. Bazı ağ türlerinde (Token Ring gibi) daha büyük MTU'lar vardır ve bazı türlerde daha küçük MTU'lar vardır, ancak değerler her fiziksel teknoloji için sabittir.


15
"Ama değerler her fiziksel teknoloji için sabittir" - bu doğru değildir. Ethernet en fazla 1500 MTU'ya sahipti, ancak daha düşük bir MTU kullanabilirsiniz. Jumbo çerçevelerin ortaya çıkmasıyla, belirtilen gerçek bir maksimum yoktur ve maksimum, donanıma ve sürücüye bağlı olarak değişir.
WhirlWind

4
@Whirl: doğru, yapılandırılabilirler, ancak genellikle değildirler; "konfigüre edilebilir" özneldir, çünkü bunu yapmak için çekirdeğe girmek gerekir. Bu, OP seviyesinde olduğu gibi uygulama düzeyinde uğraşabilecek bir şey değil.
Eter

3
HiroProtagonist: 1500 maksimumdur, bu nedenle 600'e sahip olmak şaşırtıcı değildir.
Nicolas Raoul

30
neden 64K (65535 bayt) sınırlama? Çünkü TCP Üstbilgisindeki Pencere Boyutu özniteliği sadece 16 bittir. Sadece bahsetmek istedim, bazen birine yardımcı olabilir ..... büyük cevap btw @Ether!
Cacho Santa

2
Ayrıca, pencere ölçeklendirme kullanarak yükseltmek mümkündür. Bu durumda maksimum 1 GiB
Martin Melka

86

Bu mükemmel bir soru ve aslında işte bu kadar çok koşuyorum. 65k ve 1500 gibi bir çok "teknik olarak doğru" cevap var. Ağ arayüzleri yazmak ve 65k kullanmak aptalca bir sürü iş yaptım ve 1500 sizi de büyük belaya sokabilir. İşim birçok farklı donanım / platform / yönlendirici üzerinde çalışıyor ve dürüst olmak gerekirse başladığım yer 1400 bayt. Eğer 1400'den fazlasına İHTİYACINIZ VARSA, yukarı çıkmaya başlayabilirsiniz, muhtemelen 1450'ye ve bazen 1480'e gidebilirsiniz? Bundan daha fazlasına ihtiyacınız varsa, elbette 2 pakete bölünmeniz gerekir, bunun birkaç belirgin yolu vardır.

Sorun şu ki, bir veri paketi oluşturma ve TCP üzerinden yazma hakkında konuşuyorsunuz, ancak elbette taranan başlık verileri var ve böylece, sizi 1500 veya daha fazlasına koyan "bagajınız" var. çok sayıda donanımın alt sınırları vardır.

Eğer "iterseniz", gerçekten tuhaf şeyler olabilir. Açıkçası kesilmiş veriler, ya da nadiren gördüğüm veriler düştü. Bozulmuş veriler de nadiren de olsa kesinlikle olur.


GET isteklerinin ortalama değeri yaklaşık 600 bayttır?

10
65K değil, 64K demek istiyorsun. 'Başladığım yer 1400 bayt' ile ne demek istediğini bilmiyorum. TCP API'sindeki paket boyutları hakkında endişelenmenize gerek yoktur. MTU yolunu belirlemeye ve gözlemlemeye özen gösterir. send()Eğer uygunsa bir tane 2G yazamamanın bir nedeni yoktur .
Lorne Marquis

19
Sizin 1480'isholmalıdır 1460. IP üstbilgisi ve TCP üstbilgisi (isteğe bağlı üstbilgi alanları kullanılmadığı sürece) en az 20 bayt alır ve bu nedenle (Jumbo olmayan çerçeve) Ethernet için maks 1500 - 20 -20 = 1460.
Eugene Beresovsky

2
Wireshark aracılığıyla bir sunucunun büyük paketler (1400 baytın üzerinde) gönderdiğini ve müşterinin maksimum 1400 baytlık birkaç paket olarak demonte ettiğini aldığını gördüm. paketin sökülmesinden kim sorumludur? @Nektario ...?
inbaly

2
@EugeneBeresovsky isteğe bağlı başlıklarla iyi + 40 bayt'a kadar, ancak değişken olduğu için 1420 sınır görünecektir. 1400 önerisi ile küçük bir dolgu olsun. 128 ile bölünebileceğinden 1408 ile gideceğim
Garet Claborn

22

Uygulama düzeyinde, uygulama akış yönelimli bir protokol olarak TCP kullanır. TCP de segmentlere sahiptir ve güvenilir olmayan IP paketleriyle çalışmanın ayrıntılarını soyutlar.

TCP, paketler yerine segmentlerle ilgilenir. Her TCP segmenti, bir TCP üstbilgisinin içinde bulunan bir sıra numarasına sahiptir. TCP segmentinde gönderilen gerçek veriler değişkendir.

İçin bir değer yoktur getsockopt maksimum TCP bölüm boyutunu (MSS) alır Eğer TCP_MAXSEG denilen kullanabileceğinizi bazı OS üzerinde desteklenir. Yine de tüm işletim sistemlerinde desteklenmez.

Tam olarak ne yapmaya çalıştığınızdan emin değilim ama kullanılan tampon boyutunu küçültmek istiyorsanız ayrıca şunları da inceleyebilirsiniz: SO_SNDBUF ve SO_RCVBUF.


Tüm mesajlarınızı büyük bir TCP paketine sığdırabilirseniz TCP'yi bir mesaj kuyruğu olarak kullanıp kullanamayacağınızı merak ediyorum.
CMCDragonkai


4

TCP API'sinde paket yok.

Altta yatan protokollerde genellikle TCP üzerinden IP yapıldığında olduğu gibi ilgilenmediğiniz paketler vardır, çünkü muhtemelen ilgilenmediğiniz çok hassas performans optimizasyonları dışında kullanıcıyla hiçbir ilgisi yoktur ( sorunun formülasyonu).

Bir send()API çağrısında maksimum bayt sayısının ne olduğunu sorarsanız , bu uygulamaya ve ayarlara bağlıdır. Genellikle birkaç kilobayta kadar olan parçalar için send () öğesini çağırırsınız ve sistemin tamamen veya kısmen kabul etmeyi reddetmesine her zaman hazır olursunuz, bu durumda verilerinizi içine beslemek için manuel olarak daha küçük parçalara bölünmeyi yönetmeniz gerekir. TCP gönderme () API'sı.


8
TCP, paketlerin yanı sıra bir kısmı IP üstbilgisiyle çakışan bir paket üstbilgisine sahiptir. Sadece görmemeniz gerektiği için var olmadığı anlamına gelmez. TCP her zaman IP üzerinden yapılır. Üstbilgiler üst üste geldiğinden IP olmadan yapamazsınız.
WhirlWind

23
@WhirlWind TCP'nin segmentleri vardır. IP'nin paketleri vardır.
Lorne Marquis

1
TCP'nin segmentleri vardır (veya paket olarak adlandırın, sorun değil). TCP API'sında paket yok.
Pavel Radzivilovsky

13
@NathanLong Zarar, gereksiz karışıklığa neden olmanızdır. TCP segmentleri, UDP datagramları, IP paketleri, Ethernet çerçeveleri, ...
Lorquis Marquis

1
@Chexxor Peki, Ethernet çerçeveleri içindeki IP paketleri içindeki TCP segmentlerini tanımlamak için hangi dili kullanacaksınız? Farklı şeyler için aynı terimi kullanarak sorunu karıştırmaya gerek yoktur, bu şeylerin yazarları farklı terimleri kullanmak için çok fazla sorun yaşadıklarında.
Lorne Marquis

3

Genellikle bu, bağlantının kullandığı arabirime bağlı olacaktır. MTU'yu almak için muhtemelen bir ioctl () kullanabilirsiniz ve eğer ethernet ise, genellikle VLAN içermeyen ethernet için 14 olan donanım başlığının boyutunu çıkararak maksimum paket boyutunu elde edebilirsiniz.

Bu, MTU'nun ağ boyunca en azından bu kadar büyük olması durumunda geçerlidir. TCP, etkili MTU'nuzu azaltmak için MTU bulma yolunu kullanabilir.

Soru, neden umursuyorsun?


6
Bu, yalnızca ilk bağlantıda maksimum paket boyutunu elde etmenizi sağlar. Bildiğim kadarıyla, yol boyunca herhangi bir düğümün büyük paketleri sevmemesine izin verilir ve yol boyunca herhangi bir yere bölünebilir.
Matti Virkkunen

Evet, bu doğru ... yani sorunuz iyi - neden bunu isteyesiniz?
WhirlWind

Bir lan bağlantısı üzerinden video / görüntü iletmek istiyorum
Alexa

1
TCP akış yönelimli olduğu için bu neden önemlidir?
WhirlWind

3

Linux makineleriniz varsa, "ifconfig eth0 mtu 9000 up" bir arabirim için MTU'yu ayarlama komutudur. Ancak, şunu söylemeliyim ki, büyük MTU ağ iletimi bu kadar kararlı değilse bazı dezavantajlara sahiptir ve daha fazla çekirdek alanı belleği kullanabilir.


3

Görünüşe göre internette çoğu web sitesi MTU değeri için 1460 bayt kullanıyor. Bazen 1452 olur ve bir VPN kullanıyorsanız, IPSec başlıkları için daha da fazla düşer.

Varsayılan pencere boyutu en fazla 65535 bayta kadar değişir. Kendi kaynak IP değerlerime bakmak ve diğer İnternet sağlayıcılarının ne kullandığını kontrol etmek için http://tcpcheck.com adresini kullanıyorum.


2

Bir çözüm, TCP_MAXSEG soket seçeneğini ( http://linux.die.net/man/7/tcp ), temel ağ ile "güvenli" bir değere ayarlamak olabilir (örn. Ethernet üzerinde güvenli olmak için 1400 olarak ayarlanmış) ve sistem çağrısında büyük bir arabellek kullanın. Bu şekilde pahalı olan daha az sistem çağrısı olabilir. Çekirdek verileri MSS ile eşleşecek şekilde böler.

Bu şekilde kesilmiş verileri önleyebilirsiniz ve uygulamanızın küçük arabellekler hakkında endişelenmesine gerek kalmaz.


Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.